diff options
Diffstat (limited to 'src')
137 files changed, 3308 insertions, 3268 deletions
diff --git a/src/server/authserver/Server/AuthSocket.cpp b/src/server/authserver/Server/AuthSocket.cpp index 6bfe918643c..c2131f5dbf7 100644 --- a/src/server/authserver/Server/AuthSocket.cpp +++ b/src/server/authserver/Server/AuthSocket.cpp @@ -267,12 +267,12 @@ void AuthSocket::_SetVSFields(const std::string& rI) uint8 mDigest[SHA_DIGEST_LENGTH]; memset(mDigest, 0, SHA_DIGEST_LENGTH); if (I.GetNumBytes() <= SHA_DIGEST_LENGTH) - memcpy(mDigest, I.AsByteArray(), I.GetNumBytes()); + memcpy(mDigest, I.AsByteArray().get(), I.GetNumBytes()); std::reverse(mDigest, mDigest + SHA_DIGEST_LENGTH); SHA1Hash sha; - sha.UpdateData(s.AsByteArray(), s.GetNumBytes()); + sha.UpdateData(s.AsByteArray().get(), s.GetNumBytes()); sha.UpdateData(mDigest, SHA_DIGEST_LENGTH); sha.Finalize(); BigNumber x; @@ -484,13 +484,13 @@ bool AuthSocket::_HandleLogonChallenge() pkt << uint8(WOW_FAIL_VERSION_INVALID); // B may be calculated < 32B so we force minimal length to 32B - pkt.append(B.AsByteArray(32), 32); // 32 bytes + pkt.append(B.AsByteArray(32).get(), 32); // 32 bytes pkt << uint8(1); - pkt.append(g.AsByteArray(), 1); + pkt.append(g.AsByteArray().get(), 1); pkt << uint8(32); - pkt.append(N.AsByteArray(32), 32); - pkt.append(s.AsByteArray(), s.GetNumBytes()); // 32 bytes - pkt.append(unk3.AsByteArray(16), 16); + pkt.append(N.AsByteArray(32).get(), 32); + pkt.append(s.AsByteArray().get(), s.GetNumBytes()); // 32 bytes + pkt.append(unk3.AsByteArray(16).get(), 16); uint8 securityFlags = 0; pkt << uint8(securityFlags); // security flags (0x0...0x04) @@ -574,7 +574,7 @@ bool AuthSocket::_HandleLogonProof() uint8 t[32]; uint8 t1[16]; uint8 vK[40]; - memcpy(t, S.AsByteArray(32), 32); + memcpy(t, S.AsByteArray(32).get(), 32); for (int i = 0; i < 16; ++i) t1[i] = t[i * 2]; @@ -629,7 +629,7 @@ bool AuthSocket::_HandleLogonProof() M.SetBinary(sha.GetDigest(), 20); // Check if SRP6 results match (password is correct), else send an error - if (!memcmp(M.AsByteArray(), lp.M1, 20)) + if (!memcmp(M.AsByteArray().get(), lp.M1, 20)) { TC_LOG_DEBUG(LOG_FILTER_AUTHSERVER, "'%s:%d' User '%s' successfully authenticated", socket().getRemoteAddress().c_str(), socket().getRemotePort(), _login.c_str()); @@ -800,7 +800,7 @@ bool AuthSocket::_HandleReconnectChallenge() pkt << uint8(AUTH_RECONNECT_CHALLENGE); pkt << uint8(0x00); _reconnectProof.SetRand(16 * 8); - pkt.append(_reconnectProof.AsByteArray(16), 16); // 16 bytes random + pkt.append(_reconnectProof.AsByteArray(16).get(), 16); // 16 bytes random pkt << uint64(0x00) << uint64(0x00); // 16 bytes zeros socket().send((char const*)pkt.contents(), pkt.size()); return true; diff --git a/src/server/collision/Models/GameObjectModel.cpp b/src/server/collision/Models/GameObjectModel.cpp index 9db3d706fca..a3af175a977 100644 --- a/src/server/collision/Models/GameObjectModel.cpp +++ b/src/server/collision/Models/GameObjectModel.cpp @@ -119,7 +119,7 @@ bool GameObjectModel::initialize(const GameObject& go, const GameObjectDisplayIn //ID = 0; iPos = Vector3(go.GetPositionX(), go.GetPositionY(), go.GetPositionZ()); phasemask = go.GetPhaseMask(); - iScale = go.GetFloatValue(OBJECT_FIELD_SCALE_X); + iScale = go.GetObjectScale(); iInvScale = 1.f / iScale; G3D::Matrix3 iRotation = G3D::Matrix3::fromEulerAnglesZYX(go.GetOrientation(), 0, 0); diff --git a/src/server/game/AI/ScriptedAI/ScriptedFollowerAI.cpp b/src/server/game/AI/ScriptedAI/ScriptedFollowerAI.cpp index 8f46896f6e8..befd6b9d16e 100644 --- a/src/server/game/AI/ScriptedAI/ScriptedFollowerAI.cpp +++ b/src/server/game/AI/ScriptedAI/ScriptedFollowerAI.cpp @@ -311,7 +311,7 @@ void FollowerAI::StartFollow(Player* player, uint32 factionForFollower, const Qu Player* FollowerAI::GetLeaderForFollower() { - if (Player* player = Unit::GetPlayer(*me, m_uiLeaderGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, m_uiLeaderGUID)) { if (player->IsAlive()) return player; diff --git a/src/server/game/AI/SmartScripts/SmartAI.cpp b/src/server/game/AI/SmartScripts/SmartAI.cpp index c5b5cd5dfef..febf2e789a2 100644 --- a/src/server/game/AI/SmartScripts/SmartAI.cpp +++ b/src/server/game/AI/SmartScripts/SmartAI.cpp @@ -343,7 +343,7 @@ void SmartAI::UpdateAI(uint32 diff) { if (me->FindNearestCreature(mFollowArrivedEntry, INTERACTION_DISTANCE, true)) { - if (Player* player = me->GetPlayer(*me, mFollowGuid)) + if (Player* player = ObjectAccessor::GetPlayer(*me, mFollowGuid)) { if (!mFollowCreditType) player->RewardPlayerAndGroupAtEvent(mFollowCredit, me); @@ -365,7 +365,9 @@ void SmartAI::UpdateAI(uint32 diff) return; } mFollowArrivedTimer = 1000; - } else mFollowArrivedTimer -= diff; + } + else + mFollowArrivedTimer -= diff; } if (!UpdateVictim()) diff --git a/src/server/game/AI/SmartScripts/SmartScript.cpp b/src/server/game/AI/SmartScripts/SmartScript.cpp index 65b1e6c331e..b4e18b66a69 100644 --- a/src/server/game/AI/SmartScripts/SmartScript.cpp +++ b/src/server/game/AI/SmartScripts/SmartScript.cpp @@ -1401,7 +1401,7 @@ void SmartScript::ProcessAction(SmartScriptHolder& e, Unit* unit, uint32 var0, u e.GetTargetType() == SMART_TARGET_GAMEOBJECT_GUID || e.GetTargetType() == SMART_TARGET_GAMEOBJECT_DISTANCE || e.GetTargetType() == SMART_TARGET_CLOSEST_CREATURE || e.GetTargetType() == SMART_TARGET_CLOSEST_GAMEOBJECT || e.GetTargetType() == SMART_TARGET_OWNER_OR_SUMMONER || e.GetTargetType() == SMART_TARGET_ACTION_INVOKER || - e.GetTargetType() == SMART_TARGET_CLOSEST_ENEMY) + e.GetTargetType() == SMART_TARGET_CLOSEST_ENEMY || e.GetTargetType() == SMART_TARGET_CLOSEST_FRIENDLY) { ObjectList* targets = GetTargets(e, unit); if (!targets) @@ -2506,6 +2506,14 @@ ObjectList* SmartScript::GetTargets(SmartScriptHolder const& e, Unit* invoker /* break; } + case SMART_TARGET_CLOSEST_FRIENDLY: + { + if (me) + if (Unit* target = DoFindClosestFriendlyInRange(e.target.closestFriendly.maxDist)) + l->push_back(target); + + break; + } case SMART_TARGET_POSITION: default: break; @@ -2623,7 +2631,7 @@ void SmartScript::ProcessEvent(SmartScriptHolder& e, Unit* unit, uint32 var0, ui return; Unit* target = DoSelectLowestHpFriendly((float)e.event.friendlyHealt.radius, e.event.friendlyHealt.hpDeficit); - if (!target) + if (!target || !target->IsInCombat()) return; ProcessTimedAction(e, e.event.friendlyHealt.repeatMin, e.event.friendlyHealt.repeatMax, target); break; @@ -2940,6 +2948,55 @@ void SmartScript::ProcessEvent(SmartScriptHolder& e, Unit* unit, uint32 var0, ui ProcessAction(e, unit, var0); break; } + case SMART_EVENT_FRIENDLY_HEALTH_PCT: + { + if (!me || !me->IsInCombat()) + return; + + ObjectList* _targets = NULL; + + switch (e.GetTargetType()) + { + case SMART_TARGET_CREATURE_RANGE: + case SMART_TARGET_CREATURE_GUID: + case SMART_TARGET_CREATURE_DISTANCE: + case SMART_TARGET_CLOSEST_CREATURE: + case SMART_TARGET_CLOSEST_PLAYER: + case SMART_TARGET_PLAYER_RANGE: + case SMART_TARGET_PLAYER_DISTANCE: + _targets = GetTargets(e); + break; + default: + return; + } + + if (!_targets) + return; + + Unit* target = NULL; + + for (ObjectList::const_iterator itr = _targets->begin(); itr != _targets->end(); ++itr) + { + if (IsUnit(*itr) && me->IsFriendlyTo((*itr)->ToUnit()) && (*itr)->ToUnit()->IsAlive() && (*itr)->ToUnit()->IsInCombat()) + { + uint32 healthPct = uint32((*itr)->ToUnit()->GetHealthPct()); + + if (healthPct > e.event.friendlyHealtPct.maxHpPct || healthPct < e.event.friendlyHealtPct.minHpPct) + continue; + + target = (*itr)->ToUnit(); + break; + } + } + + delete _targets; + + if (!target) + return; + + ProcessTimedAction(e, e.event.friendlyHealtPct.repeatMin, e.event.friendlyHealtPct.repeatMax, target); + break; + } default: TC_LOG_ERROR(LOG_FILTER_SQL, "SmartScript::ProcessEvent: Unhandled Event type %u", e.GetEventType()); break; @@ -3019,6 +3076,7 @@ void SmartScript::UpdateTimer(SmartScriptHolder& e, uint32 const diff) case SMART_EVENT_HAS_AURA: case SMART_EVENT_TARGET_BUFFED: case SMART_EVENT_IS_BEHIND_TARGET: + case SMART_EVENT_FRIENDLY_HEALTH_PCT: { ProcessEvent(e); if (e.GetScriptType() == SMART_SCRIPT_TYPE_TIMED_ACTIONLIST) @@ -3324,6 +3382,18 @@ void SmartScript::DoFindFriendlyMissingBuff(std::list<Creature*>& list, float ra cell.Visit(p, grid_creature_searcher, *me->GetMap(), *me, range); } +Unit* SmartScript::DoFindClosestFriendlyInRange(float range) +{ + if (!me) + return NULL; + + Unit* unit = NULL; + Trinity::AnyFriendlyUnitInObjectRangeCheck u_check(me, me, range); + Trinity::UnitLastSearcher<Trinity::AnyFriendlyUnitInObjectRangeCheck> searcher(me, unit, u_check); + me->VisitNearbyObject(range, searcher); + return unit; +} + void SmartScript::SetScript9(SmartScriptHolder& e, uint32 entry) { mTimedActionList.clear(); diff --git a/src/server/game/AI/SmartScripts/SmartScript.h b/src/server/game/AI/SmartScripts/SmartScript.h index 6801c132331..b22f2d81b26 100644 --- a/src/server/game/AI/SmartScripts/SmartScript.h +++ b/src/server/game/AI/SmartScripts/SmartScript.h @@ -89,6 +89,7 @@ class SmartScript Unit* DoSelectLowestHpFriendly(float range, uint32 MinHPDiff); void DoFindFriendlyCC(std::list<Creature*>& _list, float range); void DoFindFriendlyMissingBuff(std::list<Creature*>& list, float range, uint32 spellid); + Unit* DoFindClosestFriendlyInRange(float range); void StoreTargetList(ObjectList* targets, uint32 id) { diff --git a/src/server/game/AI/SmartScripts/SmartScriptMgr.cpp b/src/server/game/AI/SmartScripts/SmartScriptMgr.cpp index 99693355d70..1e20d2e6fbb 100644 --- a/src/server/game/AI/SmartScripts/SmartScriptMgr.cpp +++ b/src/server/game/AI/SmartScripts/SmartScriptMgr.cpp @@ -301,6 +301,7 @@ bool SmartAIMgr::IsTargetValid(SmartScriptHolder const& e) case SMART_TARGET_CLOSEST_GAMEOBJECT: case SMART_TARGET_CLOSEST_CREATURE: case SMART_TARGET_CLOSEST_ENEMY: + case SMART_TARGET_CLOSEST_FRIENDLY: case SMART_TARGET_STORED: break; default: @@ -544,6 +545,31 @@ bool SmartAIMgr::IsEventValid(SmartScriptHolder& e) } break; } + case SMART_EVENT_FRIENDLY_HEALTH_PCT: + if (!IsMinMaxValid(e, e.event.friendlyHealtPct.repeatMin, e.event.friendlyHealtPct.repeatMax)) + return false; + + if (e.event.friendlyHealtPct.maxHpPct > 100 || e.event.friendlyHealtPct.minHpPct > 100) + { + TC_LOG_ERROR(LOG_FILTER_SQL, "SmartAIMgr: Entry %d SourceType %u Event %u Action %u has pct value above 100, skipped.", e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType()); + return false; + } + + switch (e.GetTargetType()) + { + case SMART_TARGET_CREATURE_RANGE: + case SMART_TARGET_CREATURE_GUID: + case SMART_TARGET_CREATURE_DISTANCE: + case SMART_TARGET_CLOSEST_CREATURE: + case SMART_TARGET_CLOSEST_PLAYER: + case SMART_TARGET_PLAYER_RANGE: + case SMART_TARGET_PLAYER_DISTANCE: + break; + default: + TC_LOG_ERROR(LOG_FILTER_SQL, "SmartAIMgr: Entry %d SourceType %u Event %u Action %u uses invalid target_type %u, skipped.", e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.GetTargetType()); + return false; + } + break; case SMART_EVENT_GO_STATE_CHANGED: case SMART_EVENT_GO_EVENT_INFORM: case SMART_EVENT_TIMED_EVENT_TRIGGERED: diff --git a/src/server/game/AI/SmartScripts/SmartScriptMgr.h b/src/server/game/AI/SmartScripts/SmartScriptMgr.h index 740be9276b2..05880c07ff4 100644 --- a/src/server/game/AI/SmartScripts/SmartScriptMgr.h +++ b/src/server/game/AI/SmartScripts/SmartScriptMgr.h @@ -155,8 +155,9 @@ enum SMART_EVENT SMART_EVENT_GO_EVENT_INFORM = 71, // eventId SMART_EVENT_ACTION_DONE = 72, // eventId (SharedDefines.EventId) SMART_EVENT_ON_SPELLCLICK = 73, // clicker (unit) + SMART_EVENT_FRIENDLY_HEALTH_PCT = 74, // minHpPct, maxHpPct, repeatMin, repeatMax - SMART_EVENT_END = 74 + SMART_EVENT_END = 75 }; struct SmartEvent @@ -363,6 +364,14 @@ struct SmartEvent struct { + uint32 minHpPct; + uint32 maxHpPct; + uint32 repeatMin; + uint32 repeatMax; + } friendlyHealtPct; + + struct + { uint32 param1; uint32 param2; uint32 param3; @@ -1001,7 +1010,9 @@ enum SMARTAI_TARGETS SMART_TARGET_OWNER_OR_SUMMONER = 23, // Unit's owner or summoner SMART_TARGET_THREAT_LIST = 24, // All units on creature's threat list SMART_TARGET_CLOSEST_ENEMY = 25, // maxDist - SMART_TARGET_END = 26 + SMART_TARGET_CLOSEST_FRIENDLY = 26, // maxDist + + SMART_TARGET_END = 27 }; struct SmartTarget @@ -1090,6 +1101,11 @@ struct SmartTarget struct { + uint32 maxDist; + } closestFriendly; + + struct + { uint32 param1; uint32 param2; uint32 param3; @@ -1225,7 +1241,8 @@ const uint32 SmartAIEventMask[SMART_EVENT_END][2] = {SMART_EVENT_GO_STATE_CHANGED, SMART_SCRIPT_TYPE_MASK_GAMEOBJECT }, {SMART_EVENT_GO_EVENT_INFORM, SMART_SCRIPT_TYPE_MASK_GAMEOBJECT }, {SMART_EVENT_ACTION_DONE, SMART_SCRIPT_TYPE_MASK_CREATURE }, - {SMART_EVENT_ON_SPELLCLICK, SMART_SCRIPT_TYPE_MASK_CREATURE } + {SMART_EVENT_ON_SPELLCLICK, SMART_SCRIPT_TYPE_MASK_CREATURE }, + {SMART_EVENT_FRIENDLY_HEALTH_PCT, SMART_SCRIPT_TYPE_MASK_CREATURE }, }; enum SmartEventFlags diff --git a/src/server/game/Entities/Creature/Creature.cpp b/src/server/game/Entities/Creature/Creature.cpp index b46ee4703db..169d5feae03 100644 --- a/src/server/game/Entities/Creature/Creature.cpp +++ b/src/server/game/Entities/Creature/Creature.cpp @@ -522,12 +522,17 @@ void Creature::Update(uint32 diff) if (!IsAlive()) break; - // if creature is charmed, switch to charmed AI + // if creature is charmed, switch to charmed AI (and back) if (NeedChangeAI) { UpdateCharmAI(); NeedChangeAI = false; IsAIEnabled = true; + if (!IsInEvadeMode() && LastCharmerGUID) + if (Unit* charmer = ObjectAccessor::GetUnit(*this, LastCharmerGUID)) + i_AI->AttackStart(charmer); + + LastCharmerGUID = 0; } if (!IsInEvadeMode() && IsAIEnabled) @@ -2631,7 +2636,7 @@ void Creature::SetDisplayId(uint32 modelId) if (CreatureModelInfo const* minfo = sObjectMgr->GetCreatureModelInfo(modelId)) { - SetFloatValue(UNIT_FIELD_BOUNDINGRADIUS, minfo->bounding_radius * GetFloatValue(OBJECT_FIELD_SCALE_X)); - SetFloatValue(UNIT_FIELD_COMBATREACH, minfo->combat_reach * GetFloatValue(OBJECT_FIELD_SCALE_X)); + SetFloatValue(UNIT_FIELD_BOUNDINGRADIUS, minfo->bounding_radius * GetObjectScale()); + SetFloatValue(UNIT_FIELD_COMBATREACH, minfo->combat_reach * GetObjectScale()); } } diff --git a/src/server/game/Entities/GameObject/GameObject.cpp b/src/server/game/Entities/GameObject/GameObject.cpp index 906c1f281bc..f903e0b2ee5 100644 --- a/src/server/game/Entities/GameObject/GameObject.cpp +++ b/src/server/game/Entities/GameObject/GameObject.cpp @@ -1195,13 +1195,6 @@ void GameObject::Use(Unit* user) // calculate the distance between the player and this slot float thisDistance = player->GetDistance2d(x_i, y_i); - /* debug code. It will spawn a npc on each slot to visualize them. - Creature* helper = player->SummonCreature(14496, x_i, y_i, GetPositionZ(), GetOrientation(), TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 10000); - std::ostringstream output; - output << i << ": thisDist: " << thisDistance; - helper->MonsterSay(output.str().c_str(), LANG_UNIVERSAL, 0); - */ - if (thisDistance <= lowestDist) { nearest_slot = itr->first; @@ -1222,8 +1215,6 @@ void GameObject::Use(Unit* user) return; } } - //else - //player->GetSession()->SendNotification("There's nowhere left for you to sit."); return; } diff --git a/src/server/game/Entities/Object/Object.h b/src/server/game/Entities/Object/Object.h index 2bfb9633066..4c48d80762d 100644 --- a/src/server/game/Entities/Object/Object.h +++ b/src/server/game/Entities/Object/Object.h @@ -134,6 +134,7 @@ class Object uint32 GetEntry() const { return GetUInt32Value(OBJECT_FIELD_ENTRY); } void SetEntry(uint32 entry) { SetUInt32Value(OBJECT_FIELD_ENTRY, entry); } + float GetObjectScale() const { return GetFloatValue(OBJECT_FIELD_SCALE_X); } virtual void SetObjectScale(float scale) { SetFloatValue(OBJECT_FIELD_SCALE_X, scale); } TypeID GetTypeId() const { return m_objectTypeId; } diff --git a/src/server/game/Entities/Pet/Pet.cpp b/src/server/game/Entities/Pet/Pet.cpp index 4c8d48222e5..69a381ceb3d 100644 --- a/src/server/game/Entities/Pet/Pet.cpp +++ b/src/server/game/Entities/Pet/Pet.cpp @@ -1548,16 +1548,16 @@ void Pet::InitLevelupSpellsForLevel() { for (uint8 i = 0; i < MAX_CREATURE_SPELL_DATA_SLOT; ++i) { - SpellInfo const* spellEntry = sSpellMgr->GetSpellInfo(defSpells->spellid[i]); - if (!spellEntry) + SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(defSpells->spellid[i]); + if (!spellInfo) continue; // will called first if level down - if (spellEntry->SpellLevel > level) - unlearnSpell(spellEntry->Id, true); + if (spellInfo->SpellLevel > level) + unlearnSpell(spellInfo->Id, true); // will called if level up else - learnSpell(spellEntry->Id); + learnSpell(spellInfo->Id); } } } diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp index d1b42151e0a..2ff86f81880 100644 --- a/src/server/game/Entities/Player/Player.cpp +++ b/src/server/game/Entities/Player/Player.cpp @@ -7961,8 +7961,7 @@ void Player::_ApplyItemBonuses(ItemTemplate const* proto, uint8 slot, bool apply ApplyHealthRegenBonus(int32(val), apply); break; case ITEM_MOD_SPELL_PENETRATION: - ApplyModInt32Value(PLAYER_FIELD_MOD_TARGET_RESISTANCE, -val, apply); - m_spellPenetrationItemMod += apply ? val : -val; + ApplySpellPenetrationBonus(val, apply); break; case ITEM_MOD_BLOCK_VALUE: HandleBaseModValue(SHIELD_BLOCK_VALUE, FLAT_MOD, float(val), apply); @@ -14146,8 +14145,7 @@ void Player::ApplyEnchantment(Item* item, EnchantmentSlot slot, bool apply, bool TC_LOG_DEBUG(LOG_FILTER_PLAYER_ITEMS, "+ %u HEALTH_REGENERATION", enchant_amount); break; case ITEM_MOD_SPELL_PENETRATION: - ApplyModInt32Value(PLAYER_FIELD_MOD_TARGET_RESISTANCE, enchant_amount, apply); - m_spellPenetrationItemMod += apply ? int32(enchant_amount) : -int32(enchant_amount); + ApplySpellPenetrationBonus(enchant_amount, apply); TC_LOG_DEBUG(LOG_FILTER_PLAYER_ITEMS, "+ %u SPELL_PENETRATION", enchant_amount); break; case ITEM_MOD_BLOCK_VALUE: @@ -26304,7 +26302,7 @@ float Player::GetCollisionHeight(bool mounted) const CreatureModelDataEntry const* modelData = sCreatureModelDataStore.LookupEntry(displayInfo->ModelId); ASSERT(modelData); - float scaleMod = GetFloatValue(OBJECT_FIELD_SCALE_X); // 99% sure about this + float scaleMod = GetObjectScale(); // 99% sure about this return scaleMod * mountModelData->MountHeight + modelData->CollisionHeight * 0.5f; } diff --git a/src/server/game/Entities/Player/Player.h b/src/server/game/Entities/Player/Player.h index 2cdf89dce75..6cc8c0c3929 100644 --- a/src/server/game/Entities/Player/Player.h +++ b/src/server/game/Entities/Player/Player.h @@ -1738,6 +1738,7 @@ class Player : public Unit, public GridObject<Player> bool UpdateStats(Stats stat); bool UpdateAllStats(); + void ApplySpellPenetrationBonus(int32 amount, bool apply); void UpdateResistances(uint32 school); void UpdateArmor(); void UpdateMaxHealth(); diff --git a/src/server/game/Entities/Totem/Totem.cpp b/src/server/game/Entities/Totem/Totem.cpp index 3b283ca39c2..ddea24c6439 100644 --- a/src/server/game/Entities/Totem/Totem.cpp +++ b/src/server/game/Entities/Totem/Totem.cpp @@ -109,7 +109,7 @@ void Totem::UnSummon(uint32 msTime) RemoveAurasDueToSpell(GetSpell(), GetGUID()); // clear owner's totem slot - for (int i = SUMMON_SLOT_TOTEM; i < MAX_TOTEM_SLOT; ++i) + for (uint8 i = SUMMON_SLOT_TOTEM; i < MAX_TOTEM_SLOT; ++i) { if (GetOwner()->m_SummonSlot[i] == GetGUID()) { diff --git a/src/server/game/Entities/Unit/StatSystem.cpp b/src/server/game/Entities/Unit/StatSystem.cpp index 7651297a078..e6cc30c867a 100644 --- a/src/server/game/Entities/Unit/StatSystem.cpp +++ b/src/server/game/Entities/Unit/StatSystem.cpp @@ -184,6 +184,12 @@ bool Player::UpdateAllStats() return true; } +void Player::ApplySpellPenetrationBonus(int32 amount, bool apply) +{ + ApplyModInt32Value(PLAYER_FIELD_MOD_TARGET_RESISTANCE, -amount, apply); + m_spellPenetrationItemMod += apply ? amount : -amount; +} + void Player::UpdateResistances(uint32 school) { if (school > SPELL_SCHOOL_NORMAL) diff --git a/src/server/game/Entities/Unit/Unit.cpp b/src/server/game/Entities/Unit/Unit.cpp index 4c64023ca60..7e67a9e6e09 100644 --- a/src/server/game/Entities/Unit/Unit.cpp +++ b/src/server/game/Entities/Unit/Unit.cpp @@ -162,7 +162,7 @@ ProcEventInfo::ProcEventInfo(Unit* actor, Unit* actionTarget, Unit* procTarget, #endif Unit::Unit(bool isWorldObject) : WorldObject(isWorldObject), m_movedPlayer(NULL), m_lastSanctuaryTime(0), - m_TempSpeed(0.0f), IsAIEnabled(false), NeedChangeAI(false), + IsAIEnabled(false), NeedChangeAI(false), LastCharmerGUID(0), m_ControlledByPlayer(false), movespline(new Movement::MoveSpline()), i_AI(NULL), i_disabledAI(NULL), m_AutoRepeatFirstCast(false), m_procDeep(0), m_removedAurasCount(0), i_motionMaster(this), m_ThreatManager(this), @@ -195,8 +195,6 @@ Unit::Unit(bool isWorldObject) : for (uint8 i = 0; i < CURRENT_MAX_SPELL; ++i) m_currentSpells[i] = NULL; - m_addDmgOnce = 0; - for (uint8 i = 0; i < MAX_SUMMON_SLOT; ++i) m_SummonSlot[i] = 0; @@ -1550,75 +1548,93 @@ uint32 Unit::CalcArmorReducedDamage(Unit* victim, const uint32 damage, SpellInfo return std::max<uint32>(damage * (1.0f - tmpvalue), 1); } -void Unit::CalcAbsorbResist(Unit* victim, SpellSchoolMask schoolMask, DamageEffectType damagetype, uint32 const damage, uint32 *absorb, uint32 *resist, SpellInfo const* spellInfo) +uint32 Unit::CalcSpellResistance(Unit* victim, SpellSchoolMask schoolMask, SpellInfo const* spellInfo) const { - if (!victim || !victim->IsAlive() || !damage) - return; + // Magic damage, check for resists + if (!(schoolMask & SPELL_SCHOOL_MASK_SPELL)) + return 0; - DamageInfo dmgInfo = DamageInfo(this, victim, damage, spellInfo, schoolMask, damagetype); + // Ignore spells that can't be resisted + if (spellInfo && spellInfo->AttributesEx4 & SPELL_ATTR4_IGNORE_RESISTANCES) + return 0; - // Magic damage, check for resists - // Ignore spells that cant be resisted - if ((schoolMask & SPELL_SCHOOL_MASK_NORMAL) == 0 && (!spellInfo || (spellInfo->AttributesEx4 & SPELL_ATTR4_IGNORE_RESISTANCES) == 0)) - { - float victimResistance = float(victim->GetResistance(schoolMask)); - victimResistance += float(GetTotalAuraModifierByMiscMask(SPELL_AURA_MOD_TARGET_RESISTANCE, schoolMask)); + uint32 const BOSS_LEVEL = 83; + uint32 const BOSS_RESISTANCE_CONSTANT = 510; + uint32 resistanceConstant = 0; + uint8 level = victim->getLevel(); - if (Player* player = ToPlayer()) - victimResistance -= float(player->GetSpellPenetrationItemMod()); + if (level == BOSS_LEVEL) + resistanceConstant = BOSS_RESISTANCE_CONSTANT; + else + resistanceConstant = level * 5; - // Resistance can't be lower then 0. - if (victimResistance < 0.0f) - victimResistance = 0.0f; + int32 baseVictimResistance = victim->GetResistance(schoolMask); + baseVictimResistance += GetTotalAuraModifierByMiscMask(SPELL_AURA_MOD_TARGET_RESISTANCE, schoolMask); - static uint32 const BOSS_LEVEL = 83; - static float const BOSS_RESISTANCE_CONSTANT = 510.0f; - uint32 level = victim->getLevel(); - float resistanceConstant = 0.0f; + if (Player const* player = ToPlayer()) + baseVictimResistance -= player->GetSpellPenetrationItemMod(); - if (level == BOSS_LEVEL) - resistanceConstant = BOSS_RESISTANCE_CONSTANT; - else - resistanceConstant = level * 5.0f; + // Resistance can't be lower then 0 + int32 victimResistance = std::max<int32>(baseVictimResistance, 0); - float averageResist = victimResistance / (victimResistance + resistanceConstant); - float discreteResistProbability[11]; - for (uint32 i = 0; i < 11; ++i) - { - discreteResistProbability[i] = 0.5f - 2.5f * fabs(0.1f * i - averageResist); - if (discreteResistProbability[i] < 0.0f) - discreteResistProbability[i] = 0.0f; - } + if (victimResistance > 0) + { + int32 ignoredResistance = 0; - if (averageResist <= 0.1f) - { - discreteResistProbability[0] = 1.0f - 7.5f * averageResist; - discreteResistProbability[1] = 5.0f * averageResist; - discreteResistProbability[2] = 2.5f * averageResist; - } + AuraEffectList const& ResIgnoreAurasAb = GetAuraEffectsByType(SPELL_AURA_MOD_ABILITY_IGNORE_TARGET_RESIST); + for (AuraEffectList::const_iterator itr = ResIgnoreAurasAb.begin(); itr != ResIgnoreAurasAb.end(); ++itr) + if (((*itr)->GetMiscValue() & schoolMask) && (*itr)->IsAffectedOnSpell(spellInfo)) + ignoredResistance += (*itr)->GetAmount(); - float r = float(rand_norm()); - uint32 i = 0; - float probabilitySum = discreteResistProbability[0]; + AuraEffectList const& ResIgnoreAuras = GetAuraEffectsByType(SPELL_AURA_MOD_IGNORE_TARGET_RESIST); + for (AuraEffectList::const_iterator itr = ResIgnoreAuras.begin(); itr != ResIgnoreAuras.end(); ++itr) + if ((*itr)->GetMiscValue() & schoolMask) + ignoredResistance += (*itr)->GetAmount(); - while (r >= probabilitySum && i < 10) - probabilitySum += discreteResistProbability[++i]; + ignoredResistance = std::min<int32>(ignoredResistance, 100); + ApplyPct(victimResistance, 100 - ignoredResistance); + } - float damageResisted = float(damage * i / 10); + if (victimResistance <= 0) + return 0; - AuraEffectList const& ResIgnoreAurasAb = GetAuraEffectsByType(SPELL_AURA_MOD_ABILITY_IGNORE_TARGET_RESIST); - for (AuraEffectList::const_iterator j = ResIgnoreAurasAb.begin(); j != ResIgnoreAurasAb.end(); ++j) - if (((*j)->GetMiscValue() & schoolMask) && (*j)->IsAffectedOnSpell(spellInfo)) - AddPct(damageResisted, -(*j)->GetAmount()); + float averageResist = float(victimResistance) / float(victimResistance + resistanceConstant); - AuraEffectList const& ResIgnoreAuras = GetAuraEffectsByType(SPELL_AURA_MOD_IGNORE_TARGET_RESIST); - for (AuraEffectList::const_iterator j = ResIgnoreAuras.begin(); j != ResIgnoreAuras.end(); ++j) - if ((*j)->GetMiscValue() & schoolMask) - AddPct(damageResisted, -(*j)->GetAmount()); + float discreteResistProbability[11]; + for (uint32 i = 0; i < 11; ++i) + { + discreteResistProbability[i] = 0.5f - 2.5f * fabs(0.1f * i - averageResist); + if (discreteResistProbability[i] < 0.0f) + discreteResistProbability[i] = 0.0f; + } - dmgInfo.ResistDamage(uint32(damageResisted)); + if (averageResist <= 0.1f) + { + discreteResistProbability[0] = 1.0f - 7.5f * averageResist; + discreteResistProbability[1] = 5.0f * averageResist; + discreteResistProbability[2] = 2.5f * averageResist; } + uint32 resistance = 0; + float r = float(rand_norm()); + float probabilitySum = discreteResistProbability[0]; + + while (r >= probabilitySum && resistance < 10) + probabilitySum += discreteResistProbability[++resistance]; + + return resistance * 10; +} + +void Unit::CalcAbsorbResist(Unit* victim, SpellSchoolMask schoolMask, DamageEffectType damagetype, uint32 const damage, uint32* absorb, uint32* resist, SpellInfo const* spellInfo /*= NULL*/) +{ + if (!victim || !victim->IsAlive() || !damage) + return; + + DamageInfo dmgInfo = DamageInfo(this, victim, damage, spellInfo, schoolMask, damagetype); + + uint32 spellResistance = CalcSpellResistance(victim, schoolMask, spellInfo); + dmgInfo.ResistDamage(CalculatePct(damage, spellResistance)); + // Ignore Absorption Auras float auraAbsorbMod = 0; AuraEffectList const& AbsIgnoreAurasA = GetAuraEffectsByType(SPELL_AURA_MOD_TARGET_ABSORB_SCHOOL); @@ -1835,7 +1851,7 @@ void Unit::CalcAbsorbResist(Unit* victim, SpellSchoolMask schoolMask, DamageEffe *absorb = dmgInfo.GetAbsorb(); } -void Unit::CalcHealAbsorb(Unit* victim, const SpellInfo* healSpell, uint32 &healAmount, uint32 &absorb) +void Unit::CalcHealAbsorb(Unit* victim, SpellInfo const* healSpell, uint32 &healAmount, uint32 &absorb) { if (!healAmount) return; @@ -2243,24 +2259,26 @@ bool Unit::isBlockCritical() return false; } -int32 Unit::GetMechanicResistChance(const SpellInfo* spell) const +int32 Unit::GetMechanicResistChance(SpellInfo const* spellInfo) const { - if (!spell) + if (!spellInfo) return 0; - int32 resist_mech = 0; + + int32 resistMech = 0; for (uint8 eff = 0; eff < MAX_SPELL_EFFECTS; ++eff) { - if (!spell->Effects[eff].IsEffect()) - break; - int32 effect_mech = spell->GetEffectMechanic(eff); - if (effect_mech) + if (!spellInfo->Effects[eff].IsEffect()) + break; + + int32 effectMech = spellInfo->GetEffectMechanic(eff); + if (effectMech) { - int32 temp = GetTotalAuraModifierByMiscValue(SPELL_AURA_MOD_MECHANIC_RESISTANCE, effect_mech); - if (resist_mech < temp) - resist_mech = temp; + int32 temp = GetTotalAuraModifierByMiscValue(SPELL_AURA_MOD_MECHANIC_RESISTANCE, effectMech); + if (resistMech < temp) + resistMech = temp; } } - return resist_mech; + return resistMech; } bool Unit::CanUseAttackType(uint8 attacktype) const @@ -2279,23 +2297,23 @@ bool Unit::CanUseAttackType(uint8 attacktype) const } // Melee based spells hit result calculations -SpellMissInfo Unit::MeleeSpellHitResult(Unit* victim, SpellInfo const* spell) +SpellMissInfo Unit::MeleeSpellHitResult(Unit* victim, SpellInfo const* spellInfo) { // Spells with SPELL_ATTR3_IGNORE_HIT_RESULT will additionally fully ignore // resist and deflect chances - if (spell->AttributesEx3 & SPELL_ATTR3_IGNORE_HIT_RESULT) + if (spellInfo->AttributesEx3 & SPELL_ATTR3_IGNORE_HIT_RESULT) return SPELL_MISS_NONE; WeaponAttackType attType = BASE_ATTACK; // Check damage class instead of attack type to correctly handle judgements // - they are meele, but can't be dodged/parried/deflected because of ranged dmg class - if (spell->DmgClass == SPELL_DAMAGE_CLASS_RANGED) + if (spellInfo->DmgClass == SPELL_DAMAGE_CLASS_RANGED) attType = RANGED_ATTACK; int32 attackerWeaponSkill; // skill value for these spells (for example judgements) is 5* level - if (spell->DmgClass == SPELL_DAMAGE_CLASS_RANGED && !spell->IsRangedWeaponSpell()) + if (spellInfo->DmgClass == SPELL_DAMAGE_CLASS_RANGED && !spellInfo->IsRangedWeaponSpell()) attackerWeaponSkill = getLevel() * 5; // bonus from skills is 0.04% per skill Diff else @@ -2305,7 +2323,7 @@ SpellMissInfo Unit::MeleeSpellHitResult(Unit* victim, SpellInfo const* spell) uint32 roll = urand (0, 10000); - uint32 missChance = uint32(MeleeSpellMissChance(victim, attType, skillDiff, spell->Id) * 100.0f); + uint32 missChance = uint32(MeleeSpellMissChance(victim, attType, skillDiff, spellInfo->Id) * 100.0f); // Roll miss uint32 tmp = missChance; if (roll < tmp) @@ -2316,12 +2334,12 @@ SpellMissInfo Unit::MeleeSpellHitResult(Unit* victim, SpellInfo const* spell) // Get effects mechanic and chance for (uint8 eff = 0; eff < MAX_SPELL_EFFECTS; ++eff) { - int32 effect_mech = spell->GetEffectMechanic(eff); + int32 effect_mech = spellInfo->GetEffectMechanic(eff); if (effect_mech) { int32 temp = victim->GetTotalAuraModifierByMiscValue(SPELL_AURA_MOD_MECHANIC_RESISTANCE, effect_mech); - if (resist_mech < temp*100) - resist_mech = temp*100; + if (resist_mech < temp * 100) + resist_mech = temp * 100; } } // Roll chance @@ -2331,14 +2349,14 @@ SpellMissInfo Unit::MeleeSpellHitResult(Unit* victim, SpellInfo const* spell) bool canDodge = true; bool canParry = true; - bool canBlock = spell->AttributesEx3 & SPELL_ATTR3_BLOCKABLE_SPELL; + bool canBlock = spellInfo->AttributesEx3 & SPELL_ATTR3_BLOCKABLE_SPELL; // Same spells cannot be parry/dodge - if (spell->Attributes & SPELL_ATTR0_IMPOSSIBLE_DODGE_PARRY_BLOCK) + if (spellInfo->Attributes & SPELL_ATTR0_IMPOSSIBLE_DODGE_PARRY_BLOCK) return SPELL_MISS_NONE; // Chance resist mechanic - int32 resist_chance = victim->GetMechanicResistChance(spell) * 100; + int32 resist_chance = victim->GetMechanicResistChance(spellInfo) * 100; tmp += resist_chance; if (roll < tmp) return SPELL_MISS_RESIST; @@ -2353,7 +2371,7 @@ SpellMissInfo Unit::MeleeSpellHitResult(Unit* victim, SpellInfo const* spell) if (victim->HasInArc(M_PI, this) || victim->HasAuraType(SPELL_AURA_IGNORE_HIT_DIRECTION)) { int32 deflect_chance = victim->GetTotalAuraModifier(SPELL_AURA_DEFLECT_SPELLS) * 100; - tmp+=deflect_chance; + tmp += deflect_chance; if (roll < tmp) return SPELL_MISS_DEFLECT; } @@ -2374,7 +2392,7 @@ SpellMissInfo Unit::MeleeSpellHitResult(Unit* victim, SpellInfo const* spell) } else // Only deterrence as of 3.3.5 { - if (spell->AttributesCu & SPELL_ATTR0_CU_REQ_CASTER_BEHIND_TARGET) + if (spellInfo->AttributesCu & SPELL_ATTR0_CU_REQ_CASTER_BEHIND_TARGET) canParry = false; } } @@ -2392,13 +2410,19 @@ SpellMissInfo Unit::MeleeSpellHitResult(Unit* victim, SpellInfo const* spell) AuraEffectList const& ignore = GetAuraEffectsByType(SPELL_AURA_IGNORE_COMBAT_RESULT); for (AuraEffectList::const_iterator i = ignore.begin(); i != ignore.end(); ++i) { - if (!(*i)->IsAffectedOnSpell(spell)) + if (!(*i)->IsAffectedOnSpell(spellInfo)) continue; switch ((*i)->GetMiscValue()) { - case MELEE_HIT_DODGE: canDodge = false; break; - case MELEE_HIT_BLOCK: canBlock = false; break; - case MELEE_HIT_PARRY: canParry = false; break; + case MELEE_HIT_DODGE: + canDodge = false; + break; + case MELEE_HIT_BLOCK: + canBlock = false; + break; + case MELEE_HIT_PARRY: + canParry = false; + break; default: TC_LOG_DEBUG(LOG_FILTER_UNITS, "Spell %u SPELL_AURA_IGNORE_COMBAT_RESULT has unhandled state %d", (*i)->GetId(), (*i)->GetMiscValue()); break; @@ -2456,18 +2480,18 @@ SpellMissInfo Unit::MeleeSpellHitResult(Unit* victim, SpellInfo const* spell) } /// @todo need use unit spell resistances in calculations -SpellMissInfo Unit::MagicSpellHitResult(Unit* victim, SpellInfo const* spell) +SpellMissInfo Unit::MagicSpellHitResult(Unit* victim, SpellInfo const* spellInfo) { // Can`t miss on dead target (on skinning for example) if (!victim->IsAlive() && victim->GetTypeId() != TYPEID_PLAYER) return SPELL_MISS_NONE; - SpellSchoolMask schoolMask = spell->GetSchoolMask(); + SpellSchoolMask schoolMask = spellInfo->GetSchoolMask(); // PvP - PvE spell misschances per leveldif > 2 int32 lchance = victim->GetTypeId() == TYPEID_PLAYER ? 7 : 11; int32 thisLevel = getLevelForTarget(victim); if (GetTypeId() == TYPEID_UNIT && ToCreature()->IsTrigger()) - thisLevel = std::max<int32>(thisLevel, spell->SpellLevel); + thisLevel = std::max<int32>(thisLevel, spellInfo->SpellLevel); int32 leveldif = int32(victim->getLevelForTarget(this)) - thisLevel; // Base hit chance from attacker and victim levels @@ -2479,18 +2503,18 @@ SpellMissInfo Unit::MagicSpellHitResult(Unit* victim, SpellInfo const* spell) // Spellmod from SPELLMOD_RESIST_MISS_CHANCE if (Player* modOwner = GetSpellModOwner()) - modOwner->ApplySpellMod(spell->Id, SPELLMOD_RESIST_MISS_CHANCE, modHitChance); + modOwner->ApplySpellMod(spellInfo->Id, SPELLMOD_RESIST_MISS_CHANCE, modHitChance); // Increase from attacker SPELL_AURA_MOD_INCREASES_SPELL_PCT_TO_HIT auras modHitChance += GetTotalAuraModifierByMiscMask(SPELL_AURA_MOD_INCREASES_SPELL_PCT_TO_HIT, schoolMask); // Spells with SPELL_ATTR3_IGNORE_HIT_RESULT will ignore target's avoidance effects - if (!(spell->AttributesEx3 & SPELL_ATTR3_IGNORE_HIT_RESULT)) + if (!(spellInfo->AttributesEx3 & SPELL_ATTR3_IGNORE_HIT_RESULT)) { // Chance hit from victim SPELL_AURA_MOD_ATTACKER_SPELL_HIT_CHANCE auras modHitChance += victim->GetTotalAuraModifierByMiscMask(SPELL_AURA_MOD_ATTACKER_SPELL_HIT_CHANCE, schoolMask); // Reduce spell hit chance for Area of effect spells from victim SPELL_AURA_MOD_AOE_AVOIDANCE aura - if (spell->IsTargetingArea()) + if (spellInfo->IsTargetingArea()) modHitChance -= victim->GetTotalAuraModifier(SPELL_AURA_MOD_AOE_AVOIDANCE); // Decrease hit chance from victim rating bonus @@ -2502,10 +2526,7 @@ SpellMissInfo Unit::MagicSpellHitResult(Unit* victim, SpellInfo const* spell) // Increase hit chance from attacker SPELL_AURA_MOD_SPELL_HIT_CHANCE and attacker ratings HitChance += int32(m_modSpellHitChance * 100.0f); - if (HitChance < 100) - HitChance = 100; - else if (HitChance > 10000) - HitChance = 10000; + RoundToInterval(HitChance, 100, 10000); int32 tmp = 10000 - HitChance; @@ -2516,30 +2537,30 @@ SpellMissInfo Unit::MagicSpellHitResult(Unit* victim, SpellInfo const* spell) // Spells with SPELL_ATTR3_IGNORE_HIT_RESULT will additionally fully ignore // resist and deflect chances - if (spell->AttributesEx3 & SPELL_ATTR3_IGNORE_HIT_RESULT) + if (spellInfo->AttributesEx3 & SPELL_ATTR3_IGNORE_HIT_RESULT) return SPELL_MISS_NONE; // Chance resist mechanic (select max value from every mechanic spell effect) - int32 resist_chance = victim->GetMechanicResistChance(spell) * 100; + int32 resist_chance = victim->GetMechanicResistChance(spellInfo) * 100; tmp += resist_chance; // Chance resist debuff - if (!spell->IsPositive()) + if (!spellInfo->IsPositive()) { - bool bNegativeAura = true; + bool hasAura = false; for (uint8 i = 0; i < MAX_SPELL_EFFECTS; ++i) { - if (spell->Effects[i].ApplyAuraName == 0) + if (spellInfo->Effects[i].IsAura()) { - bNegativeAura = false; + hasAura = true; break; } } - if (bNegativeAura) + if (hasAura) { - tmp += victim->GetMaxPositiveAuraModifierByMiscValue(SPELL_AURA_MOD_DEBUFF_RESISTANCE, int32(spell->Dispel)) * 100; - tmp += victim->GetMaxNegativeAuraModifierByMiscValue(SPELL_AURA_MOD_DEBUFF_RESISTANCE, int32(spell->Dispel)) * 100; + tmp += victim->GetMaxPositiveAuraModifierByMiscValue(SPELL_AURA_MOD_DEBUFF_RESISTANCE, int32(spellInfo->Dispel)) * 100; + tmp += victim->GetMaxNegativeAuraModifierByMiscValue(SPELL_AURA_MOD_DEBUFF_RESISTANCE, int32(spellInfo->Dispel)) * 100; } } @@ -2567,19 +2588,19 @@ SpellMissInfo Unit::MagicSpellHitResult(Unit* victim, SpellInfo const* spell) // Parry // For spells // Resist -SpellMissInfo Unit::SpellHitResult(Unit* victim, SpellInfo const* spell, bool CanReflect) +SpellMissInfo Unit::SpellHitResult(Unit* victim, SpellInfo const* spellInfo, bool CanReflect) { // Check for immune - if (victim->IsImmunedToSpell(spell)) + if (victim->IsImmunedToSpell(spellInfo)) return SPELL_MISS_IMMUNE; // All positive spells can`t miss /// @todo client not show miss log for this spells - so need find info for this in dbc and use it! - if (spell->IsPositive() - &&(!IsHostileTo(victim))) // prevent from affecting enemy by "positive" spell + if (spellInfo->IsPositive() && !IsHostileTo(victim)) // prevent from affecting enemy by "positive" spell return SPELL_MISS_NONE; + // Check for immune - if (victim->IsImmunedToDamage(spell)) + if (victim->IsImmunedToDamage(spellInfo)) return SPELL_MISS_IMMUNE; if (this == victim) @@ -2595,25 +2616,25 @@ SpellMissInfo Unit::SpellHitResult(Unit* victim, SpellInfo const* spell, bool Ca int32 reflectchance = victim->GetTotalAuraModifier(SPELL_AURA_REFLECT_SPELLS); Unit::AuraEffectList const& mReflectSpellsSchool = victim->GetAuraEffectsByType(SPELL_AURA_REFLECT_SPELLS_SCHOOL); for (Unit::AuraEffectList::const_iterator i = mReflectSpellsSchool.begin(); i != mReflectSpellsSchool.end(); ++i) - if ((*i)->GetMiscValue() & spell->GetSchoolMask()) + if ((*i)->GetMiscValue() & spellInfo->GetSchoolMask()) reflectchance += (*i)->GetAmount(); if (reflectchance > 0 && roll_chance_i(reflectchance)) { // Start triggers for remove charges if need (trigger only for victim, and mark as active spell) - ProcDamageAndSpell(victim, PROC_FLAG_NONE, PROC_FLAG_TAKEN_SPELL_MAGIC_DMG_CLASS_NEG, PROC_EX_REFLECT, 1, BASE_ATTACK, spell); + ProcDamageAndSpell(victim, PROC_FLAG_NONE, PROC_FLAG_TAKEN_SPELL_MAGIC_DMG_CLASS_NEG, PROC_EX_REFLECT, 1, BASE_ATTACK, spellInfo); return SPELL_MISS_REFLECT; } } - switch (spell->DmgClass) + switch (spellInfo->DmgClass) { case SPELL_DAMAGE_CLASS_RANGED: case SPELL_DAMAGE_CLASS_MELEE: - return MeleeSpellHitResult(victim, spell); + return MeleeSpellHitResult(victim, spellInfo); case SPELL_DAMAGE_CLASS_NONE: return SPELL_MISS_NONE; case SPELL_DAMAGE_CLASS_MAGIC: - return MagicSpellHitResult(victim, spell); + return MagicSpellHitResult(victim, spellInfo); } return SPELL_MISS_NONE; } @@ -2970,11 +2991,11 @@ void Unit::SetCurrentCastedSpell(Spell* pSpell) if (m_currentSpells[CURRENT_AUTOREPEAT_SPELL]) { // break autorepeat if not Auto Shot - if (m_currentSpells[CURRENT_AUTOREPEAT_SPELL]->m_spellInfo->Id != 75) + if (m_currentSpells[CURRENT_AUTOREPEAT_SPELL]->GetSpellInfo()->Id != 75) InterruptSpell(CURRENT_AUTOREPEAT_SPELL); m_AutoRepeatFirstCast = true; } - if (pSpell->m_spellInfo->CalcCastTime(this) > 0) + if (pSpell->GetCastTime() > 0) AddUnitState(UNIT_STATE_CASTING); break; @@ -2987,7 +3008,7 @@ void Unit::SetCurrentCastedSpell(Spell* pSpell) // it also does break autorepeat if not Auto Shot if (m_currentSpells[CURRENT_AUTOREPEAT_SPELL] && - m_currentSpells[CURRENT_AUTOREPEAT_SPELL]->m_spellInfo->Id != 75) + m_currentSpells[CURRENT_AUTOREPEAT_SPELL]->GetSpellInfo()->Id != 75) InterruptSpell(CURRENT_AUTOREPEAT_SPELL); AddUnitState(UNIT_STATE_CASTING); @@ -2996,7 +3017,7 @@ void Unit::SetCurrentCastedSpell(Spell* pSpell) case CURRENT_AUTOREPEAT_SPELL: { // only Auto Shoot does not break anything - if (pSpell->m_spellInfo->Id != 75) + if (pSpell->GetSpellInfo()->Id != 75) { // generic autorepeats break generic non-delayed and channeled non-delayed spells InterruptSpell(CURRENT_GENERIC_SPELL, false); @@ -5717,8 +5738,8 @@ bool Unit::HandleDummyAuraProc(Unit* victim, uint32 damage, AuraEffect* triggere // if damage is more than need or target die from damage deal finish spell if (triggeredByAura->GetAmount() <= int32(damage) || GetHealth() <= damage) { - // remember guid before aura delete - uint64 casterGuid = triggeredByAura->GetCasterGUID(); + // remember caster before aura delete + Unit* caster = triggeredByAura->GetCaster(); // Remove aura (before cast for prevent infinite loop handlers) RemoveAurasDueToSpell(triggeredByAura->GetId()); @@ -5726,7 +5747,7 @@ bool Unit::HandleDummyAuraProc(Unit* victim, uint32 damage, AuraEffect* triggere uint32 spell = sSpellMgr->GetSpellWithRank(27285, dummySpell->GetRank()); // Cast finish spell (triggeredByAura already not exist!) - if (Unit* caster = GetUnit(*this, casterGuid)) + if (caster) caster->CastSpell(this, spell, true, castItem); return true; // no hidden cooldown } @@ -5741,14 +5762,14 @@ bool Unit::HandleDummyAuraProc(Unit* victim, uint32 damage, AuraEffect* triggere // if damage is more than need deal finish spell if (triggeredByAura->GetAmount() <= int32(damage)) { - // remember guid before aura delete - uint64 casterGuid = triggeredByAura->GetCasterGUID(); + // remember caster before aura delete + Unit* caster = triggeredByAura->GetCaster(); // Remove aura (before cast for prevent infinite loop handlers) RemoveAurasDueToSpell(triggeredByAura->GetId()); // Cast finish spell (triggeredByAura already not exist!) - if (Unit* caster = GetUnit(*this, casterGuid)) + if (caster) caster->CastSpell(this, 32865, true, castItem); return true; // no hidden cooldown } @@ -7588,7 +7609,8 @@ bool Unit::HandleAuraProc(Unit* victim, uint32 damage, Aura* triggeredByAura, Sp // Blood of the North // Reaping // Death Rune Mastery - if (dummySpell->SpellIconID == 3041 || dummySpell->SpellIconID == 22 || dummySpell->SpellIconID == 2622) + /// @todo move those to spell scripts + if (dummySpell->SpellIconID == 3041 || (dummySpell->SpellIconID == 22 && dummySpell->Id != 62459) || dummySpell->SpellIconID == 2622) { *handled = true; // Convert recently used Blood Rune to Death Rune @@ -14066,11 +14088,10 @@ void Unit::ProcDamageAndSpellFor(bool isVictim, Unit* target, uint32 procFlag, u if (spellInfo->AttributesEx3 & SPELL_ATTR3_DISABLE_PROC) SetCantProc(true); - i->aura->CallScriptProcHandlers(aurApp, eventInfo); + bool handled = i->aura->CallScriptProcHandlers(aurApp, eventInfo); - // This bool is needed till separate aura effect procs are still here - bool handled = false; - if (HandleAuraProc(target, damage, i->aura, procSpell, procFlag, procExtra, cooldown, &handled)) + // "handled" is needed as long as proc can be handled in multiple places + if (!handled && HandleAuraProc(target, damage, i->aura, procSpell, procFlag, procExtra, cooldown, &handled)) { TC_LOG_DEBUG(LOG_FILTER_SPELLS_AURAS, "ProcDamageAndSpell: casting spell %u (triggered with value by %s aura of spell %u)", spellInfo->Id, (isVictim?"a victim's":"an attacker's"), Id); takeCharges = true; @@ -14353,22 +14374,6 @@ Player* Unit::GetSpellModOwner() const } ///----------Pet responses methods----------------- -void Unit::SendPetCastFail(uint32 spellid, SpellCastResult result) -{ - if (result == SPELL_CAST_OK) - return; - - Unit* owner = GetCharmerOrOwner(); - if (!owner || owner->GetTypeId() != TYPEID_PLAYER) - return; - - WorldPacket data(SMSG_PET_CAST_FAILED, 1 + 4 + 1); - data << uint8(0); // cast count - data << uint32(spellid); - data << uint8(result); - owner->ToPlayer()->GetSession()->SendPacket(&data); -} - void Unit::SendPetActionFeedback(uint8 msg) { Unit* owner = GetOwner(); @@ -15831,16 +15836,13 @@ void Unit::RemoveCharmedBy(Unit* charmer) if (Creature* creature = ToCreature()) { + // Creature will restore its old AI on next update if (creature->AI()) creature->AI()->OnCharmed(false); - if (type != CHARM_TYPE_VEHICLE) // Vehicles' AI is never modified - { - creature->AIM_Initialize(); - - if (creature->AI() && charmer && charmer->IsAlive()) - creature->AI()->AttackStart(charmer); - } + // Vehicle should not attack its passenger after he exists the seat + if (type != CHARM_TYPE_VEHICLE) + LastCharmerGUID = charmer->GetGUID(); } else ToPlayer()->SetClientControl(this, 1); @@ -15925,7 +15927,7 @@ void Unit::RestoreFaction() Unit* Unit::GetRedirectThreatTarget() { - return _redirectThreadInfo.GetTargetGUID() ? GetUnit(*this, _redirectThreadInfo.GetTargetGUID()) : NULL; + return _redirectThreadInfo.GetTargetGUID() ? ObjectAccessor::GetUnit(*this, _redirectThreadInfo.GetTargetGUID()) : NULL; } bool Unit::CreateVehicleKit(uint32 id, uint32 creatureEntry) diff --git a/src/server/game/Entities/Unit/Unit.h b/src/server/game/Entities/Unit/Unit.h index 5e2e746ae63..c90357a9eb8 100644 --- a/src/server/game/Entities/Unit/Unit.h +++ b/src/server/game/Entities/Unit/Unit.h @@ -951,7 +951,8 @@ struct CalcDamageInfo }; // Spell damage info structure based on structure sending in SMSG_SPELLNONMELEEDAMAGELOG opcode -struct SpellNonMeleeDamage{ +struct SpellNonMeleeDamage +{ SpellNonMeleeDamage(Unit* _attacker, Unit* _target, uint32 _SpellID, uint32 _schoolMask) : target(_target), attacker(_attacker), SpellID(_SpellID), damage(0), overkill(0), schoolMask(_schoolMask), absorb(0), resist(0), physicalLog(false), unused(false), blocked(0), HitInfo(0), cleanDamage(0) @@ -1470,16 +1471,16 @@ class Unit : public WorldObject void ApplyResilience(Unit const* victim, float* crit, int32* damage, bool isCrit, CombatRating type) const; float MeleeSpellMissChance(Unit const* victim, WeaponAttackType attType, int32 skillDiff, uint32 spellId) const; - SpellMissInfo MeleeSpellHitResult(Unit* victim, SpellInfo const* spell); - SpellMissInfo MagicSpellHitResult(Unit* victim, SpellInfo const* spell); - SpellMissInfo SpellHitResult(Unit* victim, SpellInfo const* spell, bool canReflect = false); + SpellMissInfo MeleeSpellHitResult(Unit* victim, SpellInfo const* spellInfo); + SpellMissInfo MagicSpellHitResult(Unit* victim, SpellInfo const* spellInfo); + SpellMissInfo SpellHitResult(Unit* victim, SpellInfo const* spellInfo, bool canReflect = false); float GetUnitDodgeChance() const; float GetUnitParryChance() const; float GetUnitBlockChance() const; float GetUnitMissChance(WeaponAttackType attType) const; float GetUnitCriticalChance(WeaponAttackType attackType, const Unit* victim) const; - int32 GetMechanicResistChance(const SpellInfo* spell) const; + int32 GetMechanicResistChance(SpellInfo const* spellInfo) const; bool CanUseAttackType(uint8 attacktype) const; virtual uint32 GetShieldBlockValue() const =0; @@ -1647,8 +1648,8 @@ class Unit : public WorldObject Player* GetSpellModOwner() const; Unit* GetOwner() const; - Guardian *GetGuardianPet() const; - Minion *GetFirstMinion() const; + Guardian* GetGuardianPet() const; + Minion* GetFirstMinion() const; Unit* GetCharmer() const; Unit* GetCharm() const; Unit* GetCharmerOrOwner() const; @@ -1839,7 +1840,6 @@ class Unit : public WorldObject Spell* FindCurrentSpellBySpellId(uint32 spell_id) const; int32 GetCurrentSpellCastTime(uint32 spell_id) const; - uint32 m_addDmgOnce; uint64 m_SummonSlot[MAX_SUMMON_SLOT]; uint64 m_ObjectSlot[MAX_GAMEOBJECT_SLOT]; @@ -1980,30 +1980,28 @@ class Unit : public WorldObject void ApplySpellImmune(uint32 spellId, uint32 op, uint32 type, bool apply); void ApplySpellDispelImmunity(const SpellInfo* spellProto, DispelType type, bool apply); - virtual bool IsImmunedToSpell(SpellInfo const* spellInfo) const; - // redefined in Creature + virtual bool IsImmunedToSpell(SpellInfo const* spellInfo) const; // redefined in Creature + bool IsImmunedToDamage(SpellSchoolMask meleeSchoolMask) const; bool IsImmunedToDamage(SpellInfo const* spellInfo) const; - virtual bool IsImmunedToSpellEffect(SpellInfo const* spellInfo, uint32 index) const; - // redefined in Creature + virtual bool IsImmunedToSpellEffect(SpellInfo const* spellInfo, uint32 index) const; // redefined in Creature + static bool IsDamageReducedByArmor(SpellSchoolMask damageSchoolMask, SpellInfo const* spellInfo = NULL, uint8 effIndex = MAX_SPELL_EFFECTS); - uint32 CalcArmorReducedDamage(Unit* victim, const uint32 damage, SpellInfo const* spellInfo, WeaponAttackType attackType=MAX_ATTACK); - void CalcAbsorbResist(Unit* victim, SpellSchoolMask schoolMask, DamageEffectType damagetype, const uint32 damage, uint32 *absorb, uint32 *resist, SpellInfo const* spellInfo = NULL); - void CalcHealAbsorb(Unit* victim, const SpellInfo* spellProto, uint32 &healAmount, uint32 &absorb); + uint32 CalcArmorReducedDamage(Unit* victim, const uint32 damage, SpellInfo const* spellInfo, WeaponAttackType attackType = MAX_ATTACK); + uint32 CalcSpellResistance(Unit* victim, SpellSchoolMask schoolMask, SpellInfo const* spellInfo) const; + void CalcAbsorbResist(Unit* victim, SpellSchoolMask schoolMask, DamageEffectType damagetype, uint32 const damage, uint32* absorb, uint32* resist, SpellInfo const* spellInfo = NULL); + void CalcHealAbsorb(Unit* victim, SpellInfo const* spellInfo, uint32& healAmount, uint32& absorb); void UpdateSpeed(UnitMoveType mtype, bool forced); float GetSpeed(UnitMoveType mtype) const; float GetSpeedRate(UnitMoveType mtype) const { return m_speed_rate[mtype]; } void SetSpeed(UnitMoveType mtype, float rate, bool forced = false); - float m_TempSpeed; - - bool isHover() const { return HasAuraType(SPELL_AURA_HOVER); } float ApplyEffectModifiers(SpellInfo const* spellProto, uint8 effect_index, float value) const; int32 CalculateSpellDamage(Unit const* target, SpellInfo const* spellProto, uint8 effect_index, int32 const* basePoints = NULL) const; int32 CalcSpellDuration(SpellInfo const* spellProto); int32 ModSpellDuration(SpellInfo const* spellProto, Unit const* target, int32 duration, bool positive, uint32 effectMask); - void ModSpellCastTime(SpellInfo const* spellProto, int32 & castTime, Spell* spell=NULL); + void ModSpellCastTime(SpellInfo const* spellProto, int32& castTime, Spell* spell = NULL); float CalculateLevelPenalty(SpellInfo const* spellProto) const; void addFollower(FollowerReference* pRef) { m_FollowingRefManager.insertFirst(pRef); } @@ -2039,7 +2037,6 @@ class Unit : public WorldObject void ClearComboPointHolders(); ///----------Pet responses methods----------------- - void SendPetCastFail(uint32 spellid, SpellCastResult msg); void SendPetActionFeedback (uint8 msg); void SendPetTalk (uint32 pettalk); void SendPetAIReaction(uint64 guid); @@ -2077,6 +2074,7 @@ class Unit : public WorldObject friend class VehicleJoinEvent; bool IsAIEnabled, NeedChangeAI; + uint64 LastCharmerGUID; bool CreateVehicleKit(uint32 id, uint32 creatureEntry); void RemoveVehicleKit(); Vehicle* GetVehicleKit()const { return m_vehicleKit; } diff --git a/src/server/game/Globals/ObjectMgr.cpp b/src/server/game/Globals/ObjectMgr.cpp index 88a8664e8a4..b8899ae0cd9 100644 --- a/src/server/game/Globals/ObjectMgr.cpp +++ b/src/server/game/Globals/ObjectMgr.cpp @@ -8202,10 +8202,8 @@ void ObjectMgr::LoadGossipMenuItems() _gossipMenuItemsStore.clear(); QueryResult result = WorldDatabase.Query( - // 0 1 2 3 4 - "SELECT menu_id, id, option_icon, option_text, option_id, npc_option_npcflag, " - // 5 6 7 8 9 - "action_menu_id, action_poi_id, box_coded, box_money, box_text " + // 0 1 2 3 4 5 6 7 8 9 10 + "SELECT menu_id, id, option_icon, option_text, option_id, npc_option_npcflag, action_menu_id, action_poi_id, box_coded, box_money, box_text " "FROM gossip_menu_option ORDER BY menu_id, id"); if (!result) diff --git a/src/server/game/Grids/ObjectGridLoader.cpp b/src/server/game/Grids/ObjectGridLoader.cpp index dacb72d5de6..879dd48c759 100644 --- a/src/server/game/Grids/ObjectGridLoader.cpp +++ b/src/server/game/Grids/ObjectGridLoader.cpp @@ -217,8 +217,7 @@ void ObjectGridStoper::Visit(CreatureMapType &m) { iter->GetSource()->CombatStop(); iter->GetSource()->DeleteThreatList(); - if (iter->GetSource()->IsAIEnabled) - iter->GetSource()->AI()->EnterEvadeMode(); + iter->GetSource()->AI()->EnterEvadeMode(); } } } diff --git a/src/server/game/Handlers/CharacterHandler.cpp b/src/server/game/Handlers/CharacterHandler.cpp index 415b67467c0..0554820364d 100644 --- a/src/server/game/Handlers/CharacterHandler.cpp +++ b/src/server/game/Handlers/CharacterHandler.cpp @@ -224,7 +224,10 @@ void WorldSession::HandleCharEnum(PreparedQueryResult result) TC_LOG_INFO(LOG_FILTER_NETWORKIO, "Loading char guid %u from account %u.", guidlow, GetAccountId()); if (Player::BuildEnumData(result, &data)) { - _legitCharacters.insert(guidlow); + // Do not allow banned characters to log in + if (!(*result)[20].GetUInt32()) + _legitCharacters.insert(guidlow); + if (!sWorld->HasCharacterNameData(guidlow)) // This can happen if characters are inserted into the database manually. Core hasn't loaded name data yet. sWorld->AddCharacterNameData(guidlow, (*result)[1].GetString(), (*result)[4].GetUInt8(), (*result)[2].GetUInt8(), (*result)[3].GetUInt8(), (*result)[7].GetUInt8()); ++num; diff --git a/src/server/game/Handlers/PetHandler.cpp b/src/server/game/Handlers/PetHandler.cpp index 2a14be85cc5..32cd7ee4725 100644 --- a/src/server/game/Handlers/PetHandler.cpp +++ b/src/server/game/Handlers/PetHandler.cpp @@ -32,9 +32,6 @@ #include "Group.h" #include "SpellInfo.h" #include "Player.h" -#include "GridNotifiers.h" -#include "GridNotifiersImpl.h" -#include "CellImpl.h" void WorldSession::HandleDismissCritter(WorldPacket& recvData) { @@ -298,10 +295,6 @@ void WorldSession::HandlePetActionHelper(Unit* pet, uint64 guid1, uint32 spellid return; } - if (spellInfo->StartRecoveryCategory > 0) - if (pet->GetCharmInfo() && pet->GetCharmInfo()->GetGlobalCooldownMgr().HasGlobalCooldown(spellInfo)) - return; - for (uint32 i = 0; i < MAX_SPELL_EFFECTS; ++i) { if (spellInfo->Effects[i].TargetA.GetTarget() == TARGET_UNIT_SRC_AREA_ENEMY || spellInfo->Effects[i].TargetA.GetTarget() == TARGET_UNIT_DEST_AREA_ENEMY || spellInfo->Effects[i].TargetA.GetTarget() == TARGET_DEST_DYNOBJ_ENEMY) @@ -381,10 +374,10 @@ void WorldSession::HandlePetActionHelper(Unit* pet, uint64 guid1, uint32 spellid } else { - if (pet->isPossessed() || pet->IsVehicle()) + if (pet->isPossessed() || pet->IsVehicle()) /// @todo: confirm this check Spell::SendCastResult(GetPlayer(), spellInfo, 0, result); else - pet->SendPetCastFail(spellid, result); + spell->SendPetCastResult(result); if (!pet->ToCreature()->HasSpellCooldown(spellid)) GetPlayer()->SendClearCooldown(spellid, pet); @@ -774,34 +767,6 @@ void WorldSession::HandlePetCastSpellOpcode(WorldPacket& recvPacket) return; } - if (spellInfo->StartRecoveryCategory > 0) // Check if spell is affected by GCD - if (caster->GetTypeId() == TYPEID_UNIT && caster->GetCharmInfo() && caster->GetCharmInfo()->GetGlobalCooldownMgr().HasGlobalCooldown(spellInfo)) - { - caster->SendPetCastFail(spellId, SPELL_FAILED_NOT_READY); - return; - } - - // check spell focus object - if (spellInfo->RequiresSpellFocus && caster->IsVehicle()) - { - CellCoord p(Trinity::ComputeCellCoord(caster->GetPositionX(), caster->GetPositionY())); - Cell cell(p); - - GameObject* ok = NULL; - Trinity::GameObjectFocusCheck goCheck(caster, spellInfo->RequiresSpellFocus); - Trinity::GameObjectSearcher<Trinity::GameObjectFocusCheck> checker(caster, ok, goCheck); - - TypeContainerVisitor<Trinity::GameObjectSearcher<Trinity::GameObjectFocusCheck>, GridTypeMapContainer > objectChecker(checker); - Map& map = *caster->GetMap(); - cell.Visit(p, objectChecker, map, *caster, caster->GetVisibilityRange()); - - if (!ok) - { - caster->SendPetCastFail(spellId, SPELL_FAILED_REQUIRES_SPELL_FOCUS); - return; - } - } - // do not cast not learned spells if (!caster->HasSpell(spellId) || spellInfo->IsPassive()) return; @@ -816,26 +781,19 @@ void WorldSession::HandlePetCastSpellOpcode(WorldPacket& recvPacket) spell->m_cast_count = castCount; // probably pending spell cast spell->m_targets = targets; - /// @todo need to check victim? - SpellCastResult result; - if (caster->m_movedPlayer) - result = spell->CheckPetCast(caster->m_movedPlayer->GetSelectedUnit()); - else - result = spell->CheckPetCast(NULL); + SpellCastResult result = spell->CheckPetCast(NULL); if (result == SPELL_CAST_OK) { - if (caster->GetTypeId() == TYPEID_UNIT) + if (Creature* creature = caster->ToCreature()) { - Creature* pet = caster->ToCreature(); - pet->AddCreatureSpellCooldown(spellId); - if (pet->IsPet()) + creature->AddCreatureSpellCooldown(spellId); + if (Pet* pet = creature->ToPet()) { - Pet* p = (Pet*)pet; // 10% chance to play special pet attack talk, else growl // actually this only seems to happen on special spells, fire shield for imp, torment for voidwalker, but it's stupid to check every spell - if (p->getPetType() == SUMMON_PET && (urand(0, 100) < 10)) - pet->SendPetTalk((uint32)PET_TALK_SPECIAL_SPELL); + if (pet->getPetType() == SUMMON_PET && (urand(0, 100) < 10)) + pet->SendPetTalk(PET_TALK_SPECIAL_SPELL); else pet->SendPetAIReaction(guid); } @@ -845,7 +803,8 @@ void WorldSession::HandlePetCastSpellOpcode(WorldPacket& recvPacket) } else { - caster->SendPetCastFail(spellId, result); + spell->SendPetCastResult(result); + if (caster->GetTypeId() == TYPEID_PLAYER) { if (!caster->ToPlayer()->HasSpellCooldown(spellId)) diff --git a/src/server/game/Instances/InstanceScript.h b/src/server/game/Instances/InstanceScript.h index 1e349207b2f..943ae672046 100644 --- a/src/server/game/Instances/InstanceScript.h +++ b/src/server/game/Instances/InstanceScript.h @@ -22,8 +22,6 @@ #include "ZoneScript.h" #include "World.h" #include "ObjectMgr.h" -//#include "GameObject.h" -//#include "Map.h" #define OUT_SAVE_INST_DATA TC_LOG_DEBUG(LOG_FILTER_TSCR, "Saving Instance Data for Instance %s (Map %d, Instance Id %d)", instance->GetMapName(), instance->GetId(), instance->GetInstanceId()) #define OUT_SAVE_INST_DATA_COMPLETE TC_LOG_DEBUG(LOG_FILTER_TSCR, "Saving Instance Data for Instance %s (Map %d, Instance Id %d) completed.", instance->GetMapName(), instance->GetId(), instance->GetInstanceId()) @@ -235,4 +233,16 @@ class InstanceScript : public ZoneScript MinionInfoMap minions; uint32 completedEncounters; // completed encounter mask, bit indexes are DungeonEncounter.dbc boss numbers, used for packets }; -#endif + +template<class AI, class T> +AI* GetInstanceAI(T* obj, char const* scriptName) +{ + if (InstanceMap* instance = obj->GetMap()->ToInstanceMap()) + if (instance->GetInstanceScript()) + if (instance->GetScriptId() == sObjectMgr->GetScriptId(scriptName)) + return new AI(obj); + + return NULL; +} + +#endif // TRINITY_INSTANCE_DATA_H diff --git a/src/server/game/Scripting/ScriptLoader.cpp b/src/server/game/Scripting/ScriptLoader.cpp index 76defc03da4..ed0972c3301 100644 --- a/src/server/game/Scripting/ScriptLoader.cpp +++ b/src/server/game/Scripting/ScriptLoader.cpp @@ -172,6 +172,7 @@ void AddSC_boss_sulfuron(); void AddSC_boss_majordomo(); void AddSC_boss_ragnaros(); void AddSC_instance_molten_core(); +void AddSC_instance_ragefire_chasm(); //Ragefire Chasm void AddSC_the_scarlet_enclave(); //Scarlet Enclave void AddSC_the_scarlet_enclave_c1(); void AddSC_the_scarlet_enclave_c2(); @@ -230,6 +231,7 @@ void AddSC_boss_archaedas(); //Uldaman void AddSC_boss_ironaya(); void AddSC_uldaman(); void AddSC_instance_uldaman(); +void AddSC_instance_the_stockade(); //The Stockade void AddSC_boss_akilzon(); //Zul'Aman void AddSC_boss_halazzi(); void AddSC_boss_hex_lord_malacrass(); @@ -309,10 +311,12 @@ void AddSC_boss_mal_ganis(); void AddSC_boss_meathook(); void AddSC_culling_of_stratholme(); void AddSC_instance_culling_of_stratholme(); +void AddSC_instance_dire_maul(); //Dire Maul void AddSC_boss_celebras_the_cursed(); //Maraudon void AddSC_boss_landslide(); void AddSC_boss_noxxion(); void AddSC_boss_ptheradras(); +void AddSC_instance_maraudon(); void AddSC_boss_onyxia(); //Onyxia's Lair void AddSC_instance_onyxias_lair(); void AddSC_boss_amnennar_the_coldbringer(); //Razorfen Downs @@ -565,8 +569,10 @@ void AddSC_boss_hydromancer_thespia(); //CR Steam Vault void AddSC_boss_mekgineer_steamrigger(); void AddSC_boss_warlord_kalithresh(); void AddSC_instance_steam_vault(); +void AddSC_instance_the_slave_pens(); //The Slave Pens void AddSC_boss_hungarfen(); //CR Underbog void AddSC_boss_the_black_stalker(); +void AddSC_instance_the_underbog(); void AddSC_boss_gruul(); //Gruul's Lair void AddSC_boss_high_king_maulgar(); void AddSC_instance_gruuls_lair(); @@ -827,6 +833,7 @@ void AddEasternKingdomsScripts() AddSC_boss_majordomo(); AddSC_boss_ragnaros(); AddSC_instance_molten_core(); + AddSC_instance_ragefire_chasm(); //Ragefire Chasm AddSC_the_scarlet_enclave(); //Scarlet Enclave AddSC_the_scarlet_enclave_c1(); AddSC_the_scarlet_enclave_c2(); @@ -881,6 +888,7 @@ void AddEasternKingdomsScripts() AddSC_boss_muru(); AddSC_boss_kiljaeden(); AddSC_sunwell_plateau(); + AddSC_instance_the_stockade(); //The Stockade AddSC_boss_archaedas(); //Uldaman AddSC_boss_ironaya(); AddSC_uldaman(); @@ -968,10 +976,12 @@ void AddKalimdorScripts() AddSC_boss_meathook(); AddSC_culling_of_stratholme(); AddSC_instance_culling_of_stratholme(); + AddSC_instance_dire_maul(); //Dire Maul AddSC_boss_celebras_the_cursed(); //Maraudon AddSC_boss_landslide(); AddSC_boss_noxxion(); AddSC_boss_ptheradras(); + AddSC_instance_maraudon(); AddSC_boss_onyxia(); //Onyxia's Lair AddSC_instance_onyxias_lair(); AddSC_boss_amnennar_the_coldbringer(); //Razorfen Downs @@ -1067,8 +1077,10 @@ void AddOutlandScripts() AddSC_boss_mekgineer_steamrigger(); AddSC_boss_warlord_kalithresh(); AddSC_instance_steam_vault(); + AddSC_instance_the_slave_pens(); //The Slave Pens AddSC_boss_hungarfen(); //CR Underbog AddSC_boss_the_black_stalker(); + AddSC_instance_the_underbog(); AddSC_boss_gruul(); //Gruul's Lair AddSC_boss_high_king_maulgar(); AddSC_instance_gruuls_lair(); diff --git a/src/server/game/Server/WorldSocket.cpp b/src/server/game/Server/WorldSocket.cpp index 08da34b9ace..625ebff8471 100644 --- a/src/server/game/Server/WorldSocket.cpp +++ b/src/server/game/Server/WorldSocket.cpp @@ -730,11 +730,11 @@ int WorldSocket::HandleSendAuthSession() BigNumber seed1; seed1.SetRand(16 * 8); - packet.append(seed1.AsByteArray(16), 16); // new encryption seeds + packet.append(seed1.AsByteArray(16).get(), 16); // new encryption seeds BigNumber seed2; seed2.SetRand(16 * 8); - packet.append(seed2.AsByteArray(16), 16); // new encryption seeds + packet.append(seed2.AsByteArray(16).get(), 16); // new encryption seeds return SendPacket(packet); } diff --git a/src/server/game/Spells/Auras/SpellAuraEffects.cpp b/src/server/game/Spells/Auras/SpellAuraEffects.cpp index 20b6e67c5db..01de61f2b0f 100644 --- a/src/server/game/Spells/Auras/SpellAuraEffects.cpp +++ b/src/server/game/Spells/Auras/SpellAuraEffects.cpp @@ -2069,7 +2069,7 @@ void AuraEffect::HandleAuraModScale(AuraApplication const* aurApp, uint8 mode, b Unit* target = aurApp->GetTarget(); - float scale = target->GetFloatValue(OBJECT_FIELD_SCALE_X); + float scale = target->GetObjectScale(); ApplyPercentModFloatVar(scale, float(GetAmount()), apply); target->SetObjectScale(scale); } @@ -2089,7 +2089,7 @@ void AuraEffect::HandleAuraCloneCaster(AuraApplication const* aurApp, uint8 mode // What must be cloned? at least display and scale target->SetDisplayId(caster->GetDisplayId()); - //target->SetObjectScale(caster->GetFloatValue(OBJECT_FIELD_SCALE_X)); // we need retail info about how scaling is handled (aura maybe?) + //target->SetObjectScale(caster->GetObjectScale()); // we need retail info about how scaling is handled (aura maybe?) target->SetFlag(UNIT_FIELD_FLAGS_2, UNIT_FLAG2_MIRROR_IMAGE); } else diff --git a/src/server/game/Spells/Auras/SpellAuras.cpp b/src/server/game/Spells/Auras/SpellAuras.cpp index 2846137ad95..149f422554a 100644 --- a/src/server/game/Spells/Auras/SpellAuras.cpp +++ b/src/server/game/Spells/Auras/SpellAuras.cpp @@ -998,8 +998,7 @@ int32 Aura::CalcDispelChance(Unit* auraTarget, bool offensive) const if (offensive && auraTarget) resistChance += auraTarget->GetTotalAuraModifier(SPELL_AURA_MOD_DISPEL_RESIST); - resistChance = resistChance < 0 ? 0 : resistChance; - resistChance = resistChance > 100 ? 100 : resistChance; + RoundToInterval(resistChance, 0, 100); return 100 - resistChance; } @@ -2269,8 +2268,9 @@ bool Aura::CallScriptPrepareProcHandlers(AuraApplication const* aurApp, ProcEven return prepare; } -void Aura::CallScriptProcHandlers(AuraApplication const* aurApp, ProcEventInfo& eventInfo) +bool Aura::CallScriptProcHandlers(AuraApplication const* aurApp, ProcEventInfo& eventInfo) { + bool handled = false; for (std::list<AuraScript*>::iterator scritr = m_loadedScripts.begin(); scritr != m_loadedScripts.end(); ++scritr) { (*scritr)->_PrepareScriptCall(AURA_SCRIPT_HOOK_PROC, aurApp); @@ -2278,8 +2278,11 @@ void Aura::CallScriptProcHandlers(AuraApplication const* aurApp, ProcEventInfo& for (; hookItr != hookItrEnd; ++hookItr) hookItr->Call(*scritr, eventInfo); + handled |= (*scritr)->_IsDefaultActionPrevented(); (*scritr)->_FinishScriptCall(); } + + return handled; } void Aura::CallScriptAfterProcHandlers(AuraApplication const* aurApp, ProcEventInfo& eventInfo) diff --git a/src/server/game/Spells/Auras/SpellAuras.h b/src/server/game/Spells/Auras/SpellAuras.h index e865d415438..9e7d0cce82c 100644 --- a/src/server/game/Spells/Auras/SpellAuras.h +++ b/src/server/game/Spells/Auras/SpellAuras.h @@ -229,7 +229,7 @@ class Aura // Spell Proc Hooks bool CallScriptCheckProcHandlers(AuraApplication const* aurApp, ProcEventInfo& eventInfo); bool CallScriptPrepareProcHandlers(AuraApplication const* aurApp, ProcEventInfo& eventInfo); - void CallScriptProcHandlers(AuraApplication const* aurApp, ProcEventInfo& eventInfo); + bool CallScriptProcHandlers(AuraApplication const* aurApp, ProcEventInfo& eventInfo); void CallScriptAfterProcHandlers(AuraApplication const* aurApp, ProcEventInfo& eventInfo); bool CallScriptEffectProcHandlers(AuraEffect const* aurEff, AuraApplication const* aurApp, ProcEventInfo& eventInfo); void CallScriptAfterEffectProcHandlers(AuraEffect const* aurEff, AuraApplication const* aurApp, ProcEventInfo& eventInfo); diff --git a/src/server/game/Spells/Spell.cpp b/src/server/game/Spells/Spell.cpp index 96e1d06070d..539b38bdac4 100644 --- a/src/server/game/Spells/Spell.cpp +++ b/src/server/game/Spells/Spell.cpp @@ -2038,6 +2038,15 @@ void Spell::SearchChainTargets(std::list<WorldObject*>& targets, uint32 chainTar } } +GameObject* Spell::SearchSpellFocus() +{ + GameObject* focus = NULL; + Trinity::GameObjectFocusCheck check(m_caster, m_spellInfo->RequiresSpellFocus); + Trinity::GameObjectSearcher<Trinity::GameObjectFocusCheck> searcher(m_caster, focus, check); + SearchTargets<Trinity::GameObjectSearcher<Trinity::GameObjectFocusCheck> > (searcher, GRID_MAP_TYPE_MASK_GAMEOBJECT, m_caster, m_caster, m_caster->GetVisibilityRange()); + return focus; +} + void Spell::prepareDataForTriggerSystem(AuraEffect const* /*triggeredByAura*/) { //========================================================================================== @@ -3041,18 +3050,20 @@ void Spell::prepare(SpellCastTargets const* targets, AuraEffect const* triggered // Prepare data for triggers prepareDataForTriggerSystem(triggeredByAura); - if (m_caster->GetTypeId() == TYPEID_PLAYER) - m_caster->ToPlayer()->SetSpellModTakingSpell(this, true); - // calculate cast time (calculated after first CheckCast check to prevent charge counting for first CheckCast fail) - m_casttime = m_spellInfo->CalcCastTime(m_caster, this); - if (m_caster->GetTypeId() == TYPEID_PLAYER) + if (Player* player = m_caster->ToPlayer()) { - m_caster->ToPlayer()->SetSpellModTakingSpell(this, false); - - // Set casttime to 0 if .cheat casttime is enabled. - if (m_caster->ToPlayer()->GetCommandStatus(CHEAT_CASTTIME)) - m_casttime = 0; + if (!player->GetCommandStatus(CHEAT_CASTTIME)) + { + player->SetSpellModTakingSpell(this, true); + // calculate cast time (calculated after first CheckCast check to prevent charge counting for first CheckCast fail) + m_casttime = m_spellInfo->CalcCastTime(this); + player->SetSpellModTakingSpell(this, false); + } + else + m_casttime = 0; // Set cast time to 0 if .cheat casttime is enabled. } + else + m_casttime = m_spellInfo->CalcCastTime(this); // don't allow channeled spells / spells with cast time to be casted while moving // (even if they are interrupted on moving, spells with almost immediate effect get to have their effect processed before movement interrupter kicks in) @@ -3755,27 +3766,9 @@ void Spell::finish(bool ok) m_caster->AttackStop(); } -void Spell::SendCastResult(SpellCastResult result) +void Spell::WriteCastResultInfo(WorldPacket& data, Player* caster, SpellInfo const* spellInfo, uint8 castCount, SpellCastResult result, SpellCustomErrors customError) { - if (result == SPELL_CAST_OK) - return; - - if (m_caster->GetTypeId() != TYPEID_PLAYER) - return; - - if (m_caster->ToPlayer()->GetSession()->PlayerLoading()) // don't send cast results at loading time - return; - - SendCastResult(m_caster->ToPlayer(), m_spellInfo, m_cast_count, result, m_customError); -} - -void Spell::SendCastResult(Player* caster, SpellInfo const* spellInfo, uint8 cast_count, SpellCastResult result, SpellCustomErrors customError /*= SPELL_CUSTOM_ERROR_NONE*/) -{ - if (result == SPELL_CAST_OK) - return; - - WorldPacket data(SMSG_CAST_FAILED, (4+1+1)); - data << uint8(cast_count); // single cast or multi 2.3 (0/1) + data << uint8(castCount); // single cast or multi 2.3 (0/1) data << uint32(spellInfo->Id); data << uint8(result); // problem switch (result) @@ -3876,9 +3869,52 @@ void Spell::SendCastResult(Player* caster, SpellInfo const* spellInfo, uint8 cas default: break; } +} + +void Spell::SendCastResult(Player* caster, SpellInfo const* spellInfo, uint8 castCount, SpellCastResult result, SpellCustomErrors customError /*= SPELL_CUSTOM_ERROR_NONE*/) +{ + if (result == SPELL_CAST_OK) + return; + + WorldPacket data(SMSG_CAST_FAILED, 1 + 4 + 1); + WriteCastResultInfo(data, caster, spellInfo, castCount, result, customError); + caster->GetSession()->SendPacket(&data); } +void Spell::SendCastResult(SpellCastResult result) +{ + if (result == SPELL_CAST_OK) + return; + + if (m_caster->GetTypeId() != TYPEID_PLAYER) + return; + + if (m_caster->ToPlayer()->GetSession()->PlayerLoading()) // don't send cast results at loading time + return; + + SendCastResult(m_caster->ToPlayer(), m_spellInfo, m_cast_count, result, m_customError); +} + +void Spell::SendPetCastResult(SpellCastResult result) +{ + if (result == SPELL_CAST_OK) + return; + + Unit* owner = m_caster->GetCharmerOrOwner(); + if (!owner) + return; + + Player* player = owner->ToPlayer(); + if (!player) + return; + + WorldPacket data(SMSG_PET_CAST_FAILED, 1 + 4 + 1); + WriteCastResultInfo(data, player, m_spellInfo, m_cast_count, result, m_customError); + + player->GetSession()->SendPacket(&data); +} + void Spell::SendSpellStart() { if (!IsNeedSendToClient()) @@ -4981,9 +5017,17 @@ SpellCastResult Spell::CheckCast(bool strict) return SPELL_FAILED_NOT_MOUNTED; } + // check spell focus object + if (m_spellInfo->RequiresSpellFocus) + { + focusObject = SearchSpellFocus(); + if (!focusObject) + return SPELL_FAILED_REQUIRES_SPELL_FOCUS; + } + SpellCastResult castResult = SPELL_CAST_OK; - // always (except passive spells) check items (focus object can be required for any type casts) + // always (except passive spells) check items (only player related checks) if (!m_spellInfo->IsPassive()) { castResult = CheckItems(); @@ -5585,6 +5629,11 @@ SpellCastResult Spell::CheckPetCast(Unit* target) if (creatureCaster->HasSpellCooldown(m_spellInfo->Id)) return SPELL_FAILED_NOT_READY; + // Check if spell is affected by GCD + if (m_spellInfo->StartRecoveryCategory > 0) + if (m_caster->GetCharmInfo() && m_caster->GetCharmInfo()->GetGlobalCooldownMgr().HasGlobalCooldown(m_spellInfo)) + return SPELL_FAILED_NOT_READY; + return CheckCast(true); } @@ -5947,26 +5996,6 @@ SpellCastResult Spell::CheckItems() return SPELL_FAILED_EQUIPPED_ITEM_CLASS; } - // check spell focus object - if (m_spellInfo->RequiresSpellFocus) - { - CellCoord p(Trinity::ComputeCellCoord(m_caster->GetPositionX(), m_caster->GetPositionY())); - Cell cell(p); - - GameObject* ok = NULL; - Trinity::GameObjectFocusCheck go_check(m_caster, m_spellInfo->RequiresSpellFocus); - Trinity::GameObjectSearcher<Trinity::GameObjectFocusCheck> checker(m_caster, ok, go_check); - - TypeContainerVisitor<Trinity::GameObjectSearcher<Trinity::GameObjectFocusCheck>, GridTypeMapContainer > object_checker(checker); - Map& map = *m_caster->GetMap(); - cell.Visit(p, object_checker, map, *m_caster, m_caster->GetVisibilityRange()); - - if (!ok) - return SPELL_FAILED_REQUIRES_SPELL_FOCUS; - - focusObject = ok; // game object found in range - } - // do not take reagents for these item casts if (!(m_CastItem && m_CastItem->GetTemplate()->Flags & ITEM_PROTO_FLAG_TRIGGERED_CAST)) { diff --git a/src/server/game/Spells/Spell.h b/src/server/game/Spells/Spell.h index 191a7461fe9..927ecd32f29 100644 --- a/src/server/game/Spells/Spell.h +++ b/src/server/game/Spells/Spell.h @@ -370,6 +370,8 @@ class Spell void SearchAreaTargets(std::list<WorldObject*>& targets, float range, Position const* position, Unit* referer, SpellTargetObjectTypes objectType, SpellTargetCheckTypes selectionType, ConditionList* condList); void SearchChainTargets(std::list<WorldObject*>& targets, uint32 chainTargets, WorldObject* target, SpellTargetObjectTypes objectType, SpellTargetCheckTypes selectType, ConditionList* condList, bool isChainHeal); + GameObject* SearchSpellFocus(); + void prepare(SpellCastTargets const* targets, AuraEffect const* triggeredByAura = NULL); void cancel(); void update(uint32 difftime); @@ -415,8 +417,10 @@ class Spell void CheckSrc() { if (!m_targets.HasSrc()) m_targets.SetSrc(*m_caster); } void CheckDst() { if (!m_targets.HasDst()) m_targets.SetDst(*m_caster); } - static void SendCastResult(Player* caster, SpellInfo const* spellInfo, uint8 cast_count, SpellCastResult result, SpellCustomErrors customError = SPELL_CUSTOM_ERROR_NONE); + static void WriteCastResultInfo(WorldPacket& data, Player* caster, SpellInfo const* spellInfo, uint8 castCount, SpellCastResult result, SpellCustomErrors customError); + static void SendCastResult(Player* caster, SpellInfo const* spellInfo, uint8 castCount, SpellCastResult result, SpellCustomErrors customError = SPELL_CUSTOM_ERROR_NONE); void SendCastResult(SpellCastResult result); + void SendPetCastResult(SpellCastResult result); void SendSpellStart(); void SendSpellGo(); void SendSpellCooldown(); diff --git a/src/server/game/Spells/SpellInfo.cpp b/src/server/game/Spells/SpellInfo.cpp index a58c2ee19e4..04437b82f2d 100644 --- a/src/server/game/Spells/SpellInfo.cpp +++ b/src/server/game/Spells/SpellInfo.cpp @@ -1006,8 +1006,12 @@ bool SpellInfo::NeedsExplicitUnitTarget() const bool SpellInfo::NeedsToBeTriggeredByCaster() const { + if (AttributesCu & SPELL_ATTR0_CU_TRIGGERED_BY_CASTER) + return true; + if (NeedsExplicitUnitTarget()) return true; + for (uint8 i = 0; i < MAX_SPELL_EFFECTS; ++i) { if (Effects[i].IsEffect()) @@ -1017,6 +1021,7 @@ bool SpellInfo::NeedsToBeTriggeredByCaster() const return true; } } + return false; } @@ -1714,7 +1719,7 @@ uint32 SpellInfo::GetAllEffectsMechanicMask() const uint32 mask = 0; if (Mechanic) mask |= 1 << Mechanic; - for (int i = 0; i < MAX_SPELL_EFFECTS; ++i) + for (uint8 i = 0; i < MAX_SPELL_EFFECTS; ++i) if (Effects[i].IsEffect() && Effects[i].Mechanic) mask |= 1 << Effects[i].Mechanic; return mask; @@ -1724,9 +1729,9 @@ uint32 SpellInfo::GetEffectMechanicMask(uint8 effIndex) const { uint32 mask = 0; if (Mechanic) - mask |= 1<< Mechanic; + mask |= 1 << Mechanic; if (Effects[effIndex].IsEffect() && Effects[effIndex].Mechanic) - mask |= 1<< Effects[effIndex].Mechanic; + mask |= 1 << Effects[effIndex].Mechanic; return mask; } @@ -1734,10 +1739,10 @@ uint32 SpellInfo::GetSpellMechanicMaskByEffectMask(uint32 effectMask) const { uint32 mask = 0; if (Mechanic) - mask |= 1<< Mechanic; - for (int i = 0; i < MAX_SPELL_EFFECTS; ++i) + mask |= 1 << Mechanic; + for (uint8 i = 0; i < MAX_SPELL_EFFECTS; ++i) if ((effectMask & (1 << i)) && Effects[i].Mechanic) - mask |= 1<< Effects[i].Mechanic; + mask |= 1 << Effects[i].Mechanic; return mask; } @@ -2052,7 +2057,7 @@ int32 SpellInfo::GetMaxDuration() const return (DurationEntry->Duration[2] == -1) ? -1 : abs(DurationEntry->Duration[2]); } -uint32 SpellInfo::CalcCastTime(Unit* caster, Spell* spell) const +uint32 SpellInfo::CalcCastTime(Spell* spell /*= NULL*/) const { // not all spells have cast time index and this is all is pasiive abilities if (!CastTimeEntry) @@ -2060,8 +2065,8 @@ uint32 SpellInfo::CalcCastTime(Unit* caster, Spell* spell) const int32 castTime = CastTimeEntry->CastTime; - if (caster) - caster->ModSpellCastTime(this, castTime, spell); + if (spell) + spell->GetCaster()->ModSpellCastTime(this, castTime, spell); if (Attributes & SPELL_ATTR0_REQ_AMMO && (!IsAutoRepeatRangedSpell())) castTime += 500; diff --git a/src/server/game/Spells/SpellInfo.h b/src/server/game/Spells/SpellInfo.h index 6ed742a3b8e..6acde5afa74 100644 --- a/src/server/game/Spells/SpellInfo.h +++ b/src/server/game/Spells/SpellInfo.h @@ -176,7 +176,7 @@ enum SpellCustomAttributes SPELL_ATTR0_CU_CONE_LINE = 0x00000004, SPELL_ATTR0_CU_SHARE_DAMAGE = 0x00000008, SPELL_ATTR0_CU_NO_INITIAL_THREAT = 0x00000010, - SPELL_ATTR0_CU_NONE2 = 0x00000020, // UNUSED + SPELL_ATTR0_CU_TRIGGERED_BY_CASTER = 0x00000020, // @todo: need generic solution, some triggered spells will be casted by target instead of caster SPELL_ATTR0_CU_AURA_CC = 0x00000040, SPELL_ATTR0_CU_DIRECT_DAMAGE = 0x00000100, SPELL_ATTR0_CU_CHARGE = 0x00000200, @@ -444,7 +444,7 @@ public: uint32 GetMaxTicks() const; - uint32 CalcCastTime(Unit* caster = NULL, Spell* spell = NULL) const; + uint32 CalcCastTime(Spell* spell = NULL) const; uint32 GetRecoveryTime() const; int32 CalcPowerCost(Unit const* caster, SpellSchoolMask schoolMask) const; diff --git a/src/server/game/Spells/SpellMgr.cpp b/src/server/game/Spells/SpellMgr.cpp index 24bd19d2d24..ebf7121eb54 100644 --- a/src/server/game/Spells/SpellMgr.cpp +++ b/src/server/game/Spells/SpellMgr.cpp @@ -2972,6 +2972,9 @@ void SpellMgr::LoadSpellInfoCustomAttributes() case 72293: // Mark of the Fallen Champion (Deathbringer Saurfang) spellInfo->AttributesCu |= SPELL_ATTR0_CU_NEGATIVE_EFF0; break; + case 38729: // Rod of Purification + spellInfo->AttributesCu |= SPELL_ATTR0_CU_TRIGGERED_BY_CASTER; + break; default: break; } @@ -3103,6 +3106,17 @@ void SpellMgr::LoadSpellInfoCorrections() // Entries were not updated after spell effect change, we have to do that manually :/ spellInfo->AttributesEx3 |= SPELL_ATTR3_CAN_PROC_WITH_TRIGGERED; break; + case 5308: // Execute (Rank 1) + case 20658: // Execute (Rank 2) + case 20660: // Execute (Rank 3) + case 20661: // Execute (Rank 4) + case 20662: // Execute (Rank 5) + case 25234: // Execute (Rank 6) + case 25236: // Execute (Rank 7) + case 47470: // Execute (Rank 8) + case 47471: // Execute (Rank 9) + spellInfo->AttributesEx3 |= SPELL_ATTR3_CANT_TRIGGER_PROC; + break; case 59725: // Improved Spell Reflection - aoe aura // Target entry seems to be wrong for this spell :/ spellInfo->Effects[EFFECT_0].TargetA = SpellImplicitTargetInfo(TARGET_UNIT_CASTER_AREA_PARTY); @@ -3360,10 +3374,6 @@ void SpellMgr::LoadSpellInfoCorrections() case 53313: // Entangling Roots (Rank 8) -- Nature's Grasp Proc spellInfo->CastTimeEntry = sSpellCastTimesStore.LookupEntry(1); break; - case 59414: // Pulsing Shockwave Aura (Loken) - // this flag breaks movement, remove it - spellInfo->AttributesEx &= ~SPELL_ATTR1_CHANNELED_1; - break; case 61719: // Easter Lay Noblegarden Egg Aura - Interrupt flags copied from aura which this aura is linked with spellInfo->AuraInterruptFlags = AURA_INTERRUPT_FLAG_HITBYSPELL | AURA_INTERRUPT_FLAG_TAKE_DAMAGE; break; diff --git a/src/server/game/Spells/SpellScript.cpp b/src/server/game/Spells/SpellScript.cpp index 5fb4d69cd02..bb9aab023af 100644 --- a/src/server/game/Spells/SpellScript.cpp +++ b/src/server/game/Spells/SpellScript.cpp @@ -909,6 +909,7 @@ bool AuraScript::_IsDefaultActionPrevented() case AURA_SCRIPT_HOOK_EFFECT_ABSORB: case AURA_SCRIPT_HOOK_EFFECT_SPLIT: case AURA_SCRIPT_HOOK_PREPARE_PROC: + case AURA_SCRIPT_HOOK_PROC: case AURA_SCRIPT_HOOK_EFFECT_PROC: return m_defaultActionPrevented; default: @@ -927,6 +928,7 @@ void AuraScript::PreventDefaultAction() case AURA_SCRIPT_HOOK_EFFECT_ABSORB: case AURA_SCRIPT_HOOK_EFFECT_SPLIT: case AURA_SCRIPT_HOOK_PREPARE_PROC: + case AURA_SCRIPT_HOOK_PROC: case AURA_SCRIPT_HOOK_EFFECT_PROC: m_defaultActionPrevented = true; break; diff --git a/src/server/game/Spells/SpellScript.h b/src/server/game/Spells/SpellScript.h index 6f1df2560dc..f7940b2b8da 100644 --- a/src/server/game/Spells/SpellScript.h +++ b/src/server/game/Spells/SpellScript.h @@ -74,9 +74,9 @@ class _SpellScript EffectHook(uint8 _effIndex); virtual ~EffectHook() { } - uint8 GetAffectedEffectsMask(SpellInfo const* spellEntry); - bool IsEffectAffected(SpellInfo const* spellEntry, uint8 effIndex); - virtual bool CheckEffect(SpellInfo const* spellEntry, uint8 effIndex) = 0; + uint8 GetAffectedEffectsMask(SpellInfo const* spellInfo); + bool IsEffectAffected(SpellInfo const* spellInfo, uint8 effIndex); + virtual bool CheckEffect(SpellInfo const* spellInfo, uint8 effIndex) = 0; std::string EffIndexToString(); protected: uint8 effIndex; @@ -86,7 +86,7 @@ class _SpellScript { public: EffectNameCheck(uint16 _effName) { effName = _effName; } - bool Check(SpellInfo const* spellEntry, uint8 effIndex); + bool Check(SpellInfo const* spellInfo, uint8 effIndex); std::string ToString(); private: uint16 effName; @@ -96,7 +96,7 @@ class _SpellScript { public: EffectAuraNameCheck(uint16 _effAurName) { effAurName = _effAurName; } - bool Check(SpellInfo const* spellEntry, uint8 effIndex); + bool Check(SpellInfo const* spellInfo, uint8 effIndex); std::string ToString(); private: uint16 effAurName; @@ -114,7 +114,7 @@ class _SpellScript virtual void Register() = 0; // Function called on server startup, if returns false script won't be used in core // use for: dbc/template data presence/correctness checks - virtual bool Validate(SpellInfo const* /*spellEntry*/) { return true; } + virtual bool Validate(SpellInfo const* /*spellInfo*/) { return true; } // Function called when script is created, if returns false script will be unloaded afterwards // use for: initializing local script variables (DO NOT USE CONSTRUCTOR FOR THIS PURPOSE!) virtual bool Load() { return true; } @@ -185,7 +185,7 @@ class SpellScript : public _SpellScript public: EffectHandler(SpellEffectFnType _pEffectHandlerScript, uint8 _effIndex, uint16 _effName); std::string ToString(); - bool CheckEffect(SpellInfo const* spellEntry, uint8 effIndex); + bool CheckEffect(SpellInfo const* spellInfo, uint8 effIndex); void Call(SpellScript* spellScript, SpellEffIndex effIndex); private: SpellEffectFnType pEffectHandlerScript; @@ -204,7 +204,7 @@ class SpellScript : public _SpellScript { public: TargetHook(uint8 _effectIndex, uint16 _targetType, bool _area); - bool CheckEffect(SpellInfo const* spellEntry, uint8 effIndex); + bool CheckEffect(SpellInfo const* spellInfo, uint8 effIndex); std::string ToString(); protected: uint16 targetType; @@ -488,7 +488,7 @@ class AuraScript : public _SpellScript public: EffectBase(uint8 _effIndex, uint16 _effName); std::string ToString(); - bool CheckEffect(SpellInfo const* spellEntry, uint8 effIndex); + bool CheckEffect(SpellInfo const* spellInfo, uint8 effIndex); }; class EffectPeriodicHandler : public EffectBase { diff --git a/src/server/game/Warden/WardenCheckMgr.cpp b/src/server/game/Warden/WardenCheckMgr.cpp index 51bb2e52342..a8bcd61db73 100644 --- a/src/server/game/Warden/WardenCheckMgr.cpp +++ b/src/server/game/Warden/WardenCheckMgr.cpp @@ -94,7 +94,7 @@ void WardenCheckMgr::LoadWardenChecks() { uint8 temp[24]; memset(temp, 0, len); - memcpy(temp, wardenCheck->Data.AsByteArray(), wardenCheck->Data.GetNumBytes()); + memcpy(temp, wardenCheck->Data.AsByteArray().get(), wardenCheck->Data.GetNumBytes()); std::reverse(temp, temp + len); wardenCheck->Data.SetBinary((uint8*)temp, len); } @@ -126,7 +126,7 @@ void WardenCheckMgr::LoadWardenChecks() { uint8 *temp = new uint8[len]; memset(temp, 0, len); - memcpy(temp, wr->Result.AsByteArray(), wr->Result.GetNumBytes()); + memcpy(temp, wr->Result.AsByteArray().get(), wr->Result.GetNumBytes()); std::reverse(temp, temp + len); wr->Result.SetBinary((uint8*)temp, len); delete [] temp; diff --git a/src/server/game/Warden/WardenMac.cpp b/src/server/game/Warden/WardenMac.cpp index 74ca285c525..27e859e741d 100644 --- a/src/server/game/Warden/WardenMac.cpp +++ b/src/server/game/Warden/WardenMac.cpp @@ -42,7 +42,7 @@ void WardenMac::Init(WorldSession* pClient, BigNumber* K) { _session = pClient; // Generate Warden Key - SHA1Randx WK(K->AsByteArray(), K->GetNumBytes()); + SHA1Randx WK(K->AsByteArray().get(), K->GetNumBytes()); WK.Generate(_inputKey, 16); WK.Generate(_outputKey, 16); /* diff --git a/src/server/game/Warden/WardenWin.cpp b/src/server/game/Warden/WardenWin.cpp index 1ce96b44ee6..60a1fecedc9 100644 --- a/src/server/game/Warden/WardenWin.cpp +++ b/src/server/game/Warden/WardenWin.cpp @@ -46,7 +46,7 @@ void WardenWin::Init(WorldSession* session, BigNumber* k) { _session = session; // Generate Warden Key - SHA1Randx WK(k->AsByteArray(), k->GetNumBytes()); + SHA1Randx WK(k->AsByteArray().get(), k->GetNumBytes()); WK.Generate(_inputKey, 16); WK.Generate(_outputKey, 16); @@ -266,7 +266,7 @@ void WardenWin::RequestData() case PAGE_CHECK_A: case PAGE_CHECK_B: { - buff.append(wd->Data.AsByteArray(0, false), wd->Data.GetNumBytes()); + buff.append(wd->Data.AsByteArray(0, false).get(), wd->Data.GetNumBytes()); buff << uint32(wd->Address); buff << uint8(wd->Length); break; @@ -279,7 +279,7 @@ void WardenWin::RequestData() } case DRIVER_CHECK: { - buff.append(wd->Data.AsByteArray(0, false), wd->Data.GetNumBytes()); + buff.append(wd->Data.AsByteArray(0, false).get(), wd->Data.GetNumBytes()); buff << uint8(index++); break; } @@ -295,7 +295,7 @@ void WardenWin::RequestData() } /*case PROC_CHECK: { - buff.append(wd->i.AsByteArray(0, false), wd->i.GetNumBytes()); + buff.append(wd->i.AsByteArray(0, false).get(), wd->i.GetNumBytes()); buff << uint8(index++); buff << uint8(index++); buff << uint32(wd->Address); @@ -395,7 +395,7 @@ void WardenWin::HandleData(ByteBuffer &buff) continue; } - if (memcmp(buff.contents() + buff.rpos(), rs->Result.AsByteArray(0, false), rd->Length) != 0) + if (memcmp(buff.contents() + buff.rpos(), rs->Result.AsByteArray(0, false).get(), rd->Length) != 0) { TC_LOG_DEBUG(LOG_FILTER_WARDEN, "RESULT MEM_CHECK fail CheckId %u account Id %u", *itr, _session->GetAccountId()); checkFailed = *itr; @@ -474,7 +474,7 @@ void WardenWin::HandleData(ByteBuffer &buff) continue; } - if (memcmp(buff.contents() + buff.rpos(), rs->Result.AsByteArray(0, false), 20) != 0) // SHA1 + if (memcmp(buff.contents() + buff.rpos(), rs->Result.AsByteArray(0, false).get(), 20) != 0) // SHA1 { TC_LOG_DEBUG(LOG_FILTER_WARDEN, "RESULT MPQ_CHECK fail, CheckId %u account Id %u", *itr, _session->GetAccountId()); checkFailed = *itr; diff --git a/src/server/scripts/Commands/cs_debug.cpp b/src/server/scripts/Commands/cs_debug.cpp index c01a8e95559..bb2167abbe7 100644 --- a/src/server/scripts/Commands/cs_debug.cpp +++ b/src/server/scripts/Commands/cs_debug.cpp @@ -1309,7 +1309,35 @@ public: char* mask2 = strtok(NULL, " \n"); uint32 moveFlags = (uint32)atoi(mask1); - target->SetUnitMovementFlags(moveFlags); + + static uint32 const FlagsWithHandlers = MOVEMENTFLAG_MASK_HAS_PLAYER_STATUS_OPCODE | + MOVEMENTFLAG_WALKING | MOVEMENTFLAG_SWIMMING | + MOVEMENTFLAG_SPLINE_ENABLED; + + bool unhandledFlag = (moveFlags ^ target->GetUnitMovementFlags()) & ~FlagsWithHandlers; + + target->SetWalk(moveFlags & MOVEMENTFLAG_WALKING); + target->SetDisableGravity(moveFlags & MOVEMENTFLAG_DISABLE_GRAVITY); + target->SetSwim(moveFlags & MOVEMENTFLAG_SWIMMING); + target->SetCanFly(moveFlags & MOVEMENTFLAG_CAN_FLY); + target->SetWaterWalking(moveFlags & MOVEMENTFLAG_WATERWALKING); + target->SetFeatherFall(moveFlags & MOVEMENTFLAG_FALLING_SLOW); + target->SetHover(moveFlags & MOVEMENTFLAG_HOVER); + + if (moveFlags & (MOVEMENTFLAG_DISABLE_GRAVITY | MOVEMENTFLAG_CAN_FLY)) + moveFlags &= ~MOVEMENTFLAG_FALLING; + + if (moveFlags & MOVEMENTFLAG_ROOT) + { + target->SetControlled(true, UNIT_STATE_ROOT); + moveFlags &= ~MOVEMENTFLAG_MASK_MOVING; + } + + if (target->HasUnitMovementFlag(MOVEMENTFLAG_SPLINE_ENABLED) && !(moveFlags & MOVEMENTFLAG_SPLINE_ENABLED)) + target->StopMoving(); + + if (unhandledFlag) + target->SetUnitMovementFlags(moveFlags); if (mask2) { @@ -1317,7 +1345,9 @@ public: target->SetExtraUnitMovementFlags(moveFlagsExtra); } - target->SendMovementFlagUpdate(); + if (mask2 || unhandledFlag) + target->SendMovementFlagUpdate(); + handler->PSendSysMessage(LANG_MOVEFLAGS_SET, target->GetUnitMovementFlags(), target->GetExtraUnitMovementFlags()); } diff --git a/src/server/scripts/EasternKingdoms/CMakeLists.txt b/src/server/scripts/EasternKingdoms/CMakeLists.txt index 53d37d83610..a0377cea0fd 100644 --- a/src/server/scripts/EasternKingdoms/CMakeLists.txt +++ b/src/server/scripts/EasternKingdoms/CMakeLists.txt @@ -207,6 +207,7 @@ set(scripts_STAT_SRCS EasternKingdoms/Karazhan/boss_moroes.cpp EasternKingdoms/Karazhan/boss_terestian_illhoof.cpp EasternKingdoms/Karazhan/karazhan.h + EasternKingdoms/TheStockade/instance_the_stockade.cpp ) message(" -> Prepared: Eastern Kingdoms") diff --git a/src/server/scripts/EasternKingdoms/ScarletEnclave/chapter1.cpp b/src/server/scripts/EasternKingdoms/ScarletEnclave/chapter1.cpp index c0db8e3eb0f..7feb0e47926 100644 --- a/src/server/scripts/EasternKingdoms/ScarletEnclave/chapter1.cpp +++ b/src/server/scripts/EasternKingdoms/ScarletEnclave/chapter1.cpp @@ -143,7 +143,7 @@ public: wait_timer = 5000; me->CastSpell(me, SPELL_DK_INITIATE_VISUAL, true); - if (Player* starter = Unit::GetPlayer(*me, playerGUID)) + if (Player* starter = ObjectAccessor::GetPlayer(*me, playerGUID)) sCreatureTextMgr->SendChat(me, SAY_EVENT_ATTACK, 0, CHAT_MSG_ADDON, LANG_ADDON, TEXT_RANGE_NORMAL, 0, TEAM_OTHER, false, starter); phase = PHASE_TO_ATTACK; @@ -228,8 +228,8 @@ public: me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_IMMUNE_TO_PC); phase = PHASE_ATTACKING; - if (Player* target = Unit::GetPlayer(*me, playerGUID)) - me->AI()->AttackStart(target); + if (Player* target = ObjectAccessor::GetPlayer(*me, playerGUID)) + AttackStart(target); wait_timer = 0; } } @@ -505,93 +505,89 @@ public: ## npc_dark_rider_of_acherus ######*/ -enum Spells_DR +enum DarkRiderOfAcherus { + SAY_DARK_RIDER = 0, SPELL_DESPAWN_HORSE = 51918 }; -enum Says_DR -{ - SAY_DARK_RIDER = 0 -}; - class npc_dark_rider_of_acherus : public CreatureScript { -public: - npc_dark_rider_of_acherus() : CreatureScript("npc_dark_rider_of_acherus") { } - - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return new npc_dark_rider_of_acherusAI(creature); - } - - struct npc_dark_rider_of_acherusAI : public ScriptedAI - { - npc_dark_rider_of_acherusAI(Creature* creature) : ScriptedAI(creature) {} - - uint32 PhaseTimer; - uint32 Phase; - bool Intro; - uint64 TargetGUID; + public: + npc_dark_rider_of_acherus() : CreatureScript("npc_dark_rider_of_acherus") { } - void Reset() OVERRIDE + struct npc_dark_rider_of_acherusAI : public ScriptedAI { - PhaseTimer = 4000; - Phase = 0; - Intro = false; - TargetGUID = 0; - } + npc_dark_rider_of_acherusAI(Creature* creature) : ScriptedAI(creature) { } - void UpdateAI(uint32 diff) OVERRIDE - { - if (!Intro || !TargetGUID) - return; + void Reset() OVERRIDE + { + PhaseTimer = 4000; + Phase = 0; + Intro = false; + TargetGUID = 0; + } - if (PhaseTimer <= diff) + void UpdateAI(uint32 diff) OVERRIDE { - switch (Phase) + if (!Intro || !TargetGUID) + return; + + if (PhaseTimer <= diff) { - case 0: - me->MonsterSay(SAY_DARK_RIDER, LANG_UNIVERSAL, 0); - PhaseTimer = 5000; - Phase = 1; - break; - case 1: - if (Unit* target = Unit::GetUnit(*me, TargetGUID)) - DoCast(target, SPELL_DESPAWN_HORSE, true); - PhaseTimer = 3000; - Phase = 2; - break; - case 2: - me->SetVisible(false); - PhaseTimer = 2000; - Phase = 3; - break; - case 3: - me->DespawnOrUnsummon(); - break; - default: - break; + switch (Phase) + { + case 0: + Talk(SAY_DARK_RIDER); + PhaseTimer = 5000; + Phase = 1; + break; + case 1: + if (Unit* target = ObjectAccessor::GetUnit(*me, TargetGUID)) + DoCast(target, SPELL_DESPAWN_HORSE, true); + PhaseTimer = 3000; + Phase = 2; + break; + case 2: + me->SetVisible(false); + PhaseTimer = 2000; + Phase = 3; + break; + case 3: + me->DespawnOrUnsummon(); + break; + default: + break; + } } - } else PhaseTimer -= diff; - - } + else + PhaseTimer -= diff; + } - void InitDespawnHorse(Unit* who) - { - if (!who) - return; + void InitDespawnHorse(Unit* who) + { + if (!who) + return; - TargetGUID = who->GetGUID(); - me->SetWalk(true); - me->SetSpeed(MOVE_RUN, 0.4f); - me->GetMotionMaster()->MoveChase(who); - me->SetTarget(TargetGUID); - Intro = true; - } + TargetGUID = who->GetGUID(); + me->SetWalk(true); + me->SetSpeed(MOVE_RUN, 0.4f); + me->GetMotionMaster()->MoveChase(who); + me->SetTarget(TargetGUID); + Intro = true; + } - }; + private: + uint32 PhaseTimer; + uint32 Phase; + bool Intro; + uint64 TargetGUID; + }; + CreatureAI* GetAI(Creature* creature) const OVERRIDE + { + return new npc_dark_rider_of_acherusAI(creature); + } }; /*###### @@ -644,7 +640,6 @@ public: } void MoveInLineOfSight(Unit* who) OVERRIDE - { ScriptedAI::MoveInLineOfSight(who); diff --git a/src/server/scripts/EasternKingdoms/ScarletEnclave/chapter2.cpp b/src/server/scripts/EasternKingdoms/ScarletEnclave/chapter2.cpp index 44eef7602c8..ba6f0f23656 100644 --- a/src/server/scripts/EasternKingdoms/ScarletEnclave/chapter2.cpp +++ b/src/server/scripts/EasternKingdoms/ScarletEnclave/chapter2.cpp @@ -96,7 +96,7 @@ public: { if (speechTimer <= diff) { - Player* player = Unit::GetPlayer(*me, playerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, playerGUID); if (!player) { EnterEvadeMode(); @@ -683,7 +683,7 @@ public: { if (ExecuteSpeech_Timer <= diff) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (!player) { diff --git a/src/server/scripts/EasternKingdoms/SunwellPlateau/boss_muru.cpp b/src/server/scripts/EasternKingdoms/SunwellPlateau/boss_muru.cpp index aa53790ee5f..c3d00ddba53 100644 --- a/src/server/scripts/EasternKingdoms/SunwellPlateau/boss_muru.cpp +++ b/src/server/scripts/EasternKingdoms/SunwellPlateau/boss_muru.cpp @@ -410,7 +410,7 @@ public: void JustSummoned(Creature* summoned) OVERRIDE { if (instance) - if (Player* Target = Unit::GetPlayer(*me, instance->GetData64(DATA_PLAYER_GUID))) + if (Player* Target = ObjectAccessor::GetPlayer(*me, instance->GetData64(DATA_PLAYER_GUID))) summoned->AI()->AttackStart(Target); Summons.Summon(summoned); diff --git a/src/server/scripts/EasternKingdoms/TheStockade/instance_the_stockade.cpp b/src/server/scripts/EasternKingdoms/TheStockade/instance_the_stockade.cpp new file mode 100644 index 00000000000..9550ac13208 --- /dev/null +++ b/src/server/scripts/EasternKingdoms/TheStockade/instance_the_stockade.cpp @@ -0,0 +1,47 @@ +/* + * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +/* +This placeholder for the instance is needed for dungeon finding to be able +to give credit after the boss defined in lastEncounterDungeon is killed. +Without it, the party doing random dungeon won't get satchel of spoils and +gets instead the deserter debuff. +*/ + +#include "ScriptMgr.h" +#include "InstanceScript.h" + +class instance_the_stockade : public InstanceMapScript +{ +public: + instance_the_stockade() : InstanceMapScript("instance_the_stockade", 34) { } + + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_the_stockade_InstanceMapScript(map); + } + + struct instance_the_stockade_InstanceMapScript : public InstanceScript + { + instance_the_stockade_InstanceMapScript(Map* map) : InstanceScript(map) {} + }; +}; + +void AddSC_instance_the_stockade() +{ + new instance_the_stockade(); +} diff --git a/src/server/scripts/EasternKingdoms/ZulAman/zulaman.cpp b/src/server/scripts/EasternKingdoms/ZulAman/zulaman.cpp index bbc8d523cb8..4c3b50e4c3a 100644 --- a/src/server/scripts/EasternKingdoms/ZulAman/zulaman.cpp +++ b/src/server/scripts/EasternKingdoms/ZulAman/zulaman.cpp @@ -150,8 +150,7 @@ class npc_zulaman_hostage : public CreatureScript void JustDied(Unit* /*killer*/) OVERRIDE { - Player* player = Unit::GetPlayer(*me, PlayerGUID); - if (player) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) player->SendLoot(me->GetGUID(), LOOT_CORPSE); } diff --git a/src/server/scripts/EasternKingdoms/zone_eversong_woods.cpp b/src/server/scripts/EasternKingdoms/zone_eversong_woods.cpp index d8750a82bc4..5381b19ebf3 100644 --- a/src/server/scripts/EasternKingdoms/zone_eversong_woods.cpp +++ b/src/server/scripts/EasternKingdoms/zone_eversong_woods.cpp @@ -98,14 +98,14 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (PlayerGUID) - if (Player* player = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) player->FailQuest(QUEST_UNEXPECTED_RESULT); } void UpdateAI(uint32 /*diff*/) OVERRIDE { if (KillCount >= 3 && PlayerGUID) - if (Player* player = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) player->CompleteQuest(QUEST_UNEXPECTED_RESULT); if (Summon) @@ -207,7 +207,7 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (PlayerGUID && !Completed) - if (Player* player = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) player->FailQuest(QUEST_POWERING_OUR_DEFENSES); } @@ -218,7 +218,7 @@ public: Talk(EMOTE); Completed = true; if (PlayerGUID) - if (Player* player = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) player->CompleteQuest(QUEST_POWERING_OUR_DEFENSES); me->DealDamage(me, me->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false); diff --git a/src/server/scripts/EasternKingdoms/zone_isle_of_queldanas.cpp b/src/server/scripts/EasternKingdoms/zone_isle_of_queldanas.cpp index 3ebcd315eaf..32a7feffa72 100644 --- a/src/server/scripts/EasternKingdoms/zone_isle_of_queldanas.cpp +++ b/src/server/scripts/EasternKingdoms/zone_isle_of_queldanas.cpp @@ -113,32 +113,22 @@ public: { npc_greengill_slaveAI(Creature* creature) : ScriptedAI(creature) {} - uint64 PlayerGUID; + void EnterCombat(Unit* /*who*/) OVERRIDE { } - void EnterCombat(Unit* /*who*/)OVERRIDE {} - - void Reset() OVERRIDE - { - PlayerGUID = 0; - } - - void SpellHit(Unit* caster, const SpellInfo* spell) OVERRIDE + void SpellHit(Unit* caster, SpellInfo const* spellInfo) OVERRIDE { - if (!caster) + Player* player = caster->ToPlayer(); + if (!player) return; - if (caster->GetTypeId() == TYPEID_PLAYER && spell->Id == ORB && !me->HasAura(ENRAGE)) + if (spellInfo->Id == ORB && !me->HasAura(ENRAGE)) { - PlayerGUID = caster->GetGUID(); - if (PlayerGUID) - { - Player* player = Unit::GetPlayer(*me, PlayerGUID); - if (player && player->GetQuestStatus(QUESTG) == QUEST_STATUS_INCOMPLETE) - DoCast(player, 45110, true); - } + if (player->GetQuestStatus(QUESTG) == QUEST_STATUS_INCOMPLETE) + DoCast(player, 45110, true); + DoCast(me, ENRAGE); - Unit* Myrmidon = me->FindNearestCreature(DM, 70); - if (Myrmidon) + + if (Creature* Myrmidon = me->FindNearestCreature(DM, 70)) { me->AddThreat(Myrmidon, 100000.0f); AttackStart(Myrmidon); diff --git a/src/server/scripts/EasternKingdoms/zone_silverpine_forest.cpp b/src/server/scripts/EasternKingdoms/zone_silverpine_forest.cpp index 5fb8aca22e8..8ddd609da29 100644 --- a/src/server/scripts/EasternKingdoms/zone_silverpine_forest.cpp +++ b/src/server/scripts/EasternKingdoms/zone_silverpine_forest.cpp @@ -232,7 +232,7 @@ public: { Unit* target = NULL; if (PlayerGUID) - if (Player* player = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) if (player->IsAlive() && RAND(0, 1)) target = player; @@ -248,7 +248,7 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (PlayerGUID) - if (Player* player = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) if (player->GetQuestStatus(QUEST_PYREWOOD_AMBUSH) == QUEST_STATUS_INCOMPLETE) player->FailQuest(QUEST_PYREWOOD_AMBUSH); } @@ -301,7 +301,7 @@ public: case 5: //end if (PlayerGUID) { - if (Player* player = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) { me->MonsterSay(NPCSAY_END, LANG_UNIVERSAL, 0); //not blizzlike player->GroupEventHappens(QUEST_PYREWOOD_AMBUSH, me); diff --git a/src/server/scripts/EasternKingdoms/zone_tirisfal_glades.cpp b/src/server/scripts/EasternKingdoms/zone_tirisfal_glades.cpp index d84b02d613e..b06786caf44 100644 --- a/src/server/scripts/EasternKingdoms/zone_tirisfal_glades.cpp +++ b/src/server/scripts/EasternKingdoms/zone_tirisfal_glades.cpp @@ -132,7 +132,7 @@ public: ++m_uiPhase; break; case 2: - if (Player* player = Unit::GetPlayer(*me, m_uiPlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, m_uiPlayerGUID)) player->AreaExploredOrEventHappens(QUEST_590); DoCast(me, SPELL_DRINK, true); diff --git a/src/server/scripts/Events/childrens_week.cpp b/src/server/scripts/Events/childrens_week.cpp index 5d4b0797081..ca9d4cbc49e 100644 --- a/src/server/scripts/Events/childrens_week.cpp +++ b/src/server/scripts/Events/childrens_week.cpp @@ -181,8 +181,8 @@ class npc_winterfin_playmate : public CreatureScript if (timer <= diff) { - Player* player = Player::GetPlayer(*me, playerGUID); - Creature* orphan = Creature::GetCreature(*me, orphanGUID); + Player* player = ObjectAccessor::GetPlayer(*me, playerGUID); + Creature* orphan = ObjectAccessor::GetCreature(*me, orphanGUID); if (!orphan || !player) { @@ -280,8 +280,8 @@ class npc_snowfall_glade_playmate : public CreatureScript if (timer <= diff) { - Player* player = Player::GetPlayer(*me, playerGUID); - Creature* orphan = Creature::GetCreature(*me, orphanGUID); + Player* player = ObjectAccessor::GetPlayer(*me, playerGUID); + Creature* orphan = ObjectAccessor::GetCreature(*me, orphanGUID); if (!orphan || !player) { @@ -381,8 +381,8 @@ class npc_the_biggest_tree : public CreatureScript if (timer <= diff) { - Player* player = Player::GetPlayer(*me, playerGUID); - Creature* orphan = Creature::GetCreature(*me, orphanGUID); + Player* player = ObjectAccessor::GetPlayer(*me, playerGUID); + Creature* orphan = ObjectAccessor::GetCreature(*me, orphanGUID); if (!orphan || !player) { @@ -468,8 +468,8 @@ class npc_high_oracle_soo_roo : public CreatureScript if (timer <= diff) { - Player* player = Player::GetPlayer(*me, playerGUID); - Creature* orphan = Creature::GetCreature(*me, orphanGUID); + Player* player = ObjectAccessor::GetPlayer(*me, playerGUID); + Creature* orphan = ObjectAccessor::GetCreature(*me, orphanGUID); if (!orphan || !player) { @@ -557,8 +557,8 @@ class npc_elder_kekek : public CreatureScript if (timer <= diff) { - Player* player = Player::GetPlayer(*me, playerGUID); - Creature* orphan = Creature::GetCreature(*me, orphanGUID); + Player* player = ObjectAccessor::GetPlayer(*me, playerGUID); + Creature* orphan = ObjectAccessor::GetCreature(*me, orphanGUID); if (!player || !orphan) { @@ -646,8 +646,8 @@ class npc_the_etymidian : public CreatureScript if (timer <= diff) { - Player* player = Player::GetPlayer(*me, playerGUID); - Creature* orphan = Creature::GetCreature(*me, orphanGUID); + Player* player = ObjectAccessor::GetPlayer(*me, playerGUID); + Creature* orphan = ObjectAccessor::GetCreature(*me, orphanGUID); if (!orphan || !player) { @@ -768,8 +768,8 @@ class npc_alexstraza_the_lifebinder : public CreatureScript if (timer <= diff) { - Player* player = Player::GetPlayer(*me, playerGUID); - Creature* orphan = Creature::GetCreature(*me, orphanGUID); + Player* player = ObjectAccessor::GetPlayer(*me, playerGUID); + Creature* orphan = ObjectAccessor::GetCreature(*me, orphanGUID); if (!orphan || !player) { diff --git a/src/server/scripts/Kalimdor/CMakeLists.txt b/src/server/scripts/Kalimdor/CMakeLists.txt index 752f8d3a2af..17c360a54b2 100644 --- a/src/server/scripts/Kalimdor/CMakeLists.txt +++ b/src/server/scripts/Kalimdor/CMakeLists.txt @@ -67,6 +67,7 @@ set(scripts_STAT_SRCS Kalimdor/Maraudon/boss_landslide.cpp Kalimdor/Maraudon/boss_celebras_the_cursed.cpp Kalimdor/Maraudon/boss_noxxion.cpp + Kalimdor/Maraudon/instance_maraudon.cpp Kalimdor/TempleOfAhnQiraj/boss_fankriss.cpp Kalimdor/TempleOfAhnQiraj/boss_huhuran.cpp Kalimdor/TempleOfAhnQiraj/instance_temple_of_ahnqiraj.cpp @@ -112,6 +113,8 @@ set(scripts_STAT_SRCS Kalimdor/OnyxiasLair/boss_onyxia.cpp Kalimdor/OnyxiasLair/onyxias_lair.h Kalimdor/OnyxiasLair/instance_onyxias_lair.cpp + Kalimdor/RagefireChasm/instance_ragefire_chasm.cpp + Kalimdor/DireMaul/instance_dire_maul.cpp ) message(" -> Prepared: Kalimdor") diff --git a/src/server/scripts/Kalimdor/DireMaul/instance_dire_maul.cpp b/src/server/scripts/Kalimdor/DireMaul/instance_dire_maul.cpp new file mode 100644 index 00000000000..a478d7aea25 --- /dev/null +++ b/src/server/scripts/Kalimdor/DireMaul/instance_dire_maul.cpp @@ -0,0 +1,47 @@ +/* + * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +/* +This placeholder for the instance is needed for dungeon finding to be able +to give credit after the boss defined in lastEncounterDungeon is killed. +Without it, the party doing random dungeon won't get satchel of spoils and +gets instead the deserter debuff. +*/ + +#include "ScriptMgr.h" +#include "InstanceScript.h" + +class instance_dire_maul : public InstanceMapScript +{ +public: + instance_dire_maul() : InstanceMapScript("instance_dire_maul", 429) { } + + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_dire_maul_InstanceMapScript(map); + } + + struct instance_dire_maul_InstanceMapScript : public InstanceScript + { + instance_dire_maul_InstanceMapScript(Map* map) : InstanceScript(map) {} + }; +}; + +void AddSC_instance_dire_maul() +{ + new instance_dire_maul(); +} diff --git a/src/server/scripts/Kalimdor/Maraudon/instance_maraudon.cpp b/src/server/scripts/Kalimdor/Maraudon/instance_maraudon.cpp new file mode 100644 index 00000000000..a44f4078a9b --- /dev/null +++ b/src/server/scripts/Kalimdor/Maraudon/instance_maraudon.cpp @@ -0,0 +1,47 @@ +/* + * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +/* +This placeholder for the instance is needed for dungeon finding to be able +to give credit after the boss defined in lastEncounterDungeon is killed. +Without it, the party doing random dungeon won't get satchel of spoils and +gets instead the deserter debuff. +*/ + +#include "ScriptMgr.h" +#include "InstanceScript.h" + +class instance_maraudon : public InstanceMapScript +{ +public: + instance_maraudon() : InstanceMapScript("instance_maraudon", 349) { } + + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_maraudon_InstanceMapScript(map); + } + + struct instance_maraudon_InstanceMapScript : public InstanceScript + { + instance_maraudon_InstanceMapScript(Map* map) : InstanceScript(map) {} + }; +}; + +void AddSC_instance_maraudon() +{ + new instance_maraudon(); +} diff --git a/src/server/scripts/Kalimdor/RagefireChasm/instance_ragefire_chasm.cpp b/src/server/scripts/Kalimdor/RagefireChasm/instance_ragefire_chasm.cpp new file mode 100644 index 00000000000..6b13fecb26a --- /dev/null +++ b/src/server/scripts/Kalimdor/RagefireChasm/instance_ragefire_chasm.cpp @@ -0,0 +1,47 @@ +/* + * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +/* +This placeholder for the instance is needed for dungeon finding to be able +to give credit after the boss defined in lastEncounterDungeon is killed. +Without it, the party doing random dungeon won't get satchel of spoils and +gets instead the deserter debuff. +*/ + +#include "ScriptMgr.h" +#include "InstanceScript.h" + +class instance_ragefire_chasm : public InstanceMapScript +{ +public: + instance_ragefire_chasm() : InstanceMapScript("instance_ragefire_chasm", 389) { } + + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_ragefire_chasm_InstanceMapScript(map); + } + + struct instance_ragefire_chasm_InstanceMapScript : public InstanceScript + { + instance_ragefire_chasm_InstanceMapScript(Map* map) : InstanceScript(map) {} + }; +}; + +void AddSC_instance_ragefire_chasm() +{ + new instance_ragefire_chasm(); +} diff --git a/src/server/scripts/Kalimdor/ZulFarrak/zulfarrak.cpp b/src/server/scripts/Kalimdor/ZulFarrak/zulfarrak.cpp index c8d83a54e1e..a2f98b21589 100644 --- a/src/server/scripts/Kalimdor/ZulFarrak/zulfarrak.cpp +++ b/src/server/scripts/Kalimdor/ZulFarrak/zulfarrak.cpp @@ -145,7 +145,7 @@ public: break; case 3: me->setFaction(FACTION_HOSTILE); - if (Player* target = Player::GetPlayer(*me, PlayerGUID)) + if (Player* target = ObjectAccessor::GetPlayer(*me, PlayerGUID)) AttackStart(target); if (instance) diff --git a/src/server/scripts/Kalimdor/zone_azshara.cpp b/src/server/scripts/Kalimdor/zone_azshara.cpp index 01b8b9c1bcf..f48bd1f9339 100644 --- a/src/server/scripts/Kalimdor/zone_azshara.cpp +++ b/src/server/scripts/Kalimdor/zone_azshara.cpp @@ -35,7 +35,6 @@ EndContentData */ #include "ScriptedGossip.h" #include "Player.h" #include "SpellInfo.h" -#include "WorldSession.h" /*###### ## npc_spitelashes @@ -371,7 +370,7 @@ public: DoTeleportTo(3706.39f, -3969.15f, 35.9118f); //begin swimming and summon depth charges - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (!player) return; @@ -396,8 +395,7 @@ public: if (GrenadeTimer <= diff) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); - if (player) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) { Talk(SAY_RIZZLE_GRENADE, player->GetGUID()); DoCast(player, SPELL_RIZZLE_FROST_GRENADE, true); @@ -407,7 +405,7 @@ public: if (CheckTimer <= diff) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (!player) { me->DespawnOrUnsummon(); @@ -429,13 +427,6 @@ public: } - void SendText(int32 iTextEntry, Player* player) - { - LocaleConstant loc_idx = player->GetSession()->GetSessionDbLocaleIndex(); - const char* text = sObjectMgr->GetTrinityString(iTextEntry, loc_idx); - sWorld->SendServerMessage(SERVER_MSG_STRING, text, player); - } - void AttackStart(Unit* who) OVERRIDE { if (!who || PlayerGUID) diff --git a/src/server/scripts/Kalimdor/zone_azuremyst_isle.cpp b/src/server/scripts/Kalimdor/zone_azuremyst_isle.cpp index f5c8c90d921..e0d181646e1 100644 --- a/src/server/scripts/Kalimdor/zone_azuremyst_isle.cpp +++ b/src/server/scripts/Kalimdor/zone_azuremyst_isle.cpp @@ -134,7 +134,7 @@ public: { me->RemoveAurasDueToSpell(SPELL_IRRIDATION); - if (Player* player = Unit::GetPlayer(*me, pCaster)) + if (Player* player = ObjectAccessor::GetPlayer(*me, pCaster)) { Talk(SAY_HEAL, player->GetGUID()); diff --git a/src/server/scripts/Kalimdor/zone_moonglade.cpp b/src/server/scripts/Kalimdor/zone_moonglade.cpp index 6885e44a245..509adb566cd 100644 --- a/src/server/scripts/Kalimdor/zone_moonglade.cpp +++ b/src/server/scripts/Kalimdor/zone_moonglade.cpp @@ -350,7 +350,7 @@ public: if (!PlayerGUID) return; - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (player && player->GetQuestStatus(10965) == QUEST_STATUS_INCOMPLETE) { player->FailQuest(10965); @@ -361,7 +361,7 @@ public: void EnterEvadeMode() OVERRIDE { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (player && player->IsInCombat() && player->getAttackerForHelper()) { AttackStart(player->getAttackerForHelper()); @@ -398,7 +398,7 @@ public: { if (checkPlayerTimer <= diff) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (player && player->IsInCombat() && player->getAttackerForHelper()) AttackStart(player->getAttackerForHelper()); checkPlayerTimer = 1000; @@ -407,9 +407,8 @@ public: if (EventOnWait && EventTimer <= diff) { - - Player* player = Unit::GetPlayer(*me, PlayerGUID); - if (!player || (player && player->GetQuestStatus(10965) == QUEST_STATUS_NONE)) + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); + if (!player || player->GetQuestStatus(10965) == QUEST_STATUS_NONE) { me->setDeathState(JUST_DIED); return; diff --git a/src/server/scripts/Kalimdor/zone_mulgore.cpp b/src/server/scripts/Kalimdor/zone_mulgore.cpp index 5cd0b9f568b..6b42b971531 100644 --- a/src/server/scripts/Kalimdor/zone_mulgore.cpp +++ b/src/server/scripts/Kalimdor/zone_mulgore.cpp @@ -162,7 +162,7 @@ public: switch (EventPhase) { case 1: - if (Unit* unit = Unit::GetUnit(*me, PlayerGUID)) + if (Unit* unit = ObjectAccessor::GetUnit(*me, PlayerGUID)) { if (GameObject* go = unit->GetGameObject(SPELL_LUNCH)) { @@ -176,7 +176,7 @@ public: me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_STATE_USE_STANDING); break; case 3: - if (Player* unit = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* unit = ObjectAccessor::GetPlayer(*me, PlayerGUID)) unit->TalkedToCreature(me->GetEntry(), me->GetGUID()); me->UpdateEntry(NPC_KYLE_FRIENDLY); diff --git a/src/server/scripts/Kalimdor/zone_orgrimmar.cpp b/src/server/scripts/Kalimdor/zone_orgrimmar.cpp index afd320af3ac..7928ab10978 100644 --- a/src/server/scripts/Kalimdor/zone_orgrimmar.cpp +++ b/src/server/scripts/Kalimdor/zone_orgrimmar.cpp @@ -89,7 +89,7 @@ public: { if (ResetTimer <= diff) { - if (Player* player = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) { if (player->GetTypeId() == TYPEID_PLAYER && player->GetQuestStatus(QUEST_SHATTERED_SALUTE) == QUEST_STATUS_INCOMPLETE) player->FailQuest(QUEST_SHATTERED_SALUTE); diff --git a/src/server/scripts/Kalimdor/zone_silithus.cpp b/src/server/scripts/Kalimdor/zone_silithus.cpp index 154f8b0f80f..fd8a1069ff7 100644 --- a/src/server/scripts/Kalimdor/zone_silithus.cpp +++ b/src/server/scripts/Kalimdor/zone_silithus.cpp @@ -526,7 +526,7 @@ public: void HandleAnimation() { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (!player) return; @@ -1002,14 +1002,13 @@ public: void CheckEventFail() { - Player* player = Unit::GetPlayer(*me, PlayerGUID); - + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (!player) return; if (Group* EventGroup = player->GetGroup()) { - Player* groupMember; + Player* groupMember = NULL; uint8 GroupMemberCount = 0; uint8 DeadMemberCount = 0; @@ -1019,7 +1018,7 @@ public: for (Group::member_citerator itr = members.begin(); itr!= members.end(); ++itr) { - groupMember = (Unit::GetPlayer(*me, itr->guid)); + groupMember = ObjectAccessor::GetPlayer(*me, itr->guid); if (!groupMember) continue; if (!groupMember->IsWithinDistInMap(me, EVENT_AREA_RADIUS) && groupMember->GetQuestStatus(QUEST_A_PAWN_ON_THE_ETERNAL_BOARD) == QUEST_STATUS_INCOMPLETE) diff --git a/src/server/scripts/Kalimdor/zone_the_barrens.cpp b/src/server/scripts/Kalimdor/zone_the_barrens.cpp index 62867c46f78..122ce84091b 100644 --- a/src/server/scripts/Kalimdor/zone_the_barrens.cpp +++ b/src/server/scripts/Kalimdor/zone_the_barrens.cpp @@ -366,18 +366,20 @@ public: void UpdateAI(uint32 diff) OVERRIDE { - if (EventInProgress) { - Player* pWarrior = NULL; + if (EventInProgress) + { + Player* warrior = NULL; if (PlayerGUID) - pWarrior = Unit::GetPlayer(*me, PlayerGUID); + warrior = ObjectAccessor::GetPlayer(*me, PlayerGUID); - if (!pWarrior) + if (!warrior) return; - if (!pWarrior->IsAlive() && pWarrior->GetQuestStatus(1719) == QUEST_STATUS_INCOMPLETE) { + if (!warrior->IsAlive() && warrior->GetQuestStatus(1719) == QUEST_STATUS_INCOMPLETE) + { Talk(SAY_TWIGGY_FLATHEAD_DOWN); - pWarrior->FailQuest(1719); + warrior->FailQuest(1719); for (uint8 i = 0; i < 6; ++i) // unsummon challengers { @@ -401,11 +403,12 @@ public: if (!EventGrate && EventInProgress) { float x, y, z; - pWarrior->GetPosition(x, y, z); + warrior->GetPosition(x, y, z); - if (x >= -1684 && x <= -1674 && y >= -4334 && y <= -4324) { - pWarrior->AreaExploredOrEventHappens(1719); - Talk(SAY_TWIGGY_FLATHEAD_BEGIN, pWarrior->GetGUID()); + if (x >= -1684 && x <= -1674 && y >= -4334 && y <= -4324) + { + warrior->AreaExploredOrEventHappens(1719); + Talk(SAY_TWIGGY_FLATHEAD_BEGIN, warrior->GetGUID()); for (uint8 i = 0; i < 6; ++i) { @@ -447,19 +450,20 @@ public: if (Wave < 6 && AffrayChallenger[Wave] && !EventBigWill) { Talk(SAY_TWIGGY_FLATHEAD_FRAY); - Creature* creature = Unit::GetCreature((*me), AffrayChallenger[Wave]); + Creature* creature = ObjectAccessor::GetCreature(*me, AffrayChallenger[Wave]); if (creature && (creature->IsAlive())) { creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); creature->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE); creature->HandleEmoteCommand(EMOTE_ONESHOT_ROAR); creature->setFaction(14); - creature->AI()->AttackStart(pWarrior); + creature->AI()->AttackStart(warrior); ++Wave; WaveTimer = 20000; } } - else if (Wave >= 6 && !EventBigWill) { + else if (Wave >= 6 && !EventBigWill) + { if (Creature* creature = me->SummonCreature(NPC_BIG_WILL, -1722, -4341, 6.12f, 6.26f, TEMPSUMMON_TIMED_OR_DEAD_DESPAWN, 480000)) { BigWill = creature->GetGUID(); @@ -473,7 +477,7 @@ public: } else if (Wave >= 6 && EventBigWill && BigWill) { - Creature* creature = Unit::GetCreature((*me), BigWill); + Creature* creature = ObjectAccessor::GetCreature(*me, BigWill); if (!creature || !creature->IsAlive()) { Talk(SAY_TWIGGY_FLATHEAD_OVER); diff --git a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/ahnkahet.h b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/ahnkahet.h index 8473ee1d39d..5b8cf0a4d44 100644 --- a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/ahnkahet.h +++ b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/ahnkahet.h @@ -18,33 +18,71 @@ #ifndef AHNKAHET_H_ #define AHNKAHET_H_ -enum Data64 +#define AhnKahetScriptName "instance_ahnkahet" + +uint32 const EncounterCount = 5; + +enum DataTypes +{ + // Encounter States/Boss GUIDs + DATA_ELDER_NADOX = 0, + DATA_PRINCE_TALDARAM = 1, + DATA_JEDOGA_SHADOWSEEKER = 2, + DATA_AMANITAR = 3, + DATA_HERALD_VOLAZJ = 4, + + // Additional Data + DATA_SPHERE_1 = 5, + DATA_SPHERE_2 = 6, + DATA_PRINCE_TALDARAM_PLATFORM = 7, + DATA_PL_JEDOGA_TARGET = 8, + DATA_ADD_JEDOGA_OPFER = 9, + DATA_ADD_JEDOGA_INITIAND = 10, + DATA_JEDOGA_TRIGGER_SWITCH = 11, + DATA_JEDOGA_RESET_INITIANDS = 12, + DATA_ALL_INITIAND_DEAD = 13 +}; + +enum CreatureIds { - DATA_ELDER_NADOX, - DATA_PRINCE_TALDARAM, - DATA_JEDOGA_SHADOWSEEKER, - DATA_HERALD_VOLAZJ, - DATA_AMANITAR, - DATA_SPHERE1, - DATA_SPHERE2, - DATA_PRINCE_TALDARAM_PLATFORM, - DATA_PL_JEDOGA_TARGET, - DATA_ADD_JEDOGA_OPFER, - DATA_ADD_JEDOGA_INITIAND + NPC_ELDER_NADOX = 29309, + NPC_PRINCE_TALDARAM = 29308, + NPC_JEDOGA_SHADOWSEEKER = 29310, + NPC_AMANITAR = 30258, + NPC_HERALD_VOLAZJ = 29311, + + // Elder Nadox + NPC_AHNKAHAR_GUARDIAN = 30176, + NPC_AHNKAHAR_SWARMER = 30178, + + // Jedoga Shadowseeker + NPC_INITIAND = 30114, + NPC_JEDOGA_CONTROLLER = 30181, + + // Amanitar + NPC_HEALTHY_MUSHROOM = 30391, + NPC_POISONOUS_MUSHROOM = 30435, + + // Herald Volazj + //NPC_TWISTED_VISAGE_1 = 30621, + //NPC_TWISTED_VISAGE_2 = 30622, + //NPC_TWISTED_VISAGE_3 = 30623, + //NPC_TWISTED_VISAGE_4 = 30624, + NPC_TWISTED_VISAGE = 30625 }; -enum Data +enum GameObjectIds { - DATA_ELDER_NADOX_EVENT, - DATA_PRINCE_TALDARAM_EVENT, - DATA_JEDOGA_SHADOWSEEKER_EVENT, - DATA_HERALD_VOLAZJ_EVENT, - DATA_AMANITAR_EVENT, - DATA_SPHERE1_EVENT, - DATA_SPHERE2_EVENT, - DATA_JEDOGA_TRIGGER_SWITCH, - DATA_JEDOGA_RESET_INITIANDS, - DATA_ALL_INITIAND_DEAD + GO_PRINCE_TALDARAM_GATE = 192236, + GO_PRINCE_TALDARAM_PLATFORM = 193564, + GO_SPHERE_1 = 193093, + GO_SPHERE_2 = 193094 }; +template<class AI> +AI* GetAhnKahetAI(Creature* creature) +{ + return GetInstanceAI<AI>(creature, AhnKahetScriptName); +} + #endif // AHNKAHET_H_ diff --git a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_amanitar.cpp b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_amanitar.cpp index 7a20d1f581c..7132ba825f1 100644 --- a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_amanitar.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_amanitar.cpp @@ -35,8 +35,6 @@ enum Spells enum Creatures { - NPC_HEALTHY_MUSHROOM = 30391, - NPC_POISONOUS_MUSHROOM = 30435, NPC_TRIGGER = 19656 }; @@ -52,129 +50,112 @@ enum Events class boss_amanitar : public CreatureScript { -public: - boss_amanitar() : CreatureScript("boss_amanitar") { } - - struct boss_amanitarAI : public BossAI - { - boss_amanitarAI(Creature* creature) : BossAI(creature, DATA_AMANITAR) { } + public: + boss_amanitar() : CreatureScript("boss_amanitar") { } - void Reset() OVERRIDE + struct boss_amanitarAI : public BossAI { - _Reset(); + boss_amanitarAI(Creature* creature) : BossAI(creature, DATA_AMANITAR) { } - me->SetMeleeDamageSchool(SPELL_SCHOOL_NATURE); - me->ApplySpellImmune(0, IMMUNITY_SCHOOL, SPELL_SCHOOL_MASK_NATURE, true); - summons.DespawnAll(); + void Reset() OVERRIDE + { + _Reset(); + me->SetMeleeDamageSchool(SPELL_SCHOOL_NATURE); + me->ApplySpellImmune(0, IMMUNITY_SCHOOL, SPELL_SCHOOL_MASK_NATURE, true); + } - if (instance) + void EnterCombat(Unit* /*who*/) OVERRIDE { - instance->DoRemoveAurasDueToSpellOnPlayers(SPELL_MINI); - instance->SetData(DATA_AMANITAR_EVENT, NOT_STARTED); + _EnterCombat(); + + events.ScheduleEvent(EVENT_ROOT, urand(5, 9) * IN_MILLISECONDS); + events.ScheduleEvent(EVENT_BASH, urand(10, 14) * IN_MILLISECONDS); + events.ScheduleEvent(EVENT_BOLT, urand(15, 20) * IN_MILLISECONDS); + events.ScheduleEvent(EVENT_MINI, urand(12, 18) * IN_MILLISECONDS); + events.ScheduleEvent(EVENT_SPAWN, 5 * IN_MILLISECONDS); } - } - void JustDied(Unit* /*Killer*/) OVERRIDE - { - if (instance) + void JustDied(Unit* /*killer*/) OVERRIDE { _JustDied(); - instance->SetData(DATA_AMANITAR_EVENT, DONE); instance->DoRemoveAurasDueToSpellOnPlayers(SPELL_MINI); - summons.DespawnAll(); } - } - - void EnterCombat(Unit* /*who*/) OVERRIDE - { - _EnterCombat(); - - events.ScheduleEvent(EVENT_ROOT, urand(5, 9) * IN_MILLISECONDS); - events.ScheduleEvent(EVENT_BASH, urand(10, 14) * IN_MILLISECONDS); - events.ScheduleEvent(EVENT_BOLT, urand(15, 20) * IN_MILLISECONDS); - events.ScheduleEvent(EVENT_MINI, urand(12, 18) * IN_MILLISECONDS); - events.ScheduleEvent(EVENT_SPAWN, 5 * IN_MILLISECONDS); - me->SetInCombatWithZone(); - if (instance) - instance->SetData(DATA_AMANITAR_EVENT, IN_PROGRESS); - } - - void SpawnAdds() - { - uint8 u = 0; - - for (uint8 i = 0; i < 30; ++i) + void SpawnAdds() { - Position pos; - me->GetPosition(&pos); - me->GetRandomNearPosition(pos, 30.0f); - pos.m_positionZ = me->GetMap()->GetHeight(pos.GetPositionX(), pos.GetPositionY(), MAX_HEIGHT) + 2.0f; + uint8 u = 0; - if (Creature* trigger = me->SummonCreature(NPC_TRIGGER, pos)) + for (uint8 i = 0; i < 30; ++i) { - Creature* temp1 = trigger->FindNearestCreature(NPC_HEALTHY_MUSHROOM, 4.0f, true); - Creature* temp2 = trigger->FindNearestCreature(NPC_POISONOUS_MUSHROOM, 4.0f, true); - if (temp1 || temp2) - { - trigger->DisappearAndDie(); - } - else + Position pos; + me->GetPosition(&pos); + me->GetRandomNearPosition(pos, 30.0f); + pos.m_positionZ = me->GetMap()->GetHeight(pos.GetPositionX(), pos.GetPositionY(), MAX_HEIGHT) + 2.0f; + + if (Creature* trigger = me->SummonCreature(NPC_TRIGGER, pos)) { - u = 1 - u; - trigger->DisappearAndDie(); - me->SummonCreature(u > 0 ? NPC_POISONOUS_MUSHROOM : NPC_HEALTHY_MUSHROOM, pos, TEMPSUMMON_TIMED_OR_CORPSE_DESPAWN, 60 * IN_MILLISECONDS); + Creature* temp1 = trigger->FindNearestCreature(NPC_HEALTHY_MUSHROOM, 4.0f, true); + Creature* temp2 = trigger->FindNearestCreature(NPC_POISONOUS_MUSHROOM, 4.0f, true); + if (temp1 || temp2) + { + trigger->DisappearAndDie(); + } + else + { + u = 1 - u; + trigger->DisappearAndDie(); + me->SummonCreature(u > 0 ? NPC_POISONOUS_MUSHROOM : NPC_HEALTHY_MUSHROOM, pos, TEMPSUMMON_TIMED_OR_CORPSE_DESPAWN, 60 * IN_MILLISECONDS); + } } } } - } - void UpdateAI(uint32 diff) OVERRIDE - { - if (!UpdateVictim()) - return; + void UpdateAI(uint32 diff) OVERRIDE + { + if (!UpdateVictim()) + return; - events.Update(diff); + events.Update(diff); - if (me->HasUnitState(UNIT_STATE_CASTING)) - return; + if (me->HasUnitState(UNIT_STATE_CASTING)) + return; - while (uint32 eventId = events.ExecuteEvent()) - { - switch (eventId) + while (uint32 eventId = events.ExecuteEvent()) { - case EVENT_SPAWN: - SpawnAdds(); - events.ScheduleEvent(EVENT_SPAWN, 20 * IN_MILLISECONDS); - break; - case EVENT_MINI: - DoCast(SPELL_MINI); - events.ScheduleEvent(EVENT_MINI, urand(25, 30) * IN_MILLISECONDS); - break; - case EVENT_ROOT: - DoCast(SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true), SPELL_ENTANGLING_ROOTS, true); - events.ScheduleEvent(EVENT_ROOT, urand(10, 15) * IN_MILLISECONDS); - break; - case EVENT_BASH: - DoCastVictim(SPELL_BASH); - events.ScheduleEvent(EVENT_BASH, urand(7, 12) * IN_MILLISECONDS); - break; - case EVENT_BOLT: - DoCast(SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true), SPELL_VENOM_BOLT_VOLLEY, true); - events.ScheduleEvent(EVENT_BOLT, urand(18, 22) * IN_MILLISECONDS); - break; - default: - break; + switch (eventId) + { + case EVENT_SPAWN: + SpawnAdds(); + events.ScheduleEvent(EVENT_SPAWN, 20 * IN_MILLISECONDS); + break; + case EVENT_MINI: + DoCast(SPELL_MINI); + events.ScheduleEvent(EVENT_MINI, urand(25, 30) * IN_MILLISECONDS); + break; + case EVENT_ROOT: + DoCast(SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true), SPELL_ENTANGLING_ROOTS, true); + events.ScheduleEvent(EVENT_ROOT, urand(10, 15) * IN_MILLISECONDS); + break; + case EVENT_BASH: + DoCastVictim(SPELL_BASH); + events.ScheduleEvent(EVENT_BASH, urand(7, 12) * IN_MILLISECONDS); + break; + case EVENT_BOLT: + DoCast(SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true), SPELL_VENOM_BOLT_VOLLEY, true); + events.ScheduleEvent(EVENT_BOLT, urand(18, 22) * IN_MILLISECONDS); + break; + default: + break; + } } + DoMeleeAttackIfReady(); } - DoMeleeAttackIfReady(); - } - }; + }; - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return new boss_amanitarAI(creature); - } + CreatureAI* GetAI(Creature* creature) const OVERRIDE + { + return GetAhnKahetAI<boss_amanitarAI>(creature); + } }; class npc_amanitar_mushrooms : public CreatureScript diff --git a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_elder_nadox.cpp b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_elder_nadox.cpp index 057ee41a3a0..c549de9dda1 100644 --- a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_elder_nadox.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_elder_nadox.cpp @@ -41,12 +41,6 @@ enum Spells SPELL_GUARDIAN_AURA = 56151 }; -enum Creatures -{ - NPC_AHNKAHAR_SWARMER = 30178, - NPC_AHNKAHAR_GUARDIAN = 30176 -}; - enum Events { EVENT_PLAGUE = 1, @@ -62,38 +56,22 @@ class boss_elder_nadox : public CreatureScript public: boss_elder_nadox() : CreatureScript("boss_elder_nadox") { } - struct boss_elder_nadoxAI : public ScriptedAI + struct boss_elder_nadoxAI : public BossAI { - boss_elder_nadoxAI(Creature* creature) : ScriptedAI(creature), summons(me) - { - instance = creature->GetInstanceScript(); - } - - bool GuardianDied; - uint8 AmountHealthModifier; - InstanceScript* instance; - SummonList summons; - EventMap events; + boss_elder_nadoxAI(Creature* creature) : BossAI(creature, DATA_ELDER_NADOX) { } void Reset() OVERRIDE { - events.Reset(); - summons.DespawnAll(); - + _Reset(); AmountHealthModifier = 1; GuardianDied = false; - - if (instance) - instance->SetData(DATA_ELDER_NADOX_EVENT, NOT_STARTED); } void EnterCombat(Unit* /*who*/) OVERRIDE { + _EnterCombat(); Talk(SAY_AGGRO); - if (instance) - instance->SetData(DATA_ELDER_NADOX_EVENT, IN_PROGRESS); - events.ScheduleEvent(EVENT_PLAGUE, 13 * IN_MILLISECONDS); events.ScheduleEvent(EVENT_SUMMON_SWARMER, 10 * IN_MILLISECONDS); @@ -104,12 +82,6 @@ class boss_elder_nadox : public CreatureScript } } - void JustSummoned(Creature* summon) OVERRIDE - { - summons.Summon(summon); - summon->AI()->DoZoneInCombat(); - } - void SummonedCreatureDies(Creature* summon, Unit* /*killer*/) OVERRIDE { if (summon->GetEntry() == NPC_AHNKAHAR_GUARDIAN) @@ -124,19 +96,16 @@ class boss_elder_nadox : public CreatureScript return 0; } - void KilledUnit(Unit* /*victim*/) OVERRIDE + void KilledUnit(Unit* who) OVERRIDE { - Talk(SAY_SLAY); + if (who->GetTypeId() == TYPEID_PLAYER) + Talk(SAY_SLAY); } void JustDied(Unit* /*killer*/) OVERRIDE { + _JustDied(); Talk(SAY_DEATH); - - summons.DespawnAll(); - - if (instance) - instance->SetData(DATA_ELDER_NADOX_EVENT, DONE); } void UpdateAI(uint32 diff) OVERRIDE @@ -185,11 +154,15 @@ class boss_elder_nadox : public CreatureScript DoMeleeAttackIfReady(); } + + private: + bool GuardianDied; + uint8 AmountHealthModifier; }; CreatureAI* GetAI(Creature* creature) const OVERRIDE { - return new boss_elder_nadoxAI(creature); + return GetAhnKahetAI<boss_elder_nadoxAI>(creature); } }; diff --git a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_herald_volazj.cpp b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_herald_volazj.cpp index 481df79c890..5bb68a4c886 100644 --- a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_herald_volazj.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_herald_volazj.cpp @@ -41,12 +41,6 @@ enum Spells SPELL_INSANITY_PHASING_5 = 57512 }; -enum Creatures -{ - NPC_TWISTED_VISAGE = 30625 -}; - - enum Yells { SAY_AGGRO = 0, @@ -157,7 +151,7 @@ public: if (instance) { - instance->SetData(DATA_HERALD_VOLAZJ, NOT_STARTED); + instance->SetBossState(DATA_HERALD_VOLAZJ, NOT_STARTED); instance->DoStopTimedAchievement(ACHIEVEMENT_TIMED_TYPE_EVENT, ACHIEV_QUICK_DEMISE_START_EVENT); } @@ -180,7 +174,7 @@ public: if (instance) { - instance->SetData(DATA_HERALD_VOLAZJ, IN_PROGRESS); + instance->SetBossState(DATA_HERALD_VOLAZJ, IN_PROGRESS); instance->DoStartTimedAchievement(ACHIEVEMENT_TIMED_TYPE_EVENT, ACHIEV_QUICK_DEMISE_START_EVENT); } } @@ -302,7 +296,7 @@ public: Talk(SAY_DEATH); if (instance) - instance->SetData(DATA_HERALD_VOLAZJ, DONE); + instance->SetBossState(DATA_HERALD_VOLAZJ, DONE); Summons.DespawnAll(); ResetPlayersPhaseMask(); diff --git a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_jedoga_shadowseeker.cpp b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_jedoga_shadowseeker.cpp index 5095f590fdb..78513fec486 100644 --- a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_jedoga_shadowseeker.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_jedoga_shadowseeker.cpp @@ -46,11 +46,6 @@ enum Spells SPELL_THUNDERSHOCK_H = 60029 // 30Y }; -enum Creatures -{ - NPC_JEDOGA_CONTROLLER = 30181 -}; - const Position JedogaPosition[2] = { {372.330994f, -705.278015f, -0.624178f, 5.427970f}, @@ -109,7 +104,7 @@ public: if (instance) { if (!bFirstTime) - instance->SetData(DATA_JEDOGA_SHADOWSEEKER_EVENT, FAIL); + instance->SetBossState(DATA_JEDOGA_SHADOWSEEKER, FAIL); instance->SetData64(DATA_PL_JEDOGA_TARGET, 0); instance->SetData64(DATA_ADD_JEDOGA_OPFER, 0); @@ -127,7 +122,7 @@ public: Talk(TEXT_AGGRO); me->SetInCombatWithZone(); - instance->SetData(DATA_JEDOGA_SHADOWSEEKER_EVENT, IN_PROGRESS); + instance->SetBossState(DATA_JEDOGA_SHADOWSEEKER, IN_PROGRESS); } void AttackStart(Unit* who) OVERRIDE @@ -150,7 +145,7 @@ public: { Talk(TEXT_DEATH); if (instance) - instance->SetData(DATA_JEDOGA_SHADOWSEEKER_EVENT, DONE); + instance->SetBossState(DATA_JEDOGA_SHADOWSEEKER, DONE); } void DoAction(int32 action) OVERRIDE @@ -168,7 +163,6 @@ public: } void MoveInLineOfSight(Unit* who) OVERRIDE - { if (!instance || !who || (who->GetTypeId() == TYPEID_UNIT && who->GetEntry() == NPC_JEDOGA_CONTROLLER)) return; @@ -179,7 +173,7 @@ public: bPreDone = true; } - if (instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) != IN_PROGRESS || !bOnGround) + if (instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) != IN_PROGRESS || !bOnGround) return; if (!me->GetVictim() && me->CanCreatureAttack(who)) @@ -229,7 +223,7 @@ public: { AttackStart(target); instance->SetData(DATA_JEDOGA_RESET_INITIANDS, 0); - if (instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) != IN_PROGRESS) + if (instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) != IN_PROGRESS) EnterCombat(target); } else if (!me->IsInCombat()) @@ -252,7 +246,8 @@ public: me->GetMotionMaster()->MovePoint(0, JedogaPosition[0]); instance->SetData(DATA_JEDOGA_TRIGGER_SWITCH, 1); - if (instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) == IN_PROGRESS) OpferRufen(); + if (instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) == IN_PROGRESS) + OpferRufen(); bOnGround = false; uiOpFerTimer = urand(15*IN_MILLISECONDS, 30*IN_MILLISECONDS); @@ -289,7 +284,7 @@ public: if (!instance) return; - if (instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) != IN_PROGRESS && instance->GetData(DATA_ALL_INITIAND_DEAD)) + if (instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) != IN_PROGRESS && instance->GetData(DATA_ALL_INITIAND_DEAD)) MoveDown(); if (bOpFerok && !bOnGround && !bCanDown) Opfern(); @@ -372,7 +367,7 @@ public: bWalking = false; bCheckTimer = 2*IN_MILLISECONDS; - if (instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) != IN_PROGRESS) + if (instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) != IN_PROGRESS) { me->RemoveAurasDueToSpell(SPELL_SPHERE_VISUAL); me->ApplySpellImmune(0, IMMUNITY_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, false); @@ -412,15 +407,13 @@ public: instance->SetData64(DATA_PL_JEDOGA_TARGET, killer->GetGUID()); } - void EnterCombat(Unit* who) OVERRIDE + void EnterCombat(Unit* /*who*/) OVERRIDE { - if ((instance && instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) == IN_PROGRESS) || !who) - return; } void AttackStart(Unit* victim) OVERRIDE { - if ((instance && instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) == IN_PROGRESS) || !victim) + if ((instance && instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) == IN_PROGRESS) || !victim) return; ScriptedAI::AttackStart(victim); @@ -429,7 +422,7 @@ public: void MoveInLineOfSight(Unit* who) OVERRIDE { - if ((instance && instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) == IN_PROGRESS) || !who) + if ((instance && instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) == IN_PROGRESS) || !who) return; ScriptedAI::MoveInLineOfSight(who); @@ -482,14 +475,14 @@ public: } if (!bWalking) { - if (instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) != IN_PROGRESS && me->HasAura(SPELL_SPHERE_VISUAL)) + if (instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) != IN_PROGRESS && me->HasAura(SPELL_SPHERE_VISUAL)) { me->RemoveAurasDueToSpell(SPELL_SPHERE_VISUAL); me->ApplySpellImmune(0, IMMUNITY_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, false); me->ApplySpellImmune(0, IMMUNITY_DAMAGE, SPELL_SCHOOL_MASK_MAGIC, false); me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE + UNIT_FLAG_NON_ATTACKABLE); } - if (instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) == IN_PROGRESS && !me->HasAura(SPELL_SPHERE_VISUAL)) + if (instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) == IN_PROGRESS && !me->HasAura(SPELL_SPHERE_VISUAL)) { DoCast(me, SPELL_SPHERE_VISUAL, false); me->ApplySpellImmune(0, IMMUNITY_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, true); @@ -561,7 +554,7 @@ public: if (!bRemoved && me->GetPositionX() > 440.0f) { - if (instance->GetData(DATA_PRINCE_TALDARAM_EVENT) == DONE) + if (instance->GetBossState(DATA_PRINCE_TALDARAM) == DONE) { me->InterruptNonMeleeSpells(true); bRemoved = true; @@ -585,7 +578,7 @@ public: me->InterruptNonMeleeSpells(true); bCasted2 = false; } - if (!bRemoved2 && instance->GetData(DATA_JEDOGA_SHADOWSEEKER_EVENT) == DONE) + if (!bRemoved2 && instance->GetBossState(DATA_JEDOGA_SHADOWSEEKER) == DONE) { me->InterruptNonMeleeSpells(true); bRemoved2 = true; diff --git a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_prince_taldaram.cpp b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_prince_taldaram.cpp index 2cfc714c1f7..2f01cc734e6 100644 --- a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_prince_taldaram.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/boss_prince_taldaram.cpp @@ -69,11 +69,6 @@ enum CombatPhase VANISHED, FEEDING }; -enum GameObjects -{ - GO_SPHERE1 = 193093, - GO_SPHERE2 = 193094 -}; class boss_taldaram : public CreatureScript { @@ -113,13 +108,13 @@ public: uiPhaseTimer = 0; uiEmbraceTarget = 0; if (instance) - instance->SetData(DATA_PRINCE_TALDARAM_EVENT, NOT_STARTED); + instance->SetBossState(DATA_PRINCE_TALDARAM, NOT_STARTED); } void EnterCombat(Unit* /*who*/) OVERRIDE { if (instance) - instance->SetData(DATA_PRINCE_TALDARAM_EVENT, IN_PROGRESS); + instance->SetBossState(DATA_PRINCE_TALDARAM, IN_PROGRESS); Talk(SAY_AGGRO); } @@ -267,7 +262,7 @@ public: Talk(SAY_DEATH); if (instance) - instance->SetData(DATA_PRINCE_TALDARAM_EVENT, DONE); + instance->SetBossState(DATA_PRINCE_TALDARAM, DONE); } void KilledUnit(Unit* victim) OVERRIDE @@ -287,21 +282,10 @@ public: bool CheckSpheres() { - if (!instance) - return false; - - uint64 uiSphereGuids[2]; - uiSphereGuids[0] = instance->GetData64(DATA_SPHERE1); - uiSphereGuids[1] = instance->GetData64(DATA_SPHERE2); - - for (uint8 i=0; i < 2; ++i) - { - GameObject* pSpheres = instance->instance->GetGameObject(uiSphereGuids[i]); - if (!pSpheres) + for (uint8 i = 0; i < 2; ++i) + if (!instance->GetData(DATA_SPHERE_1 + i)) return false; - if (pSpheres->GetGoState() != GO_STATE_ACTIVE) - return false; - } + RemovePrison(); return true; } @@ -332,7 +316,7 @@ public: CreatureAI* GetAI(Creature* creature) const OVERRIDE { - return new boss_taldaramAI(creature); + return GetAhnKahetAI<boss_taldaramAI>(creature); } }; @@ -390,39 +374,38 @@ public: class prince_taldaram_sphere : public GameObjectScript { -public: - prince_taldaram_sphere() : GameObjectScript("prince_taldaram_sphere") { } - - bool OnGossipHello(Player* /*player*/, GameObject* go) OVERRIDE - { - InstanceScript* instance = go->GetInstanceScript(); - if (!instance) - return true; + public: + prince_taldaram_sphere() : GameObjectScript("prince_taldaram_sphere") { } - Creature* pPrinceTaldaram = Unit::GetCreature(*go, instance->GetData64(DATA_PRINCE_TALDARAM)); - if (pPrinceTaldaram && pPrinceTaldaram->IsAlive()) + bool OnGossipHello(Player* /*player*/, GameObject* go) { - // maybe these are hacks :( - go->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); - go->SetGoState(GO_STATE_ACTIVE); + InstanceScript* instance = go->GetInstanceScript(); + if (!instance) + return false; - switch (go->GetEntry()) + Creature* PrinceTaldaram = ObjectAccessor::GetCreature(*go, instance->GetData64(DATA_PRINCE_TALDARAM)); + if (PrinceTaldaram && PrinceTaldaram->IsAlive()) { - case GO_SPHERE1: - instance->SetData(DATA_SPHERE1_EVENT, IN_PROGRESS); - pPrinceTaldaram->AI()->Talk(SAY_1); - break; + // maybe these are hacks :( + go->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); + go->SetGoState(GO_STATE_ACTIVE); - case GO_SPHERE2: - instance->SetData(DATA_SPHERE2_EVENT, IN_PROGRESS); - pPrinceTaldaram->AI()->Talk(SAY_1); - break; - } + switch (go->GetEntry()) + { + case GO_SPHERE_1: + instance->SetData(DATA_SPHERE_1, IN_PROGRESS); + PrinceTaldaram->AI()->Talk(SAY_1); + break; + case GO_SPHERE_2: + instance->SetData(DATA_SPHERE_2, IN_PROGRESS); + PrinceTaldaram->AI()->Talk(SAY_1); + break; + } - CAST_AI(boss_taldaram::boss_taldaramAI, pPrinceTaldaram->AI())->CheckSpheres(); + CAST_AI(boss_taldaram::boss_taldaramAI, PrinceTaldaram->AI())->CheckSpheres(); + } + return true; } - return true; - } }; void AddSC_boss_taldaram() diff --git a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/instance_ahnkahet.cpp b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/instance_ahnkahet.cpp index a7b82583d08..7207bbd3aab 100644 --- a/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/instance_ahnkahet.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/Ahnkahet/instance_ahnkahet.cpp @@ -20,321 +20,314 @@ #include "InstanceScript.h" #include "ahnkahet.h" -/* Ahn'kahet encounters: -0 - Elder Nadox -1 - Prince Taldaram -2 - Jedoga Shadowseeker -3 - Herald Volazj -4 - Amanitar (Heroic only) -*/ - -#define MAX_ENCOUNTER 5 - -enum Achievements +DoorData const doorData[] = { - ACHIEV_VOLUNTEER_WORK = 2056 + { GO_PRINCE_TALDARAM_GATE, DATA_PRINCE_TALDARAM, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { 0, 0, DOOR_TYPE_ROOM, BOUNDARY_NONE } // END }; class instance_ahnkahet : public InstanceMapScript { -public: - instance_ahnkahet() : InstanceMapScript("instance_ahnkahet", 619) { } - - struct instance_ahnkahet_InstanceScript : public InstanceScript - { - instance_ahnkahet_InstanceScript(Map* map) : InstanceScript(map) {} - - uint64 Elder_Nadox; - uint64 Prince_Taldaram; - uint64 Jedoga_Shadowseeker; - uint64 Herald_Volazj; - uint64 Amanitar; - - uint64 Prince_TaldaramSpheres[2]; - uint64 Prince_TaldaramPlatform; - uint64 Prince_TaldaramGate; - - std::set<uint64> InitiandGUIDs; - uint64 JedogaSacrifices; - uint64 JedogaTarget; + public: + instance_ahnkahet() : InstanceMapScript(AhnKahetScriptName, 619) { } - uint32 m_auiEncounter[MAX_ENCOUNTER]; - uint32 spheres[2]; + struct instance_ahnkahet_InstanceScript : public InstanceScript + { + instance_ahnkahet_InstanceScript(Map* map) : InstanceScript(map) + { + SetBossNumber(EncounterCount); + LoadDoorData(doorData); - uint8 InitiandCnt; - uint8 switchtrigger; + ElderNadoxGUID = 0; + PrinceTaldaramGUID = 0; + JedogaShadowseekerGUID = 0; + AmanitarGUID = 0; + HeraldVolazjGUID = 0; - std::string str_data; + PrinceTaldaramPlatformGUID = 0; + JedogaSacrifices = 0; + JedogaTarget = 0; + SwitchTrigger = 0; - void Initialize() OVERRIDE - { - memset(&m_auiEncounter, 0, sizeof(m_auiEncounter)); - InitiandGUIDs.clear(); - - Elder_Nadox =0; - Prince_Taldaram =0; - Jedoga_Shadowseeker =0; - Herald_Volazj =0; - Amanitar =0; - - spheres[0] = NOT_STARTED; - spheres[1] = NOT_STARTED; - - InitiandCnt = 0; - switchtrigger = 0; - JedogaSacrifices = 0; - JedogaTarget = 0; - } + SpheresState[0] = 0; + SpheresState[1] = 0; - bool IsEncounterInProgress() const OVERRIDE - { - for (uint8 i = 0; i < MAX_ENCOUNTER; ++i) - if (m_auiEncounter[i] == IN_PROGRESS) - return true; + InitiandGUIDs.clear(); + } - return false; - } + void OnCreatureCreate(Creature* creature) OVERRIDE + { + switch (creature->GetEntry()) + { + case NPC_ELDER_NADOX: + ElderNadoxGUID = creature->GetGUID(); + break; + case NPC_PRINCE_TALDARAM: + PrinceTaldaramGUID = creature->GetGUID(); + break; + case NPC_JEDOGA_SHADOWSEEKER: + JedogaShadowseekerGUID = creature->GetGUID(); + break; + case NPC_AMANITAR: + AmanitarGUID = creature->GetGUID(); + break; + case NPC_HERALD_VOLAZJ: + HeraldVolazjGUID = creature->GetGUID(); + break; + case NPC_INITIAND: + InitiandGUIDs.insert(creature->GetGUID()); + break; + default: + break; + } + } - void OnCreatureCreate(Creature* creature) OVERRIDE - { - switch (creature->GetEntry()) + void OnGameObjectCreate(GameObject* go) OVERRIDE { - case 29309: Elder_Nadox = creature->GetGUID(); break; - case 29308: Prince_Taldaram = creature->GetGUID(); break; - case 29310: Jedoga_Shadowseeker = creature->GetGUID(); break; - case 29311: Herald_Volazj = creature->GetGUID(); break; - case 30258: Amanitar = creature->GetGUID(); break; - case 30114: InitiandGUIDs.insert(creature->GetGUID()); break; + switch (go->GetEntry()) + { + case GO_PRINCE_TALDARAM_PLATFORM: + PrinceTaldaramPlatformGUID = go->GetGUID(); + if (GetBossState(DATA_PRINCE_TALDARAM) == DONE) + HandleGameObject(0, true, go); + break; + case GO_SPHERE_1: + if (SpheresState[0]) + { + go->SetGoState(GO_STATE_ACTIVE); + go->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); + } + else + go->RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); + break; + case GO_SPHERE_2: + if (SpheresState[1]) + { + go->SetGoState(GO_STATE_ACTIVE); + go->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); + } + else + go->RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); + break; + case GO_PRINCE_TALDARAM_GATE: + AddDoor(go, true); + break; + default: + break; + } } - } - void OnGameObjectCreate(GameObject* go) OVERRIDE - { - switch (go->GetEntry()) + void OnGameObjectRemove(GameObject* go) OVERRIDE { - case 193564: - Prince_TaldaramPlatform = go->GetGUID(); - if (m_auiEncounter[1] == DONE) - HandleGameObject(0, true, go); - break; - - case 193093: - Prince_TaldaramSpheres[0] = go->GetGUID(); - if (spheres[0] == IN_PROGRESS) - { - go->SetGoState(GO_STATE_ACTIVE); - go->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); - } - else - go->RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); - break; - case 193094: - Prince_TaldaramSpheres[1] = go->GetGUID(); - if (spheres[1] == IN_PROGRESS) - { - go->SetGoState(GO_STATE_ACTIVE); - go->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); - } - else - go->RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); - break; - case 192236: - Prince_TaldaramGate = go->GetGUID(); // Web gate past Prince Taldaram - if (m_auiEncounter[1] == DONE) - HandleGameObject(0, true, go); - break; + switch (go->GetEntry()) + { + case GO_PRINCE_TALDARAM_GATE: + AddDoor(go, false); + break; + default: + break; + } } - } - void SetData64(uint32 idx, uint64 guid) OVERRIDE - { - switch (idx) + void SetData(uint32 type, uint32 data) OVERRIDE { - case DATA_ADD_JEDOGA_OPFER: - JedogaSacrifices = guid; - break; + switch (type) + { + case DATA_SPHERE_1: + case DATA_SPHERE_2: + SpheresState[type - DATA_SPHERE_1] = data; + break; + case DATA_JEDOGA_TRIGGER_SWITCH: + SwitchTrigger = data; + break; + case DATA_JEDOGA_RESET_INITIANDS: + for (std::set<uint64>::const_iterator itr = InitiandGUIDs.begin(); itr != InitiandGUIDs.end(); ++itr) + { + if (Creature* creature = instance->GetCreature(*itr)) + { + creature->Respawn(); + if (!creature->IsInEvadeMode()) + creature->AI()->EnterEvadeMode(); + } + } + break; + default: + break; + } + } - case DATA_PL_JEDOGA_TARGET: - JedogaTarget = guid; - break; + uint32 GetData(uint32 type) const OVERRIDE + { + switch (type) + { + case DATA_SPHERE_1: + case DATA_SPHERE_2: + return SpheresState[type - DATA_SPHERE_1]; + case DATA_ALL_INITIAND_DEAD: + for (std::set<uint64>::const_iterator itr = InitiandGUIDs.begin(); itr != InitiandGUIDs.end(); ++itr) + { + Creature* cr = instance->GetCreature(*itr); + if (!cr || cr->IsAlive()) + return 0; + } + return 1; + case DATA_JEDOGA_TRIGGER_SWITCH: + return SwitchTrigger; + default: + break; + } + return 0; } - } - uint64 GetData64(uint32 identifier) const OVERRIDE - { - switch (identifier) + void SetData64(uint32 type, uint64 data) OVERRIDE { - case DATA_ELDER_NADOX: return Elder_Nadox; - case DATA_PRINCE_TALDARAM: return Prince_Taldaram; - case DATA_JEDOGA_SHADOWSEEKER: return Jedoga_Shadowseeker; - case DATA_HERALD_VOLAZJ: return Herald_Volazj; - case DATA_AMANITAR: return Amanitar; - case DATA_SPHERE1: return Prince_TaldaramSpheres[0]; - case DATA_SPHERE2: return Prince_TaldaramSpheres[1]; - case DATA_PRINCE_TALDARAM_PLATFORM: return Prince_TaldaramPlatform; - case DATA_ADD_JEDOGA_INITIAND: + switch (type) { - std::vector<uint64> vInitiands; - vInitiands.clear(); - for (std::set<uint64>::const_iterator itr = InitiandGUIDs.begin(); itr != InitiandGUIDs.end(); ++itr) - { - Creature* cr = instance->GetCreature(*itr); - if (cr && cr->IsAlive()) - vInitiands.push_back(*itr); - } - if (vInitiands.empty()) - return 0; - uint8 j = urand(0, vInitiands.size() -1); - return vInitiands[j]; + case DATA_ADD_JEDOGA_OPFER: + JedogaSacrifices = data; + break; + case DATA_PL_JEDOGA_TARGET: + JedogaTarget = data; + break; + default: + break; } - case DATA_ADD_JEDOGA_OPFER: return JedogaSacrifices; - case DATA_PL_JEDOGA_TARGET: return JedogaTarget; } - return 0; - } - void SetData(uint32 type, uint32 data) OVERRIDE - { - switch (type) + uint64 GetData64(uint32 type) const OVERRIDE { - case DATA_ELDER_NADOX_EVENT: - m_auiEncounter[0] = data; - break; - case DATA_PRINCE_TALDARAM_EVENT: - if (data == DONE) - HandleGameObject(Prince_TaldaramGate, true); - m_auiEncounter[1] = data; - break; - case DATA_JEDOGA_SHADOWSEEKER_EVENT: - m_auiEncounter[2] = data; - if (data == DONE) + switch (type) + { + case DATA_ELDER_NADOX: + return ElderNadoxGUID; + case DATA_PRINCE_TALDARAM: + return PrinceTaldaramGUID; + case DATA_JEDOGA_SHADOWSEEKER: + return JedogaShadowseekerGUID; + case DATA_AMANITAR: + return AmanitarGUID; + case DATA_HERALD_VOLAZJ: + return HeraldVolazjGUID; + case DATA_PRINCE_TALDARAM_PLATFORM: + return PrinceTaldaramPlatformGUID; + case DATA_ADD_JEDOGA_INITIAND: { + std::vector<uint64> vInitiands; + vInitiands.clear(); for (std::set<uint64>::const_iterator itr = InitiandGUIDs.begin(); itr != InitiandGUIDs.end(); ++itr) { Creature* cr = instance->GetCreature(*itr); if (cr && cr->IsAlive()) - { - cr->SetVisible(false); - cr->setDeathState(JUST_DIED); - cr->RemoveCorpse(); - } + vInitiands.push_back(*itr); } + if (vInitiands.empty()) + return 0; + + return Trinity::Containers::SelectRandomContainerElement(vInitiands); } - break; - case DATA_HERALD_VOLAZJ_EVENT: - m_auiEncounter[3] = data; - break; - case DATA_AMANITAR_EVENT: - m_auiEncounter[4] = data; - break; - case DATA_SPHERE1_EVENT: - spheres[0] = data; - break; - case DATA_SPHERE2_EVENT: - spheres[1] = data; - break; - case DATA_JEDOGA_TRIGGER_SWITCH: - switchtrigger = data; - break; - case DATA_JEDOGA_RESET_INITIANDS: - for (std::set<uint64>::const_iterator itr = InitiandGUIDs.begin(); itr != InitiandGUIDs.end(); ++itr) - { - Creature* cr = instance->GetCreature(*itr); - if (cr) + case DATA_ADD_JEDOGA_OPFER: + return JedogaSacrifices; + case DATA_PL_JEDOGA_TARGET: + return JedogaTarget; + default: + break; + } + return 0; + } + + bool SetBossState(uint32 type, EncounterState state) OVERRIDE + { + if (!InstanceScript::SetBossState(type, state)) + return false; + + switch (type) + { + case DATA_JEDOGA_SHADOWSEEKER: + if (state == DONE) { - cr->Respawn(); - if (!cr->IsInEvadeMode()) cr->AI()->EnterEvadeMode(); + for (std::set<uint64>::const_iterator itr = InitiandGUIDs.begin(); itr != InitiandGUIDs.end(); ++itr) + { + if (Creature* cr = instance->GetCreature(*itr)) + cr->DespawnOrUnsummon(); + } } - } - break; + break; + default: + break; + } + return true; } - if (data == DONE) - SaveToDB(); - } - uint32 GetData(uint32 type) const OVERRIDE - { - switch (type) + std::string GetSaveData() OVERRIDE { - case DATA_ELDER_NADOX_EVENT: return m_auiEncounter[0]; - case DATA_PRINCE_TALDARAM_EVENT: return m_auiEncounter[1]; - case DATA_JEDOGA_SHADOWSEEKER_EVENT: return m_auiEncounter[2]; - case DATA_HERALD_VOLAZJ: return m_auiEncounter[3]; - case DATA_AMANITAR_EVENT: return m_auiEncounter[4]; - case DATA_SPHERE1_EVENT: return spheres[0]; - case DATA_SPHERE2_EVENT: return spheres[1]; - case DATA_ALL_INITIAND_DEAD: - for (std::set<uint64>::const_iterator itr = InitiandGUIDs.begin(); itr != InitiandGUIDs.end(); ++itr) - { - Creature* cr = instance->GetCreature(*itr); - if (!cr || (cr && cr->IsAlive())) - return 0; - } - return 1; - case DATA_JEDOGA_TRIGGER_SWITCH: return switchtrigger; - } - return 0; - } + OUT_SAVE_INST_DATA; - std::string GetSaveData() OVERRIDE - { - OUT_SAVE_INST_DATA; + std::ostringstream saveStream; + saveStream << "A K " << GetBossSaveData() << SpheresState[0] << ' ' << SpheresState[1]; - std::ostringstream saveStream; - saveStream << "A K " << m_auiEncounter[0] << ' ' << m_auiEncounter[1] << ' ' - << m_auiEncounter[2] << ' ' << m_auiEncounter[3] << ' ' << m_auiEncounter[4] << ' ' - << spheres[0] << ' ' << spheres[1]; + OUT_SAVE_INST_DATA_COMPLETE; + return saveStream.str(); + } - str_data = saveStream.str(); + void Load(char const* str) OVERRIDE + { + if (!str) + { + OUT_LOAD_INST_DATA_FAIL; + return; + } - OUT_SAVE_INST_DATA_COMPLETE; - return str_data; - } + OUT_LOAD_INST_DATA(str); - void Load(const char* in) OVERRIDE - { - if (!in) - { - OUT_LOAD_INST_DATA_FAIL; - return; - } + char dataHead1, dataHead2; - OUT_LOAD_INST_DATA(in); + std::istringstream loadStream(str); + loadStream >> dataHead1 >> dataHead2; + + if (dataHead1 == 'A' && dataHead2 == 'K') + { + for (uint32 i = 0; i < EncounterCount; ++i) + { + uint32 tmpState; + loadStream >> tmpState; + if (tmpState == IN_PROGRESS || tmpState > SPECIAL) + tmpState = NOT_STARTED; + SetBossState(i, EncounterState(tmpState)); + } - char dataHead1, dataHead2; - uint16 data0, data1, data2, data3, data4, data5, data6; + loadStream >> SpheresState[0]; + loadStream >> SpheresState[1]; + } + else + OUT_LOAD_INST_DATA_FAIL; - std::istringstream loadStream(in); - loadStream >> dataHead1 >> dataHead2 >> data0 >> data1 >> data2 >> data3 >> data4 >> data5 >> data6; + OUT_LOAD_INST_DATA_COMPLETE; + } - if (dataHead1 == 'A' && dataHead2 == 'K') - { - m_auiEncounter[0] = data0; - m_auiEncounter[1] = data1; - m_auiEncounter[2] = data2; - m_auiEncounter[3] = data3; - m_auiEncounter[4] = data4; + protected: + uint64 ElderNadoxGUID; + uint64 PrinceTaldaramGUID; + uint64 JedogaShadowseekerGUID; + uint64 AmanitarGUID; + uint64 HeraldVolazjGUID; - for (uint8 i = 0; i < MAX_ENCOUNTER; ++i) - if (m_auiEncounter[i] == IN_PROGRESS) - m_auiEncounter[i] = NOT_STARTED; + uint64 PrinceTaldaramPlatformGUID; + uint64 JedogaSacrifices; + uint64 JedogaTarget; - spheres[0] = data5; - spheres[1] = data6; + std::set<uint64> InitiandGUIDs; - } else OUT_LOAD_INST_DATA_FAIL; + uint8 SpheresState[2]; + uint8 SwitchTrigger; + }; - OUT_LOAD_INST_DATA_COMPLETE; + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_ahnkahet_InstanceScript(map); } - }; - - InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE - { - return new instance_ahnkahet_InstanceScript(map); - } }; void AddSC_instance_ahnkahet() { - new instance_ahnkahet(); + new instance_ahnkahet(); } diff --git a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/azjol_nerub.h b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/azjol_nerub.h index 5970a85cc38..5087ed0cec3 100644 --- a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/azjol_nerub.h +++ b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/azjol_nerub.h @@ -15,24 +15,49 @@ * with this program. If not, see <http://www.gnu.org/licenses/>. */ -#ifndef DEF_AZJOL_NERUB_H -#define DEF_AZJOL_NERUB_H +#ifndef AZJOL_NERUB_H_ +#define AZJOL_NERUB_H_ -enum Data64 +#define AzjolNerubScriptName "instance_azjol_nerub" + +uint32 const EncounterCount = 3; + +enum DataTypes { - DATA_KRIKTHIR_THE_GATEWATCHER, - DATA_HADRONOX, - DATA_ANUBARAK, - DATA_WATCHER_GASHRA, - DATA_WATCHER_SILTHIK, - DATA_WATCHER_NARJIL + // Encounter States/Boss GUIDs + DATA_KRIKTHIR_THE_GATEWATCHER = 0, + DATA_HADRONOX = 1, + DATA_ANUBARAK = 2, + + // Additional Data + DATA_WATCHER_GASHRA = 3, + DATA_WATCHER_SILTHIK = 4, + DATA_WATCHER_NARJIL = 5 }; -enum Data +enum CreatureIds { - DATA_KRIKTHIR_THE_GATEWATCHER_EVENT, - DATA_HADRONOX_EVENT, - DATA_ANUBARAK_EVENT + NPC_KRIKTHIR = 28684, + NPC_HADRONOX = 28921, + NPC_ANUBARAK = 29120, + + NPC_WATCHER_NARJIL = 28729, + NPC_WATCHER_GASHRA = 28730, + NPC_WATCHER_SILTHIK = 28731 }; -#endif +enum GameObjectIds +{ + GO_KRIKTHIR_DOOR = 192395, + GO_ANUBARAK_DOOR_1 = 192396, + GO_ANUBARAK_DOOR_2 = 192397, + GO_ANUBARAK_DOOR_3 = 192398 +}; + +template<class AI> +AI* GetAzjolNerubAI(Creature* creature) +{ + return GetInstanceAI<AI>(creature, AzjolNerubScriptName); +} + +#endif // AZJOL_NERUB_H_ diff --git a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_anubarak.cpp b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_anubarak.cpp index 05e758f5cf9..81530265617 100644 --- a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_anubarak.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_anubarak.cpp @@ -132,7 +132,7 @@ public: if (instance) { - instance->SetData(DATA_ANUBARAK_EVENT, NOT_STARTED); + instance->SetBossState(DATA_ANUBARAK, NOT_STARTED); instance->DoStopTimedAchievement(ACHIEVEMENT_TIMED_TYPE_EVENT, ACHIEV_TIMED_START_EVENT); } } @@ -165,7 +165,7 @@ public: void DelayEventStart() { if (instance) - instance->SetData(DATA_ANUBARAK_EVENT, IN_PROGRESS); + instance->SetBossState(DATA_ANUBARAK, IN_PROGRESS); } void UpdateAI(uint32 diff) OVERRIDE @@ -336,7 +336,7 @@ public: Talk(SAY_DEATH); Summons.DespawnAll(); if (instance) - instance->SetData(DATA_ANUBARAK_EVENT, DONE); + instance->SetBossState(DATA_ANUBARAK, DONE); } void KilledUnit(Unit* victim) OVERRIDE diff --git a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_hadronox.cpp b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_hadronox.cpp index 6b556f4fe4d..1664a1375ae 100644 --- a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_hadronox.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_hadronox.cpp @@ -84,8 +84,8 @@ public: uiDoorsTimer = urand(20*IN_MILLISECONDS, 30*IN_MILLISECONDS); uiCheckDistanceTimer = 2*IN_MILLISECONDS; - if (instance && (instance->GetData(DATA_HADRONOX_EVENT) != DONE && !bFirstTime)) - instance->SetData(DATA_HADRONOX_EVENT, FAIL); + if (instance && (instance->GetBossState(DATA_HADRONOX) != DONE && !bFirstTime)) + instance->SetBossState(DATA_HADRONOX, FAIL); bFirstTime = false; } @@ -103,13 +103,13 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (instance) - instance->SetData(DATA_HADRONOX_EVENT, DONE); + instance->SetBossState(DATA_HADRONOX, DONE); } void EnterCombat(Unit* /*who*/) OVERRIDE { if (instance) - instance->SetData(DATA_HADRONOX_EVENT, IN_PROGRESS); + instance->SetBossState(DATA_HADRONOX, IN_PROGRESS); me->SetInCombatWithZone(); } diff --git a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_krikthir_the_gatewatcher.cpp b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_krikthir_the_gatewatcher.cpp index 2222d16f68b..c5e40052a9d 100644 --- a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_krikthir_the_gatewatcher.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/boss_krikthir_the_gatewatcher.cpp @@ -105,7 +105,7 @@ public: uiCurseFatigueTimer = 12*IN_MILLISECONDS; if (instance) - instance->SetData(DATA_KRIKTHIR_THE_GATEWATCHER_EVENT, NOT_STARTED); + instance->SetBossState(DATA_KRIKTHIR_THE_GATEWATCHER, NOT_STARTED); } void EnterCombat(Unit* /*who*/) OVERRIDE @@ -115,7 +115,7 @@ public: uiSummonTimer = 15*IN_MILLISECONDS; if (instance) - instance->SetData(DATA_KRIKTHIR_THE_GATEWATCHER_EVENT, IN_PROGRESS); + instance->SetBossState(DATA_KRIKTHIR_THE_GATEWATCHER, IN_PROGRESS); } void Summon() @@ -176,7 +176,7 @@ public: Talk(SAY_DEATH); if (instance) - instance->SetData(DATA_KRIKTHIR_THE_GATEWATCHER_EVENT, DONE); + instance->SetBossState(DATA_KRIKTHIR_THE_GATEWATCHER, DONE); } void KilledUnit(Unit* victim) OVERRIDE @@ -537,15 +537,14 @@ class achievement_watch_him_die : public AchievementCriteriaScript return false; InstanceScript* instance = target->GetInstanceScript(); - Creature* Watcher[3]; if (!instance) return false; for (uint8 n = 0; n < 3; ++n) { - Watcher[n] = ObjectAccessor::GetCreature(*target, instance->GetData64(DATA_WATCHER_GASHRA + n)); - if (Watcher[n] && !Watcher[n]->IsAlive()) - return false; + if (Creature* watcher = ObjectAccessor::GetCreature(*target, instance->GetData64(DATA_WATCHER_GASHRA + n))) + if (!watcher->IsAlive()) + return false; } return true; diff --git a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/instance_azjol_nerub.cpp b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/instance_azjol_nerub.cpp index 261a2748579..b20a28b7a75 100644 --- a/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/instance_azjol_nerub.cpp +++ b/src/server/scripts/Northrend/AzjolNerub/AzjolNerub/instance_azjol_nerub.cpp @@ -19,196 +19,171 @@ #include "InstanceScript.h" #include "azjol_nerub.h" -#define MAX_ENCOUNTER 3 - -/* Azjol Nerub encounters: -0 - Krik'thir the Gatewatcher -1 - Hadronox -2 - Anub'arak -*/ +DoorData const doorData[] = +{ + { GO_KRIKTHIR_DOOR, DATA_KRIKTHIR_THE_GATEWATCHER, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_ANUBARAK_DOOR_1, DATA_ANUBARAK, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { GO_ANUBARAK_DOOR_2, DATA_ANUBARAK, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { GO_ANUBARAK_DOOR_3, DATA_ANUBARAK, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { 0, 0, DOOR_TYPE_ROOM, BOUNDARY_NONE } // END +}; class instance_azjol_nerub : public InstanceMapScript { -public: - instance_azjol_nerub() : InstanceMapScript("instance_azjol_nerub", 601) { } - - struct instance_azjol_nerub_InstanceScript : public InstanceScript - { - instance_azjol_nerub_InstanceScript(Map* map) : InstanceScript(map) {} - - uint64 uiKrikthir; - uint64 uiHadronox; - uint64 uiAnubarak; - uint64 uiWatcherGashra; - uint64 uiWatcherSilthik; - uint64 uiWatcherNarjil; - uint64 uiAnubarakDoor[3]; - - uint64 uiKrikthirDoor; - - uint32 auiEncounter[MAX_ENCOUNTER]; - - void Initialize() OVERRIDE - { - memset(&auiEncounter, 0, sizeof(auiEncounter)); - memset(&uiAnubarakDoor, 0, sizeof(uiAnubarakDoor)); - - uiKrikthir = 0; - uiHadronox = 0; - uiAnubarak = 0; - uiWatcherGashra = 0; - uiWatcherSilthik = 0; - uiWatcherNarjil = 0; - uiKrikthirDoor = 0; - } + public: + instance_azjol_nerub() : InstanceMapScript(AzjolNerubScriptName, 601) { } - bool IsEncounterInProgress() const OVERRIDE + struct instance_azjol_nerub_InstanceScript : public InstanceScript { - for (uint8 i = 0; i < MAX_ENCOUNTER; ++i) - if (auiEncounter[i] == IN_PROGRESS) - return true; - - return false; - } - - void OnCreatureCreate(Creature* creature) OVERRIDE - { - switch (creature->GetEntry()) + instance_azjol_nerub_InstanceScript(Map* map) : InstanceScript(map) { - case 28684: uiKrikthir = creature->GetGUID(); break; - case 28921: uiHadronox = creature->GetGUID(); break; - case 29120: uiAnubarak = creature->GetGUID(); break; - case 28730: uiWatcherGashra = creature->GetGUID(); break; - case 28731: uiWatcherSilthik = creature->GetGUID(); break; - case 28729: uiWatcherNarjil = creature->GetGUID(); break; + SetBossNumber(EncounterCount); + LoadDoorData(doorData); + + KrikthirGUID = 0; + HadronoxGUID = 0; + AnubarakGUID = 0; + WatcherGashraGUID = 0; + WatcherSilthikGUID = 0; + WatcherNarjilGUID = 0; } - } - void OnGameObjectCreate(GameObject* go) OVERRIDE - { - switch (go->GetEntry()) + void OnCreatureCreate(Creature* creature) OVERRIDE { - case 192395: - uiKrikthirDoor = go->GetGUID(); - if (auiEncounter[0] == DONE) - HandleGameObject(0, true, go); - break; - case 192396: - uiAnubarakDoor[0] = go->GetGUID(); - break; - case 192397: - uiAnubarakDoor[1] = go->GetGUID(); - break; - case 192398: - uiAnubarakDoor[2] = go->GetGUID(); - break; + switch (creature->GetEntry()) + { + case NPC_KRIKTHIR: + KrikthirGUID = creature->GetGUID(); + break; + case NPC_HADRONOX: + HadronoxGUID = creature->GetGUID(); + break; + case NPC_ANUBARAK: + AnubarakGUID = creature->GetGUID(); + break; + case NPC_WATCHER_NARJIL: + WatcherNarjilGUID = creature->GetGUID(); + break; + case NPC_WATCHER_GASHRA: + WatcherGashraGUID = creature->GetGUID(); + break; + case NPC_WATCHER_SILTHIK: + WatcherSilthikGUID = creature->GetGUID(); + break; + default: + break; + } } - } - uint64 GetData64(uint32 identifier) const OVERRIDE - { - switch (identifier) + void OnGameObjectCreate(GameObject* go) OVERRIDE { - case DATA_KRIKTHIR_THE_GATEWATCHER: return uiKrikthir; - case DATA_HADRONOX: return uiHadronox; - case DATA_ANUBARAK: return uiAnubarak; - case DATA_WATCHER_GASHRA: return uiWatcherGashra; - case DATA_WATCHER_SILTHIK: return uiWatcherSilthik; - case DATA_WATCHER_NARJIL: return uiWatcherNarjil; + switch (go->GetEntry()) + { + case GO_KRIKTHIR_DOOR: + case GO_ANUBARAK_DOOR_1: + case GO_ANUBARAK_DOOR_2: + case GO_ANUBARAK_DOOR_3: + AddDoor(go, true); + break; + default: + break; + } } - return 0; - } - - void SetData(uint32 type, uint32 data) OVERRIDE - { - switch (type) + void OnGameObjectRemove(GameObject* go) OVERRIDE { - case DATA_KRIKTHIR_THE_GATEWATCHER_EVENT: - auiEncounter[0] = data; - if (data == DONE) - HandleGameObject(uiKrikthirDoor, true); - break; - case DATA_HADRONOX_EVENT: - auiEncounter[1] = data; - break; - case DATA_ANUBARAK_EVENT: - auiEncounter[2] = data; - if (data == IN_PROGRESS) - for (uint8 i = 0; i < 3; ++i) - HandleGameObject(uiAnubarakDoor[i], false); - else if (data == NOT_STARTED || data == DONE) - for (uint8 i = 0; i < 3; ++i) - HandleGameObject(uiAnubarakDoor[i], true); - break; + switch (go->GetEntry()) + { + case GO_KRIKTHIR_DOOR: + case GO_ANUBARAK_DOOR_1: + case GO_ANUBARAK_DOOR_2: + case GO_ANUBARAK_DOOR_3: + AddDoor(go, false); + break; + default: + break; + } } - if (data == DONE) + uint64 GetData64(uint32 type) const OVERRIDE { - SaveToDB(); + switch (type) + { + case DATA_KRIKTHIR_THE_GATEWATCHER: + return KrikthirGUID; + case DATA_HADRONOX: + return HadronoxGUID; + case DATA_ANUBARAK: + return AnubarakGUID; + case DATA_WATCHER_GASHRA: + return WatcherGashraGUID; + case DATA_WATCHER_SILTHIK: + return WatcherSilthikGUID; + case DATA_WATCHER_NARJIL: + return WatcherNarjilGUID; + default: + break; + } + + return 0; } - } - uint32 GetData(uint32 type) const OVERRIDE - { - switch (type) + std::string GetSaveData() OVERRIDE { - case DATA_KRIKTHIR_THE_GATEWATCHER_EVENT: return auiEncounter[0]; - case DATA_HADRONOX_EVENT: return auiEncounter[1]; - case DATA_ANUBARAK_EVENT: return auiEncounter[2]; - } - - return 0; - } - - std::string GetSaveData() OVERRIDE - { - OUT_SAVE_INST_DATA; - - std::ostringstream saveStream; - saveStream << "A N " << auiEncounter[0] << ' ' << auiEncounter[1] << ' ' - << auiEncounter[2]; + OUT_SAVE_INST_DATA; - OUT_SAVE_INST_DATA_COMPLETE; - return saveStream.str(); - } + std::ostringstream saveStream; + saveStream << "A N " << GetBossSaveData(); - void Load(const char* in) OVERRIDE - { - if (!in) - { - OUT_LOAD_INST_DATA_FAIL; - return; + OUT_SAVE_INST_DATA_COMPLETE; + return saveStream.str(); } - OUT_LOAD_INST_DATA(in); - - char dataHead1, dataHead2; - uint16 data0, data1, data2; - - std::istringstream loadStream(in); - loadStream >> dataHead1 >> dataHead2 >> data0 >> data1 >> data2; - - if (dataHead1 == 'A' && dataHead2 == 'N') + void Load(char const* str) OVERRIDE { - auiEncounter[0] = data0; - auiEncounter[1] = data1; - auiEncounter[2] = data2; - - for (uint8 i = 0; i < MAX_ENCOUNTER; ++i) - if (auiEncounter[i] == IN_PROGRESS) - auiEncounter[i] = NOT_STARTED; + if (!str) + { + OUT_LOAD_INST_DATA_FAIL; + return; + } + + OUT_LOAD_INST_DATA(str); + + char dataHead1, dataHead2; + + std::istringstream loadStream(str); + loadStream >> dataHead1 >> dataHead2; + + if (dataHead1 == 'A' && dataHead2 == 'N') + { + for (uint32 i = 0; i < EncounterCount; ++i) + { + uint32 tmpState; + loadStream >> tmpState; + if (tmpState == IN_PROGRESS || tmpState > SPECIAL) + tmpState = NOT_STARTED; + SetBossState(i, EncounterState(tmpState)); + } + } + else + OUT_LOAD_INST_DATA_FAIL; + + OUT_LOAD_INST_DATA_COMPLETE; + } - } else OUT_LOAD_INST_DATA_FAIL; + protected: + uint64 KrikthirGUID; + uint64 HadronoxGUID; + uint64 AnubarakGUID; + uint64 WatcherGashraGUID; + uint64 WatcherSilthikGUID; + uint64 WatcherNarjilGUID; + }; - OUT_LOAD_INST_DATA_COMPLETE; + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_azjol_nerub_InstanceScript(map); } - }; - - InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE - { - return new instance_azjol_nerub_InstanceScript(map); - } }; void AddSC_instance_azjol_nerub() diff --git a/src/server/scripts/Northrend/CrusadersColiseum/TrialOfTheCrusader/boss_northrend_beasts.cpp b/src/server/scripts/Northrend/CrusadersColiseum/TrialOfTheCrusader/boss_northrend_beasts.cpp index 50179d138ae..d90ed543376 100644 --- a/src/server/scripts/Northrend/CrusadersColiseum/TrialOfTheCrusader/boss_northrend_beasts.cpp +++ b/src/server/scripts/Northrend/CrusadersColiseum/TrialOfTheCrusader/boss_northrend_beasts.cpp @@ -352,7 +352,7 @@ class npc_snobold_vassal : public CreatureScript void JustDied(Unit* /*killer*/) OVERRIDE { - if (Unit* target = Unit::GetPlayer(*me, _targetGUID)) + if (Unit* target = ObjectAccessor::GetPlayer(*me, _targetGUID)) if (target->IsAlive()) target->RemoveAurasDueToSpell(SPELL_SNOBOLLED); if (_instance) @@ -379,7 +379,7 @@ class npc_snobold_vassal : public CreatureScript if (!UpdateVictim() || _targetDied) return; - if (Unit* target = Unit::GetPlayer(*me, _targetGUID)) + if (Unit* target = ObjectAccessor::GetPlayer(*me, _targetGUID)) { if (!target->IsAlive()) { @@ -428,13 +428,13 @@ class npc_snobold_vassal : public CreatureScript return; case EVENT_HEAD_CRACK: // commented out while SPELL_SNOBOLLED gets fixed - //if (Unit* target = Unit::GetPlayer(*me, m_uiTargetGUID)) + //if (Unit* target = ObjectAccessor::GetPlayer(*me, m_uiTargetGUID)) DoCastVictim(SPELL_HEAD_CRACK); _events.ScheduleEvent(EVENT_HEAD_CRACK, 30*IN_MILLISECONDS); return; case EVENT_BATTER: // commented out while SPELL_SNOBOLLED gets fixed - //if (Unit* target = Unit::GetPlayer(*me, m_uiTargetGUID)) + //if (Unit* target = ObjectAccessor::GetPlayer(*me, m_uiTargetGUID)) DoCastVictim(SPELL_BATTER); _events.ScheduleEvent(EVENT_BATTER, 10*IN_MILLISECONDS); return; @@ -907,7 +907,7 @@ class boss_icehowl : public CreatureScript else { // Landed from Hop backwards (start trample) - if (Unit::GetPlayer(*me, _trampleTargetGUID)) + if (ObjectAccessor::GetPlayer(*me, _trampleTargetGUID)) _stage = 4; else _stage = 6; @@ -1046,7 +1046,7 @@ class boss_icehowl : public CreatureScript { case EVENT_TRAMPLE: { - if (Unit* target = Unit::GetPlayer(*me, _trampleTargetGUID)) + if (Unit* target = ObjectAccessor::GetPlayer(*me, _trampleTargetGUID)) { me->StopMoving(); me->AttackStop(); diff --git a/src/server/scripts/Northrend/DraktharonKeep/boss_tharon_ja.cpp b/src/server/scripts/Northrend/DraktharonKeep/boss_tharon_ja.cpp index e090f3db7c0..efca060b67c 100644 --- a/src/server/scripts/Northrend/DraktharonKeep/boss_tharon_ja.cpp +++ b/src/server/scripts/Northrend/DraktharonKeep/boss_tharon_ja.cpp @@ -17,29 +17,48 @@ #include "ScriptMgr.h" #include "ScriptedCreature.h" -#include "drak_tharon_keep.h" +#include "SpellScript.h" +#include "SpellAuraEffects.h" #include "Player.h" +#include "drak_tharon_keep.h" + +/* + * Known Issues: Spell 49356 and 53463 will be interrupted for an unknown reason + */ enum Spells { - //skeletal spells (phase 1) + // Skeletal Spells (phase 1) SPELL_CURSE_OF_LIFE = 49527, - H_SPELL_CURSE_OF_LIFE = 59972, SPELL_RAIN_OF_FIRE = 49518, - H_SPELL_RAIN_OF_FIRE = 59971, SPELL_SHADOW_VOLLEY = 49528, - H_SPELL_SHADOW_VOLLEY = 59973, - SPELL_DECAY_FLESH = 49356, //casted at end of phase 1, starts phase 2 - //flesh spells (phase 2) + SPELL_DECAY_FLESH = 49356, // casted at end of phase 1, starts phase 2 + // Flesh Spells (phase 2) SPELL_GIFT_OF_THARON_JA = 52509, + SPELL_CLEAR_GIFT_OF_THARON_JA = 53242, SPELL_EYE_BEAM = 49544, - H_SPELL_EYE_BEAM = 59965, SPELL_LIGHTNING_BREATH = 49537, - H_SPELL_LIGHTNING_BREATH = 59963, SPELL_POISON_CLOUD = 49548, - H_SPELL_POISON_CLOUD = 59969, - SPELL_RETURN_FLESH = 53463, //Channeled spell ending phase two and returning to phase 1. This ability will stun the party for 6 seconds. + SPELL_RETURN_FLESH = 53463, // Channeled spell ending phase two and returning to phase 1. This ability will stun the party for 6 seconds. SPELL_ACHIEVEMENT_CHECK = 61863, + SPELL_FLESH_VISUAL = 52582, + SPELL_DUMMY = 49551 +}; + +enum Events +{ + EVENT_CURSE_OF_LIFE = 1, + EVENT_RAIN_OF_FIRE, + EVENT_SHADOW_VOLLEY, + + EVENT_EYE_BEAM, + EVENT_LIGHTNING_BREATH, + EVENT_POISON_CLOUD, + + EVENT_DECAY_FLESH, + EVENT_GOING_FLESH, + EVENT_RETURN_FLESH, + EVENT_GOING_SKELETAL }; enum Yells @@ -50,204 +69,178 @@ enum Yells SAY_SKELETON = 3, SAY_DEATH = 4 }; + enum Models { - MODEL_FLESH = 27073, - MODEL_SKELETON = 27511 -}; -enum CombatPhase -{ - SKELETAL, - GOING_FLESH, - FLESH, - GOING_SKELETAL + MODEL_FLESH = 27073 }; class boss_tharon_ja : public CreatureScript { -public: - boss_tharon_ja() : CreatureScript("boss_tharon_ja") { } + public: + boss_tharon_ja() : CreatureScript("boss_tharon_ja") { } - struct boss_tharon_jaAI : public ScriptedAI - { - boss_tharon_jaAI(Creature* creature) : ScriptedAI(creature) + struct boss_tharon_jaAI : public BossAI { - instance = creature->GetInstanceScript(); - } - - uint32 uiPhaseTimer; - uint32 uiCurseOfLifeTimer; - uint32 uiRainOfFireTimer; - uint32 uiShadowVolleyTimer; - uint32 uiEyeBeamTimer; - uint32 uiLightningBreathTimer; - uint32 uiPoisonCloudTimer; + boss_tharon_jaAI(Creature* creature) : BossAI(creature, DATA_THARON_JA) { } - CombatPhase Phase; - - InstanceScript* instance; - - void Reset() OVERRIDE - { - uiPhaseTimer = 20*IN_MILLISECONDS; - uiCurseOfLifeTimer = 1*IN_MILLISECONDS; - uiRainOfFireTimer = urand(14*IN_MILLISECONDS, 18*IN_MILLISECONDS); - uiShadowVolleyTimer = urand(8*IN_MILLISECONDS, 10*IN_MILLISECONDS); - Phase = SKELETAL; - me->SetDisplayId(me->GetNativeDisplayId()); - instance->SetBossState(DATA_THARON_JA, NOT_STARTED); - } + void Reset() OVERRIDE + { + _Reset(); + me->RestoreDisplayId(); + } - void EnterCombat(Unit* /*who*/) OVERRIDE - { - Talk(SAY_AGGRO); - instance->SetBossState(DATA_THARON_JA, IN_PROGRESS); - } + void EnterCombat(Unit* /*who*/) OVERRIDE + { + Talk(SAY_AGGRO); + _EnterCombat(); - void UpdateAI(uint32 diff) OVERRIDE - { - //Return since we have no target - if (!UpdateVictim()) - return; + events.ScheduleEvent(EVENT_DECAY_FLESH, 20000); + events.ScheduleEvent(EVENT_CURSE_OF_LIFE, 1000); + events.ScheduleEvent(EVENT_RAIN_OF_FIRE, urand(14000, 18000)); + events.ScheduleEvent(EVENT_SHADOW_VOLLEY, urand(8000, 10000)); + } - switch (Phase) + void KilledUnit(Unit* who) OVERRIDE { - case SKELETAL: - if (uiCurseOfLifeTimer < diff) - { - if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) - DoCast(target, SPELL_CURSE_OF_LIFE); - uiCurseOfLifeTimer = urand(10*IN_MILLISECONDS, 15*IN_MILLISECONDS); - } else uiCurseOfLifeTimer -= diff; + if (who->GetTypeId() == TYPEID_PLAYER) + Talk(SAY_KILL); + } - if (uiShadowVolleyTimer < diff) - { - DoCastVictim(SPELL_SHADOW_VOLLEY); - uiShadowVolleyTimer = urand(8*IN_MILLISECONDS, 10*IN_MILLISECONDS); - } else uiShadowVolleyTimer -= diff; + void JustDied(Unit* /*killer*/) OVERRIDE + { + _JustDied(); - if (uiRainOfFireTimer < diff) - { - DoCastAOE(SPELL_RAIN_OF_FIRE); - uiRainOfFireTimer = urand(14*IN_MILLISECONDS, 18*IN_MILLISECONDS); - } else uiRainOfFireTimer -= diff; + Talk(SAY_DEATH); + DoCastAOE(SPELL_CLEAR_GIFT_OF_THARON_JA, true); + DoCastAOE(SPELL_ACHIEVEMENT_CHECK, true); + } - if (uiPhaseTimer < diff) - { - DoCast(SPELL_DECAY_FLESH); - Phase = GOING_FLESH; - uiPhaseTimer = 6*IN_MILLISECONDS; - } else uiPhaseTimer -= diff; - - DoMeleeAttackIfReady(); - break; - case GOING_FLESH: - if (uiPhaseTimer < diff) - { - Talk(SAY_FLESH); - me->SetDisplayId(MODEL_FLESH); - - std::list<Unit*> playerList; - SelectTargetList(playerList, 5, SELECT_TARGET_TOPAGGRO, 0, true); - for (std::list<Unit*>::const_iterator itr = playerList.begin(); itr != playerList.end(); ++itr) - { - Unit* temp = (*itr); - me->AddAura(SPELL_GIFT_OF_THARON_JA, temp); - temp->SetDisplayId(MODEL_SKELETON); - } - uiPhaseTimer = 20*IN_MILLISECONDS; - uiLightningBreathTimer = urand(3*IN_MILLISECONDS, 4*IN_MILLISECONDS); - uiEyeBeamTimer = urand(4*IN_MILLISECONDS, 8*IN_MILLISECONDS); - uiPoisonCloudTimer = urand(6*IN_MILLISECONDS, 7*IN_MILLISECONDS); - Phase = FLESH; - } else uiPhaseTimer -= diff; - break; - case FLESH: - if (uiLightningBreathTimer < diff) - { - if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) - DoCast(target, SPELL_LIGHTNING_BREATH); - uiLightningBreathTimer = urand(6*IN_MILLISECONDS, 7*IN_MILLISECONDS); - } else uiLightningBreathTimer -= diff; + void UpdateAI(uint32 diff) OVERRIDE + { + if (!UpdateVictim()) + return; - if (uiEyeBeamTimer < diff) - { - if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) - DoCast(target, SPELL_EYE_BEAM); - uiEyeBeamTimer = urand(4*IN_MILLISECONDS, 6*IN_MILLISECONDS); - } else uiEyeBeamTimer -= diff; + events.Update(diff); - if (uiPoisonCloudTimer < diff) - { - DoCastAOE(SPELL_POISON_CLOUD); - uiPoisonCloudTimer = urand(10*IN_MILLISECONDS, 12*IN_MILLISECONDS); - } else uiPoisonCloudTimer -= diff; + if (me->HasUnitState(UNIT_STATE_CASTING)) + return; - if (uiPhaseTimer < diff) - { - DoCast(SPELL_RETURN_FLESH); - Phase = GOING_SKELETAL; - uiPhaseTimer = 6*IN_MILLISECONDS; - } else uiPhaseTimer -= diff; - DoMeleeAttackIfReady(); - break; - case GOING_SKELETAL: - if (uiPhaseTimer < diff) + while (uint32 eventId = events.ExecuteEvent()) + { + switch (eventId) { - Talk(SAY_SKELETON); - me->DeMorph(); - Phase = SKELETAL; - uiPhaseTimer = 20*IN_MILLISECONDS; - uiCurseOfLifeTimer = 1*IN_MILLISECONDS; - uiRainOfFireTimer = urand(14*IN_MILLISECONDS, 18*IN_MILLISECONDS); - uiShadowVolleyTimer = urand(8*IN_MILLISECONDS, 10*IN_MILLISECONDS); - - std::list<Unit*> playerList; - SelectTargetList(playerList, 5, SELECT_TARGET_TOPAGGRO, 0, true); - for (std::list<Unit*>::const_iterator itr = playerList.begin(); itr != playerList.end(); ++itr) - { - Unit* temp = (*itr); - if (temp->HasAura(SPELL_GIFT_OF_THARON_JA)) - temp->RemoveAura(SPELL_GIFT_OF_THARON_JA); - temp->DeMorph(); - } - } else uiPhaseTimer -= diff; - break; + case EVENT_CURSE_OF_LIFE: + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100.0f, true)) + DoCast(target, SPELL_CURSE_OF_LIFE); + events.ScheduleEvent(EVENT_CURSE_OF_LIFE, urand(10000, 15000)); + return; + case EVENT_SHADOW_VOLLEY: + DoCastVictim(SPELL_SHADOW_VOLLEY); + events.ScheduleEvent(EVENT_SHADOW_VOLLEY, urand(8000, 10000)); + return; + case EVENT_RAIN_OF_FIRE: + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100.0f, true)) + DoCast(target, SPELL_RAIN_OF_FIRE); + events.ScheduleEvent(EVENT_RAIN_OF_FIRE, urand(14000, 18000)); + return; + case EVENT_LIGHTNING_BREATH: + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100.0f, true)) + DoCast(target, SPELL_LIGHTNING_BREATH); + events.ScheduleEvent(EVENT_LIGHTNING_BREATH, urand(6000, 7000)); + return; + case EVENT_EYE_BEAM: + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100.0f, true)) + DoCast(target, SPELL_EYE_BEAM); + events.ScheduleEvent(EVENT_EYE_BEAM, urand(4000, 6000)); + return; + case EVENT_POISON_CLOUD: + DoCastAOE(SPELL_POISON_CLOUD); + events.ScheduleEvent(EVENT_POISON_CLOUD, urand(10000, 12000)); + return; + case EVENT_DECAY_FLESH: + DoCastAOE(SPELL_DECAY_FLESH); + events.ScheduleEvent(EVENT_GOING_FLESH, 6000); + return; + case EVENT_GOING_FLESH: + Talk(SAY_FLESH); + me->SetDisplayId(MODEL_FLESH); + DoCastAOE(SPELL_GIFT_OF_THARON_JA, true); + DoCast(me, SPELL_FLESH_VISUAL, true); + DoCast(me, SPELL_DUMMY, true); + + events.Reset(); + events.ScheduleEvent(EVENT_RETURN_FLESH, 20000); + events.ScheduleEvent(EVENT_LIGHTNING_BREATH, urand(3000, 4000)); + events.ScheduleEvent(EVENT_EYE_BEAM, urand(4000, 8000)); + events.ScheduleEvent(EVENT_POISON_CLOUD, urand(6000, 7000)); + break; + case EVENT_RETURN_FLESH: + DoCastAOE(SPELL_RETURN_FLESH); + events.ScheduleEvent(EVENT_GOING_SKELETAL, 6000); + return; + case EVENT_GOING_SKELETAL: + Talk(SAY_SKELETON); + me->RestoreDisplayId(); + DoCastAOE(SPELL_CLEAR_GIFT_OF_THARON_JA, true); + + events.Reset(); + events.ScheduleEvent(EVENT_DECAY_FLESH, 20000); + events.ScheduleEvent(EVENT_CURSE_OF_LIFE, 1000); + events.ScheduleEvent(EVENT_RAIN_OF_FIRE, urand(14000, 18000)); + events.ScheduleEvent(EVENT_SHADOW_VOLLEY, urand(8000, 10000)); + break; + default: + break; + } + } + + DoMeleeAttackIfReady(); } - } + }; - void KilledUnit(Unit* /*victim*/) OVERRIDE + CreatureAI* GetAI(Creature* creature) const OVERRIDE { - Talk(SAY_KILL); + return GetDrakTharonKeepAI<boss_tharon_jaAI>(creature); } +}; + +class spell_tharon_ja_clear_gift_of_tharon_ja : public SpellScriptLoader +{ + public: + spell_tharon_ja_clear_gift_of_tharon_ja() : SpellScriptLoader("spell_tharon_ja_clear_gift_of_tharon_ja") { } - void JustDied(Unit* /*killer*/) OVERRIDE + class spell_tharon_ja_clear_gift_of_tharon_ja_SpellScript : public SpellScript { - Talk(SAY_DEATH); + PrepareSpellScript(spell_tharon_ja_clear_gift_of_tharon_ja_SpellScript); - if (instance) + bool Validate(SpellInfo const* /*spellInfo*/) OVERRIDE { - // clean morph on players - Map::PlayerList const &PlayerList = instance->instance->GetPlayers(); - - for (Map::PlayerList::const_iterator i = PlayerList.begin(); i != PlayerList.end(); ++i) - if (Player* player = i->GetSource()) - player->DeMorph(); + if (!sSpellMgr->GetSpellInfo(SPELL_GIFT_OF_THARON_JA)) + return false; + return true; + } - DoCast(me, SPELL_ACHIEVEMENT_CHECK); + void HandleScript(SpellEffIndex /*effIndex*/) + { + if (Unit* target = GetHitUnit()) + target->RemoveAura(SPELL_GIFT_OF_THARON_JA); + } - instance->SetBossState(DATA_THARON_JA, DONE); + void Register() OVERRIDE + { + OnEffectHitTarget += SpellEffectFn(spell_tharon_ja_clear_gift_of_tharon_ja_SpellScript::HandleScript, EFFECT_0, SPELL_EFFECT_SCRIPT_EFFECT); } - } - }; + }; - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return GetDrakTharonKeepAI<boss_tharon_jaAI>(creature); - } + SpellScript* GetSpellScript() const OVERRIDE + { + return new spell_tharon_ja_clear_gift_of_tharon_ja_SpellScript(); + } }; void AddSC_boss_tharon_ja() { - new boss_tharon_ja; + new boss_tharon_ja(); + new spell_tharon_ja_clear_gift_of_tharon_ja(); } diff --git a/src/server/scripts/Northrend/DraktharonKeep/drak_tharon_keep.h b/src/server/scripts/Northrend/DraktharonKeep/drak_tharon_keep.h index 072a5f2f534..c2d957b7c0a 100644 --- a/src/server/scripts/Northrend/DraktharonKeep/drak_tharon_keep.h +++ b/src/server/scripts/Northrend/DraktharonKeep/drak_tharon_keep.h @@ -18,9 +18,6 @@ #ifndef DRAK_THARON_KEEP_H_ #define DRAK_THARON_KEEP_H_ -#include "Map.h" -#include "Creature.h" - #define DrakTharonKeepScriptName "instance_drak_tharon_keep" uint32 const EncounterCount = 4; @@ -89,11 +86,7 @@ enum GameObjectIds template<class AI> AI* GetDrakTharonKeepAI(Creature* creature) { - if (InstanceMap* instance = creature->GetMap()->ToInstanceMap()) - if (instance->GetInstanceScript()) - if (instance->GetScriptId() == sObjectMgr->GetScriptId(DrakTharonKeepScriptName)) - return new AI(creature); - return NULL; + return GetInstanceAI<AI>(creature, DrakTharonKeepScriptName); } #endif // DRAK_THARON_KEEP_H_ diff --git a/src/server/scripts/Northrend/DraktharonKeep/instance_drak_tharon_keep.cpp b/src/server/scripts/Northrend/DraktharonKeep/instance_drak_tharon_keep.cpp index 240e27ad026..d9e34ee2af3 100644 --- a/src/server/scripts/Northrend/DraktharonKeep/instance_drak_tharon_keep.cpp +++ b/src/server/scripts/Northrend/DraktharonKeep/instance_drak_tharon_keep.cpp @@ -36,7 +36,7 @@ class instance_drak_tharon_keep : public InstanceMapScript KingDredGUID = 0; TharonJaGUID = 0; - memset(TrollgoreInvaderSummonerGuids, 0, 4 * sizeof(uint64)); + memset(TrollgoreInvaderSummonerGuids, 0, 3 * sizeof(uint64)); memset(NovosCrystalGUIDs, 0, 4 * sizeof(uint64)); memset(NovosSummonerGUIDs, 0, 4 * sizeof(uint64)); } diff --git a/src/server/scripts/Northrend/FrozenHalls/HallsOfReflection/halls_of_reflection.cpp b/src/server/scripts/Northrend/FrozenHalls/HallsOfReflection/halls_of_reflection.cpp index 6408417e902..3f81b517721 100644 --- a/src/server/scripts/Northrend/FrozenHalls/HallsOfReflection/halls_of_reflection.cpp +++ b/src/server/scripts/Northrend/FrozenHalls/HallsOfReflection/halls_of_reflection.cpp @@ -714,7 +714,9 @@ class npc_jaina_or_sylvanas_escape_hor : public CreatureScript // AI of Part2 struct npc_jaina_or_sylvanas_escape_horAI : public ScriptedAI { - npc_jaina_or_sylvanas_escape_horAI(Creature* creature) : ScriptedAI(creature) + npc_jaina_or_sylvanas_escape_horAI(Creature* creature) : ScriptedAI(creature), + _instance(creature->GetInstanceScript()), _lichkingGUID(0), _walltargetGUID(0), + _icewallGUID(0), _icewall(0), _isattackingwall(0) { _instance = me->GetInstanceScript(); } diff --git a/src/server/scripts/Northrend/FrozenHalls/HallsOfReflection/instance_halls_of_reflection.cpp b/src/server/scripts/Northrend/FrozenHalls/HallsOfReflection/instance_halls_of_reflection.cpp index 40110b8a509..50600453368 100644 --- a/src/server/scripts/Northrend/FrozenHalls/HallsOfReflection/instance_halls_of_reflection.cpp +++ b/src/server/scripts/Northrend/FrozenHalls/HallsOfReflection/instance_halls_of_reflection.cpp @@ -79,20 +79,27 @@ public: { SetBossNumber(MAX_ENCOUNTER); events.Reset(); + _falricGUID = 0; _marwynGUID = 0; _jainaOrSylvanasPart1GUID = 0; + _jainaOrSylvanasPart2GUID = 0; + _lichkingPart1GUID = 0; _frostwornGeneralGUID = 0; + _frostmourneGUID = 0; _entranceDoorGUID = 0; _frostwornDoorGUID = 0; _arthasDoorGUID = 0; + _escapeDoorGUID = 0; + _caveGUID = 0; + _teamInInstance = 0; _waveCount = 0; - _mobsaticewall = 0; _introEvent = NOT_STARTED; _frostwornGeneral = NOT_STARTED; _escapeevent = NOT_STARTED; + _mobsaticewall = 0; } void OnPlayerEnter(Player* player) OVERRIDE diff --git a/src/server/scripts/Northrend/IcecrownCitadel/boss_professor_putricide.cpp b/src/server/scripts/Northrend/IcecrownCitadel/boss_professor_putricide.cpp index 8e783fa9361..927b3dfe467 100644 --- a/src/server/scripts/Northrend/IcecrownCitadel/boss_professor_putricide.cpp +++ b/src/server/scripts/Northrend/IcecrownCitadel/boss_professor_putricide.cpp @@ -955,7 +955,7 @@ class spell_putricide_slime_puddle : public SpellScriptLoader void ScaleRange(std::list<WorldObject*>& targets) { - targets.remove_if(ExactDistanceCheck(GetCaster(), 2.5f * GetCaster()->GetFloatValue(OBJECT_FIELD_SCALE_X))); + targets.remove_if(ExactDistanceCheck(GetCaster(), 2.5f * GetCaster()->GetObjectScale())); } void Register() OVERRIDE diff --git a/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp b/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp index 999e7081d52..1b03022c9bd 100644 --- a/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp +++ b/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp @@ -196,6 +196,22 @@ class FrostBombExplosion : public BasicEvent uint64 _sindragosaGUID; }; +class FrostBeaconSelector +{ + public: + FrostBeaconSelector(Unit* source) : _source(source) { } + + bool operator()(Unit* target) const + { + return target->GetTypeId() == TYPEID_PLAYER && + target != _source->GetVictim() && + !target->HasAura(SPELL_ICE_TOMB_UNTARGETABLE); + } + + private: + Unit* _source; +}; + class boss_sindragosa : public CreatureScript { public: @@ -466,7 +482,7 @@ class boss_sindragosa : public CreatureScript me->GetMotionMaster()->MovePoint(POINT_AIR_PHASE_FAR, SindragosaAirPosFar); break; case EVENT_ICE_TOMB: - if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 1, 0.0f, true, -SPELL_ICE_TOMB_UNTARGETABLE)) + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 1, FrostBeaconSelector(me))) { Talk(EMOTE_WARN_FROZEN_ORB, target->GetGUID()); DoCast(target, SPELL_ICE_TOMB_DUMMY, true); diff --git a/src/server/scripts/Northrend/IcecrownCitadel/boss_the_lich_king.cpp b/src/server/scripts/Northrend/IcecrownCitadel/boss_the_lich_king.cpp index 3c28483337b..fba64a89d83 100644 --- a/src/server/scripts/Northrend/IcecrownCitadel/boss_the_lich_king.cpp +++ b/src/server/scripts/Northrend/IcecrownCitadel/boss_the_lich_king.cpp @@ -2445,12 +2445,12 @@ class spell_the_lich_king_defile : public SpellScriptLoader void CorrectRange(std::list<WorldObject*>& targets) { - targets.remove_if(ExactDistanceCheck(GetCaster(), 10.0f * GetCaster()->GetFloatValue(OBJECT_FIELD_SCALE_X))); + targets.remove_if(ExactDistanceCheck(GetCaster(), 10.0f * GetCaster()->GetObjectScale())); } void ChangeDamageAndGrow() { - SetHitDamage(int32(GetHitDamage() * GetCaster()->GetFloatValue(OBJECT_FIELD_SCALE_X))); + SetHitDamage(int32(GetHitDamage() * GetCaster()->GetObjectScale())); // HACK: target player should cast this spell on defile // however with current aura handling auras cast by different units // cannot stack on the same aura object increasing the stack count diff --git a/src/server/scripts/Northrend/Naxxramas/boss_kelthuzad.cpp b/src/server/scripts/Northrend/Naxxramas/boss_kelthuzad.cpp index 5578d199ec3..a77b21a900b 100644 --- a/src/server/scripts/Northrend/Naxxramas/boss_kelthuzad.cpp +++ b/src/server/scripts/Northrend/Naxxramas/boss_kelthuzad.cpp @@ -283,6 +283,18 @@ public: SummonList spawns; // adds spawn by the trigger. kept in separated list (i.e. not in summons) + void ResetPlayerScale() + { + std::map<uint64, float>::const_iterator itr; + for (itr = chained.begin(); itr != chained.end(); ++itr) + { + if (Player* charmed = ObjectAccessor::GetPlayer(*me, itr->first)) + charmed->SetObjectScale(itr->second); + } + + chained.clear(); + } + void Reset() OVERRIDE { _Reset(); @@ -292,14 +304,8 @@ public: me->setFaction(35); me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE | UNIT_FLAG_DISABLE_MOVE | UNIT_FLAG_NOT_SELECTABLE); - std::map<uint64, float>::const_iterator itr; - for (itr = chained.begin(); itr != chained.end(); ++itr) - { - if (Player* charmed = Unit::GetPlayer(*me, (*itr).first)) - charmed->SetObjectScale((*itr).second); - } - chained.clear(); + ResetPlayerScale(); spawns.DespawnAll(); FindGameObjects(); @@ -340,13 +346,7 @@ public: _JustDied(); Talk(SAY_DEATH); - std::map<uint64, float>::const_iterator itr; - for (itr = chained.begin(); itr != chained.end(); ++itr) - { - if (Player* player = Unit::GetPlayer(*me, (*itr).first)) - player->SetObjectScale((*itr).second); - } - chained.clear(); + ResetPlayerScale(); } void EnterCombat(Unit* /*who*/) OVERRIDE @@ -507,7 +507,7 @@ public: if (target && !target->IsCharmed() && (chained.find(target->GetGUID()) == chained.end())) { DoCast(target, SPELL_CHAINS_OF_KELTHUZAD); - float scale = target->GetFloatValue(OBJECT_FIELD_SCALE_X); + float scale = target->GetObjectScale(); chained.insert(std::make_pair(target->GetGUID(), scale)); target->SetObjectScale(scale * 2); events.ScheduleEvent(EVENT_CHAINED_SPELL, 2000); //core has 2000ms to set unit flag charm @@ -523,11 +523,11 @@ public: std::map<uint64, float>::iterator itr; for (itr = chained.begin(); itr != chained.end();) { - if (Unit* player = Unit::GetPlayer(*me, (*itr).first)) + if (Unit* player = ObjectAccessor::GetPlayer(*me, itr->first)) { if (!player->IsCharmed()) { - player->SetObjectScale((*itr).second); + player->SetObjectScale(itr->second); std::map<uint64, float>::iterator next = itr; ++next; chained.erase(itr); diff --git a/src/server/scripts/Northrend/Nexus/EyeOfEternity/boss_malygos.cpp b/src/server/scripts/Northrend/Nexus/EyeOfEternity/boss_malygos.cpp index 4da66452d48..4a1670d1048 100644 --- a/src/server/scripts/Northrend/Nexus/EyeOfEternity/boss_malygos.cpp +++ b/src/server/scripts/Northrend/Nexus/EyeOfEternity/boss_malygos.cpp @@ -1967,7 +1967,7 @@ class spell_arcane_overload : public SpellScriptLoader { Creature* arcaneOverload = GetCaster()->ToCreature(); targets.remove_if(ExactDistanceCheck(arcaneOverload, - GetSpellInfo()->Effects[EFFECT_0].CalcRadius(arcaneOverload) * arcaneOverload->GetFloatValue(OBJECT_FIELD_SCALE_X))); + GetSpellInfo()->Effects[EFFECT_0].CalcRadius(arcaneOverload) * arcaneOverload->GetObjectScale())); } void Register() OVERRIDE diff --git a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_bjarngrim.cpp b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_bjarngrim.cpp index 2077049641f..944eacda34e 100644 --- a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_bjarngrim.cpp +++ b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_bjarngrim.cpp @@ -181,7 +181,7 @@ public: SetEquipmentSlots(false, EQUIP_SWORD, EQUIP_SHIELD, EQUIP_NO_CHANGE); if (instance) - instance->SetData(TYPE_BJARNGRIM, NOT_STARTED); + instance->SetBossState(DATA_BJARNGRIM, NOT_STARTED); } void EnterEvadeMode() OVERRIDE @@ -202,7 +202,7 @@ public: me->CallForHelp(30.0f); if (instance) - instance->SetData(TYPE_BJARNGRIM, IN_PROGRESS); + instance->SetBossState(DATA_BJARNGRIM, IN_PROGRESS); } void KilledUnit(Unit* /*victim*/) OVERRIDE @@ -215,7 +215,7 @@ public: Talk(SAY_DEATH); if (instance) - instance->SetData(TYPE_BJARNGRIM, DONE); + instance->SetBossState(DATA_BJARNGRIM, DONE); } /// @todo remove when removal is done by the core diff --git a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_ionar.cpp b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_ionar.cpp index dfb21edf9af..af6beca608d 100644 --- a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_ionar.cpp +++ b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_ionar.cpp @@ -116,7 +116,7 @@ public: me->SetVisible(true); if (instance) - instance->SetData(TYPE_IONAR, NOT_STARTED); + instance->SetBossState(DATA_IONAR, NOT_STARTED); } void EnterCombat(Unit* /*who*/) OVERRIDE @@ -124,7 +124,7 @@ public: Talk(SAY_AGGRO); if (instance) - instance->SetData(TYPE_IONAR, IN_PROGRESS); + instance->SetBossState(DATA_IONAR, IN_PROGRESS); } void JustDied(Unit* /*killer*/) OVERRIDE @@ -134,7 +134,7 @@ public: lSparkList.DespawnAll(); if (instance) - instance->SetData(TYPE_IONAR, DONE); + instance->SetBossState(DATA_IONAR, DONE); } void KilledUnit(Unit* /*victim*/) OVERRIDE @@ -338,7 +338,7 @@ public: void UpdateAI(uint32 uiDiff) OVERRIDE { // Despawn if the encounter is not running - if (instance && instance->GetData(TYPE_IONAR) != IN_PROGRESS) + if (instance && instance->GetBossState(DATA_IONAR) != IN_PROGRESS) { me->DespawnOrUnsummon(); return; diff --git a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_loken.cpp b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_loken.cpp index d8ab71870a8..61687de1b58 100644 --- a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_loken.cpp +++ b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_loken.cpp @@ -97,7 +97,7 @@ public: if (instance) { - instance->SetData(TYPE_LOKEN, NOT_STARTED); + instance->SetBossState(DATA_LOKEN, NOT_STARTED); instance->DoStopTimedAchievement(ACHIEVEMENT_TIMED_TYPE_EVENT, ACHIEV_TIMELY_DEATH_START_EVENT); } } @@ -108,7 +108,7 @@ public: if (instance) { - instance->SetData(TYPE_LOKEN, IN_PROGRESS); + instance->SetBossState(DATA_LOKEN, IN_PROGRESS); instance->DoStartTimedAchievement(ACHIEVEMENT_TIMED_TYPE_EVENT, ACHIEV_TIMELY_DEATH_START_EVENT); } } @@ -119,7 +119,7 @@ public: if (instance) { - instance->SetData(TYPE_LOKEN, DONE); + instance->SetBossState(DATA_LOKEN, DONE); instance->DoRemoveAurasDueToSpellOnPlayers(SPELL_PULSING_SHOCKWAVE_AURA); } } @@ -140,6 +140,7 @@ public: if (m_uiResumePulsingShockwave_Timer <= uiDiff) { DoCast(me, SPELL_PULSING_SHOCKWAVE_AURA, true); + me->ClearUnitState(UNIT_STATE_CASTING); // this flag breaks movement DoCast(me, SPELL_PULSING_SHOCKWAVE_N, true); m_uiResumePulsingShockwave_Timer = 0; diff --git a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_volkhan.cpp b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_volkhan.cpp index 725293a7e60..b6790a088ad 100644 --- a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_volkhan.cpp +++ b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/boss_volkhan.cpp @@ -121,7 +121,7 @@ public: m_lGolemGUIDList.clear(); if (instance) - instance->SetData(TYPE_VOLKHAN, NOT_STARTED); + instance->SetBossState(DATA_VOLKHAN, NOT_STARTED); } void EnterCombat(Unit* /*who*/) OVERRIDE @@ -129,7 +129,7 @@ public: Talk(SAY_AGGRO); if (instance) - instance->SetData(TYPE_VOLKHAN, IN_PROGRESS); + instance->SetBossState(DATA_VOLKHAN, IN_PROGRESS); } void AttackStart(Unit* who) OVERRIDE @@ -151,7 +151,7 @@ public: DespawnGolem(); if (instance) - instance->SetData(TYPE_VOLKHAN, DONE); + instance->SetBossState(DATA_VOLKHAN, DONE); } void KilledUnit(Unit* /*victim*/) OVERRIDE diff --git a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/halls_of_lightning.h b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/halls_of_lightning.h index c45feab1e8a..17c049e8292 100644 --- a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/halls_of_lightning.h +++ b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/halls_of_lightning.h @@ -1,6 +1,5 @@ /* * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2006-2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/> * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the @@ -16,22 +15,20 @@ * with this program. If not, see <http://www.gnu.org/licenses/>. */ -#ifndef DEF_HALLS_OF_LIGHTNING_H -#define DEF_HALLS_OF_LIGHTNING_H +#ifndef HALLS_OF_LIGHTNING_H_ +#define HALLS_OF_LIGHTNING_H_ -enum Types -{ - MAX_ENCOUNTER = 4, +#define HoLScriptName "instance_halls_of_lightning" - DATA_BJARNGRIM = 1, - DATA_IONAR = 2, - DATA_LOKEN = 3, - DATA_VOLKHAN = 4, +uint32 const EncounterCount = 4; - TYPE_BJARNGRIM = 10, - TYPE_IONAR = 11, - TYPE_LOKEN = 12, - TYPE_VOLKHAN = 13, +enum DataTypes +{ + // Encounter States/Boss GUIDs + DATA_BJARNGRIM = 0, + DATA_VOLKHAN = 1, + DATA_IONAR = 2, + DATA_LOKEN = 3 }; enum CreaturesIds @@ -44,11 +41,17 @@ enum CreaturesIds enum GameObjectIds { - GO_BJARNGRIM_DOOR = 191416, //_doors10 - GO_VOLKHAN_DOOR = 191325, //_doors07 - GO_IONAR_DOOR = 191326, //_doors05 - GO_LOKEN_DOOR = 191324, //_doors02 + GO_BJARNGRIM_DOOR = 191416, + GO_VOLKHAN_DOOR = 191325, + GO_IONAR_DOOR = 191326, + GO_LOKEN_DOOR = 191324, GO_LOKEN_THRONE = 192654 }; -#endif +template<class AI> +AI* GetHallsOfLightningAI(Creature* creature) +{ + return GetInstanceAI<AI>(creature, HoLScriptName); +} + +#endif // HALLS_OF_LIGHTNING_H_ diff --git a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/instance_halls_of_lightning.cpp b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/instance_halls_of_lightning.cpp index e6d2ededd73..6baf5dc6d93 100644 --- a/src/server/scripts/Northrend/Ulduar/HallsOfLightning/instance_halls_of_lightning.cpp +++ b/src/server/scripts/Northrend/Ulduar/HallsOfLightning/instance_halls_of_lightning.cpp @@ -1,6 +1,5 @@ /* * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2006-2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/> * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the @@ -16,240 +15,186 @@ * with this program. If not, see <http://www.gnu.org/licenses/>. */ -/* ScriptData -SDName: Instance_Halls_of_Lightning -SD%Complete: 90% -SDComment: All ready. -SDCategory: Halls of Lightning -EndScriptData */ - #include "ScriptMgr.h" #include "InstanceScript.h" #include "halls_of_lightning.h" -/* Halls of Lightning encounters: -0 - General Bjarngrim -1 - Volkhan -2 - Ionar -3 - Loken -*/ +DoorData const doorData[] = +{ + { GO_BJARNGRIM_DOOR, DATA_BJARNGRIM, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_VOLKHAN_DOOR, DATA_VOLKHAN, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_IONAR_DOOR, DATA_IONAR, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_LOKEN_DOOR, DATA_LOKEN, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { 0, 0, DOOR_TYPE_ROOM, BOUNDARY_NONE } // END +}; class instance_halls_of_lightning : public InstanceMapScript { -public: - instance_halls_of_lightning() : InstanceMapScript("instance_halls_of_lightning", 602) { } - - InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE - { - return new instance_halls_of_lightning_InstanceMapScript(map); - } - - struct instance_halls_of_lightning_InstanceMapScript : public InstanceScript - { - instance_halls_of_lightning_InstanceMapScript(Map* map) : InstanceScript(map) {} + public: + instance_halls_of_lightning() : InstanceMapScript(HoLScriptName, 602) { } - uint32 m_auiEncounter[MAX_ENCOUNTER]; - - uint64 m_uiGeneralBjarngrimGUID; - uint64 m_uiIonarGUID; - uint64 m_uiLokenGUID; - uint64 m_uiVolkhanGUID; - - uint64 m_uiBjarngrimDoorGUID; - uint64 m_uiVolkhanDoorGUID; - uint64 m_uiIonarDoorGUID; - uint64 m_uiLokenDoorGUID; - uint64 m_uiLokenGlobeGUID; - - void Initialize() OVERRIDE + struct instance_halls_of_lightning_InstanceMapScript : public InstanceScript { - memset(&m_auiEncounter, 0, sizeof(m_auiEncounter)); + instance_halls_of_lightning_InstanceMapScript(Map* map) : InstanceScript(map) + { + SetBossNumber(EncounterCount); + LoadDoorData(doorData); - m_uiGeneralBjarngrimGUID = 0; - m_uiVolkhanGUID = 0; - m_uiIonarGUID = 0; - m_uiLokenGUID = 0; + GeneralBjarngrimGUID = 0; + VolkhanGUID = 0; + IonarGUID = 0; + LokenGUID = 0; - m_uiBjarngrimDoorGUID = 0; - m_uiVolkhanDoorGUID = 0; - m_uiIonarDoorGUID = 0; - m_uiLokenDoorGUID = 0; - m_uiLokenGlobeGUID = 0; - } + LokenGlobeGUID = 0; + } - void OnCreatureCreate(Creature* creature) OVERRIDE - { - switch (creature->GetEntry()) + void OnCreatureCreate(Creature* creature) OVERRIDE { - case NPC_BJARNGRIM: - m_uiGeneralBjarngrimGUID = creature->GetGUID(); - break; - case NPC_VOLKHAN: - m_uiVolkhanGUID = creature->GetGUID(); - break; - case NPC_IONAR: - m_uiIonarGUID = creature->GetGUID(); - break; - case NPC_LOKEN: - m_uiLokenGUID = creature->GetGUID(); - break; + switch (creature->GetEntry()) + { + case NPC_BJARNGRIM: + GeneralBjarngrimGUID = creature->GetGUID(); + break; + case NPC_VOLKHAN: + VolkhanGUID = creature->GetGUID(); + break; + case NPC_IONAR: + IonarGUID = creature->GetGUID(); + break; + case NPC_LOKEN: + LokenGUID = creature->GetGUID(); + break; + default: + break; + } } - } - void OnGameObjectCreate(GameObject* go) OVERRIDE - { - switch (go->GetEntry()) + void OnGameObjectCreate(GameObject* go) OVERRIDE { - case GO_BJARNGRIM_DOOR: - m_uiBjarngrimDoorGUID = go->GetGUID(); - if (m_auiEncounter[0] == DONE) - go->SetGoState(GO_STATE_ACTIVE); - else - go->SetGoState(GO_STATE_READY); - break; - case GO_VOLKHAN_DOOR: - m_uiVolkhanDoorGUID = go->GetGUID(); - if (m_auiEncounter[1] == DONE) - go->SetGoState(GO_STATE_ACTIVE); - else - go->SetGoState(GO_STATE_READY); - break; - case GO_IONAR_DOOR: - m_uiIonarDoorGUID = go->GetGUID(); - if (m_auiEncounter[2] == DONE) - go->SetGoState(GO_STATE_ACTIVE); - else - go->SetGoState(GO_STATE_READY); - break; - case GO_LOKEN_DOOR: - m_uiLokenDoorGUID = go->GetGUID(); - if (m_auiEncounter[3] == DONE) - go->SetGoState(GO_STATE_ACTIVE); - else - go->SetGoState(GO_STATE_READY); - break; - case GO_LOKEN_THRONE: - m_uiLokenGlobeGUID = go->GetGUID(); - break; + switch (go->GetEntry()) + { + case GO_BJARNGRIM_DOOR: + case GO_VOLKHAN_DOOR: + case GO_IONAR_DOOR: + case GO_LOKEN_DOOR: + AddDoor(go, true); + break; + case GO_LOKEN_THRONE: + LokenGlobeGUID = go->GetGUID(); + break; + default: + break; + } } - } - void SetData(uint32 uiType, uint32 uiData) OVERRIDE - { - switch (uiType) + void OnGameObjectRemove(GameObject* go) OVERRIDE { - case TYPE_BJARNGRIM: - if (uiData == DONE) - if (GameObject* pDoor = instance->GetGameObject(m_uiBjarngrimDoorGUID)) - pDoor->SetGoState(GO_STATE_ACTIVE); - m_auiEncounter[0] = uiData; - break; - case TYPE_VOLKHAN: - if (uiData == DONE) - if (GameObject* pDoor = instance->GetGameObject(m_uiVolkhanDoorGUID)) - pDoor->SetGoState(GO_STATE_ACTIVE); - m_auiEncounter[1] = uiData; - break; - case TYPE_IONAR: - if (uiData == DONE) - if (GameObject* pDoor = instance->GetGameObject(m_uiIonarDoorGUID)) - pDoor->SetGoState(GO_STATE_ACTIVE); - m_auiEncounter[2] = uiData; - break; - case TYPE_LOKEN: - if (uiData == DONE) - { - if (GameObject* pDoor = instance->GetGameObject(m_uiLokenDoorGUID)) - pDoor->SetGoState(GO_STATE_ACTIVE); - - // Appears to be type 5 GO with animation. Need to figure out how this work, code below only placeholder - if (GameObject* pGlobe = instance->GetGameObject(m_uiLokenGlobeGUID)) - pGlobe->SetGoState(GO_STATE_ACTIVE); - } - m_auiEncounter[3] = uiData; - break; + switch (go->GetEntry()) + { + case GO_BJARNGRIM_DOOR: + case GO_VOLKHAN_DOOR: + case GO_IONAR_DOOR: + case GO_LOKEN_DOOR: + AddDoor(go, false); + break; + default: + break; + } } - if (uiData == DONE) - SaveToDB(); - } - - uint32 GetData(uint32 uiType) const OVERRIDE - { - switch (uiType) + bool SetBossState(uint32 type, EncounterState state) OVERRIDE { - case TYPE_BJARNGRIM: - return m_auiEncounter[0]; - case TYPE_VOLKHAN: - return m_auiEncounter[1]; - case TYPE_IONAR: - return m_auiEncounter[2]; - case TYPE_LOKEN: - return m_auiEncounter[3]; + if (!InstanceScript::SetBossState(type, state)) + return false; + + switch (type) + { + case DATA_LOKEN: + if (state == DONE) + if (GameObject* globe = instance->GetGameObject(LokenGlobeGUID)) + globe->SendCustomAnim(0); + break; + default: + break; + } + + return true; } - return 0; - } - uint64 GetData64(uint32 uiData) const OVERRIDE - { - switch (uiData) + uint64 GetData64(uint32 type) const OVERRIDE { - case DATA_BJARNGRIM: - return m_uiGeneralBjarngrimGUID; - case DATA_VOLKHAN: - return m_uiVolkhanGUID; - case DATA_IONAR: - return m_uiIonarGUID; - case DATA_LOKEN: - return m_uiLokenGUID; + switch (type) + { + case DATA_BJARNGRIM: + return GeneralBjarngrimGUID; + case DATA_VOLKHAN: + return VolkhanGUID; + case DATA_IONAR: + return IonarGUID; + case DATA_LOKEN: + return LokenGUID; + default: + break; + } + return 0; } - return 0; - } - std::string GetSaveData() OVERRIDE - { - OUT_SAVE_INST_DATA; + std::string GetSaveData() OVERRIDE + { + OUT_SAVE_INST_DATA; - std::ostringstream saveStream; - saveStream << "H L " << m_auiEncounter[0] << ' ' << m_auiEncounter[1] << ' ' - << m_auiEncounter[2] << ' ' << m_auiEncounter[3]; + std::ostringstream saveStream; + saveStream << "H L " << GetBossSaveData(); - OUT_SAVE_INST_DATA_COMPLETE; - return saveStream.str(); - } + OUT_SAVE_INST_DATA_COMPLETE; + return saveStream.str(); + } - void Load(const char* in) OVERRIDE - { - if (!in) + void Load(const char* str) OVERRIDE { - OUT_LOAD_INST_DATA_FAIL; - return; - } + if (!str) + { + OUT_LOAD_INST_DATA_FAIL; + return; + } - OUT_LOAD_INST_DATA(in); + OUT_LOAD_INST_DATA(str); - char dataHead1, dataHead2; - uint16 data0, data1, data2, data3; + char dataHead1, dataHead2; - std::istringstream loadStream(in); - loadStream >> dataHead1 >> dataHead2 >> data0 >> data1 >> data2 >> data3; + std::istringstream loadStream(str); + loadStream >> dataHead1 >> dataHead2; - if (dataHead1 == 'H' && dataHead2 == 'L') - { - m_auiEncounter[0] = data0; - m_auiEncounter[1] = data1; - m_auiEncounter[2] = data2; - m_auiEncounter[3] = data3; + if (dataHead1 == 'H' && dataHead2 == 'L') + { + for (uint32 i = 0; i < EncounterCount; ++i) + { + uint32 tmpState; + loadStream >> tmpState; + if (tmpState == IN_PROGRESS || tmpState > SPECIAL) + tmpState = NOT_STARTED; + SetBossState(i, EncounterState(tmpState)); + } + } + else + OUT_LOAD_INST_DATA_FAIL; - for (uint8 i = 0; i < MAX_ENCOUNTER; ++i) - if (m_auiEncounter[i] == IN_PROGRESS) - m_auiEncounter[i] = NOT_STARTED; - } else OUT_LOAD_INST_DATA_FAIL; + OUT_LOAD_INST_DATA_COMPLETE; + } - OUT_LOAD_INST_DATA_COMPLETE; - } - }; + protected: + uint64 GeneralBjarngrimGUID; + uint64 VolkhanGUID; + uint64 IonarGUID; + uint64 LokenGUID; + + uint64 LokenGlobeGUID; + }; + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_halls_of_lightning_InstanceMapScript(map); + } }; void AddSC_instance_halls_of_lightning() diff --git a/src/server/scripts/Northrend/zone_borean_tundra.cpp b/src/server/scripts/Northrend/zone_borean_tundra.cpp index 6d2a48910fe..da8511a98d5 100644 --- a/src/server/scripts/Northrend/zone_borean_tundra.cpp +++ b/src/server/scripts/Northrend/zone_borean_tundra.cpp @@ -142,7 +142,7 @@ public: break; case 7: DoCast(me, SPELL_EXPLODE_CART, true); - if (Player* caster = Unit::GetPlayer(*me, casterGuid)) + if (Player* caster = ObjectAccessor::GetPlayer(*me, casterGuid)) caster->KilledMonster(me->GetCreatureTemplate(), me->GetGUID()); phaseTimer = 5000; phase = 8; @@ -857,7 +857,7 @@ public: { if (me->IsWithinDistInMap(who, INTERACTION_DISTANCE)) { - if (Player* pHarpooner = Unit::GetPlayer(*me, HarpoonerGUID)) + if (Player* pHarpooner = ObjectAccessor::GetPlayer(*me, HarpoonerGUID)) { pHarpooner->KilledMonsterCredit(26175, 0); pHarpooner->RemoveAura(SPELL_DRAKE_HATCHLING_SUBDUED); @@ -873,7 +873,7 @@ public: { if (WithRedDragonBlood && HarpoonerGUID && !me->HasAura(SPELL_RED_DRAGONBLOOD)) { - if (Player* pHarpooner = Unit::GetPlayer(*me, HarpoonerGUID)) + if (Player* pHarpooner = ObjectAccessor::GetPlayer(*me, HarpoonerGUID)) { EnterEvadeMode(); StartFollow(pHarpooner, 35, NULL); @@ -1718,7 +1718,7 @@ public: void GotStinged(uint64 casterGUID) { - if (Player* caster = Player::GetPlayer(*me, casterGUID)) + if (Player* caster = ObjectAccessor::GetPlayer(*me, casterGUID)) { uint32 step = caster->GetAuraCount(SPELL_NEURAL_NEEDLE) + 1; switch (step) @@ -2378,7 +2378,7 @@ public: { me->StopMoving(); me->SetUInt32Value(UNIT_NPC_FLAGS, 0); - if (Player* player = me->GetPlayer(*me, uiPlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, uiPlayerGUID)) me->SetFacingToObject(player); uiEventTimer = 3000; uiEventPhase = 1; @@ -2392,7 +2392,7 @@ public: void AttackPlayer() { me->setFaction(14); - if (Player* player = me->GetPlayer(*me, uiPlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, uiPlayerGUID)) me->AI()->AttackStart(player); } @@ -2428,7 +2428,7 @@ public: { case NPC_SALTY_JOHN_THORPE: Talk(SAY_HIDDEN_CULTIST_4); - if (Player* player = me->GetPlayer(*me, uiPlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, uiPlayerGUID)) me->SetFacingToObject(player); uiEventTimer = 3000; uiEventPhase = 3; diff --git a/src/server/scripts/Northrend/zone_grizzly_hills.cpp b/src/server/scripts/Northrend/zone_grizzly_hills.cpp index 9b68b37507b..1a080824136 100644 --- a/src/server/scripts/Northrend/zone_grizzly_hills.cpp +++ b/src/server/scripts/Northrend/zone_grizzly_hills.cpp @@ -638,7 +638,7 @@ public: switch (eventId) { case EVENT_STRAGGLER_1: - if (Player* player = Unit::GetPlayer(*me, _playerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, _playerGUID)) DoCast(player, SPELL_VENTURE_STRAGGLER_CREDIT); me->GetMotionMaster()->MovePoint(0, me->GetPositionX()-7, me->GetPositionY()+7, me->GetPositionZ()); _events.ScheduleEvent(EVENT_STRAGGLER_2, 2500); diff --git a/src/server/scripts/Northrend/zone_howling_fjord.cpp b/src/server/scripts/Northrend/zone_howling_fjord.cpp index 15273088940..4626ffabd79 100644 --- a/src/server/scripts/Northrend/zone_howling_fjord.cpp +++ b/src/server/scripts/Northrend/zone_howling_fjord.cpp @@ -338,7 +338,7 @@ public: void JustSummoned(Creature* summon) OVERRIDE { - if (Player* player = me->GetPlayer(*me, uiPlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, uiPlayerGUID)) { if (player->IsAlive()) { diff --git a/src/server/scripts/Northrend/zone_sholazar_basin.cpp b/src/server/scripts/Northrend/zone_sholazar_basin.cpp index c1bca1dae76..bf284c5138b 100644 --- a/src/server/scripts/Northrend/zone_sholazar_basin.cpp +++ b/src/server/scripts/Northrend/zone_sholazar_basin.cpp @@ -465,23 +465,18 @@ public: #####*/ #define SAY_OFFER "Care to try Grimbooze Thunderbrew's new jungle punch?" -#define SAY_HEMET_1 "Aye, I'll try it." -#define SAY_HEMET_2 "That's exactly what I needed!" -#define SAY_HEMET_3 "It's got my vote! That'll put hair on your chest like nothing else will." -#define SAY_HADRIUS_1 "I'm always up for something of Grimbooze's." -#define SAY_HADRIUS_2 "Well, so far, it tastes like something my wife would drink..." -#define SAY_HADRIUS_3 "Now, there's the kick I've come to expect from Grimbooze's drinks! I like it!" -#define SAY_TAMARA_1 "Sure!" -#define SAY_TAMARA_2 "Oh my..." -#define SAY_TAMARA_3 "Tastes like I'm drinking... engine degreaser!" - -enum utils + +enum JunglePunch { - NPC_HEMET = 27986, - NPC_HADRIUS = 28047, - NPC_TAMARA = 28568, SPELL_OFFER = 51962, - QUEST_ENTRY = 12645, + QUEST_TASTE_TEST = 12645, + + SAY_HEMET_HADRIUS_TAMARA_1 = 0, + SAY_HEMET_HADRIUS_TAMARA_2 = 1, + SAY_HEMET_HADRIUS_TAMARA_3 = 2, + + SAY_HEMET_4 = 3, // unused + SAY_HEMET_5 = 4 // unused }; enum NesingwaryChildrensWeek @@ -492,12 +487,12 @@ enum NesingwaryChildrensWeek ORPHAN_WOLVAR = 33532, + TEXT_NESINGWARY_1 = 5, + TEXT_WOLVAR_ORPHAN_6 = 6, TEXT_WOLVAR_ORPHAN_7 = 7, TEXT_WOLVAR_ORPHAN_8 = 8, - TEXT_WOLVAR_ORPHAN_9 = 9, - - TEXT_NESINGWARY_1 = 1, + TEXT_WOLVAR_ORPHAN_9 = 9 }; class npc_jungle_punch_target : public CreatureScript @@ -520,7 +515,6 @@ public: } void MoveInLineOfSight(Unit* who) OVERRIDE - { if (!phase && who && who->GetDistance2d(me) < 10.0f) if (Player* player = who->ToPlayer()) @@ -540,8 +534,8 @@ public: { if (timer <= diff) { - Player* player = Player::GetPlayer(*me, playerGUID); - Creature* orphan = Creature::GetCreature(*me, orphanGUID); + Player* player = ObjectAccessor::GetPlayer(*me, playerGUID); + Creature* orphan = ObjectAccessor::GetCreature(*me, orphanGUID); if (!orphan || !player) { @@ -585,99 +579,55 @@ public: timer -= diff; } - void UpdateAI(uint32 uiDiff) OVERRIDE + void UpdateAI(uint32 diff) OVERRIDE { if (phase) - proceedCwEvent(uiDiff); + proceedCwEvent(diff); if (!sayStep) return; - if (sayTimer < uiDiff) + if (sayTimer < diff) { - switch (sayStep) - { - case 0: - { - switch (me->GetEntry()) - { - case NPC_HEMET: me->MonsterSay(SAY_HEMET_1, LANG_UNIVERSAL, 0); break; - case NPC_HADRIUS: me->MonsterSay(SAY_HADRIUS_1, LANG_UNIVERSAL, 0); break; - case NPC_TAMARA: me->MonsterSay(SAY_TAMARA_1, LANG_UNIVERSAL, 0); break; - } - sayTimer = 3000; - sayStep++; - break; - } - case 1: - { - switch (me->GetEntry()) - { - case NPC_HEMET: me->MonsterSay(SAY_HEMET_2, LANG_UNIVERSAL, 0); break; - case NPC_HADRIUS: me->MonsterSay(SAY_HADRIUS_2, LANG_UNIVERSAL, 0); break; - case NPC_TAMARA: me->MonsterSay(SAY_TAMARA_2, LANG_UNIVERSAL, 0); break; - } - sayTimer = 3000; - sayStep++; - break; - } - case 2: - { - switch (me->GetEntry()) - { - case NPC_HEMET: me->MonsterSay(SAY_HEMET_3, LANG_UNIVERSAL, 0); break; - case NPC_HADRIUS: me->MonsterSay(SAY_HADRIUS_3, LANG_UNIVERSAL, 0); break; - case NPC_TAMARA: me->MonsterSay(SAY_TAMARA_3, LANG_UNIVERSAL, 0); break; - } - sayTimer = 3000; - sayStep = 0; - break; - } - } + Talk(SAY_HEMET_HADRIUS_TAMARA_1 + sayStep - 1); + sayTimer = 3000; + sayStep++; + + if (sayStep > 3) // end + sayStep = 0; } else - sayTimer -= uiDiff; + sayTimer -= diff; } - void SpellHit(Unit* caster, const SpellInfo* proto) OVERRIDE + void SpellHit(Unit* caster, SpellInfo const* spellInfo) OVERRIDE { - if (!proto || proto->Id != SPELL_OFFER) + if (spellInfo->Id != SPELL_OFFER) return; - if (!caster->ToPlayer()) + Player* player = caster->ToPlayer(); + if (!player) + return; + + Quest const* quest = sObjectMgr->GetQuestTemplate(QUEST_TASTE_TEST); + if (!quest) return; - QuestStatusMap::const_iterator itr = caster->ToPlayer()->getQuestStatusMap().find(QUEST_ENTRY); + QuestStatusMap::const_iterator itr = player->getQuestStatusMap().find(QUEST_TASTE_TEST); if (itr->second.Status != QUEST_STATUS_INCOMPLETE) return; - for (uint8 i=0; i<3; i++) + for (uint8 i = 0; i < 3; ++i) { - switch (i) - { - case 0: - if (NPC_HEMET != me->GetEntry()) - continue; - else - break; - case 1: - if (NPC_HADRIUS != me->GetEntry()) - continue; - else - break; - case 2: - if (NPC_TAMARA != me->GetEntry()) - continue; - else - break; - } + if (uint32(quest->RequiredNpcOrGo[i]) != me->GetEntry()) + continue; if (itr->second.CreatureOrGOCount[i] != 0) continue; - caster->ToPlayer()->KilledMonsterCredit(me->GetEntry(), 0); - caster->ToPlayer()->Say(SAY_OFFER, LANG_UNIVERSAL); - sayStep = 0; + player->KilledMonsterCredit(me->GetEntry(), 0); + player->Say(SAY_OFFER, LANG_UNIVERSAL); + sayStep = 1; break; } } diff --git a/src/server/scripts/Northrend/zone_wintergrasp.cpp b/src/server/scripts/Northrend/zone_wintergrasp.cpp index 0b9c319bf56..a27ce0324ff 100644 --- a/src/server/scripts/Northrend/zone_wintergrasp.cpp +++ b/src/server/scripts/Northrend/zone_wintergrasp.cpp @@ -334,13 +334,19 @@ class npc_wg_quest_giver : public CreatureScript bool OnGossipHello(Player* player, Creature* creature) OVERRIDE { - if (creature->IsQuestGiver()) - player->PrepareQuestMenu(creature->GetGUID()); - Battlefield* wintergrasp = sBattlefieldMgr->GetBattlefieldByBattleId(BATTLEFIELD_BATTLEID_WG); if (!wintergrasp) return true; + if (creature->IsVendor()) + { + player->ADD_GOSSIP_ITEM_DB(Player::GetDefaultGossipMenuForSource(creature), 0, GOSSIP_SENDER_MAIN, GOSSIP_OPTION_VENDOR); + player->PlayerTalkClass->GetGossipMenu().AddGossipMenuItemData(0, 0, 0); + } + + /// @todo: move this to conditions or something else + + // Player::PrepareQuestMenu(guid) if (creature->IsQuestGiver()) { QuestRelationBounds objectQR = sObjectMgr->GetCreatureQuestRelationBounds(creature->GetEntry()); @@ -368,6 +374,9 @@ class npc_wg_quest_giver : public CreatureScript if (!quest) continue; + if (!player->CanTakeQuest(quest, false)) + continue; + switch (questId) { // Horde attacker @@ -377,15 +386,8 @@ class npc_wg_quest_giver : public CreatureScript case QUEST_FUELING_THE_DEMOLISHERS_HORDE_ATT: case QUEST_HEALING_WITH_ROSES_HORDE_ATT: case QUEST_DEFEND_THE_SIEGE_HORDE_ATT: - if (wintergrasp->GetAttackerTeam() == TEAM_HORDE) - { - QuestStatus status = player->GetQuestStatus(questId); - - if (quest->IsAutoComplete() && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 4); - else if (status == QUEST_STATUS_NONE && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 2); - } + if (wintergrasp->GetAttackerTeam() != TEAM_HORDE) + continue; break; // Horde defender case QUEST_BONES_AND_ARROWS_HORDE_DEF: @@ -395,15 +397,8 @@ class npc_wg_quest_giver : public CreatureScript case QUEST_HEALING_WITH_ROSES_HORDE_DEF: case QUEST_TOPPLING_THE_TOWERS_HORDE_DEF: case QUEST_STOP_THE_SIEGE_HORDE_DEF: - if (wintergrasp->GetDefenderTeam() == TEAM_HORDE) - { - QuestStatus status = player->GetQuestStatus(questId); - - if (quest->IsAutoComplete() && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 4); - else if (status == QUEST_STATUS_NONE && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 2); - } + if (wintergrasp->GetDefenderTeam() != TEAM_HORDE) + continue; break; // Alliance attacker case QUEST_BONES_AND_ARROWS_ALLIANCE_ATT: @@ -411,15 +406,8 @@ class npc_wg_quest_giver : public CreatureScript case QUEST_NO_MERCY_FOR_THE_MERCILESS_ALLIANCE_ATT: case QUEST_DEFEND_THE_SIEGE_ALLIANCE_ATT: case QUEST_A_RARE_HERB_ALLIANCE_ATT: - if (wintergrasp->GetAttackerTeam() == TEAM_ALLIANCE) - { - QuestStatus status = player->GetQuestStatus(questId); - - if (quest->IsAutoComplete() && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 4); - else if (status == QUEST_STATUS_NONE && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 2); - } + if (wintergrasp->GetAttackerTeam() != TEAM_ALLIANCE) + continue; break; // Alliance defender case QUEST_BONES_AND_ARROWS_ALLIANCE_DEF: @@ -428,27 +416,20 @@ class npc_wg_quest_giver : public CreatureScript case QUEST_SHOUTHERN_SABOTAGE_ALLIANCE_DEF: case QUEST_STOP_THE_SIEGE_ALLIANCE_DEF: case QUEST_A_RARE_HERB_ALLIANCE_DEF: - if (wintergrasp->GetDefenderTeam() == TEAM_ALLIANCE) - { - QuestStatus status = player->GetQuestStatus(questId); - - if (quest->IsAutoComplete() && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 4); - else if (status == QUEST_STATUS_NONE && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 2); - } + if (wintergrasp->GetDefenderTeam() != TEAM_ALLIANCE) + continue; break; default: - QuestStatus status = player->GetQuestStatus(questId); - - if (quest->IsAutoComplete() && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 4); - else if (status == QUEST_STATUS_NONE && player->CanTakeQuest(quest, false)) - qm.AddMenuItem(questId, 2); break; } + + if (quest->IsAutoComplete()) + qm.AddMenuItem(questId, 4); + else if (player->GetQuestStatus(questId) == QUEST_STATUS_NONE) + qm.AddMenuItem(questId, 2); } } + player->SEND_GOSSIP_MENU(player->GetGossipTextId(creature), creature->GetGUID()); return true; } diff --git a/src/server/scripts/Northrend/zone_zuldrak.cpp b/src/server/scripts/Northrend/zone_zuldrak.cpp index 7281c8a5b1e..63ba44f19e8 100644 --- a/src/server/scripts/Northrend/zone_zuldrak.cpp +++ b/src/server/scripts/Northrend/zone_zuldrak.cpp @@ -198,6 +198,9 @@ enum Gurgthock EMOTE_YGGDRAS_SPAWN = 4, SAY_STINKBEARD_SPAWN = 5, SAY_GURGTHOCK_ELEMENTAL_SPAWN = 6, + SAY_GURGTHOCK_7 = 7, + SAY_QUEST_AMPHITHEATER_ANGUISH_YGGDRAS = 8, + SAY_GURGTHOCK_9 = 9, SAY_CALL_FOR_HELP = 0, SAY_RECRUIT = 0, @@ -319,9 +322,9 @@ public: uiTimer = 2000; uiPhase = 12; break; - } - break; - } + } + break; + } } void UpdateAI(uint32 diff) OVERRIDE @@ -341,8 +344,6 @@ public: if (uiPhase) { - Player* player = me->GetPlayer(*me, _playerGUID); - if (uiTimer <= diff) { switch (uiPhase) @@ -371,27 +372,14 @@ public: uiPhase = 0; break; case 6: - { - if (!player) - return; - - std::string sText = ("The grand Amphitheater of Anguish awaits, " + std::string(player->GetName()) + ". Remember, once a battle starts you have to stay in the area. WIN OR DIE!"); - - me->MonsterSay(sText.c_str(), LANG_UNIVERSAL, 0); - uiTimer = 5000; - uiPhase = 9; - } + Talk(SAY_GURGTHOCK_7, _playerGUID); + uiTimer = 5000; + uiPhase = 9; break; case 7: - { - if (!player) - return; - - std::string sText = ("Prepare to make you stand, " + std::string(player->GetName()) + "! Get in the Amphitheater and stand ready! Remember, you and your opponent must stay in the arena at all times or you will be disqualified!"); - me->MonsterSay(sText.c_str(), LANG_UNIVERSAL, 0); - uiTimer = 3000; - uiPhase = 8; - } + Talk(SAY_GURGTHOCK_9, _playerGUID); + uiTimer = 3000; + uiPhase = 8; break; case 8: Talk(SAY_QUEST_ACCEPT_MAGNATAUR); @@ -399,15 +387,9 @@ public: uiPhase = 11; break; case 9: - { - if (!player) - return; - - std::string sText = ("Here we are once again, ladies and gentlemen. The epic struggle between life and death in the Amphitheater of Anguish! For this round we have " + std::string(player->GetName()) + " versus the hulking jormungar, Yg... Yggd? Yggdoze? Who comes up with these names?! " + std::string(player->GetName()) + " versus big worm!"); - me->MonsterYell(sText.c_str(), LANG_UNIVERSAL, 0); - uiTimer = 10000; - uiPhase = 10; - } + Talk(SAY_QUEST_AMPHITHEATER_ANGUISH_YGGDRAS, _playerGUID); + uiTimer = 10000; + uiPhase = 10; break; case 10: me->SummonCreature(NPC_YGGDRAS, SpawnPosition[1], TEMPSUMMON_CORPSE_DESPAWN, 1000); @@ -420,16 +402,10 @@ public: uiPhase = 0; break; case 12: - { - if (!player) - return; - - std::string sText = ("Prepare to make you stand, " + std::string(player->GetName()) + "! Get in the Amphitheater and stand ready! Remember, you and your opponent must stay in the arena at all times or you will be disqualified!"); - me->MonsterSay(sText.c_str(), LANG_UNIVERSAL, 0); + Talk(SAY_GURGTHOCK_9, _playerGUID); uiTimer = 5000; uiPhase = 13; - } - break; + break; case 13: Talk(SAY_GURGTHOCK_ELEMENTAL_SPAWN); uiTimer = 3000; @@ -443,7 +419,8 @@ public: break; } } - else uiTimer -= diff; + else + uiTimer -= diff; } } @@ -1502,7 +1479,7 @@ public: _events.ScheduleEvent(EVENT_TURN_TO_POT, urand(25000, 41000)); break; case EVENT_EASY_123: - if (Player* player = Unit::GetPlayer(*me, _playerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, _playerGUID)) { Talk(SAY_EASY_123, _playerGUID); DoCast(player, SPELL_RANDOM_INGREDIENT_EASY_AURA); @@ -1510,7 +1487,7 @@ public: } break; case EVENT_MEDIUM_4: - if (Player* player = Unit::GetPlayer(*me, _playerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, _playerGUID)) { Talk(SAY_MEDIUM_4, _playerGUID); DoCast(player, SPELL_RANDOM_INGREDIENT_MEDIUM_AURA); @@ -1518,7 +1495,7 @@ public: } break; case EVENT_MEDIUM_5: - if (Player* player = Unit::GetPlayer(*me, _playerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, _playerGUID)) { Talk(SAY_MEDIUM_5, _playerGUID); DoCast(player, SPELL_RANDOM_INGREDIENT_MEDIUM_AURA); @@ -1526,7 +1503,7 @@ public: } break; case EVENT_HARD_6: - if (Player* player = Unit::GetPlayer(*me, _playerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, _playerGUID)) { Talk(SAY_HARD_6, _playerGUID); DoCast(player, SPELL_RANDOM_INGREDIENT_HARD_AURA); diff --git a/src/server/scripts/Outland/Auchindoun/SethekkHalls/boss_anzu.cpp b/src/server/scripts/Outland/Auchindoun/SethekkHalls/boss_anzu.cpp index 707f6c34a90..ade6c13aafe 100644 --- a/src/server/scripts/Outland/Auchindoun/SethekkHalls/boss_anzu.cpp +++ b/src/server/scripts/Outland/Auchindoun/SethekkHalls/boss_anzu.cpp @@ -18,7 +18,7 @@ /* Name: Boss_Anzu %Complete: 80% -Comment: +Comment: Category: Auchindoun, Sethekk Halls */ @@ -57,113 +57,109 @@ Position const PosSummonBrood[7] = { -69.25543f, 303.0768f, 97.84479f, 5.532694f }, { -87.59662f, 263.5181f, 92.70478f, 1.658063f }, { -73.54323f, 276.6267f, 94.25807f, 2.802979f }, - { -81.70527f, 280.8776f, 44.58830f, 0.526849f }, + { -81.70527f, 280.8776f, 44.58830f, 0.526849f } }; class boss_anzu : public CreatureScript { -public: - boss_anzu() : CreatureScript("boss_anzu") { } + public: + boss_anzu() : CreatureScript("boss_anzu") { } - struct boss_anzuAI : public BossAI - { - boss_anzuAI(Creature* creature) : BossAI(creature, DATA_ANZU) { } - - void Reset() OVERRIDE + struct boss_anzuAI : public BossAI { - summon66 = false; - summon33 = false; - } + boss_anzuAI(Creature* creature) : BossAI(creature, DATA_ANZU) { } - void EnterCombat(Unit* /*who*/) OVERRIDE - { - events.ScheduleEvent(EVENT_PARALYZING_SCREECH, 14000); - events.ScheduleEvent(EVENT_CYCLONE_OF_FEATHERS, 5000); - } + void Reset() OVERRIDE + { + _under33Percent = false; + _under66Percent = false; + } - void JustDied(Unit* /*killer*/) OVERRIDE - { - if (instance) - instance->SetData(DATA_ANZU, DONE); - } + void EnterCombat(Unit* /*who*/) OVERRIDE + { + events.ScheduleEvent(EVENT_PARALYZING_SCREECH, 14000); + events.ScheduleEvent(EVENT_CYCLONE_OF_FEATHERS, 5000); + } - void KilledUnit(Unit* /*victim*/) OVERRIDE {} + void JustDied(Unit* /*killer*/) OVERRIDE + { + if (instance) + instance->SetData(DATA_ANZU, DONE); + } - void UpdateAI(uint32 diff) OVERRIDE - { - if (!UpdateVictim()) - return; + void DamageTaken(Unit* /*killer*/, uint32 &damage) OVERRIDE + { + if (me->HealthBelowPctDamaged(33, damage) && !_under33Percent) + { + _under33Percent = true; + Talk(SAY_SUMMON_BROOD); + events.ScheduleEvent(EVENT_SUMMON, 3000); + } - events.Update(diff); + if (me->HealthBelowPctDamaged(66, damage) && !_under66Percent) + { + _under66Percent = true; + Talk(SAY_SUMMON_BROOD); + events.ScheduleEvent(EVENT_SUMMON, 3000); + } + } - while (uint32 eventId = events.ExecuteEvent()) + void UpdateAI(uint32 diff) OVERRIDE { - switch (eventId) + if (!UpdateVictim()) + return; + + events.Update(diff); + + while (uint32 eventId = events.ExecuteEvent()) { - case EVENT_PARALYZING_SCREECH: + switch (eventId) + { + case EVENT_PARALYZING_SCREECH: DoCastVictim(SPELL_PARALYZING_SCREECH); - events.ScheduleEvent(EVENT_PARALYZING_SCREECH, 26000); - break; - - case EVENT_CYCLONE_OF_FEATHERS: - if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0)) - DoCast(target, SPELL_CYCLONE_OF_FEATHERS); - events.ScheduleEvent(EVENT_CYCLONE_OF_FEATHERS, 21000); - break; - case EVENT_SUMMON: - // TODO: Add pathing for Brood of Anzu - me->SummonCreature(NPC_BROOD_OF_ANZU, PosSummonBrood[0], TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 46000); - me->SummonCreature(NPC_BROOD_OF_ANZU, PosSummonBrood[1], TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 46000); - me->SummonCreature(NPC_BROOD_OF_ANZU, PosSummonBrood[2], TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 46000); - me->SummonCreature(NPC_BROOD_OF_ANZU, PosSummonBrood[3], TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 46000); - me->SummonCreature(NPC_BROOD_OF_ANZU, PosSummonBrood[4], TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 46000); - me->SummonCreature(NPC_BROOD_OF_ANZU, PosSummonBrood[5], TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 46000); - me->SummonCreature(NPC_BROOD_OF_ANZU, PosSummonBrood[6], TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 46000); - DoCast(me, SPELL_BANISH_SELF); - events.ScheduleEvent(EVENT_SPELL_BOMB, 12000); - break; - case EVENT_SPELL_BOMB: - if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0)) - { - if (target->getPowerType() == POWER_MANA) + events.ScheduleEvent(EVENT_PARALYZING_SCREECH, 26000); + break; + case EVENT_CYCLONE_OF_FEATHERS: + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0)) + DoCast(target, SPELL_CYCLONE_OF_FEATHERS); + events.ScheduleEvent(EVENT_CYCLONE_OF_FEATHERS, 21000); + break; + case EVENT_SUMMON: + // TODO: Add pathing for Brood of Anzu + for (uint8 i = 0; i < 7; i++) + me->SummonCreature(NPC_BROOD_OF_ANZU, PosSummonBrood[i], TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 46000); + + DoCast(me, SPELL_BANISH_SELF); + events.ScheduleEvent(EVENT_SPELL_BOMB, 12000); + break; + case EVENT_SPELL_BOMB: + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0)) { - DoCast(target, SPELL_SPELL_BOMB); - Talk(SAY_SPELL_BOMB, target->GetGUID()); + if (target->getPowerType() == POWER_MANA) + { + DoCast(target, SPELL_SPELL_BOMB); + Talk(SAY_SPELL_BOMB, target->GetGUID()); + } } - } - break; - default: - break; + break; + default: + break; + } } - } - if (HealthBelowPct(66) && !summon66) - { - summon66 = true; - Talk(SAY_SUMMON_BROOD); - events.ScheduleEvent(EVENT_SUMMON, 3000); + DoMeleeAttackIfReady(); } - if (HealthBelowPct(33) && !summon33) - { - summon33 = true; - Talk(SAY_SUMMON_BROOD); - events.ScheduleEvent(EVENT_SUMMON, 3000); - } - - DoMeleeAttackIfReady(); - } + private: + bool _under33Percent; + bool _under66Percent; - private: - bool summon66; - bool summon33; + }; - }; - - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return new boss_anzuAI(creature); - } + CreatureAI* GetAI(Creature* creature) const OVERRIDE + { + return new boss_anzuAI(creature); + } }; void AddSC_boss_anzu() diff --git a/src/server/scripts/Outland/BlackTemple/black_temple.h b/src/server/scripts/Outland/BlackTemple/black_temple.h index 971cc36d7ba..fb529a6b522 100644 --- a/src/server/scripts/Outland/BlackTemple/black_temple.h +++ b/src/server/scripts/Outland/BlackTemple/black_temple.h @@ -1,6 +1,5 @@ /* * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2006-2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/> * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the @@ -19,36 +18,77 @@ #ifndef BLACK_TEMPLE_H_ #define BLACK_TEMPLE_H_ +#define BTScriptName "instance_black_temple" + uint32 const EncounterCount = 9; enum DataTypes { - DATA_AKAMA = 1, - DATA_AKAMA_SHADE = 2, - DATA_GURTOGGBLOODBOILEVENT = 3, - DATA_HIGHWARLORDNAJENTUS = 4, - DATA_HIGHWARLORDNAJENTUSEVENT = 5, - DATA_ILLIDANSTORMRAGE = 6, - DATA_ILLIDANSTORMRAGEEVENT = 7, - DATA_ILLIDARICOUNCILEVENT = 8, - DATA_ILLIDARICOUNCIL = 9, - DATA_LADYMALANDE = 10, - DATA_HIGHNETHERMANCERZEREVOR = 11, - DATA_GATHIOSTHESHATTERER = 12, - DATA_VERASDARKSHADOW = 13, - DATA_MOTHERSHAHRAZEVENT = 14, - DATA_RELIQUARYOFSOULSEVENT = 15, - DATA_SHADEOFAKAMA = 16, - DATA_SHADEOFAKAMAEVENT = 17, - DATA_SUPREMUS = 18, - DATA_SUPREMUSEVENT = 19, - DATA_TERONGOREFIENDEVENT = 20, - DATA_GAMEOBJECT_NAJENTUS_GATE = 21, - DATA_GAMEOBJECT_ILLIDAN_GATE = 22, - DATA_GAMEOBJECT_ILLIDAN_DOOR_R = 23, - DATA_GAMEOBJECT_ILLIDAN_DOOR_L = 24, - DATA_GAMEOBJECT_SUPREMUS_DOORS = 25, - DATA_BLOOD_ELF_COUNCIL_VOICE = 26 + // Encounter States/Boss GUIDs + DATA_HIGH_WARLORD_NAJENTUS = 0, + DATA_SUPREMUS = 1, + DATA_SHADE_OF_AKAMA = 2, + DATA_TERON_GOREFIEND = 3, + DATA_GURTOGG_BLOODBOIL = 4, + DATA_RELIQUARY_OF_SOULS = 5, + DATA_MOTHER_SHAHRAZ = 6, + DATA_ILLIDARI_COUNCIL = 7, + DATA_ILLIDAN_STORMRAGE = 8, + + // Additional Data + DATA_AKAMA_SHADE = 9, + DATA_AKAMA = 10, + + DATA_GATHIOS_THE_SHATTERER = 11, + DATA_HIGH_NETHERMANCER_ZEREVOR = 12, + DATA_LADY_MALANDE = 13, + DATA_VERAS_DARKSHADOW = 14, + DATA_BLOOD_ELF_COUNCIL_VOICE = 15, + + DATA_GO_ILLIDAN_GATE = 16, + DATA_GO_ILLIDAN_DOOR_R = 17, + DATA_GO_ILLIDAN_DOOR_L = 18 +}; + +enum CreatureIds +{ + NPC_HIGH_WARLORD_NAJENTUS = 22887, + NPC_SUPREMUS = 22898, + NPC_SHADE_OF_AKAMA = 22841, + NPC_AKAMA_SHADE = 23191, // This is the Akama that starts the Shade of Akama encounter. + NPC_AKAMA = 23089, // This is the Akama that starts the Illidan encounter. + + NPC_GATHIOS_THE_SHATTERER = 22949, + NPC_HIGH_NETHERMANCER_ZEREVOR = 22950, + NPC_LADY_MALANDE = 22951, + NPC_VERAS_DARKSHADOW = 22952, + NPC_ILLIDARI_COUNCIL = 23426, + NPC_BLOOD_ELF_COUNCIL_VOICE = 23499, + + NPC_ILLIDAN_STORMRAGE = 22917 }; -#endif +enum GameObjectIds +{ + GO_NAJENTUS_GATE = 185483, + GO_SUPREMUS_GATE = 185882, + GO_SHADE_OF_AKAMA_DOOR = 185478, + GO_TERON_DOOR_1 = 185480, + GO_TERON_DOOR_2 = 186153, + GO_GURTOGG_DOOR = 185892, + GO_TEMPLE_DOOR = 185479, + GO_MOTHER_SHAHRAZ_DOOR = 185482, + GO_COUNCIL_DOOR_1 = 185481, + GO_COUNCIL_DOOR_2 = 186152, + GO_ILLIDAN_GATE = 185905, + GO_ILLIDAN_DOOR_R = 186261, + GO_ILLIDAN_DOOR_L = 186262 +}; + +template<class AI> +AI* GetBlackTempleAI(Creature* creature) +{ + return GetInstanceAI<AI>(creature, BTScriptName); +} + +#endif // BLACK_TEMPLE_H_ diff --git a/src/server/scripts/Outland/BlackTemple/boss_bloodboil.cpp b/src/server/scripts/Outland/BlackTemple/boss_bloodboil.cpp index 7a11044476a..3a33885144d 100644 --- a/src/server/scripts/Outland/BlackTemple/boss_bloodboil.cpp +++ b/src/server/scripts/Outland/BlackTemple/boss_bloodboil.cpp @@ -96,7 +96,7 @@ public: void Reset() OVERRIDE { if (instance) - instance->SetData(DATA_GURTOGGBLOODBOILEVENT, NOT_STARTED); + instance->SetBossState(DATA_GURTOGG_BLOODBOIL, NOT_STARTED); TargetGUID = 0; @@ -124,7 +124,7 @@ public: DoZoneInCombat(); Talk(SAY_AGGRO); if (instance) - instance->SetData(DATA_GURTOGGBLOODBOILEVENT, IN_PROGRESS); + instance->SetBossState(DATA_GURTOGG_BLOODBOIL, IN_PROGRESS); } void KilledUnit(Unit* /*victim*/) OVERRIDE @@ -135,7 +135,7 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (instance) - instance->SetData(DATA_GURTOGGBLOODBOILEVENT, DONE); + instance->SetBossState(DATA_GURTOGG_BLOODBOIL, DONE); Talk(SAY_DEATH); } diff --git a/src/server/scripts/Outland/BlackTemple/boss_illidan.cpp b/src/server/scripts/Outland/BlackTemple/boss_illidan.cpp index 2fdfe72a6f9..4dedc774bb8 100644 --- a/src/server/scripts/Outland/BlackTemple/boss_illidan.cpp +++ b/src/server/scripts/Outland/BlackTemple/boss_illidan.cpp @@ -31,10 +31,6 @@ EndScriptData */ #include "Player.h" #include "SpellInfo.h" -#define GETGO(obj, guid) GameObject* obj = instance->instance->GetGameObject(guid) -#define GETUNIT(unit, guid) Unit* unit = Unit::GetUnit(*me, guid) -#define GETCRE(cre, guid) Creature* cre = Unit::GetCreature(*me, guid) - #define EMOTE_UNABLE_TO_SUMMON "%s is unable to summon Maiev Shadowsong and enter Phase 4. Resetting Encounter." // Other defines @@ -409,11 +405,11 @@ public: void EnrageCheck() { - if (GETUNIT(Glaive, GlaiveGUID)) + if (Creature* glaive = ObjectAccessor::GetCreature(*me, GlaiveGUID)) { - if (!me->IsWithinDistInMap(Glaive, FLAME_ENRAGE_DISTANCE)) + if (!me->IsWithinDistInMap(glaive, FLAME_ENRAGE_DISTANCE)) { - Glaive->InterruptNonMeleeSpells(true); + glaive->InterruptNonMeleeSpells(true); DoCast(me, SPELL_FLAME_ENRAGE, true); DoResetThreat(); if (SelectTarget(SELECT_TARGET_RANDOM, 0)) @@ -424,7 +420,7 @@ public: } else if (!me->HasAura(SPELL_AZZINOTH_CHANNEL)) { - Glaive->CastSpell(me, SPELL_AZZINOTH_CHANNEL, false); + glaive->CastSpell(me, SPELL_AZZINOTH_CHANNEL, false); me->RemoveAurasDueToSpell(SPELL_FLAME_ENRAGE); } } @@ -547,9 +543,9 @@ public: if (!instance) return; - instance->SetData(DATA_ILLIDANSTORMRAGEEVENT, DONE); // Completed + instance->SetBossState(DATA_ILLIDAN_STORMRAGE, DONE); - for (uint8 i = DATA_GAMEOBJECT_ILLIDAN_DOOR_R; i < DATA_GAMEOBJECT_ILLIDAN_DOOR_L + 1; ++i) + for (uint8 i = DATA_GO_ILLIDAN_DOOR_R; i < DATA_GO_ILLIDAN_DOOR_L + 1; ++i) instance->HandleGameObject(instance->GetData64(i), true); } @@ -694,13 +690,14 @@ public: } if (MaievGUID) { - GETCRE(Maiev, MaievGUID); - if (Maiev && Maiev->IsAlive()) - Maiev->AI()->DoAction(NextPhase); + if (Creature* maiev = ObjectAccessor::GetCreature(*me, MaievGUID)) + if (maiev->IsAlive()) + maiev->AI()->DoAction(NextPhase); } Phase = NextPhase; Event = EVENT_NULL; } + void CastEyeBlast() { me->InterruptNonMeleeSpells(false); @@ -738,26 +735,27 @@ public: me->SetTarget(Trigger->GetGUID()); DoCast(Trigger, SPELL_EYE_BLAST); } + void SummonFlamesOfAzzinoth() { Talk(SAY_ILLIDAN_SUMMONFLAMES); for (uint8 i = 0; i < 2; ++i) { - if (GETUNIT(Glaive, GlaiveGUID[i])) + if (Creature* glaive = ObjectAccessor::GetCreature(*me, GlaiveGUID[i])) { - Creature* Flame = me->SummonCreature(FLAME_OF_AZZINOTH, GlaivePosition[i+2].x, GlaivePosition[i+2].y, GlaivePosition[i+2].z, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 5000); - if (Flame) + if (Creature* flame = me->SummonCreature(FLAME_OF_AZZINOTH, GlaivePosition[i+2].x, GlaivePosition[i+2].y, GlaivePosition[i+2].z, 0, TEMPSUMMON_CORPSE_TIMED_DESPAWN, 5000)) { - Flame->setFaction(me->getFaction()); // Just in case the database has it as a different faction - Flame->SetMeleeDamageSchool(SPELL_SCHOOL_FIRE); - FlameGUID[i] = Flame->GetGUID(); // Record GUID in order to check if they're dead later on to move to the next phase - CAST_AI(npc_flame_of_azzinoth::flame_of_azzinothAI, Flame->AI())->SetGlaiveGUID(GlaiveGUID[i]); - Glaive->CastSpell(Flame, SPELL_AZZINOTH_CHANNEL, false); // Glaives do some random Beam type channel on it. + flame->setFaction(me->getFaction()); // Just in case the database has it as a different faction + flame->SetMeleeDamageSchool(SPELL_SCHOOL_FIRE); + FlameGUID[i] = flame->GetGUID(); // Record GUID in order to check if they're dead later on to move to the next phase + CAST_AI(npc_flame_of_azzinoth::flame_of_azzinothAI, flame->AI())->SetGlaiveGUID(GlaiveGUID[i]); + glaive->CastSpell(flame, SPELL_AZZINOTH_CHANNEL, false); // Glaives do some random Beam type channel on it. } } } } + void SummonMaiev() { DoCast(me, SPELL_SHADOW_PRISON, true); @@ -853,11 +851,9 @@ public: { if (GlaiveGUID[i]) { - if (GETUNIT(Glaive, GlaiveGUID[i])) - { - Glaive->SetVisible(false); - Glaive->setDeathState(JUST_DIED); // Despawn the Glaive - } + if (Creature* glaive = ObjectAccessor::GetCreature(*me, GlaiveGUID[i])) + glaive->DespawnOrUnsummon(); + GlaiveGUID[i] = 0; } } @@ -1173,9 +1169,10 @@ public: damage = 0; else { - GETUNIT(Illidan, IllidanGUID); - if (Illidan && Illidan->GetVictim() == me) - damage = me->CountPctFromMaxHealth(10); + if (Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID)) + if (illidan->GetVictim() == me) + damage = me->CountPctFromMaxHealth(10); + if (damage >= me->GetHealth()) damage = 0; } @@ -1190,9 +1187,9 @@ public: AttackStartNoMove(who); else if (Phase == PHASE_DEMON || Phase == PHASE_TRANSFORM_SEQUENCE) { - GETUNIT(Illidan, IllidanGUID); - if (Illidan && me->IsWithinDistInMap(Illidan, 25)) - BlinkToPlayer();// Do not let dread aura hurt her. + if (Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID)) + if (me->IsWithinDistInMap(illidan, 25)) + BlinkToPlayer(); // Do not let dread aura hurt her. AttackStartNoMove(who); } else @@ -1253,11 +1250,11 @@ public: void BlinkToPlayer() { - if (GETCRE(Illidan, IllidanGUID)) + if (Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID)) { - Unit* target = Illidan->AI()->SelectTarget(SELECT_TARGET_RANDOM, 0); + Unit* target = illidan->AI()->SelectTarget(SELECT_TARGET_RANDOM, 0); - if (!target || !me->IsWithinDistInMap(target, 80) || Illidan->IsWithinDistInMap(target, 20)) + if (!target || !me->IsWithinDistInMap(target, 80) || illidan->IsWithinDistInMap(target, 20)) { uint8 pos = rand()%4; BlinkTo(HoverPosition[pos].x, HoverPosition[pos].y, HoverPosition[pos].z); @@ -1329,8 +1326,8 @@ public: { me->SetVisible(false); me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE); - if (GETCRE(Illidan, IllidanGUID)) - CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, Illidan->AI())->DeleteFromThreatList(me->GetGUID()); + if (Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID)) + CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, illidan->AI())->DeleteFromThreatList(me->GetGUID()); me->AttackStop(); Timer[EVENT_MAIEV_STEALTH] = 60000; // reappear after 1 minute MaxTimer = 1; @@ -1372,12 +1369,12 @@ public: WalkCount = 0; if (instance) { - instance->SetData(DATA_ILLIDANSTORMRAGEEVENT, NOT_STARTED); + instance->SetBossState(DATA_ILLIDAN_STORMRAGE, NOT_STARTED); - IllidanGUID = instance->GetData64(DATA_ILLIDANSTORMRAGE); - GateGUID = instance->GetData64(DATA_GAMEOBJECT_ILLIDAN_GATE); - DoorGUID[0] = instance->GetData64(DATA_GAMEOBJECT_ILLIDAN_DOOR_R); - DoorGUID[1] = instance->GetData64(DATA_GAMEOBJECT_ILLIDAN_DOOR_L); + IllidanGUID = instance->GetData64(DATA_ILLIDAN_STORMRAGE); + GateGUID = instance->GetData64(DATA_GO_ILLIDAN_GATE); + DoorGUID[0] = instance->GetData64(DATA_GO_ILLIDAN_DOOR_R); + DoorGUID[1] = instance->GetData64(DATA_GO_ILLIDAN_DOOR_L); if (JustCreated) // close all doors at create { @@ -1466,18 +1463,18 @@ public: if (!instance) return; - instance->SetData(DATA_ILLIDANSTORMRAGEEVENT, IN_PROGRESS); + instance->SetBossState(DATA_ILLIDAN_STORMRAGE, IN_PROGRESS); for (uint8 i = 0; i < 2; ++i) instance->HandleGameObject(DoorGUID[i], false); - if (GETCRE(Illidan, IllidanGUID)) + if (Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID)) { - Illidan->RemoveAurasDueToSpell(SPELL_KNEEL); - me->SetInFront(Illidan); - Illidan->SetInFront(me); + illidan->RemoveAurasDueToSpell(SPELL_KNEEL); + me->SetInFront(illidan); + illidan->SetInFront(me); me->GetMotionMaster()->MoveIdle(); - Illidan->GetMotionMaster()->MoveIdle(); - CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, Illidan->AI())->AkamaGUID = me->GetGUID(); - CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, Illidan->AI())->EnterPhase(PHASE_TALK_SEQUENCE); + illidan->GetMotionMaster()->MoveIdle(); + CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, illidan->AI())->AkamaGUID = me->GetGUID(); + CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, illidan->AI())->EnterPhase(PHASE_TALK_SEQUENCE); } } @@ -1488,8 +1485,8 @@ public: if (!JustCreated) return; float x, y, z; - if (GETGO(Gate, GateGUID)) - Gate->GetPosition(x, y, z); + if (GameObject* gate = ObjectAccessor::GetGameObject(*me, GateGUID)) + gate->GetPosition(x, y, z); else return; // if door not spawned, don't crash server @@ -1531,8 +1528,8 @@ public: WalkCount = 0; else if (Phase == PHASE_TALK) { - if (GETCRE(Illidan, IllidanGUID)) - CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, Illidan->AI())->DeleteFromThreatList(me->GetGUID()); + if (Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID)) + CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, illidan->AI())->DeleteFromThreatList(me->GetGUID()); EnterEvadeMode(); me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE); ++WalkCount; @@ -1554,10 +1551,10 @@ public: } break; case PHASE_FIGHT_ILLIDAN: - if (GETUNIT(Illidan, IllidanGUID)) + if (Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID)) { - me->AddThreat(Illidan, 10000000.0f); - me->GetMotionMaster()->MoveChase(Illidan); + me->AddThreat(illidan, 10000000.0f); + me->GetMotionMaster()->MoveChase(illidan); } Timer = 30000; // chain lightning break; @@ -1584,10 +1581,10 @@ public: switch (TalkCount) { case 0: - if (GETCRE(Illidan, IllidanGUID)) + if (Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID)) { - CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, Illidan->AI())->Timer[EVENT_TAUNT] += 30000; - Illidan->AI()->Talk(SAY_ILLIDAN_MINION); + CAST_AI(boss_illidan_stormrage::boss_illidan_stormrageAI, illidan->AI())->Timer[EVENT_TAUNT] += 30000; + illidan->AI()->Talk(SAY_ILLIDAN_MINION); } Timer = 8000; break; @@ -1694,7 +1691,7 @@ public: { if (Check_Timer <= diff) { - if (instance && instance->GetData(DATA_ILLIDARICOUNCILEVENT) == DONE) + if (instance && instance->GetBossState(DATA_ILLIDARI_COUNCIL) == DONE) me->SetVisible(true); Check_Timer = 5000; @@ -1728,8 +1725,8 @@ public: break; case PHASE_FIGHT_ILLIDAN: { - GETUNIT(Illidan, IllidanGUID); - if (Illidan && Illidan->HealthBelowPct(90)) + Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID); + if (illidan && illidan->HealthBelowPct(90)) EnterPhase(PHASE_TALK); else { @@ -1752,9 +1749,9 @@ public: me->AddThreat(Elite, 1000000.0f); } Timer = urand(10000, 16000); - GETUNIT(Illidan, IllidanGUID); - if (Illidan && Illidan->HealthBelowPct(10)) - EnterPhase(PHASE_RETURN); + if (Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID)) + if (illidan->HealthBelowPct(10)) + EnterPhase(PHASE_RETURN); } break; default: @@ -1803,22 +1800,14 @@ public: void boss_illidan_stormrage::boss_illidan_stormrageAI::Reset() { if (instance) - instance->SetData(DATA_ILLIDANSTORMRAGEEVENT, NOT_STARTED); + instance->SetBossState(DATA_ILLIDAN_STORMRAGE, NOT_STARTED); - if (AkamaGUID) + if (Creature* akama = ObjectAccessor::GetCreature(*me, AkamaGUID)) { - if (GETCRE(Akama, AkamaGUID)) - { - if (!Akama->IsAlive()) - Akama->Respawn(); - else - { - CAST_AI(npc_akama_illidan::npc_akama_illidanAI, Akama->AI())->EnterEvadeMode(); - Akama->GetMotionMaster()->MoveTargetedHome(); - CAST_AI(npc_akama_illidan::npc_akama_illidanAI, Akama->AI())->Reset(); - } - } - AkamaGUID = 0; + if (!akama->IsAlive()) + akama->Respawn(); + else + akama->AI()->EnterEvadeMode(); } MaievGUID = 0; @@ -1908,11 +1897,11 @@ void boss_illidan_stormrage::boss_illidan_stormrageAI::HandleTalkSequence() me->SetWalk(false); break; case 9: - if (GETCRE(Akama, AkamaGUID)) + if (Creature* akama = ObjectAccessor::GetCreature(*me, AkamaGUID)) { me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE + UNIT_FLAG_NOT_SELECTABLE); - me->AddThreat(Akama, 100.0f); - CAST_AI(npc_akama_illidan::npc_akama_illidanAI, Akama->AI())->EnterPhase(PHASE_FIGHT_ILLIDAN); + me->AddThreat(akama, 100.0f); + CAST_AI(npc_akama_illidan::npc_akama_illidanAI, akama->AI())->EnterPhase(PHASE_FIGHT_ILLIDAN); EnterPhase(PHASE_NORMAL); } break; @@ -1920,23 +1909,23 @@ void boss_illidan_stormrage::boss_illidan_stormrageAI::HandleTalkSequence() SummonMaiev(); break; case 11: - if (GETUNIT(Maiev, MaievGUID)) + if (Creature* maiev = ObjectAccessor::GetCreature(*me, MaievGUID)) { - Maiev->SetVisible(true); // Maiev is now visible - Maiev->CastSpell(Maiev, SPELL_TELEPORT_VISUAL, true); // onoz she looks like she teleported! - Maiev->SetInFront(me); // Have her face us - me->SetInFront(Maiev); // Face her, so it's not rude =P - Maiev->GetMotionMaster()->MoveIdle(); + maiev->SetVisible(true); // Maiev is now visible + maiev->CastSpell(maiev, SPELL_TELEPORT_VISUAL, true); // onoz she looks like she teleported! + maiev->SetInFront(me); // Have her face us + me->SetInFront(maiev); // Face her, so it's not rude =P + maiev->GetMotionMaster()->MoveIdle(); me->GetMotionMaster()->MoveIdle(); } break; case 14: - if (GETCRE(Maiev, MaievGUID)) + if (Creature* maiev = ObjectAccessor::GetCreature(*me, MaievGUID)) { me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE + UNIT_FLAG_NOT_SELECTABLE); - Maiev->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE + UNIT_FLAG_NOT_SELECTABLE); - Maiev->AddThreat(me, 10000000.0f); // Have Maiev add a lot of threat on us so that players don't pull her off if they damage her via AOE - Maiev->AI()->AttackStart(me); // Force Maiev to attack us. + maiev->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE + UNIT_FLAG_NOT_SELECTABLE); + maiev->AddThreat(me, 10000000.0f); // Have Maiev add a lot of threat on us so that players don't pull her off if they damage her via AOE + maiev->AI()->AttackStart(me); // Force Maiev to attack us. EnterPhase(PHASE_NORMAL_MAIEV); } break; @@ -1945,26 +1934,26 @@ void boss_illidan_stormrage::boss_illidan_stormrageAI::HandleTalkSequence() Summons.DespawnAll(); break; case 17: - if (GETCRE(Akama, AkamaGUID)) + if (Creature* akama = ObjectAccessor::GetCreature(*me, AkamaGUID)) { - if (!me->IsWithinDistInMap(Akama, 15)) + if (!me->IsWithinDistInMap(akama, 15)) { float x, y, z; me->GetPosition(x, y, z); x += 10; y += 10; - Akama->GetMotionMaster()->Clear(false); + akama->GetMotionMaster()->Clear(false); // Akama->GetMotionMaster()->MoveIdle(); - Akama->SetPosition(x, y, z, 0.0f); - Akama->MonsterMoveWithSpeed(x, y, z, 0); // Illidan must not die until Akama arrives. - Akama->GetMotionMaster()->MoveChase(me); + akama->SetPosition(x, y, z, 0.0f); + akama->MonsterMoveWithSpeed(x, y, z, 0); // Illidan must not die until Akama arrives. + akama->GetMotionMaster()->MoveChase(me); } } break; case 19: // Make Maiev leave - if (GETUNIT(Maiev, MaievGUID)) + if (Creature* maiev = ObjectAccessor::GetCreature(*me, MaievGUID)) { - Maiev->CastSpell(Maiev, SPELL_TELEPORT_VISUAL, true); - Maiev->setDeathState(JUST_DIED); + maiev->CastSpell(maiev, SPELL_TELEPORT_VISUAL, true); + maiev->setDeathState(JUST_DIED); me->SetUInt32Value(UNIT_FIELD_BYTES_1, UNIT_STAND_STATE_DEAD); } break; @@ -2171,7 +2160,7 @@ public: void Reset() OVERRIDE { if (instance) - IllidanGUID = instance->GetData64(DATA_ILLIDANSTORMRAGE); + IllidanGUID = instance->GetData64(DATA_ILLIDAN_STORMRAGE); else IllidanGUID = 0; @@ -2208,22 +2197,24 @@ public: AttackStart(target); else { - me->SetVisible(false); - me->setDeathState(JUST_DIED); + me->DespawnOrUnsummon(); return; } } if (CheckTimer <= diff) { - GETUNIT(Illidan, IllidanGUID); - if (!Illidan || Illidan->ToCreature()->IsInEvadeMode()) + Creature* illidan = ObjectAccessor::GetCreature(*me, IllidanGUID); + if (!illidan || illidan->IsInEvadeMode()) { - me->SetVisible(false); - me->setDeathState(JUST_DIED); + me->DespawnOrUnsummon(); return; - } else CheckTimer = 5000; - } else CheckTimer -= diff; + } + else + CheckTimer = 5000; + } + else + CheckTimer -= diff; DoMeleeAttackIfReady(); } diff --git a/src/server/scripts/Outland/BlackTemple/boss_mother_shahraz.cpp b/src/server/scripts/Outland/BlackTemple/boss_mother_shahraz.cpp index b9172be49da..aafe5f365b2 100644 --- a/src/server/scripts/Outland/BlackTemple/boss_mother_shahraz.cpp +++ b/src/server/scripts/Outland/BlackTemple/boss_mother_shahraz.cpp @@ -114,7 +114,7 @@ public: void Reset() OVERRIDE { if (instance) - instance->SetData(DATA_MOTHERSHAHRAZEVENT, NOT_STARTED); + instance->SetBossState(DATA_MOTHER_SHAHRAZ, NOT_STARTED); for (uint8 i = 0; i<3; ++i) TargetGUID[i] = 0; @@ -137,7 +137,7 @@ public: void EnterCombat(Unit* /*who*/) OVERRIDE { if (instance) - instance->SetData(DATA_MOTHERSHAHRAZEVENT, IN_PROGRESS); + instance->SetBossState(DATA_MOTHER_SHAHRAZ, IN_PROGRESS); DoZoneInCombat(); Talk(SAY_AGGRO); @@ -151,7 +151,7 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (instance) - instance->SetData(DATA_MOTHERSHAHRAZEVENT, DONE); + instance->SetBossState(DATA_MOTHER_SHAHRAZ, DONE); Talk(SAY_DEATH); } diff --git a/src/server/scripts/Outland/BlackTemple/boss_reliquary_of_souls.cpp b/src/server/scripts/Outland/BlackTemple/boss_reliquary_of_souls.cpp index 22ea1b70c21..ab3bc98b41b 100644 --- a/src/server/scripts/Outland/BlackTemple/boss_reliquary_of_souls.cpp +++ b/src/server/scripts/Outland/BlackTemple/boss_reliquary_of_souls.cpp @@ -159,14 +159,13 @@ public: void Reset() OVERRIDE { if (instance) - instance->SetData(DATA_RELIQUARYOFSOULSEVENT, NOT_STARTED); + instance->SetBossState(DATA_RELIQUARY_OF_SOULS, NOT_STARTED); if (EssenceGUID) { - if (Creature* Essence = Unit::GetCreature(*me, EssenceGUID)) - { - Essence->DespawnOrUnsummon(); - } + if (Creature* essence = ObjectAccessor::GetCreature(*me, EssenceGUID)) + essence->DespawnOrUnsummon(); + EssenceGUID = 0; } @@ -178,7 +177,6 @@ public: } void MoveInLineOfSight(Unit* who) OVERRIDE - { if (!who) return; @@ -200,7 +198,7 @@ public: me->AddThreat(who, 10000.0f); DoZoneInCombat(); if (instance) - instance->SetData(DATA_RELIQUARYOFSOULSEVENT, IN_PROGRESS); + instance->SetBossState(DATA_RELIQUARY_OF_SOULS, IN_PROGRESS); Phase = 1; Counter = 0; @@ -246,7 +244,7 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (instance) - instance->SetData(DATA_RELIQUARYOFSOULSEVENT, DONE); + instance->SetBossState(DATA_RELIQUARY_OF_SOULS, DONE); } void UpdateAI(uint32 diff) OVERRIDE @@ -422,7 +420,6 @@ public: { damage = 0; me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); - me->Yell(SUFF_SAY_RECAP, LANG_UNIVERSAL, 0); Talk(SUFF_SAY_RECAP); me->SetReactState(REACT_PASSIVE); } @@ -431,14 +428,13 @@ public: void EnterCombat(Unit* /*who*/) OVERRIDE { if (!me->HasFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE)) - { + { Talk(SUFF_SAY_FREED); DoZoneInCombat(); DoCast(me, AURA_OF_SUFFERING, true); // linked aura need core support DoCast(me, ESSENCE_OF_SUFFERING_PASSIVE, true); DoCast(me, ESSENCE_OF_SUFFERING_PASSIVE2, true); - } - else return; + } } void KilledUnit(Unit* /*victim*/) OVERRIDE diff --git a/src/server/scripts/Outland/BlackTemple/boss_shade_of_akama.cpp b/src/server/scripts/Outland/BlackTemple/boss_shade_of_akama.cpp index 4a4304bcd24..a1a965ed015 100644 --- a/src/server/scripts/Outland/BlackTemple/boss_shade_of_akama.cpp +++ b/src/server/scripts/Outland/BlackTemple/boss_shade_of_akama.cpp @@ -123,23 +123,22 @@ enum Events EVENT_SUMMON_ASHTONGUE_SORCERER = 12, EVENT_SUMMON_ASHTONGUE_DEFENDER = 13, // Channeler - EVENT_GET_SHADE_GUID = 14, - EVENT_CHANNEL = 15, + EVENT_CHANNEL = 14, // Ashtongue Sorcerer - EVENT_SORCERER_CHANNEL = 16, + EVENT_SORCERER_CHANNEL = 15, // Ashtongue Defender - EVENT_DEBILITATING_STRIKE = 17, - EVENT_HEROIC_STRIKE = 18, - EVENT_SHIELD_BASH = 19, - EVENT_WINDFURY = 20, + EVENT_DEBILITATING_STRIKE = 16, + EVENT_HEROIC_STRIKE = 17, + EVENT_SHIELD_BASH = 18, + EVENT_WINDFURY = 29, // Ashtongue Rogue - EVENT_DEBILITATING_POISON = 21, - EVENT_EVISCERATE = 22, + EVENT_DEBILITATING_POISON = 20, + EVENT_EVISCERATE = 21, // Ashtongue Elementalist - EVENT_RAIN_OF_FIRE = 23, - EVENT_LIGHTNING_BOLT = 24, + EVENT_RAIN_OF_FIRE = 22, + EVENT_LIGHTNING_BOLT = 23, // Ashtongue Spiritbinder - EVENT_SPIRIT_HEAL = 25, + EVENT_SPIRIT_HEAL = 24 }; struct Location @@ -177,11 +176,11 @@ public: if (!HasKilledAkamaAndReseting) { for (std::list<uint64>::const_iterator itr = Channelers.begin(); itr != Channelers.end(); ++itr) - if (Creature* Channeler = (Unit::GetCreature(*me, *itr))) + if (Creature* Channeler = ObjectAccessor::GetCreature(*me, *itr)) Channeler->DespawnOrUnsummon(); for (std::list<uint64>::const_iterator itr = Spawners.begin(); itr != Spawners.end(); ++itr) - if (Creature* Spawner = (Unit::GetCreature(*me, *itr))) + if (Creature* Spawner = ObjectAccessor::GetCreature(*me, *itr)) Spawner->AI()->SetData(SETDATA_DATA, SETDATA_DESPAWN_ALL_SPAWNS); events.ScheduleEvent(EVENT_FIND_CHANNELERS_SPAWNERS, 3000); @@ -200,16 +199,16 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (instance) - instance->SetData(DATA_SHADEOFAKAMAEVENT, DONE); + instance->SetBossState(DATA_SHADE_OF_AKAMA, DONE); } - void EnterCombat(Unit* /*who*/) OVERRIDE {} + void EnterCombat(Unit* /*who*/) OVERRIDE { } void AttackStart(Unit* who) OVERRIDE { if (me->HasFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE)) { - if (Creature* Akama = Unit::GetCreature((*me), akamaGUID)) + if (Creature* Akama = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) if (Akama->IsAlive()) ScriptedAI::AttackStart(Akama); } @@ -233,7 +232,7 @@ public: events.ScheduleEvent(EVENT_START_ATTACK_AKAMA, 500); events.ScheduleEvent(EVENT_SET_CHANNELERS_SPAWNERS, 1000); me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_STATE_NONE); - if (Creature* Akama = Unit::GetCreature((*me), akamaGUID)) + if (Creature* Akama = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) me->AddThreat(Akama, 10000000.0f); } else if (spell->Id == SPELL_SHADE_SOUL_CHANNEL_2) @@ -269,7 +268,7 @@ public: switch (eventId) { case EVENT_RESET_ENCOUNTER: - if (Creature* Akama = Unit::GetCreature((*me), akamaGUID)) + if (Creature* Akama = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) if (!Akama->IsAlive()) Akama->Respawn(); break; @@ -294,7 +293,6 @@ public: Spawners.push_back((*itr)->GetGUID()); me->SetUInt32Value(UNIT_NPC_EMOTESTATE, EMOTE_STATE_STUN); - akamaGUID = instance->GetData64(DATA_AKAMA_SHADE); break; } default: @@ -312,20 +310,19 @@ public: { for (std::list<uint64>::const_iterator itr = Channelers.begin(); itr != Channelers.end(); ++itr) { - if (Creature* Channeler = (Unit::GetCreature(*me, *itr))) + if (Creature* Channeler = ObjectAccessor::GetCreature(*me, *itr)) Channeler->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); } for (std::list<uint64>::const_iterator itr = Spawners.begin(); itr != Spawners.end(); ++itr) { - if (Creature* Spawner = (Unit::GetCreature(*me, *itr))) + if (Creature* Spawner = ObjectAccessor::GetCreature(*me, *itr)) Spawner->AI()->SetData(SETDATA_DATA, SETDATA_START_SPAWNING); } - break; } case EVENT_START_ATTACK_AKAMA: - me->GetMotionMaster()->MovePoint(0, ShadeWP.x, ShadeWP.y, ShadeWP.z ,false); + me->GetMotionMaster()->MovePoint(0, ShadeWP.x, ShadeWP.y, ShadeWP.z, false); events.ScheduleEvent(EVENT_START_ATTACK_AKAMA, 1000); break; case EVENT_ADD_THREAT: @@ -343,7 +340,7 @@ public: { HasKilledAkamaAndReseting = true; me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); - instance->SetData(DATA_SHADEOFAKAMAEVENT, NOT_STARTED); + instance->SetBossState(DATA_SHADE_OF_AKAMA, NOT_STARTED); me->RemoveAllAurasExceptType(SPELL_AURA_DUMMY); me->DeleteThreatList(); me->CombatStop(); @@ -351,15 +348,15 @@ public: me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_IMMUNE_TO_PC); combatStarted = false; - if (Creature* Akama = Unit::GetCreature((*me), akamaGUID)) + if (Creature* Akama = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) Akama->DespawnOrUnsummon(); for (std::list<uint64>::const_iterator itr = Channelers.begin(); itr != Channelers.end(); ++itr) - if (Creature* Channeler = (Unit::GetCreature(*me, *itr))) + if (Creature* Channeler = ObjectAccessor::GetCreature(*me, *itr)) Channeler->DespawnOrUnsummon(); for (std::list<uint64>::const_iterator itr = Spawners.begin(); itr != Spawners.end(); ++itr) - if (Creature* Spawner = (Unit::GetCreature(*me, *itr))) + if (Creature* Spawner = ObjectAccessor::GetCreature(*me, *itr)) Spawner->AI()->SetData(SETDATA_DATA, SETDATA_DESPAWN_ALL_SPAWNS); events.ScheduleEvent(EVENT_FIND_CHANNELERS_SPAWNERS, 10000); @@ -369,7 +366,7 @@ public: if (!akamaReached) { - if (Creature* Akama = Unit::GetCreature((*me), akamaGUID)) + if (Creature* Akama = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) { if (me->IsWithinDist(Akama, 2.0f, false)) { @@ -384,7 +381,7 @@ public: events.ScheduleEvent(EVENT_ADD_THREAT, 100); for (std::list<uint64>::const_iterator itr = Spawners.begin(); itr != Spawners.end(); ++itr) - if (Creature* Spawner = (Unit::GetCreature(*me, *itr))) + if (Creature* Spawner = ObjectAccessor::GetCreature(*me, *itr)) Spawner->AI()->SetData(SETDATA_DATA, SETDATA_STOP_SPAWNING); } } @@ -401,8 +398,6 @@ public: EventMap events; std::list<uint64> Channelers; std::list<uint64> Spawners; - uint64 akamaGUID; - uint64 ShadeGUID; bool akamaReached; bool combatStarted; bool HasKilledAkamaAndReseting; @@ -443,7 +438,7 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { - if (Creature* Shade = Unit::GetCreature((*me), ShadeGUID)) + if (Creature* Shade = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_SHADE_OF_AKAMA))) if (Shade->IsAlive()) CAST_AI(boss_shade_of_akama::boss_shade_of_akamaAI, Shade->AI())->HasKilledAkama = true; me->GetMotionMaster()->Clear(true); @@ -452,17 +447,14 @@ public: void SpellHit(Unit* /*caster*/, SpellInfo const* spell) OVERRIDE { - if (!StartCombat) + if (spell->Id == SPELL_THREAT && !StartCombat) { - if (spell->Id == SPELL_THREAT) - { - me->ClearUnitState(UNIT_STATE_ROOT); - me->RemoveAura(SPELL_AKAMA_SOUL_CHANNEL); - me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_STUNNED); - if (Creature* Shade = Unit::GetCreature((*me), ShadeGUID)) - Shade->RemoveAura(SPELL_AKAMA_SOUL_CHANNEL); - StartCombat = true; - } + me->ClearUnitState(UNIT_STATE_ROOT); + me->RemoveAura(SPELL_AKAMA_SOUL_CHANNEL); + me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_STUNNED); + if (Creature* Shade = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_SHADE_OF_AKAMA))) + Shade->RemoveAura(SPELL_AKAMA_SOUL_CHANNEL); + StartCombat = true; } } @@ -485,8 +477,7 @@ public: case EVENT_SHADE_START: if (instance) { - ShadeGUID = instance->GetData64(DATA_SHADEOFAKAMA); - instance->SetData(DATA_SHADEOFAKAMAEVENT, IN_PROGRESS); + instance->SetBossState(DATA_SHADE_OF_AKAMA, IN_PROGRESS); me->RemoveFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_GOSSIP); me->RemoveAura(SPELL_STEALTH); me->SetWalk(true); @@ -550,7 +541,6 @@ public: private: InstanceScript* instance; EventMap events; - uint64 ShadeGUID; bool StartChannel; bool ShadeHasDied; bool StartCombat; @@ -587,17 +577,16 @@ public: me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); events.ScheduleEvent(EVENT_CHANNEL, 2000); - events.ScheduleEvent(EVENT_GET_SHADE_GUID, 1000); } void JustDied(Unit* /*killer*/) OVERRIDE { - if (Creature* Shade = (Unit::GetCreature((*me), ShadeGUID))) + if (Creature* Shade = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_SHADE_OF_AKAMA))) Shade->AI()->SetData(SETDATA_DATA, SETDATA_CHANNELER_DIED); } - void EnterCombat(Unit* /*who*/) OVERRIDE {} - void AttackStart(Unit* /*who*/) OVERRIDE {} + void EnterCombat(Unit* /*who*/) OVERRIDE { } + void AttackStart(Unit* /*who*/) OVERRIDE { } void UpdateAI(uint32 diff) OVERRIDE { @@ -608,7 +597,7 @@ public: switch (eventId) { case EVENT_CHANNEL: - if (Creature* Shade = (Unit::GetCreature((*me), ShadeGUID))) + if (Creature* Shade = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_SHADE_OF_AKAMA))) { if (Shade->HasFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE)) DoCast(me, SPELL_SHADE_SOUL_CHANNEL); @@ -620,10 +609,6 @@ public: } events.ScheduleEvent(EVENT_CHANNEL, 2000); break; - case EVENT_GET_SHADE_GUID: - if (instance) - ShadeGUID = instance->GetData64(DATA_SHADEOFAKAMA); - break; default: break; } @@ -633,7 +618,6 @@ public: private: InstanceScript* instance; EventMap events; - uint64 ShadeGUID; }; CreatureAI* GetAI(Creature* creature) const OVERRIDE @@ -764,25 +748,19 @@ public: npc_ashtongue_sorcererAI(Creature* creature) : ScriptedAI(creature) { instance = creature->GetInstanceScript(); - - if (instance) - { - akamaGUID = instance->GetData64(DATA_AKAMA_SHADE); - shadeGUID = instance->GetData64(DATA_SHADEOFAKAMA); - } } void Reset() OVERRIDE { if (!startedBanishing) { - if (Creature* Shade = (Unit::GetCreature((*me), shadeGUID))) + if (Creature* Shade = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_SHADE_OF_AKAMA))) { if (Shade->HasFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE)) me->GetMotionMaster()->MovePoint(0, Shade->GetPositionX(), Shade->GetPositionY(), Shade->GetPositionZ(), false); else { - if (Unit* target = me->GetCreature(*me, akamaGUID)) + if (Unit* target = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) AttackStart(target); } } @@ -795,7 +773,7 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { - if (Creature* Shade = (Unit::GetCreature((*me), shadeGUID))) + if (Creature* Shade = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_SHADE_OF_AKAMA))) Shade->AI()->SetData(SETDATA_DATA, SETDATA_CHANNELER_DIED); me->DespawnOrUnsummon(5000); } @@ -824,7 +802,7 @@ public: switch (eventId) { case EVENT_SORCERER_CHANNEL: - if (Creature* Shade = (Unit::GetCreature((*me), shadeGUID))) + if (Creature* Shade = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_SHADE_OF_AKAMA))) { if (Shade->HasFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE)) { @@ -837,7 +815,7 @@ public: me->InterruptSpell(CURRENT_CHANNELED_SPELL); Shade->AI()->SetData(SETDATA_DATA, SETDATA_CHANNELER_DIED); switchToCombat = true; - if (Unit* target = me->GetCreature(*me, akamaGUID)) + if (Unit* target = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) AttackStart(target); } } @@ -849,7 +827,7 @@ public: if (!startedBanishing) { - Creature* Shade = Unit::GetCreature((*me), shadeGUID); + Creature* Shade = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_SHADE_OF_AKAMA)); if (me->IsWithinDist(Shade, 20.0f, false)) { me->StopMoving(); @@ -866,8 +844,6 @@ public: private: InstanceScript* instance; EventMap events; - uint64 akamaGUID; - uint64 shadeGUID; uint64 summonerGuid; float distanceToShade; bool startedBanishing; @@ -894,15 +870,13 @@ public: npc_ashtongue_defenderAI(Creature* creature) : ScriptedAI(creature) { instance = creature->GetInstanceScript(); - if (instance) - akamaGUID = instance->GetData64(DATA_AKAMA_SHADE); } void Reset() OVERRIDE { summonerGuid = 0; - if (Unit* target = me->GetCreature(*me, akamaGUID)) + if (Unit* target = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) AttackStart(target); } @@ -956,13 +930,13 @@ public: break; } } + DoMeleeAttackIfReady(); } private: InstanceScript* instance; EventMap events; - uint64 akamaGUID; uint64 summonerGuid; }; @@ -986,15 +960,13 @@ public: npc_ashtongue_rogueAI(Creature* creature) : ScriptedAI(creature) { instance = creature->GetInstanceScript(); - if (instance) - akamaGUID = instance->GetData64(DATA_AKAMA_SHADE); } void Reset() OVERRIDE { summonerGuid = 0; - if (Unit* target = me->GetCreature(*me, akamaGUID)) + if (Unit* target = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) AttackStart(target); } @@ -1038,13 +1010,13 @@ public: break; } } + DoMeleeAttackIfReady(); } private: InstanceScript* instance; EventMap events; - uint64 akamaGUID; uint64 summonerGuid; }; @@ -1068,15 +1040,13 @@ public: npc_ashtongue_elementalistAI(Creature* creature) : ScriptedAI(creature) { instance = creature->GetInstanceScript(); - if (instance) - akamaGUID = instance->GetData64(DATA_AKAMA_SHADE); } void Reset() OVERRIDE { summonerGuid = 0; - if (Unit* target = me->GetCreature(*me, akamaGUID)) + if (Unit* target = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) AttackStart(target); } @@ -1120,13 +1090,13 @@ public: break; } } + DoMeleeAttackIfReady(); } private: InstanceScript* instance; EventMap events; - uint64 akamaGUID; uint64 summonerGuid; }; @@ -1150,8 +1120,6 @@ public: npc_ashtongue_spiritbinderAI(Creature* creature) : ScriptedAI(creature) { instance = creature->GetInstanceScript(); - if (instance) - akamaGUID = instance->GetData64(DATA_AKAMA_SHADE); } void Reset() OVERRIDE @@ -1160,7 +1128,7 @@ public: chainHeal = false; summonerGuid = 0; - if (Unit* target = me->GetCreature(*me, akamaGUID)) + if (Unit* target = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_AKAMA_SHADE))) AttackStart(target); } @@ -1224,7 +1192,6 @@ public: private: InstanceScript* instance; EventMap events; - uint64 akamaGUID; uint64 summonerGuid; bool spiritMend; bool chainHeal; diff --git a/src/server/scripts/Outland/BlackTemple/boss_supremus.cpp b/src/server/scripts/Outland/BlackTemple/boss_supremus.cpp index fbc3e387e8e..94423f87bdf 100644 --- a/src/server/scripts/Outland/BlackTemple/boss_supremus.cpp +++ b/src/server/scripts/Outland/BlackTemple/boss_supremus.cpp @@ -31,7 +31,7 @@ EndScriptData */ enum Supremus { EMOTE_NEW_TARGET = 0, - EMOTE_PUNCH_GROUND = 1, //Talk(EMOTE_PUNCH_GROUND); + EMOTE_PUNCH_GROUND = 1, EMOTE_GROUND_CRACK = 2, //Spells @@ -110,11 +110,7 @@ public: if (instance) { if (me->IsAlive()) - { - instance->SetData(DATA_SUPREMUSEVENT, NOT_STARTED); - //ToggleDoors(true); - } - //else ToggleDoors(false); + instance->SetBossState(DATA_SUPREMUS, NOT_STARTED); } phase = 0; @@ -126,7 +122,7 @@ public: void EnterCombat(Unit* /*who*/) OVERRIDE { if (instance) - instance->SetData(DATA_SUPREMUSEVENT, IN_PROGRESS); + instance->SetBossState(DATA_SUPREMUS, IN_PROGRESS); ChangePhase(); events.ScheduleEvent(EVENT_BERSERK, 900000, GCD_CAST); @@ -163,10 +159,8 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (instance) - { - instance->SetData(DATA_SUPREMUSEVENT, DONE); - instance->HandleGameObject(instance->GetData64(DATA_GAMEOBJECT_SUPREMUS_DOORS), true); - } + instance->SetBossState(DATA_SUPREMUS, DONE); + summons.DespawnAll(); } diff --git a/src/server/scripts/Outland/BlackTemple/boss_teron_gorefiend.cpp b/src/server/scripts/Outland/BlackTemple/boss_teron_gorefiend.cpp index a861980ae42..c02954c7b2f 100644 --- a/src/server/scripts/Outland/BlackTemple/boss_teron_gorefiend.cpp +++ b/src/server/scripts/Outland/BlackTemple/boss_teron_gorefiend.cpp @@ -247,7 +247,7 @@ public: void Reset() OVERRIDE { if (instance) - instance->SetData(DATA_TERONGOREFIENDEVENT, NOT_STARTED); + instance->SetBossState(DATA_TERON_GOREFIEND, NOT_STARTED); IncinerateTimer = urand(20000, 31000); SummonDoomBlossomTimer = 12000; @@ -276,7 +276,7 @@ public: if (me->IsWithinDistInMap(who, VISIBLE_RANGE) && me->IsWithinLOSInMap(who)) { if (instance) - instance->SetData(DATA_TERONGOREFIENDEVENT, IN_PROGRESS); + instance->SetBossState(DATA_TERON_GOREFIEND, IN_PROGRESS); me->GetMotionMaster()->Clear(false); me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); @@ -298,7 +298,7 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (instance) - instance->SetData(DATA_TERONGOREFIENDEVENT, DONE); + instance->SetBossState(DATA_TERON_GOREFIEND, DONE); Talk(SAY_DEATH); } diff --git a/src/server/scripts/Outland/BlackTemple/boss_warlord_najentus.cpp b/src/server/scripts/Outland/BlackTemple/boss_warlord_najentus.cpp index 532c66bb14a..1f4a36afad6 100644 --- a/src/server/scripts/Outland/BlackTemple/boss_warlord_najentus.cpp +++ b/src/server/scripts/Outland/BlackTemple/boss_warlord_najentus.cpp @@ -100,7 +100,7 @@ public: SpineTargetGUID = 0; if (instance) - instance->SetData(DATA_HIGHWARLORDNAJENTUSEVENT, NOT_STARTED); + instance->SetBossState(DATA_HIGH_WARLORD_NAJENTUS, NOT_STARTED); } void KilledUnit(Unit* /*victim*/) OVERRIDE @@ -112,7 +112,7 @@ public: void JustDied(Unit* /*killer*/) OVERRIDE { if (instance) - instance->SetData(DATA_HIGHWARLORDNAJENTUSEVENT, DONE); + instance->SetBossState(DATA_HIGH_WARLORD_NAJENTUS, DONE); Talk(SAY_DEATH); } @@ -130,7 +130,7 @@ public: void EnterCombat(Unit* /*who*/) OVERRIDE { if (instance) - instance->SetData(DATA_HIGHWARLORDNAJENTUSEVENT, IN_PROGRESS); + instance->SetBossState(DATA_HIGH_WARLORD_NAJENTUS, IN_PROGRESS); Talk(SAY_AGGRO); DoZoneInCombat(); @@ -228,7 +228,7 @@ public: bool OnGossipHello(Player* player, GameObject* go) OVERRIDE { if (InstanceScript* instance = go->GetInstanceScript()) - if (Creature* Najentus = Unit::GetCreature(*go, instance->GetData64(DATA_HIGHWARLORDNAJENTUS))) + if (Creature* Najentus = ObjectAccessor::GetCreature(*go, instance->GetData64(DATA_HIGH_WARLORD_NAJENTUS))) if (CAST_AI(boss_najentus::boss_najentusAI, Najentus->AI())->RemoveImpalingSpine()) { player->CastSpell(player, SPELL_CREATE_NAJENTUS_SPINE, true); diff --git a/src/server/scripts/Outland/BlackTemple/illidari_council.cpp b/src/server/scripts/Outland/BlackTemple/illidari_council.cpp index 290641437f3..05d19eb62bf 100644 --- a/src/server/scripts/Outland/BlackTemple/illidari_council.cpp +++ b/src/server/scripts/Outland/BlackTemple/illidari_council.cpp @@ -157,10 +157,10 @@ public: { if (InstanceScript* instance = me->GetInstanceScript()) { - Council[0] = instance->GetData64(DATA_GATHIOSTHESHATTERER); - Council[1] = instance->GetData64(DATA_VERASDARKSHADOW); - Council[2] = instance->GetData64(DATA_LADYMALANDE); - Council[3] = instance->GetData64(DATA_HIGHNETHERMANCERZEREVOR); + Council[0] = instance->GetData64(DATA_GATHIOS_THE_SHATTERER); + Council[1] = instance->GetData64(DATA_VERAS_DARKSHADOW); + Council[2] = instance->GetData64(DATA_LADY_MALANDE); + Council[3] = instance->GetData64(DATA_HIGH_NETHERMANCER_ZEREVOR); } else TC_LOG_ERROR(LOG_FILTER_TSCR, ERROR_INST_DATA); } @@ -265,8 +265,8 @@ public: if (instance) { - instance->SetData(DATA_ILLIDARICOUNCILEVENT, NOT_STARTED); - if (Creature* VoiceTrigger = (Unit::GetCreature(*me, instance->GetData64(DATA_BLOOD_ELF_COUNCIL_VOICE)))) + instance->SetBossState(DATA_ILLIDARI_COUNCIL, NOT_STARTED); + if (Creature* VoiceTrigger = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_BLOOD_ELF_COUNCIL_VOICE))) VoiceTrigger->AI()->EnterEvadeMode(); } @@ -289,13 +289,13 @@ public: if (target && target->IsAlive()) { - Council[0] = instance->GetData64(DATA_GATHIOSTHESHATTERER); - Council[1] = instance->GetData64(DATA_HIGHNETHERMANCERZEREVOR); - Council[2] = instance->GetData64(DATA_LADYMALANDE); - Council[3] = instance->GetData64(DATA_VERASDARKSHADOW); + Council[0] = instance->GetData64(DATA_GATHIOS_THE_SHATTERER); + Council[1] = instance->GetData64(DATA_HIGH_NETHERMANCER_ZEREVOR); + Council[2] = instance->GetData64(DATA_LADY_MALANDE); + Council[3] = instance->GetData64(DATA_VERAS_DARKSHADOW); // Start the event for the Voice Trigger - if (Creature* VoiceTrigger = (Unit::GetCreature(*me, instance->GetData64(DATA_BLOOD_ELF_COUNCIL_VOICE)))) + if (Creature* VoiceTrigger = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_BLOOD_ELF_COUNCIL_VOICE))) { CAST_AI(npc_blood_elf_council_voice_trigger::npc_blood_elf_council_voice_triggerAI, VoiceTrigger->AI())->LoadCouncilGUIDs(); CAST_AI(npc_blood_elf_council_voice_trigger::npc_blood_elf_council_voice_triggerAI, VoiceTrigger->AI())->EventStarted = true; @@ -305,13 +305,13 @@ public: { if (Council[i]) { - Unit* member = Unit::GetUnit(*me, Council[i]); - if (member && member->IsAlive()) - member->ToCreature()->AI()->AttackStart(target); + if (Creature* member = ObjectAccessor::GetCreature(*me, Council[i])) + if (member->IsAlive()) + member->AI()->AttackStart(target); } } - instance->SetData(DATA_ILLIDARICOUNCILEVENT, IN_PROGRESS); + instance->SetBossState(DATA_ILLIDARI_COUNCIL, IN_PROGRESS); EventBegun = true; } @@ -330,9 +330,9 @@ public: { if (instance) { - if (Creature* VoiceTrigger = (Unit::GetCreature(*me, instance->GetData64(DATA_BLOOD_ELF_COUNCIL_VOICE)))) + if (Creature* VoiceTrigger = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_BLOOD_ELF_COUNCIL_VOICE))) VoiceTrigger->DealDamage(VoiceTrigger, VoiceTrigger->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false); - instance->SetData(DATA_ILLIDARICOUNCILEVENT, DONE); + instance->SetBossState(DATA_ILLIDARI_COUNCIL, DONE); //me->SummonCreature(AKAMAID, 746.466980f, 304.394989f, 311.90208f, 6.272870f, TEMPSUMMON_DEAD_DESPAWN, 0); } me->DealDamage(me, me->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false); @@ -403,9 +403,8 @@ struct boss_illidari_councilAI : public ScriptedAI { if (instance) { - Creature* Controller = (Unit::GetCreature(*me, instance->GetData64(DATA_ILLIDARICOUNCIL))); - if (Controller) - CAST_AI(npc_illidari_council::npc_illidari_councilAI, Controller->AI())->StartEvent(who); + if (Creature* controller = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_ILLIDARI_COUNCIL))) + CAST_AI(npc_illidari_council::npc_illidari_councilAI, controller->AI())->StartEvent(who); } else { @@ -461,10 +460,10 @@ struct boss_illidari_councilAI : public ScriptedAI return; } - Council[0] = instance->GetData64(DATA_LADYMALANDE); - Council[1] = instance->GetData64(DATA_HIGHNETHERMANCERZEREVOR); - Council[2] = instance->GetData64(DATA_GATHIOSTHESHATTERER); - Council[3] = instance->GetData64(DATA_VERASDARKSHADOW); + Council[0] = instance->GetData64(DATA_LADY_MALANDE); + Council[1] = instance->GetData64(DATA_HIGH_NETHERMANCER_ZEREVOR); + Council[2] = instance->GetData64(DATA_GATHIOS_THE_SHATTERER); + Council[3] = instance->GetData64(DATA_VERAS_DARKSHADOW); LoadedGUIDs = true; } diff --git a/src/server/scripts/Outland/BlackTemple/instance_black_temple.cpp b/src/server/scripts/Outland/BlackTemple/instance_black_temple.cpp index bd70ce012ba..591f28a19f3 100644 --- a/src/server/scripts/Outland/BlackTemple/instance_black_temple.cpp +++ b/src/server/scripts/Outland/BlackTemple/instance_black_temple.cpp @@ -1,6 +1,5 @@ /* * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2006-2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/> * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the @@ -16,382 +15,261 @@ * with this program. If not, see <http://www.gnu.org/licenses/>. */ -/* ScriptData -SDName: Instance_Black_Temple -SD%Complete: 100 -SDComment: Instance Data Scripts and functions to acquire mobs and set encounter status for use in various Black Temple Scripts -SDCategory: Black Temple -EndScriptData */ - #include "ScriptMgr.h" #include "InstanceScript.h" #include "black_temple.h" -#include "Player.h" -/* Black Temple encounters: -0 - High Warlord Naj'entus event -1 - Supremus Event -2 - Shade of Akama Event -3 - Teron Gorefiend Event -4 - Gurtogg Bloodboil Event -5 - Reliquary Of Souls Event -6 - Mother Shahraz Event -7 - Illidari Council Event -8 - Illidan Stormrage Event -*/ +DoorData const doorData[] = +{ + { GO_NAJENTUS_GATE, DATA_HIGH_WARLORD_NAJENTUS, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_NAJENTUS_GATE, DATA_SUPREMUS, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { GO_SUPREMUS_GATE, DATA_SUPREMUS, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_SHADE_OF_AKAMA_DOOR, DATA_SHADE_OF_AKAMA, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { GO_TERON_DOOR_1, DATA_TERON_GOREFIEND, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { GO_TERON_DOOR_2, DATA_TERON_GOREFIEND, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { GO_GURTOGG_DOOR, DATA_GURTOGG_BLOODBOIL, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_TEMPLE_DOOR, DATA_RELIQUARY_OF_SOULS, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_MOTHER_SHAHRAZ_DOOR, DATA_MOTHER_SHAHRAZ, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_COUNCIL_DOOR_1, DATA_ILLIDARI_COUNCIL, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { GO_COUNCIL_DOOR_2, DATA_ILLIDARI_COUNCIL, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { 0, 0, DOOR_TYPE_ROOM, BOUNDARY_NONE } // END +}; class instance_black_temple : public InstanceMapScript { -public: - instance_black_temple() : InstanceMapScript("instance_black_temple", 564) { } - - InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE - { - return new instance_black_temple_InstanceMapScript(map); - } - - struct instance_black_temple_InstanceMapScript : public InstanceScript - { - instance_black_temple_InstanceMapScript(Map* map) : InstanceScript(map) {} - - uint32 m_auiEncounter[EncounterCount]; - std::string str_data; - - uint64 Najentus; - uint64 Akama; // This is the Akama that starts the Illidan encounter. - uint64 Akama_Shade; // This is the Akama that starts the Shade of Akama encounter. - uint64 ShadeOfAkama; - uint64 Supremus; - uint64 LadyMalande; - uint64 GathiosTheShatterer; - uint64 HighNethermancerZerevor; - uint64 VerasDarkshadow; - uint64 IllidariCouncil; - uint64 BloodElfCouncilVoice; - uint64 IllidanStormrage; - - uint64 NajentusGate; - uint64 MainTempleDoors; - uint64 ShadeOfAkamaDoor; - uint64 CommonDoor;//Teron - uint64 TeronDoor; - uint64 GuurtogDoor; - uint64 MotherDoor; - uint64 TempleDoor;//Befor mother - uint64 CouncilDoor; - uint64 SimpleDoor;//council - uint64 IllidanGate; - uint64 IllidanDoor[2]; - - void Initialize() OVERRIDE - { - memset(&m_auiEncounter, 0, sizeof(m_auiEncounter)); + public: + instance_black_temple() : InstanceMapScript(BTScriptName, 564) { } - Najentus = 0; - Akama = 0; - Akama_Shade = 0; - ShadeOfAkama = 0; - Supremus = 0; - LadyMalande = 0; - GathiosTheShatterer = 0; - HighNethermancerZerevor = 0; - VerasDarkshadow = 0; - IllidariCouncil = 0; - BloodElfCouncilVoice = 0; - IllidanStormrage = 0; - - NajentusGate = 0; - MainTempleDoors = 0; - ShadeOfAkamaDoor = 0; - CommonDoor = 0; // teron - TeronDoor = 0; - GuurtogDoor = 0; - MotherDoor = 0; - TempleDoor = 0; - SimpleDoor = 0; // Bycouncil - CouncilDoor = 0; - IllidanGate = 0; - IllidanDoor[0] = 0; - IllidanDoor[1] = 0; - } - - bool IsEncounterInProgress() const OVERRIDE - { - for (uint8 i = 0; i < EncounterCount; ++i) - if (m_auiEncounter[i] == IN_PROGRESS) - return true; - - return false; - } - - Player* GetPlayerInMap() + struct instance_black_temple_InstanceMapScript : public InstanceScript { - Map::PlayerList const& players = instance->GetPlayers(); - - if (!players.isEmpty()) + instance_black_temple_InstanceMapScript(Map* map) : InstanceScript(map) { - for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr) - { - if (Player* player = itr->GetSource()) - return player; - } + SetBossNumber(EncounterCount); + LoadDoorData(doorData); + + NajentusGUID = 0; + SupremusGUID = 0; + ShadeOfAkamaGUID = 0; + AkamaShadeGUID = 0; + AkamaGUID = 0; + GathiosTheShattererGUID = 0; + HighNethermancerZerevorGUID = 0; + LadyMalandeGUID = 0; + VerasDarkshadowGUID = 0; + IllidariCouncilGUID = 0; + BloodElfCouncilVoiceGUID = 0; + IllidanStormrageGUID = 0; + + IllidanGateGUID = 0; + + memset(IllidanDoorGUIDs, 0, 2 * sizeof(uint64)); } - TC_LOG_DEBUG(LOG_FILTER_TSCR, "Instance Black Temple: GetPlayerInMap, but PlayerList is empty!"); - return NULL; - } - - void OnCreatureCreate(Creature* creature) OVERRIDE - { - switch (creature->GetEntry()) + void OnCreatureCreate(Creature* creature) OVERRIDE { - case 22887: Najentus = creature->GetGUID(); break; - case 23089: Akama = creature->GetGUID(); break; - case 23191: Akama_Shade = creature->GetGUID(); break; - case 22841: ShadeOfAkama = creature->GetGUID(); break; - case 22898: Supremus = creature->GetGUID(); break; - case 22917: IllidanStormrage = creature->GetGUID(); break; - case 22949: GathiosTheShatterer = creature->GetGUID(); break; - case 22950: HighNethermancerZerevor = creature->GetGUID(); break; - case 22951: LadyMalande = creature->GetGUID(); break; - case 22952: VerasDarkshadow = creature->GetGUID(); break; - case 23426: IllidariCouncil = creature->GetGUID(); break; - case 23499: BloodElfCouncilVoice = creature->GetGUID(); break; + switch (creature->GetEntry()) + { + case NPC_HIGH_WARLORD_NAJENTUS: + NajentusGUID = creature->GetGUID(); + break; + case NPC_SUPREMUS: + SupremusGUID = creature->GetGUID(); + break; + case NPC_SHADE_OF_AKAMA: + ShadeOfAkamaGUID = creature->GetGUID(); + break; + case NPC_AKAMA_SHADE: + AkamaShadeGUID = creature->GetGUID(); + break; + case NPC_AKAMA: + AkamaGUID = creature->GetGUID(); + break; + case NPC_GATHIOS_THE_SHATTERER: + GathiosTheShattererGUID = creature->GetGUID(); + break; + case NPC_HIGH_NETHERMANCER_ZEREVOR: + HighNethermancerZerevorGUID = creature->GetGUID(); + break; + case NPC_LADY_MALANDE: + LadyMalandeGUID = creature->GetGUID(); + break; + case NPC_VERAS_DARKSHADOW: + VerasDarkshadowGUID = creature->GetGUID(); + break; + case NPC_ILLIDARI_COUNCIL: + IllidariCouncilGUID = creature->GetGUID(); + break; + case NPC_BLOOD_ELF_COUNCIL_VOICE: + BloodElfCouncilVoiceGUID = creature->GetGUID(); + break; + case NPC_ILLIDAN_STORMRAGE: + IllidanStormrageGUID = creature->GetGUID(); + break; + default: + break; + } } - } - void OnGameObjectCreate(GameObject* go) OVERRIDE - { - switch (go->GetEntry()) + void OnGameObjectCreate(GameObject* go) OVERRIDE { - case 185483: - NajentusGate = go->GetGUID(); // Gate past Naj'entus (at the entrance to Supermoose's courtyards) - if (m_auiEncounter[0] == DONE) - HandleGameObject(0, true, go); - break; - - case 185882: - MainTempleDoors = go->GetGUID(); // Main Temple Doors - right past Supermoose (Supremus) - if (m_auiEncounter[1] == DONE) - HandleGameObject(0, true, go); - break; - - case 185478: - ShadeOfAkamaDoor = go->GetGUID(); - break; - - case 185480: - CommonDoor = go->GetGUID(); - if (m_auiEncounter[3] == DONE) - HandleGameObject(0, true, go); - break; - - case 186153: - TeronDoor = go->GetGUID(); - if (m_auiEncounter[3] == DONE) - HandleGameObject(0, true, go); - break; - - case 185892: - GuurtogDoor = go->GetGUID(); - if (m_auiEncounter[4] == DONE) - HandleGameObject(0, true, go); - break; - - case 185479: - TempleDoor = go->GetGUID(); - if (m_auiEncounter[5] == DONE) - HandleGameObject(0, true, go); - break; - - case 185482: - MotherDoor = go->GetGUID(); - if (m_auiEncounter[6] == DONE) - HandleGameObject(0, true, go); - break; - - case 185481: - CouncilDoor = go->GetGUID(); - if (m_auiEncounter[7] == DONE) - HandleGameObject(0, true, go); - break; - - case 186152: - SimpleDoor = go->GetGUID(); - if (m_auiEncounter[7] == DONE) - HandleGameObject(0, true, go); - break; - - case 185905: - IllidanGate = go->GetGUID(); // Gate leading to Temple Summit - break; - - case 186261: - IllidanDoor[0] = go->GetGUID(); // Right door at Temple Summit - break; - - case 186262: - IllidanDoor[1] = go->GetGUID(); // Left door at Temple Summit - break; + switch (go->GetEntry()) + { + case GO_NAJENTUS_GATE: + case GO_SUPREMUS_GATE: + case GO_SHADE_OF_AKAMA_DOOR: + case GO_TERON_DOOR_1: + case GO_TERON_DOOR_2: + case GO_GURTOGG_DOOR: + case GO_TEMPLE_DOOR: + case GO_MOTHER_SHAHRAZ_DOOR: + case GO_COUNCIL_DOOR_1: + case GO_COUNCIL_DOOR_2: + AddDoor(go, true); + break; + case GO_ILLIDAN_GATE: + IllidanGateGUID = go->GetGUID(); + break; + case GO_ILLIDAN_DOOR_R: + IllidanDoorGUIDs[0] = go->GetGUID(); + break; + case GO_ILLIDAN_DOOR_L: + IllidanDoorGUIDs[1] = go->GetGUID(); + break; + default: + break; + } } - } - uint64 GetData64(uint32 identifier) const OVERRIDE - { - switch (identifier) + void OnGameObjectRemove(GameObject* go) OVERRIDE { - case DATA_HIGHWARLORDNAJENTUS: return Najentus; - case DATA_AKAMA: return Akama; - case DATA_AKAMA_SHADE: return Akama_Shade; - case DATA_SHADEOFAKAMA: return ShadeOfAkama; - case DATA_SUPREMUS: return Supremus; - case DATA_ILLIDANSTORMRAGE: return IllidanStormrage; - case DATA_GATHIOSTHESHATTERER: return GathiosTheShatterer; - case DATA_HIGHNETHERMANCERZEREVOR: return HighNethermancerZerevor; - case DATA_LADYMALANDE: return LadyMalande; - case DATA_VERASDARKSHADOW: return VerasDarkshadow; - case DATA_ILLIDARICOUNCIL: return IllidariCouncil; - case DATA_GAMEOBJECT_NAJENTUS_GATE: return NajentusGate; - case DATA_GAMEOBJECT_ILLIDAN_GATE: return IllidanGate; - case DATA_GAMEOBJECT_ILLIDAN_DOOR_R: return IllidanDoor[0]; - case DATA_GAMEOBJECT_ILLIDAN_DOOR_L: return IllidanDoor[1]; - case DATA_GAMEOBJECT_SUPREMUS_DOORS: return MainTempleDoors; - case DATA_BLOOD_ELF_COUNCIL_VOICE: return BloodElfCouncilVoice; + switch (go->GetEntry()) + { + case GO_NAJENTUS_GATE: + case GO_SUPREMUS_GATE: + case GO_SHADE_OF_AKAMA_DOOR: + case GO_TERON_DOOR_1: + case GO_TERON_DOOR_2: + case GO_GURTOGG_DOOR: + case GO_TEMPLE_DOOR: + case GO_MOTHER_SHAHRAZ_DOOR: + case GO_COUNCIL_DOOR_1: + case GO_COUNCIL_DOOR_2: + AddDoor(go, false); + break; + default: + break; + } } - return 0; - } - - void SetData(uint32 type, uint32 data) OVERRIDE - { - switch (type) + uint64 GetData64(uint32 type) const OVERRIDE { - case DATA_HIGHWARLORDNAJENTUSEVENT: - if (data == DONE) - HandleGameObject(NajentusGate, true); - m_auiEncounter[0] = data; - break; - case DATA_SUPREMUSEVENT: - if (data == DONE) - HandleGameObject(NajentusGate, true); - m_auiEncounter[1] = data; - break; - case DATA_SHADEOFAKAMAEVENT: - if (data == IN_PROGRESS) - HandleGameObject(ShadeOfAkamaDoor, false); - else - HandleGameObject(ShadeOfAkamaDoor, true); - m_auiEncounter[2] = data; - break; - case DATA_TERONGOREFIENDEVENT: - if (data == IN_PROGRESS) + switch (type) { - HandleGameObject(TeronDoor, false); - HandleGameObject(CommonDoor, false); + case DATA_HIGH_WARLORD_NAJENTUS: + return NajentusGUID; + case DATA_SUPREMUS: + return SupremusGUID; + case DATA_SHADE_OF_AKAMA: + return ShadeOfAkamaGUID; + case DATA_AKAMA_SHADE: + return AkamaShadeGUID; + case DATA_AKAMA: + return AkamaGUID; + case DATA_GATHIOS_THE_SHATTERER: + return GathiosTheShattererGUID; + case DATA_HIGH_NETHERMANCER_ZEREVOR: + return HighNethermancerZerevorGUID; + case DATA_LADY_MALANDE: + return LadyMalandeGUID; + case DATA_VERAS_DARKSHADOW: + return VerasDarkshadowGUID; + case DATA_ILLIDARI_COUNCIL: + return IllidariCouncilGUID; + case DATA_BLOOD_ELF_COUNCIL_VOICE: + return BloodElfCouncilVoiceGUID; + case DATA_ILLIDAN_STORMRAGE: + return IllidanStormrageGUID; + case DATA_GO_ILLIDAN_GATE: + return IllidanGateGUID; + case DATA_GO_ILLIDAN_DOOR_R: + return IllidanDoorGUIDs[0]; + case DATA_GO_ILLIDAN_DOOR_L: + return IllidanDoorGUIDs[1]; + default: + break; } - else - { - HandleGameObject(TeronDoor, true); - HandleGameObject(CommonDoor, true); - } - m_auiEncounter[3] = data; - break; - case DATA_GURTOGGBLOODBOILEVENT: - if (data == DONE) - HandleGameObject(GuurtogDoor, true); - m_auiEncounter[4] = data; - break; - case DATA_RELIQUARYOFSOULSEVENT: - if (data == DONE) - HandleGameObject(TempleDoor, true); - m_auiEncounter[5] = data; - break; - case DATA_MOTHERSHAHRAZEVENT: - if (data == DONE) - HandleGameObject(MotherDoor, true); - m_auiEncounter[6] = data; - break; - case DATA_ILLIDARICOUNCILEVENT: - if (data == IN_PROGRESS) - { - HandleGameObject(CouncilDoor, false); - HandleGameObject(SimpleDoor, false); - } - else - { - HandleGameObject(CouncilDoor, true); - HandleGameObject(SimpleDoor, true); - } - m_auiEncounter[7] = data; - break; - case DATA_ILLIDANSTORMRAGEEVENT: - m_auiEncounter[8] = data; - break; + + return 0; } - if (data == DONE) + std::string GetSaveData() OVERRIDE { OUT_SAVE_INST_DATA; std::ostringstream saveStream; - saveStream << m_auiEncounter[0] << ' ' << m_auiEncounter[1] << ' ' - << m_auiEncounter[2] << ' ' << m_auiEncounter[3] << ' ' << m_auiEncounter[4] - << ' ' << m_auiEncounter[5] << ' ' << m_auiEncounter[6] << ' ' << m_auiEncounter[7] - << ' ' << m_auiEncounter[8]; - - str_data = saveStream.str(); + saveStream << "B T " << GetBossSaveData(); - SaveToDB(); OUT_SAVE_INST_DATA_COMPLETE; + return saveStream.str(); } - } - uint32 GetData(uint32 type) const OVERRIDE - { - switch (type) + void Load(char const* str) OVERRIDE { - case DATA_HIGHWARLORDNAJENTUSEVENT: return m_auiEncounter[0]; - case DATA_SUPREMUSEVENT: return m_auiEncounter[1]; - case DATA_SHADEOFAKAMAEVENT: return m_auiEncounter[2]; - case DATA_TERONGOREFIENDEVENT: return m_auiEncounter[3]; - case DATA_GURTOGGBLOODBOILEVENT: return m_auiEncounter[4]; - case DATA_RELIQUARYOFSOULSEVENT: return m_auiEncounter[5]; - case DATA_MOTHERSHAHRAZEVENT: return m_auiEncounter[6]; - case DATA_ILLIDARICOUNCILEVENT: return m_auiEncounter[7]; - case DATA_ILLIDANSTORMRAGEEVENT: return m_auiEncounter[8]; - } + if (!str) + { + OUT_LOAD_INST_DATA_FAIL; + return; + } - return 0; - } + OUT_LOAD_INST_DATA(str); - std::string GetSaveData() OVERRIDE - { - return str_data; - } + char dataHead1, dataHead2; - void Load(const char* in) OVERRIDE - { - if (!in) - { - OUT_LOAD_INST_DATA_FAIL; - return; + std::istringstream loadStream(str); + loadStream >> dataHead1 >> dataHead2; + + if (dataHead1 == 'B' && dataHead2 == 'T') + { + for (uint32 i = 0; i < EncounterCount; ++i) + { + uint32 tmpState; + loadStream >> tmpState; + if (tmpState == IN_PROGRESS || tmpState > SPECIAL) + tmpState = NOT_STARTED; + SetBossState(i, EncounterState(tmpState)); + } + } + else + OUT_LOAD_INST_DATA_FAIL; + + OUT_LOAD_INST_DATA_COMPLETE; } - OUT_LOAD_INST_DATA(in); + protected: + uint64 NajentusGUID; + uint64 SupremusGUID; + uint64 ShadeOfAkamaGUID; + uint64 AkamaShadeGUID; + uint64 AkamaGUID; - std::istringstream loadStream(in); - loadStream >> m_auiEncounter[0] >> m_auiEncounter[1] >> m_auiEncounter[2] - >> m_auiEncounter[3] >> m_auiEncounter[4] >> m_auiEncounter[5] >> m_auiEncounter[6] - >> m_auiEncounter[7] >> m_auiEncounter[8]; + uint64 GathiosTheShattererGUID; + uint64 HighNethermancerZerevorGUID; + uint64 LadyMalandeGUID; + uint64 VerasDarkshadowGUID; - for (uint8 i = 0; i < EncounterCount; ++i) - if (m_auiEncounter[i] == IN_PROGRESS) - m_auiEncounter[i] = NOT_STARTED; + uint64 IllidariCouncilGUID; + uint64 BloodElfCouncilVoiceGUID; - OUT_LOAD_INST_DATA_COMPLETE; - } - }; + uint64 IllidanStormrageGUID; + + uint64 IllidanGateGUID; + uint64 IllidanDoorGUIDs[2]; + }; + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_black_temple_InstanceMapScript(map); + } }; void AddSC_instance_black_temple() diff --git a/src/server/scripts/Outland/CMakeLists.txt b/src/server/scripts/Outland/CMakeLists.txt index d7b863da0db..c828c6dfbcf 100644 --- a/src/server/scripts/Outland/CMakeLists.txt +++ b/src/server/scripts/Outland/CMakeLists.txt @@ -42,8 +42,10 @@ set(scripts_STAT_SRCS Outland/CoilfangReservoir/SerpentShrine/boss_leotheras_the_blind.cpp Outland/CoilfangReservoir/SerpentShrine/boss_lurker_below.cpp Outland/CoilfangReservoir/SerpentShrine/boss_morogrim_tidewalker.cpp - Outland/CoilfangReservoir/underbog/boss_hungarfen.cpp - Outland/CoilfangReservoir/underbog/boss_the_black_stalker.cpp + Outland/CoilfangReservoir/TheSlavePens/instance_the_slave_pens.cpp + Outland/CoilfangReservoir/TheUnderbog/boss_hungarfen.cpp + Outland/CoilfangReservoir/TheUnderbog/boss_the_black_stalker.cpp + Outland/CoilfangReservoir/TheUnderbog/instance_the_underbog.cpp Outland/zone_shattrath_city.cpp Outland/TempestKeep/Mechanar/boss_mechano_lord_capacitus.cpp Outland/TempestKeep/Mechanar/boss_pathaleon_the_calculator.cpp diff --git a/src/server/scripts/Outland/CoilfangReservoir/SerpentShrine/boss_hydross_the_unstable.cpp b/src/server/scripts/Outland/CoilfangReservoir/SerpentShrine/boss_hydross_the_unstable.cpp index db270c943e5..d6205cb3ec7 100644 --- a/src/server/scripts/Outland/CoilfangReservoir/SerpentShrine/boss_hydross_the_unstable.cpp +++ b/src/server/scripts/Outland/CoilfangReservoir/SerpentShrine/boss_hydross_the_unstable.cpp @@ -94,6 +94,8 @@ public: boss_hydross_the_unstableAI(Creature* creature) : ScriptedAI(creature), Summons(me) { instance = creature->GetInstanceScript(); + beams[0] = 0; + beams[1] = 0; } InstanceScript* instance; @@ -159,10 +161,9 @@ public: } void DeSummonBeams() { - for (uint8 i=0; i<2; ++i) + for (uint8 i = 0; i < 2; ++i) { - Creature* mob = Unit::GetCreature(*me, beams[i]); - if (mob) + if (Creature* mob = Unit::GetCreature(*me, beams[i])) { mob->setDeathState(DEAD); mob->RemoveCorpse(); diff --git a/src/server/scripts/Outland/CoilfangReservoir/TheSlavePens/instance_the_slave_pens.cpp b/src/server/scripts/Outland/CoilfangReservoir/TheSlavePens/instance_the_slave_pens.cpp new file mode 100644 index 00000000000..3475e83f02c --- /dev/null +++ b/src/server/scripts/Outland/CoilfangReservoir/TheSlavePens/instance_the_slave_pens.cpp @@ -0,0 +1,47 @@ +/* + * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +/* +This placeholder for the instance is needed for dungeon finding to be able +to give credit after the boss defined in lastEncounterDungeon is killed. +Without it, the party doing random dungeon won't get satchel of spoils and +gets instead the deserter debuff. +*/ + +#include "ScriptMgr.h" +#include "InstanceScript.h" + +class instance_the_slave_pens : public InstanceMapScript +{ +public: + instance_the_slave_pens() : InstanceMapScript("instance_the_slave_pens", 547) { } + + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_the_slave_pens_InstanceMapScript(map); + } + + struct instance_the_slave_pens_InstanceMapScript : public InstanceScript + { + instance_the_slave_pens_InstanceMapScript(Map* map) : InstanceScript(map) {} + }; +}; + +void AddSC_instance_the_slave_pens() +{ + new instance_the_slave_pens(); +} diff --git a/src/server/scripts/Outland/CoilfangReservoir/underbog/boss_hungarfen.cpp b/src/server/scripts/Outland/CoilfangReservoir/TheUnderbog/boss_hungarfen.cpp index 0db48d83ebb..0db48d83ebb 100644 --- a/src/server/scripts/Outland/CoilfangReservoir/underbog/boss_hungarfen.cpp +++ b/src/server/scripts/Outland/CoilfangReservoir/TheUnderbog/boss_hungarfen.cpp diff --git a/src/server/scripts/Outland/CoilfangReservoir/underbog/boss_the_black_stalker.cpp b/src/server/scripts/Outland/CoilfangReservoir/TheUnderbog/boss_the_black_stalker.cpp index c22dedd269e..c22dedd269e 100644 --- a/src/server/scripts/Outland/CoilfangReservoir/underbog/boss_the_black_stalker.cpp +++ b/src/server/scripts/Outland/CoilfangReservoir/TheUnderbog/boss_the_black_stalker.cpp diff --git a/src/server/scripts/Outland/CoilfangReservoir/TheUnderbog/instance_the_underbog.cpp b/src/server/scripts/Outland/CoilfangReservoir/TheUnderbog/instance_the_underbog.cpp new file mode 100644 index 00000000000..0a305edf23f --- /dev/null +++ b/src/server/scripts/Outland/CoilfangReservoir/TheUnderbog/instance_the_underbog.cpp @@ -0,0 +1,47 @@ +/* + * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +/* +This placeholder for the instance is needed for dungeon finding to be able +to give credit after the boss defined in lastEncounterDungeon is killed. +Without it, the party doing random dungeon won't get satchel of spoils and +gets instead the deserter debuff. +*/ + +#include "ScriptMgr.h" +#include "InstanceScript.h" + +class instance_the_underbog : public InstanceMapScript +{ +public: + instance_the_underbog() : InstanceMapScript("instance_the_underbog", 546) { } + + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_the_underbog_InstanceMapScript(map); + } + + struct instance_the_underbog_InstanceMapScript : public InstanceScript + { + instance_the_underbog_InstanceMapScript(Map* map) : InstanceScript(map) {} + }; +}; + +void AddSC_instance_the_underbog() +{ + new instance_the_underbog(); +} diff --git a/src/server/scripts/Outland/GruulsLair/boss_gruul.cpp b/src/server/scripts/Outland/GruulsLair/boss_gruul.cpp index 31f854803bc..0ae86f7c455 100644 --- a/src/server/scripts/Outland/GruulsLair/boss_gruul.cpp +++ b/src/server/scripts/Outland/GruulsLair/boss_gruul.cpp @@ -43,215 +43,217 @@ enum Spells { SPELL_GROWTH = 36300, SPELL_CAVE_IN = 36240, - SPELL_GROUND_SLAM = 33525, //AoE Ground Slam applying Ground Slam to everyone with a script effect (most likely the knock back, we can code it to a set knockback) + SPELL_GROUND_SLAM = 33525, // AoE Ground Slam applying Ground Slam to everyone with a script effect (most likely the knock back, we can code it to a set knockback) SPELL_REVERBERATION = 36297, SPELL_SHATTER = 33654, SPELL_SHATTER_EFFECT = 33671, SPELL_HURTFUL_STRIKE = 33813, - SPELL_STONED = 33652, //Spell is self cast by target + SPELL_STONED = 33652, // Spell is self cast by target SPELL_MAGNETIC_PULL = 28337, - SPELL_KNOCK_BACK = 24199, //Knockback spell until correct implementation is made + SPELL_KNOCK_BACK = 24199, // Knockback spell until correct implementation is made }; -class boss_gruul : public CreatureScript +enum Events { -public: - boss_gruul() : CreatureScript("boss_gruul") { } + EVENT_GROWTH = 1, + EVENT_CAVE_IN, + EVENT_CAVE_IN_STATIC, + EVENT_GROUND_SLAM, + EVENT_HURTFUL_STRIKE, + EVENT_REVERBERATION +}; - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return new boss_gruulAI(creature); - } +class boss_gruul : public CreatureScript +{ + public: + boss_gruul() : CreatureScript("boss_gruul") { } - struct boss_gruulAI : public ScriptedAI - { - boss_gruulAI(Creature* creature) : ScriptedAI(creature) + struct boss_gruulAI : public BossAI { - instance = creature->GetInstanceScript(); - } - - InstanceScript* instance; - - uint32 m_uiGrowth_Timer; - uint32 m_uiCaveIn_Timer; - uint32 m_uiCaveIn_StaticTimer; - uint32 m_uiGroundSlamTimer; - uint32 m_uiHurtfulStrike_Timer; - uint32 m_uiReverberation_Timer; + boss_gruulAI(Creature* creature) : BossAI(creature, DATA_GRUUL) { } - bool m_bPerformingGroundSlam; + uint32 m_uiGrowth_Timer; + uint32 m_uiCaveIn_Timer; + uint32 m_uiCaveIn_StaticTimer; + uint32 m_uiGroundSlamTimer; + uint32 m_uiHurtfulStrike_Timer; + uint32 m_uiReverberation_Timer; - void Reset() OVERRIDE - { - m_uiGrowth_Timer= 30000; - m_uiCaveIn_Timer= 27000; - m_uiCaveIn_StaticTimer = 30000; - m_uiGroundSlamTimer= 35000; - m_bPerformingGroundSlam= false; - m_uiHurtfulStrike_Timer= 8000; - m_uiReverberation_Timer= 60000+45000; - - if (instance) - instance->SetData(DATA_GRUULEVENT, NOT_STARTED); - } + bool m_bPerformingGroundSlam; - void EnterCombat(Unit* /*who*/) OVERRIDE - { - Talk(SAY_AGGRO); - - if (instance) - instance->SetData(DATA_GRUULEVENT, IN_PROGRESS); - } + void Reset() OVERRIDE + { + _Reset(); + m_uiGrowth_Timer= 30000; + m_uiCaveIn_Timer= 27000; + m_uiCaveIn_StaticTimer = 30000; + m_uiGroundSlamTimer= 35000; + m_bPerformingGroundSlam= false; + m_uiHurtfulStrike_Timer= 8000; + m_uiReverberation_Timer= 60000+45000; + } - void KilledUnit(Unit* /*victim*/) OVERRIDE - { - Talk(SAY_SLAY); - } + void EnterCombat(Unit* /*who*/) OVERRIDE + { + _EnterCombat(); + Talk(SAY_AGGRO); + } - void JustDied(Unit* /*killer*/) OVERRIDE - { - Talk(SAY_DEATH); + void KilledUnit(Unit* who) OVERRIDE + { + if (who->GetTypeId() == TYPEID_PLAYER) + Talk(SAY_SLAY); + } - if (instance) + void JustDied(Unit* /*killer*/) OVERRIDE { - instance->SetData(DATA_GRUULEVENT, DONE); - instance->HandleGameObject(instance->GetData64(DATA_GRUULDOOR), true); // Open the encounter door + _JustDied(); + Talk(SAY_DEATH); } - } - void SpellHitTarget(Unit* target, const SpellInfo* pSpell) OVERRIDE - { - //This to emulate effect1 (77) of SPELL_GROUND_SLAM, knock back to any direction - //It's initially wrong, since this will cause fall damage, which is by comments, not intended. - if (pSpell->Id == SPELL_GROUND_SLAM) + void SpellHitTarget(Unit* target, const SpellInfo* pSpell) OVERRIDE { - if (target->GetTypeId() == TYPEID_PLAYER) + //This to emulate effect1 (77) of SPELL_GROUND_SLAM, knock back to any direction + //It's initially wrong, since this will cause fall damage, which is by comments, not intended. + if (pSpell->Id == SPELL_GROUND_SLAM) { - switch (urand(0, 1)) + if (target->GetTypeId() == TYPEID_PLAYER) { - case 0: - target->CastSpell(target, SPELL_MAGNETIC_PULL, true, NULL, NULL, me->GetGUID()); - break; - - case 1: - target->CastSpell(target, SPELL_KNOCK_BACK, true, NULL, NULL, me->GetGUID()); - break; + switch (urand(0, 1)) + { + case 0: + target->CastSpell(target, SPELL_MAGNETIC_PULL, true, NULL, NULL, me->GetGUID()); + break; + + case 1: + target->CastSpell(target, SPELL_KNOCK_BACK, true, NULL, NULL, me->GetGUID()); + break; + } } } - } - //this part should be in the core - if (pSpell->Id == SPELL_SHATTER) - { - /// @todo use eventmap to kill this stuff - //clear this, if we are still performing - if (m_bPerformingGroundSlam) + //this part should be in the core + if (pSpell->Id == SPELL_SHATTER) { - m_bPerformingGroundSlam = false; - - //and correct movement, if not already - if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() != CHASE_MOTION_TYPE) + /// @todo use eventmap to kill this stuff + //clear this, if we are still performing + if (m_bPerformingGroundSlam) { - if (me->GetVictim()) - me->GetMotionMaster()->MoveChase(me->GetVictim()); + m_bPerformingGroundSlam = false; + + //and correct movement, if not already + if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() != CHASE_MOTION_TYPE) + { + if (me->GetVictim()) + me->GetMotionMaster()->MoveChase(me->GetVictim()); + } } } } - } - - void UpdateAI(uint32 uiDiff) OVERRIDE - { - //Return since we have no target - if (!UpdateVictim()) - return; - // Growth - // Gruul can cast this spell up to 30 times - if (m_uiGrowth_Timer <= uiDiff) + void UpdateAI(uint32 diff) OVERRIDE { - Talk(EMOTE_GROW); - DoCast(me, SPELL_GROWTH); - m_uiGrowth_Timer = 30000; - } - else - m_uiGrowth_Timer -= uiDiff; + if (!UpdateVictim()) + return; - if (m_bPerformingGroundSlam) - { - if (m_uiGroundSlamTimer <= uiDiff) - { - m_uiGroundSlamTimer =120000; - m_uiHurtfulStrike_Timer= 8000; + events.Update(diff); + + if (me->HasUnitState(UNIT_STATE_CASTING)) + return; - if (m_uiReverberation_Timer < 10000) //Give a little time to the players to undo the damage from shatter - m_uiReverberation_Timer += 10000; + /// @todo: convert this shit to eventmap - DoCast(me, SPELL_SHATTER); + // Growth + // Gruul can cast this spell up to 30 times + if (m_uiGrowth_Timer <= diff) + { + Talk(EMOTE_GROW); + DoCast(me, SPELL_GROWTH); + m_uiGrowth_Timer = 30000; } else - m_uiGroundSlamTimer -= uiDiff; - } - else - { - // Hurtful Strike - if (m_uiHurtfulStrike_Timer <= uiDiff) + m_uiGrowth_Timer -= diff; + + if (m_bPerformingGroundSlam) { - Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO, 1); + if (m_uiGroundSlamTimer <= diff) + { + m_uiGroundSlamTimer =120000; + m_uiHurtfulStrike_Timer= 8000; - if (target && me->IsWithinMeleeRange(me->GetVictim())) - DoCast(target, SPELL_HURTFUL_STRIKE); - else - DoCastVictim(SPELL_HURTFUL_STRIKE); + if (m_uiReverberation_Timer < 10000) //Give a little time to the players to undo the damage from shatter + m_uiReverberation_Timer += 10000; - m_uiHurtfulStrike_Timer= 8000; + DoCast(me, SPELL_SHATTER); + } + else + m_uiGroundSlamTimer -= diff; } else - m_uiHurtfulStrike_Timer -= uiDiff; - - // Reverberation - if (m_uiReverberation_Timer <= uiDiff) { - DoCastVictim(SPELL_REVERBERATION, true); - m_uiReverberation_Timer = urand(15000, 25000); - } - else - m_uiReverberation_Timer -= uiDiff; + // Hurtful Strike + if (m_uiHurtfulStrike_Timer <= diff) + { + Unit* target = SelectTarget(SELECT_TARGET_TOPAGGRO, 1); - // Cave In - if (m_uiCaveIn_Timer <= uiDiff) - { - if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0)) - DoCast(target, SPELL_CAVE_IN); + if (target && me->IsWithinMeleeRange(me->GetVictim())) + DoCast(target, SPELL_HURTFUL_STRIKE); + else + DoCastVictim(SPELL_HURTFUL_STRIKE); - if (m_uiCaveIn_StaticTimer >= 4000) - m_uiCaveIn_StaticTimer -= 2000; + m_uiHurtfulStrike_Timer= 8000; + } + else + m_uiHurtfulStrike_Timer -= diff; - m_uiCaveIn_Timer = m_uiCaveIn_StaticTimer; - } - else - m_uiCaveIn_Timer -= uiDiff; + // Reverberation + if (m_uiReverberation_Timer <= diff) + { + DoCastVictim(SPELL_REVERBERATION, true); + m_uiReverberation_Timer = urand(15000, 25000); + } + else + m_uiReverberation_Timer -= diff; - // Ground Slam, Gronn Lord's Grasp, Stoned, Shatter - if (m_uiGroundSlamTimer <= uiDiff) - { - me->GetMotionMaster()->Clear(); - me->GetMotionMaster()->MoveIdle(); + // Cave In + if (m_uiCaveIn_Timer <= diff) + { + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0)) + DoCast(target, SPELL_CAVE_IN); - m_bPerformingGroundSlam= true; - m_uiGroundSlamTimer = 10000; + if (m_uiCaveIn_StaticTimer >= 4000) + m_uiCaveIn_StaticTimer -= 2000; - DoCast(me, SPELL_GROUND_SLAM); - } - else - m_uiGroundSlamTimer -= uiDiff; + m_uiCaveIn_Timer = m_uiCaveIn_StaticTimer; + } + else + m_uiCaveIn_Timer -= diff; + + // Ground Slam, Gronn Lord's Grasp, Stoned, Shatter + if (m_uiGroundSlamTimer <= diff) + { + me->GetMotionMaster()->Clear(); + me->GetMotionMaster()->MoveIdle(); - DoMeleeAttackIfReady(); + m_bPerformingGroundSlam= true; + m_uiGroundSlamTimer = 10000; + + DoCast(me, SPELL_GROUND_SLAM); + } + else + m_uiGroundSlamTimer -= diff; + + DoMeleeAttackIfReady(); + } } - } - }; + }; + CreatureAI* GetAI(Creature* creature) const OVERRIDE + { + return GetGruulsLairAI<boss_gruulAI>(creature); + } }; class spell_gruul_shatter : public SpellScriptLoader diff --git a/src/server/scripts/Outland/GruulsLair/boss_high_king_maulgar.cpp b/src/server/scripts/Outland/GruulsLair/boss_high_king_maulgar.cpp index d216c0b02ee..dd44d764987 100644 --- a/src/server/scripts/Outland/GruulsLair/boss_high_king_maulgar.cpp +++ b/src/server/scripts/Outland/GruulsLair/boss_high_king_maulgar.cpp @@ -49,79 +49,35 @@ enum HighKingMaulgar SPELL_DEATH_COIL = 33130, SPELL_SUMMON_WFH = 33131, - //Kiggler the Craed + // Kiggler the Craed SPELL_GREATER_POLYMORPH = 33173, SPELL_LIGHTNING_BOLT = 36152, SPELL_ARCANE_SHOCK = 33175, SPELL_ARCANE_EXPLOSION = 33237, - //Blindeye the Seer + // Blindeye the Seer SPELL_GREATER_PW_SHIELD = 33147, SPELL_HEAL = 33144, SPELL_PRAYER_OH = 33152, - //Krosh Firehand + // Krosh Firehand SPELL_GREATER_FIREBALL = 33051, SPELL_SPELLSHIELD = 33054, - SPELL_BLAST_WAVE = 33061 -}; + SPELL_BLAST_WAVE = 33061, -bool CheckAllBossDied(InstanceScript* instance, Creature* me) -{ - if (!instance || !me) - return false; - - uint64 MaulgarGUID = 0; - uint64 KigglerGUID = 0; - uint64 BlindeyeGUID = 0; - uint64 OlmGUID = 0; - uint64 KroshGUID = 0; - - Creature* Maulgar = NULL; - Creature* Kiggler = NULL; - Creature* Blindeye = NULL; - Creature* Olm = NULL; - Creature* Krosh = NULL; - - MaulgarGUID = instance->GetData64(DATA_MAULGAR); - KigglerGUID = instance->GetData64(DATA_KIGGLERTHECRAZED); - BlindeyeGUID = instance->GetData64(DATA_BLINDEYETHESEER); - OlmGUID = instance->GetData64(DATA_OLMTHESUMMONER); - KroshGUID = instance->GetData64(DATA_KROSHFIREHAND); - - Maulgar = (Unit::GetCreature((*me), MaulgarGUID)); - Kiggler = (Unit::GetCreature((*me), KigglerGUID)); - Blindeye = (Unit::GetCreature((*me), BlindeyeGUID)); - Olm = (Unit::GetCreature((*me), OlmGUID)); - Krosh = (Unit::GetCreature((*me), KroshGUID)); - - if (!Maulgar || !Kiggler || !Blindeye || !Olm || !Krosh) - return false; - - if (!Maulgar->IsAlive() && !Kiggler->IsAlive() && !Blindeye->IsAlive() && !Olm->IsAlive() && !Krosh->IsAlive()) - return true; - - return false; -} + ACTION_ADD_DEATH = 1 +}; -//High King Maulgar AI class boss_high_king_maulgar : public CreatureScript { public: boss_high_king_maulgar() : CreatureScript("boss_high_king_maulgar") { } - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return new boss_high_king_maulgarAI(creature); - } - struct boss_high_king_maulgarAI : public ScriptedAI { boss_high_king_maulgarAI(Creature* creature) : ScriptedAI(creature) { instance = creature->GetInstanceScript(); - for (uint8 i = 0; i < 4; ++i) - Council[i] = 0; } InstanceScript* instance; @@ -134,8 +90,6 @@ public: bool Phase2; - uint64 Council[4]; - void Reset() OVERRIDE { ArcingSmash_Timer = 10000; @@ -148,23 +102,7 @@ public: Phase2 = false; - Creature* creature = NULL; - for (uint8 i = 0; i < 4; ++i) - { - if (Council[i]) - { - creature = (Unit::GetCreature((*me), Council[i])); - if (creature && !creature->IsAlive()) - { - creature->Respawn(); - creature->AI()->EnterEvadeMode(); - } - } - } - - //reset encounter - if (instance) - instance->SetData(DATA_MAULGAREVENT, NOT_STARTED); + instance->SetBossState(DATA_MAULGAR, NOT_STARTED); } void KilledUnit(Unit* /*victim*/) OVERRIDE @@ -176,72 +114,27 @@ public: { Talk(SAY_DEATH); - if (CheckAllBossDied(instance, me)) - instance->SetData(DATA_MAULGAREVENT, DONE); - } - - void AddDeath() - { - Talk(SAY_OGRE_DEATH); - } - - void EnterCombat(Unit* who) OVERRIDE - { - StartEvent(who); + instance->SetBossState(DATA_MAULGAR, DONE); } - void GetCouncil() + void DoAction(int32 actionId) { - if (instance) - { - //get council member's guid to respawn them if needed - Council[0] = instance->GetData64(DATA_KIGGLERTHECRAZED); - Council[1] = instance->GetData64(DATA_BLINDEYETHESEER); - Council[2] = instance->GetData64(DATA_OLMTHESUMMONER); - Council[3] = instance->GetData64(DATA_KROSHFIREHAND); - } + if (actionId == ACTION_ADD_DEATH) + Talk(SAY_OGRE_DEATH); } - void StartEvent(Unit* who) + void EnterCombat(Unit* /*who*/) OVERRIDE { - if (!instance) - return; - - GetCouncil(); - - Talk(SAY_AGGRO); - - instance->SetData64(DATA_MAULGAREVENT_TANK, who->GetGUID()); - instance->SetData(DATA_MAULGAREVENT, IN_PROGRESS); - DoZoneInCombat(); + instance->SetBossState(DATA_MAULGAR, IN_PROGRESS); + Talk(SAY_AGGRO); } void UpdateAI(uint32 diff) OVERRIDE { - //Only if not incombat check if the event is started - if (!me->IsInCombat() && instance && instance->GetData(DATA_MAULGAREVENT)) - { - Unit* target = Unit::GetUnit(*me, instance->GetData64(DATA_MAULGAREVENT_TANK)); - - if (target) - { - AttackStart(target); - GetCouncil(); - } - } - - //Return since we have no target if (!UpdateVictim()) return; - //someone evaded! - if (instance && !instance->GetData(DATA_MAULGAREVENT)) - { - EnterEvadeMode(); - return; - } - //ArcingSmash_Timer if (ArcingSmash_Timer <= diff) { @@ -301,19 +194,17 @@ public: } }; + CreatureAI* GetAI(Creature* creature) const OVERRIDE + { + return GetGruulsLairAI<boss_high_king_maulgarAI>(creature); + } }; -//Olm The Summoner AI class boss_olm_the_summoner : public CreatureScript { public: boss_olm_the_summoner() : CreatureScript("boss_olm_the_summoner") { } - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return new boss_olm_the_summonerAI(creature); - } - struct boss_olm_the_summonerAI : public ScriptedAI { boss_olm_the_summonerAI(Creature* creature) : ScriptedAI(creature) @@ -333,9 +224,7 @@ public: Summon_Timer = 15000; DeathCoil_Timer = 20000; - //reset encounter - if (instance) - instance->SetData(DATA_MAULGAREVENT, NOT_STARTED); + instance->SetBossState(DATA_MAULGAR, NOT_STARTED); } void AttackStart(Unit* who) OVERRIDE @@ -353,54 +242,25 @@ public: } } - void EnterCombat(Unit* who) OVERRIDE + void EnterCombat(Unit* /*who*/) OVERRIDE { - if (instance) - { - instance->SetData64(DATA_MAULGAREVENT_TANK, who->GetGUID()); - instance->SetData(DATA_MAULGAREVENT, IN_PROGRESS); - } + DoZoneInCombat(); + instance->SetBossState(DATA_MAULGAR, IN_PROGRESS); } void JustDied(Unit* /*killer*/) OVERRIDE { - if (instance) - { - Creature* Maulgar = NULL; - Maulgar = (Unit::GetCreature((*me), instance->GetData64(DATA_MAULGAR))); - - if (Maulgar) - CAST_AI(boss_high_king_maulgar::boss_high_king_maulgarAI, Maulgar->AI())->AddDeath(); + if (Creature* maulgar = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_MAULGAR))) + maulgar->AI()->DoAction(ACTION_ADD_DEATH); - if (CheckAllBossDied(instance, me)) - instance->SetData(DATA_MAULGAREVENT, DONE); - } + instance->SetBossState(DATA_MAULGAR, DONE); } void UpdateAI(uint32 diff) OVERRIDE { - //Only if not incombat check if the event is started - if (!me->IsInCombat() && instance && instance->GetData(DATA_MAULGAREVENT)) - { - Unit* target = Unit::GetUnit(*me, instance->GetData64(DATA_MAULGAREVENT_TANK)); - - if (target) - { - AttackStart(target); - } - } - - //Return since we have no target if (!UpdateVictim()) return; - //someone evaded! - if (instance && !instance->GetData(DATA_MAULGAREVENT)) - { - EnterEvadeMode(); - return; - } - //DarkDecay_Timer if (DarkDecay_Timer <= diff) { @@ -429,6 +289,10 @@ public: } }; + CreatureAI* GetAI(Creature* creature) const OVERRIDE + { + return GetGruulsLairAI<boss_olm_the_summonerAI>(creature); + } }; //Kiggler The Crazed AI @@ -437,11 +301,6 @@ class boss_kiggler_the_crazed : public CreatureScript public: boss_kiggler_the_crazed() : CreatureScript("boss_kiggler_the_crazed") { } - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return new boss_kiggler_the_crazedAI(creature); - } - struct boss_kiggler_the_crazedAI : public ScriptedAI { boss_kiggler_the_crazedAI(Creature* creature) : ScriptedAI(creature) @@ -463,59 +322,28 @@ public: ArcaneShock_Timer = 20000; ArcaneExplosion_Timer = 30000; - //reset encounter - if (instance) - instance->SetData(DATA_MAULGAREVENT, NOT_STARTED); + instance->SetBossState(DATA_MAULGAR, NOT_STARTED); } - void EnterCombat(Unit* who) OVERRIDE + void EnterCombat(Unit* /*who*/) OVERRIDE { - if (instance) - { - instance->SetData64(DATA_MAULGAREVENT_TANK, who->GetGUID()); - instance->SetData(DATA_MAULGAREVENT, IN_PROGRESS); - } + DoZoneInCombat(); + instance->SetBossState(DATA_MAULGAR, IN_PROGRESS); } void JustDied(Unit* /*killer*/) OVERRIDE { - if (instance) - { - Creature* Maulgar = NULL; - Maulgar = (Unit::GetCreature((*me), instance->GetData64(DATA_MAULGAR))); - - if (Maulgar) - CAST_AI(boss_high_king_maulgar::boss_high_king_maulgarAI, Maulgar->AI())->AddDeath(); + if (Creature* maulgar = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_MAULGAR))) + maulgar->AI()->DoAction(ACTION_ADD_DEATH); - if (CheckAllBossDied(instance, me)) - instance->SetData(DATA_MAULGAREVENT, DONE); - } + instance->SetBossState(DATA_MAULGAR, DONE); } void UpdateAI(uint32 diff) OVERRIDE { - //Only if not incombat check if the event is started - if (!me->IsInCombat() && instance && instance->GetData(DATA_MAULGAREVENT)) - { - Unit* target = Unit::GetUnit(*me, instance->GetData64(DATA_MAULGAREVENT_TANK)); - - if (target) - { - AttackStart(target); - } - } - - //Return since we have no target if (!UpdateVictim()) return; - //someone evaded! - if (instance && !instance->GetData(DATA_MAULGAREVENT)) - { - EnterEvadeMode(); - return; - } - //GreaterPolymorph_Timer if (GreaterPolymorph_Timer <= diff) { @@ -550,19 +378,17 @@ public: } }; + CreatureAI* GetAI(Creature* creature) const OVERRIDE + { + return GetGruulsLairAI<boss_kiggler_the_crazedAI>(creature); + } }; -//Blindeye The Seer AI class boss_blindeye_the_seer : public CreatureScript { public: boss_blindeye_the_seer() : CreatureScript("boss_blindeye_the_seer") { } - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return new boss_blindeye_the_seerAI(creature); - } - struct boss_blindeye_the_seerAI : public ScriptedAI { boss_blindeye_the_seerAI(Creature* creature) : ScriptedAI(creature) @@ -582,59 +408,28 @@ public: Heal_Timer = urand(25000, 40000); PrayerofHealing_Timer = urand(45000, 55000); - //reset encounter - if (instance) - instance->SetData(DATA_MAULGAREVENT, NOT_STARTED); + instance->SetBossState(DATA_MAULGAR, NOT_STARTED); } - void EnterCombat(Unit* who) OVERRIDE + void EnterCombat(Unit* /*who*/) OVERRIDE { - if (instance) - { - instance->SetData64(DATA_MAULGAREVENT_TANK, who->GetGUID()); - instance->SetData(DATA_MAULGAREVENT, IN_PROGRESS); - } + DoZoneInCombat(); + instance->SetBossState(DATA_MAULGAR, IN_PROGRESS); } void JustDied(Unit* /*killer*/) OVERRIDE { - if (instance) - { - Creature* Maulgar = NULL; - Maulgar = (Unit::GetCreature((*me), instance->GetData64(DATA_MAULGAR))); + if (Creature* maulgar = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_MAULGAR))) + maulgar->AI()->DoAction(ACTION_ADD_DEATH); - if (Maulgar) - CAST_AI(boss_high_king_maulgar::boss_high_king_maulgarAI, Maulgar->AI())->AddDeath(); - - if (CheckAllBossDied(instance, me)) - instance->SetData(DATA_MAULGAREVENT, DONE); - } + instance->SetBossState(DATA_MAULGAR, DONE); } void UpdateAI(uint32 diff) OVERRIDE { - //Only if not incombat check if the event is started - if (!me->IsInCombat() && instance && instance->GetData(DATA_MAULGAREVENT)) - { - Unit* target = Unit::GetUnit(*me, instance->GetData64(DATA_MAULGAREVENT_TANK)); - - if (target) - { - AttackStart(target); - } - } - - //Return since we have no target if (!UpdateVictim()) return; - //someone evaded! - if (instance && !instance->GetData(DATA_MAULGAREVENT)) - { - EnterEvadeMode(); - return; - } - //GreaterPowerWordShield_Timer if (GreaterPowerWordShield_Timer <= diff) { @@ -660,19 +455,17 @@ public: } }; + CreatureAI* GetAI(Creature* creature) const OVERRIDE + { + return GetGruulsLairAI<boss_blindeye_the_seerAI>(creature); + } }; -//Krosh Firehand AI class boss_krosh_firehand : public CreatureScript { public: boss_krosh_firehand() : CreatureScript("boss_krosh_firehand") { } - CreatureAI* GetAI(Creature* creature) const OVERRIDE - { - return new boss_krosh_firehandAI(creature); - } - struct boss_krosh_firehandAI : public ScriptedAI { boss_krosh_firehandAI(Creature* creature) : ScriptedAI(creature) @@ -692,59 +485,28 @@ public: SpellShield_Timer = 5000; BlastWave_Timer = 20000; - //reset encounter - if (instance) - instance->SetData(DATA_MAULGAREVENT, NOT_STARTED); + instance->SetBossState(DATA_MAULGAR, NOT_STARTED); } - void EnterCombat(Unit* who) OVERRIDE + void EnterCombat(Unit* /*who*/) OVERRIDE { - if (instance) - { - instance->SetData64(DATA_MAULGAREVENT_TANK, who->GetGUID()); - instance->SetData(DATA_MAULGAREVENT, IN_PROGRESS); - } + DoZoneInCombat(); + instance->SetBossState(DATA_MAULGAR, IN_PROGRESS); } void JustDied(Unit* /*killer*/) OVERRIDE { - if (instance) - { - Creature* Maulgar = NULL; - Maulgar = (Unit::GetCreature((*me), instance->GetData64(DATA_MAULGAR))); + if (Creature* maulgar = ObjectAccessor::GetCreature(*me, instance->GetData64(DATA_MAULGAR))) + maulgar->AI()->DoAction(ACTION_ADD_DEATH); - if (Maulgar) - CAST_AI(boss_high_king_maulgar::boss_high_king_maulgarAI, Maulgar->AI())->AddDeath(); - - if (CheckAllBossDied(instance, me)) - instance->SetData(DATA_MAULGAREVENT, DONE); - } + instance->SetBossState(DATA_MAULGAR, DONE); } void UpdateAI(uint32 diff) OVERRIDE { - //Only if not incombat check if the event is started - if (!me->IsInCombat() && instance && instance->GetData(DATA_MAULGAREVENT)) - { - Unit* target = Unit::GetUnit(*me, instance->GetData64(DATA_MAULGAREVENT_TANK)); - - if (target) - { - AttackStart(target); - } - } - - //Return since we have no target if (!UpdateVictim()) return; - //someone evaded! - if (instance && !instance->GetData(DATA_MAULGAREVENT)) - { - EnterEvadeMode(); - return; - } - //GreaterFireball_Timer if (GreaterFireball_Timer < diff || me->IsWithinDist(me->GetVictim(), 30)) { @@ -783,6 +545,11 @@ public: } else BlastWave_Timer -= diff; } }; + + CreatureAI* GetAI(Creature* creature) const OVERRIDE + { + return GetGruulsLairAI<boss_krosh_firehandAI>(creature); + } }; void AddSC_boss_high_king_maulgar() diff --git a/src/server/scripts/Outland/GruulsLair/gruuls_lair.h b/src/server/scripts/Outland/GruulsLair/gruuls_lair.h index 69ddba8c274..1425a19aa47 100644 --- a/src/server/scripts/Outland/GruulsLair/gruuls_lair.h +++ b/src/server/scripts/Outland/GruulsLair/gruuls_lair.h @@ -1,6 +1,5 @@ /* * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2006-2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/> * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the @@ -16,23 +15,39 @@ * with this program. If not, see <http://www.gnu.org/licenses/>. */ -#ifndef DEF_GRUULS_LAIR_H -#define DEF_GRUULS_LAIR_H +#ifndef GRUULS_LAIR_H_ +#define GRUULS_LAIR_H_ + +#define GLScriptName "instance_gruuls_lair" + +uint32 const EncounterCount = 2; enum DataTypes { - DATA_BLINDEYETHESEER = 1, - DATA_GRUULEVENT = 2, - DATA_KIGGLERTHECRAZED = 3, - DATA_KROSHFIREHAND = 4, - DATA_MAULGAREVENT = 5, - DATA_MAULGAREVENT_TANK = 6, - DATA_OLMTHESUMMONER = 7, - DATA_MAULGARDOOR = 8, - DATA_GRUULDOOR = 9, - DATA_MAULGAR = 10 + // Encounter States/Boss GUIDs + DATA_MAULGAR = 0, + DATA_GRUUL = 1 +}; + +enum CreatureIds +{ + NPC_MAULGAR = 18831, + NPC_KROSH_FIREHAND = 18832, + NPC_OLM_THE_SUMMONER = 18834, + NPC_KIGGLER_THE_CRAZED = 18835, + NPC_BLINDEYE_THE_SEER = 18836 }; -#define ERROR_INST_DATA "TSCR Error: Instance Data not set properly for Gruul's Lair instance (map 565). Encounters will be buggy." -#endif +enum GameObjectIds +{ + GO_MAULGAR_DOOR = 184468, + GO_GRUUL_DOOR = 184662 +}; + +template<class AI> +AI* GetGruulsLairAI(Creature* creature) +{ + return GetInstanceAI<AI>(creature, GLScriptName); +} +#endif // GRUULS_LAIR_H_ diff --git a/src/server/scripts/Outland/GruulsLair/instance_gruuls_lair.cpp b/src/server/scripts/Outland/GruulsLair/instance_gruuls_lair.cpp index d8399793df4..aa8a8d01d8a 100644 --- a/src/server/scripts/Outland/GruulsLair/instance_gruuls_lair.cpp +++ b/src/server/scripts/Outland/GruulsLair/instance_gruuls_lair.cpp @@ -1,6 +1,5 @@ /* * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> - * Copyright (C) 2006-2009 ScriptDev2 <https://scriptdev2.svn.sourceforge.net/> * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the @@ -16,184 +15,165 @@ * with this program. If not, see <http://www.gnu.org/licenses/>. */ -/* ScriptData -SDName: Instance_Gruuls_Lair -SD%Complete: 100 -SDComment: -SDCategory: Gruul's Lair -EndScriptData */ - #include "ScriptMgr.h" #include "InstanceScript.h" #include "gruuls_lair.h" -#define MAX_ENCOUNTER 2 +DoorData const doorData[] = +{ + { GO_MAULGAR_DOOR, DATA_MAULGAR, DOOR_TYPE_PASSAGE, BOUNDARY_NONE }, + { GO_GRUUL_DOOR, DATA_GRUUL, DOOR_TYPE_ROOM, BOUNDARY_NONE }, + { 0, 0, DOOR_TYPE_ROOM, BOUNDARY_NONE } // END +}; -/* Gruuls Lair encounters: -1 - High King Maulgar event -2 - Gruul event -*/ +MinionData const minionData[] = +{ + { NPC_MAULGAR, DATA_MAULGAR }, + { NPC_KROSH_FIREHAND, DATA_MAULGAR }, + { NPC_OLM_THE_SUMMONER, DATA_MAULGAR }, + { NPC_KIGGLER_THE_CRAZED, DATA_MAULGAR }, + { NPC_BLINDEYE_THE_SEER, DATA_MAULGAR } +}; class instance_gruuls_lair : public InstanceMapScript { -public: - instance_gruuls_lair() : InstanceMapScript("instance_gruuls_lair", 565) { } - - InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE - { - return new instance_gruuls_lair_InstanceMapScript(map); - } + public: + instance_gruuls_lair() : InstanceMapScript(GLScriptName, 565) { } - struct instance_gruuls_lair_InstanceMapScript : public InstanceScript - { - instance_gruuls_lair_InstanceMapScript(Map* map) : InstanceScript(map) {} - - uint32 m_auiEncounter[MAX_ENCOUNTER]; - - uint64 MaulgarEvent_Tank; - uint64 KigglerTheCrazed; - uint64 BlindeyeTheSeer; - uint64 OlmTheSummoner; - uint64 KroshFirehand; - uint64 Maulgar; - - uint64 MaulgarDoor; - uint64 GruulDoor; - - void Initialize() OVERRIDE + struct instance_gruuls_lair_InstanceMapScript : public InstanceScript { - memset(&m_auiEncounter, 0, sizeof(m_auiEncounter)); - - MaulgarEvent_Tank = 0; - KigglerTheCrazed = 0; - BlindeyeTheSeer = 0; - OlmTheSummoner = 0; - KroshFirehand = 0; - Maulgar = 0; - - MaulgarDoor = 0; - GruulDoor = 0; - } - - bool IsEncounterInProgress() const OVERRIDE - { - for (uint8 i = 0; i < MAX_ENCOUNTER; ++i) - if (m_auiEncounter[i] == IN_PROGRESS) - return true; + instance_gruuls_lair_InstanceMapScript(Map* map) : InstanceScript(map) + { + SetBossNumber(EncounterCount); + LoadDoorData(doorData); + LoadMinionData(minionData); - return false; - } + MaulgarGUID = 0; + } - void OnCreatureCreate(Creature* creature) OVERRIDE - { - switch (creature->GetEntry()) + void OnCreatureCreate(Creature* creature) OVERRIDE { - case 18835: KigglerTheCrazed = creature->GetGUID(); break; - case 18836: BlindeyeTheSeer = creature->GetGUID(); break; - case 18834: OlmTheSummoner = creature->GetGUID(); break; - case 18832: KroshFirehand = creature->GetGUID(); break; - case 18831: Maulgar = creature->GetGUID(); break; + switch (creature->GetEntry()) + { + case NPC_MAULGAR: + MaulgarGUID = creature->GetGUID(); + // no break; + case NPC_KROSH_FIREHAND: + case NPC_OLM_THE_SUMMONER: + case NPC_KIGGLER_THE_CRAZED: + case NPC_BLINDEYE_THE_SEER: + AddMinion(creature, true); + break; + default: + break; + } } - } - void OnGameObjectCreate(GameObject* go) OVERRIDE - { - switch (go->GetEntry()) + void OnCreatureRemove(Creature* creature) OVERRIDE { - case 184468: - MaulgarDoor = go->GetGUID(); - if (m_auiEncounter[0] == DONE) - HandleGameObject(0, true, go); - break; - case 184662: - GruulDoor = go->GetGUID(); - break; + switch (creature->GetEntry()) + { + case NPC_MAULGAR: + case NPC_KROSH_FIREHAND: + case NPC_OLM_THE_SUMMONER: + case NPC_KIGGLER_THE_CRAZED: + case NPC_BLINDEYE_THE_SEER: + AddMinion(creature, false); + break; + default: + break; + } } - } - void SetData64(uint32 type, uint64 data) OVERRIDE - { - if (type == DATA_MAULGAREVENT_TANK) - MaulgarEvent_Tank = data; - } - - uint64 GetData64(uint32 identifier) const OVERRIDE - { - switch (identifier) + void OnGameObjectCreate(GameObject* go) OVERRIDE { - case DATA_MAULGAREVENT_TANK: return MaulgarEvent_Tank; - case DATA_KIGGLERTHECRAZED: return KigglerTheCrazed; - case DATA_BLINDEYETHESEER: return BlindeyeTheSeer; - case DATA_OLMTHESUMMONER: return OlmTheSummoner; - case DATA_KROSHFIREHAND: return KroshFirehand; - case DATA_MAULGARDOOR: return MaulgarDoor; - case DATA_GRUULDOOR: return GruulDoor; - case DATA_MAULGAR: return Maulgar; + switch (go->GetEntry()) + { + case GO_MAULGAR_DOOR: + case GO_GRUUL_DOOR: + AddDoor(go, true); + break; + default: + break; + } } - return 0; - } - void SetData(uint32 type, uint32 data) OVERRIDE - { - switch (type) + void OnGameObjectRemove(GameObject* go) OVERRIDE { - case DATA_MAULGAREVENT: - if (data == DONE) - HandleGameObject(MaulgarDoor, true); - m_auiEncounter[0] = data; - break; - - case DATA_GRUULEVENT: - if (data == IN_PROGRESS) - HandleGameObject(GruulDoor, false); - else - HandleGameObject(GruulDoor, true); - m_auiEncounter[1] = data; - break; + switch (go->GetEntry()) + { + case GO_MAULGAR_DOOR: + case GO_GRUUL_DOOR: + AddDoor(go, false); + break; + default: + break; + } } - if (data == DONE) - SaveToDB(); - } - - uint32 GetData(uint32 type) const OVERRIDE - { - switch (type) + uint64 GetData64(uint32 type) const OVERRIDE { - case DATA_MAULGAREVENT: return m_auiEncounter[0]; - case DATA_GRUULEVENT: return m_auiEncounter[1]; + switch (type) + { + case DATA_MAULGAR: + return MaulgarGUID; + default: + break; + } + return 0; } - return 0; - } - std::string GetSaveData() OVERRIDE - { - OUT_SAVE_INST_DATA; - std::ostringstream stream; - stream << m_auiEncounter[0] << ' ' << m_auiEncounter[1]; + std::string GetSaveData() OVERRIDE + { + OUT_SAVE_INST_DATA; - OUT_SAVE_INST_DATA_COMPLETE; - return stream.str(); - } + std::ostringstream saveStream; + saveStream << "G L " << GetBossSaveData(); - void Load(const char* in) OVERRIDE - { - if (!in) + OUT_SAVE_INST_DATA_COMPLETE; + return saveStream.str(); + } + + void Load(char const* str) OVERRIDE { - OUT_LOAD_INST_DATA_FAIL; - return; + if (!str) + { + OUT_LOAD_INST_DATA_FAIL; + return; + } + + OUT_LOAD_INST_DATA(str); + + char dataHead1, dataHead2; + + std::istringstream loadStream(str); + loadStream >> dataHead1 >> dataHead2; + + if (dataHead1 == 'G' && dataHead2 == 'L') + { + for (uint32 i = 0; i < EncounterCount; ++i) + { + uint32 tmpState; + loadStream >> tmpState; + if (tmpState == IN_PROGRESS || tmpState > SPECIAL) + tmpState = NOT_STARTED; + SetBossState(i, EncounterState(tmpState)); + } + } + else + OUT_LOAD_INST_DATA_FAIL; + + OUT_LOAD_INST_DATA_COMPLETE; } - OUT_LOAD_INST_DATA(in); - std::istringstream stream(in); - stream >> m_auiEncounter[0] >> m_auiEncounter[1]; - for (uint8 i = 0; i < MAX_ENCOUNTER; ++i) - if (m_auiEncounter[i] == IN_PROGRESS) // Do not load an encounter as "In Progress" - reset it instead. - m_auiEncounter[i] = NOT_STARTED; - OUT_LOAD_INST_DATA_COMPLETE; - } - }; + protected: + uint64 MaulgarGUID; + }; + InstanceScript* GetInstanceScript(InstanceMap* map) const OVERRIDE + { + return new instance_gruuls_lair_InstanceMapScript(map); + } }; void AddSC_instance_gruuls_lair() diff --git a/src/server/scripts/Outland/HellfireCitadel/HellfireRamparts/boss_omor_the_unscarred.cpp b/src/server/scripts/Outland/HellfireCitadel/HellfireRamparts/boss_omor_the_unscarred.cpp index a87aefa72af..7e80182f1e8 100644 --- a/src/server/scripts/Outland/HellfireCitadel/HellfireRamparts/boss_omor_the_unscarred.cpp +++ b/src/server/scripts/Outland/HellfireCitadel/HellfireRamparts/boss_omor_the_unscarred.cpp @@ -132,7 +132,7 @@ class boss_omor_the_unscarred : public CreatureScript { if (ShadowWhip_Timer <= diff) { - if (Player* temp = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* temp = ObjectAccessor::GetPlayer(*me, PlayerGUID)) { //if unit dosen't have this flag, then no pulling back (script will attempt cast, even if orbital strike was resisted) if (temp->HasUnitMovementFlag(MOVEMENTFLAG_FALLING_FAR)) diff --git a/src/server/scripts/Outland/TempestKeep/Eye/boss_alar.cpp b/src/server/scripts/Outland/TempestKeep/Eye/boss_alar.cpp index 09fb235edb9..8b2cce69dc7 100644 --- a/src/server/scripts/Outland/TempestKeep/Eye/boss_alar.cpp +++ b/src/server/scripts/Outland/TempestKeep/Eye/boss_alar.cpp @@ -408,7 +408,7 @@ class boss_alar : public CreatureScript if (Summoned) { Summoned->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); - Summoned->SetObjectScale(Summoned->GetFloatValue(OBJECT_FIELD_SCALE_X)*2.5f); + Summoned->SetObjectScale(Summoned->GetObjectScale() * 2.5f); Summoned->SetDisplayId(11686); Summoned->setFaction(me->getFaction()); Summoned->SetLevel(me->getLevel()); diff --git a/src/server/scripts/Outland/TempestKeep/Eye/boss_astromancer.cpp b/src/server/scripts/Outland/TempestKeep/Eye/boss_astromancer.cpp index 3c8627c7058..c5c3f6deb12 100644 --- a/src/server/scripts/Outland/TempestKeep/Eye/boss_astromancer.cpp +++ b/src/server/scripts/Outland/TempestKeep/Eye/boss_astromancer.cpp @@ -104,7 +104,7 @@ class boss_high_astromancer_solarian : public CreatureScript instance = creature->GetInstanceScript(); defaultarmor = creature->GetArmor(); - defaultsize = creature->GetFloatValue(OBJECT_FIELD_SCALE_X); + defaultsize = creature->GetObjectScale(); } InstanceScript* instance; diff --git a/src/server/scripts/Outland/zone_blades_edge_mountains.cpp b/src/server/scripts/Outland/zone_blades_edge_mountains.cpp index 6273731f292..57eb587140f 100644 --- a/src/server/scripts/Outland/zone_blades_edge_mountains.cpp +++ b/src/server/scripts/Outland/zone_blades_edge_mountains.cpp @@ -500,7 +500,6 @@ public: } void MoveInLineOfSight(Unit* who) OVERRIDE - { if (!who || (!who->IsAlive())) return; @@ -516,15 +515,16 @@ public: void MovementInform(uint32 /*type*/, uint32 id) OVERRIDE { - Player* player = Unit::GetPlayer(*me, PlayerGUID); if (id == 1) { - GameObject* Keg = me->FindNearestGameObject(GO_KEG, 20); - if (Keg) + if (GameObject* Keg = me->FindNearestGameObject(GO_KEG, 20)) Keg->Delete(); + me->HandleEmoteCommand(7); me->SetReactState(REACT_AGGRESSIVE); me->GetMotionMaster()->MoveTargetedHome(); + + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); Creature* Credit = me->FindNearestCreature(NPC_QUEST_CREDIT, 50, true); if (player && Credit) player->KilledMonster(Credit->GetCreatureTemplate(), Credit->GetGUID()); @@ -1017,7 +1017,7 @@ class npc_simon_bunny : public CreatureScript } if (rewSpell) - if (Player* player = me->GetPlayer(*me, playerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, playerGUID)) DoCast(player, rewSpell, true); } @@ -1032,7 +1032,7 @@ class npc_simon_bunny : public CreatureScript { if (large) { - if (Player* player = me->GetPlayer(*me, playerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, playerGUID)) if (Creature* guardian = me->SummonCreature(NPC_APEXIS_GUARDIAN, me->GetPositionX(), me->GetPositionY(), me->GetPositionZ() - zCoordCorrection, 0.0f, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 20000)) guardian->AI()->AttackStart(player); @@ -1042,7 +1042,7 @@ class npc_simon_bunny : public CreatureScript { fails++; - if (Player* player = me->GetPlayer(*me, playerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, playerGUID)) DoCast(player, SPELL_BAD_PRESS_TRIGGER, true); if (fails >= 4) @@ -1065,7 +1065,7 @@ class npc_simon_bunny : public CreatureScript // Checks if player has already die or has get too far from the current node bool CheckPlayer() { - if (Player* player = me->GetPlayer(*me, playerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, playerGUID)) { if (player->isDead()) return false; diff --git a/src/server/scripts/Outland/zone_netherstorm.cpp b/src/server/scripts/Outland/zone_netherstorm.cpp index 7e99275adbd..74257c95cf3 100644 --- a/src/server/scripts/Outland/zone_netherstorm.cpp +++ b/src/server/scripts/Outland/zone_netherstorm.cpp @@ -436,9 +436,9 @@ public: // Emote Ardonis and Pathaleon void Turn_to_Pathaleons_Image() { - Creature* ardonis = Unit::GetCreature(*me, ardonisGUID); - Creature* pathaleon = Unit::GetCreature(*me, pathaleonGUID); - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Creature* ardonis = ObjectAccessor::GetCreature(*me, ardonisGUID); + Creature* pathaleon = ObjectAccessor::GetCreature(*me, pathaleonGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (!ardonis || !pathaleon || !player) return; @@ -462,9 +462,9 @@ public: //Set them back to each other void Turn_to_eachother() { - if (Unit* ardonis = Unit::GetUnit(*me, ardonisGUID)) + if (Unit* ardonis = ObjectAccessor::GetUnit(*me, ardonisGUID)) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (!player) return; @@ -519,9 +519,9 @@ public: return; } - Creature* ardonis = Creature::GetCreature(*me, ardonisGUID); - Creature* pathaleon = Creature::GetCreature(*me, pathaleonGUID); - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Creature* ardonis = ObjectAccessor::GetCreature(*me, ardonisGUID); + Creature* pathaleon = ObjectAccessor::GetCreature(*me, pathaleonGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (!ardonis || !player) { @@ -821,7 +821,7 @@ public: ManaBurnTimer = 3500; } else ManaBurnTimer -= diff; - if (Player* player = Unit::GetPlayer(*me, PlayerGUID)) // start: support for quest 10190 + if (Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID)) // start: support for quest 10190 { if (!Weak && HealthBelowPct(WeakPercent) && player->GetQuestStatus(QUEST_RECHARGING_THE_BATTERIES) == QUEST_STATUS_INCOMPLETE) diff --git a/src/server/scripts/Outland/zone_shadowmoon_valley.cpp b/src/server/scripts/Outland/zone_shadowmoon_valley.cpp index b7cf46ad8ae..cb88e5a5a9c 100644 --- a/src/server/scripts/Outland/zone_shadowmoon_valley.cpp +++ b/src/server/scripts/Outland/zone_shadowmoon_valley.cpp @@ -154,11 +154,11 @@ public: DoCast(me, SPELL_JUST_EATEN); Talk(SAY_JUST_EATEN); - if (Player* pPlr = Unit::GetPlayer(*me, uiPlayerGUID)) + if (Player* player = ObjectAccessor::GetPlayer(*me, uiPlayerGUID)) { - pPlr->KilledMonsterCredit(NPC_EVENT_PINGER, 0); + player->KilledMonsterCredit(NPC_EVENT_PINGER, 0); - if (GameObject* go = pPlr->FindNearestGameObject(GO_CARCASS, 10)) + if (GameObject* go = player->FindNearestGameObject(GO_CARCASS, 10)) go->Delete(); } @@ -298,7 +298,7 @@ public: Tapped = false; if (PlayerGUID) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (player && player->GetQuestStatus(10854) == QUEST_STATUS_INCOMPLETE) { DoCast(player, SPELL_FORCE_OF_NELTHARAKU, true); @@ -400,7 +400,7 @@ public: { if (PlayerGUID) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (player && player->GetQuestStatus(11020) == QUEST_STATUS_INCOMPLETE) player->KilledMonsterCredit(23209, 0); } @@ -760,7 +760,7 @@ public: } if (PlayerGUID) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (player) Talk(OVERLORD_SAY_1, player->GetGUID()); } @@ -771,8 +771,8 @@ public: uint32 NextStep(uint32 Step) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); - Creature* Illi = Creature::GetCreature(*me, IllidanGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); + Creature* Illi = ObjectAccessor::GetCreature(*me, IllidanGUID); if (!player) { @@ -1311,7 +1311,7 @@ public: me->RemoveFlag(UNIT_FIELD_BYTES_1, 8); break; case 5: - if (Player* AggroTarget = (Unit::GetPlayer(*me, AggroTargetGUID))) + if (Player* AggroTarget = ObjectAccessor::GetPlayer(*me, AggroTargetGUID)) { me->SetTarget(AggroTarget->GetGUID()); me->AddThreat(AggroTarget, 1); @@ -1319,7 +1319,7 @@ public: } break; case 6: - if (Player* AggroTarget = (Unit::GetPlayer(*me, AggroTargetGUID))) + if (Player* AggroTarget = ObjectAccessor::GetPlayer(*me, AggroTargetGUID)) { me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE); me->ClearUnitState(UNIT_STATE_ROOT); @@ -1456,15 +1456,13 @@ public: void CheckEventFail() { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (!player) return; if (Group* EventGroup = player->GetGroup()) { - Player* GroupMember; - uint8 GroupMemberCount = 0; uint8 DeadMemberCount = 0; uint8 FailedMemberCount = 0; @@ -1473,7 +1471,7 @@ public: for (Group::member_citerator itr = members.begin(); itr!= members.end(); ++itr) { - GroupMember = (Unit::GetPlayer(*me, itr->guid)); + Player* GroupMember = ObjectAccessor::GetPlayer(*me, itr->guid); if (!GroupMember) continue; if (!GroupMember->IsWithinDistInMap(me, EVENT_AREA_RADIUS) && GroupMember->GetQuestStatus(QUEST_BATTLE_OF_THE_CRIMSON_WATCH) == QUEST_STATUS_INCOMPLETE) @@ -1484,9 +1482,7 @@ public: ++GroupMemberCount; if (GroupMember->isDead()) - { ++DeadMemberCount; - } } if (GroupMemberCount == FailedMemberCount) @@ -1498,12 +1494,9 @@ public: { for (Group::member_citerator itr = members.begin(); itr!= members.end(); ++itr) { - GroupMember = Unit::GetPlayer(*me, itr->guid); - - if (GroupMember && GroupMember->GetQuestStatus(QUEST_BATTLE_OF_THE_CRIMSON_WATCH) == QUEST_STATUS_INCOMPLETE) - { - GroupMember->FailQuest(QUEST_BATTLE_OF_THE_CRIMSON_WATCH); - } + if (Player* groupMember = ObjectAccessor::GetPlayer(*me, itr->guid)) + if (groupMember->GetQuestStatus(QUEST_BATTLE_OF_THE_CRIMSON_WATCH) == QUEST_STATUS_INCOMPLETE) + groupMember->FailQuest(QUEST_BATTLE_OF_THE_CRIMSON_WATCH); } Failed = true; } @@ -1713,7 +1706,7 @@ void npc_lord_illidan_stormrage::npc_lord_illidan_stormrageAI::SummonNextWave() { if (PlayerGUID) { - if (Player* target = Unit::GetPlayer(*me, PlayerGUID)) + if (Player* target = ObjectAccessor::GetPlayer(*me, PlayerGUID)) { float x, y, z; target->GetPosition(x, y, z); diff --git a/src/server/scripts/Spells/spell_hunter.cpp b/src/server/scripts/Spells/spell_hunter.cpp index aca46c252da..b93efe3b0f2 100644 --- a/src/server/scripts/Spells/spell_hunter.cpp +++ b/src/server/scripts/Spells/spell_hunter.cpp @@ -33,6 +33,7 @@ enum HunterSpells { SPELL_HUNTER_ASPECT_OF_THE_BEAST_PET = 61669, + SPELL_HUNTER_ASPECT_OF_THE_VIPER = 34074, SPELL_HUNTER_ASPECT_OF_THE_VIPER_ENERGIZE = 34075, SPELL_HUNTER_BESTIAL_WRATH = 19574, SPELL_HUNTER_CHIMERA_SHOT_SERPENT = 53353, @@ -51,6 +52,8 @@ enum HunterSpells SPELL_HUNTER_READINESS = 23989, SPELL_HUNTER_SNIPER_TRAINING_R1 = 53302, SPELL_HUNTER_SNIPER_TRAINING_BUFF_R1 = 64418, + SPELL_HUNTER_VICIOUS_VIPER = 61609, + SPELL_HUNTER_VIPER_ATTACK_SPEED = 60144, SPELL_DRAENEI_GIFT_OF_THE_NAARU = 59543 }; @@ -115,9 +118,10 @@ class spell_hun_ascpect_of_the_viper : public SpellScriptLoader bool Validate(SpellInfo const* /*spellInfo*/) OVERRIDE { - if (!sSpellMgr->GetSpellInfo(SPELL_HUNTER_ASPECT_OF_THE_VIPER_ENERGIZE)) - return false; - if (!sSpellMgr->GetSpellInfo(SPELL_HUNTER_GLYPH_OF_ASPECT_OF_THE_VIPER)) + if (!sSpellMgr->GetSpellInfo(SPELL_HUNTER_ASPECT_OF_THE_VIPER_ENERGIZE) || + !sSpellMgr->GetSpellInfo(SPELL_HUNTER_GLYPH_OF_ASPECT_OF_THE_VIPER) || + !sSpellMgr->GetSpellInfo(SPELL_HUNTER_VIPER_ATTACK_SPEED) || + !sSpellMgr->GetSpellInfo(SPELL_HUNTER_VICIOUS_VIPER)) return false; return true; } @@ -135,9 +139,25 @@ class spell_hun_ascpect_of_the_viper : public SpellScriptLoader GetTarget()->CastCustomSpell(SPELL_HUNTER_ASPECT_OF_THE_VIPER_ENERGIZE, SPELLVALUE_BASE_POINT0, mana, GetTarget(), true, NULL, aurEff); } + void OnApply(AuraEffect const* aurEff, AuraEffectHandleModes /*mode*/) + { + // Hunter T7 4P Bonus + if (GetTarget()->HasAura(SPELL_HUNTER_VIPER_ATTACK_SPEED)) + GetTarget()->CastSpell(GetTarget(), SPELL_HUNTER_VICIOUS_VIPER, true, NULL, aurEff); + } + + void OnRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/) + { + // Hunter T7 4P Bonus + if (GetTarget()->HasAura(SPELL_HUNTER_VIPER_ATTACK_SPEED)) + GetTarget()->RemoveAurasDueToSpell(SPELL_HUNTER_VICIOUS_VIPER); + } + void Register() OVERRIDE { OnEffectProc += AuraEffectProcFn(spell_hun_ascpect_of_the_viper_AuraScript::HandleProc, EFFECT_0, SPELL_AURA_OBS_MOD_POWER); + AfterEffectApply += AuraEffectApplyFn(spell_hun_ascpect_of_the_viper_AuraScript::OnApply, EFFECT_0, SPELL_AURA_OBS_MOD_POWER, AURA_EFFECT_HANDLE_REAL); + AfterEffectRemove += AuraEffectRemoveFn(spell_hun_ascpect_of_the_viper_AuraScript::OnRemove, EFFECT_0, SPELL_AURA_OBS_MOD_POWER, AURA_EFFECT_HANDLE_REAL); } }; @@ -722,15 +742,10 @@ class spell_hun_sniper_training : public SpellScriptLoader PreventDefaultAction(); if (aurEff->GetAmount() <= 0) { - Unit* caster = GetCaster(); + Unit* target = GetTarget(); uint32 spellId = SPELL_HUNTER_SNIPER_TRAINING_BUFF_R1 + GetId() - SPELL_HUNTER_SNIPER_TRAINING_R1; - if (Unit* target = GetTarget()) - if (!target->HasAura(spellId)) - { - SpellInfo const* triggeredSpellInfo = sSpellMgr->GetSpellInfo(spellId); - Unit* triggerCaster = triggeredSpellInfo->NeedsToBeTriggeredByCaster() ? caster : target; - triggerCaster->CastSpell(target, triggeredSpellInfo, true, 0, aurEff); - } + if (!target->HasAura(spellId)) + target->CastSpell(target, spellId, true, 0, aurEff); } } @@ -843,6 +858,49 @@ class spell_hun_target_only_pet_and_owner : public SpellScriptLoader } }; +// 60144 - Viper Attack Speed +class spell_hun_viper_attack_speed : public SpellScriptLoader +{ + public: + spell_hun_viper_attack_speed() : SpellScriptLoader("spell_hun_viper_attack_speed") { } + + class spell_hun_viper_attack_speed_AuraScript : public AuraScript + { + PrepareAuraScript(spell_hun_viper_attack_speed_AuraScript); + + bool Validate(SpellInfo const* /*spellInfo*/) OVERRIDE + { + if (!sSpellMgr->GetSpellInfo(SPELL_HUNTER_ASPECT_OF_THE_VIPER) || + !sSpellMgr->GetSpellInfo(SPELL_HUNTER_VICIOUS_VIPER)) + return false; + return true; + } + + void OnApply(AuraEffect const* aurEff, AuraEffectHandleModes /*mode*/) + { + if (GetTarget()->HasAura(SPELL_HUNTER_ASPECT_OF_THE_VIPER)) + GetTarget()->CastSpell(GetTarget(), SPELL_HUNTER_VICIOUS_VIPER, true, NULL, aurEff); + } + + void OnRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/) + { + // possible exploit + GetTarget()->RemoveAurasDueToSpell(SPELL_HUNTER_VICIOUS_VIPER); + } + + void Register() OVERRIDE + { + AfterEffectApply += AuraEffectApplyFn(spell_hun_viper_attack_speed_AuraScript::OnApply, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL); + AfterEffectRemove += AuraEffectRemoveFn(spell_hun_viper_attack_speed_AuraScript::OnRemove, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL); + } + }; + + AuraScript* GetAuraScript() const OVERRIDE + { + return new spell_hun_viper_attack_speed_AuraScript(); + } +}; + void AddSC_hunter_spell_scripts() { new spell_hun_aspect_of_the_beast(); @@ -862,4 +920,5 @@ void AddSC_hunter_spell_scripts() new spell_hun_sniper_training(); new spell_hun_tame_beast(); new spell_hun_target_only_pet_and_owner(); + new spell_hun_viper_attack_speed(); } diff --git a/src/server/scripts/Spells/spell_warrior.cpp b/src/server/scripts/Spells/spell_warrior.cpp index 78dcaaa669c..d022eef65b9 100644 --- a/src/server/scripts/Spells/spell_warrior.cpp +++ b/src/server/scripts/Spells/spell_warrior.cpp @@ -578,9 +578,8 @@ class spell_warr_slam : public SpellScriptLoader void HandleDummy(SpellEffIndex /*effIndex*/) { - int32 bp0 = GetEffectValue(); if (GetHitUnit()) - GetCaster()->CastCustomSpell(GetHitUnit(), SPELL_WARRIOR_SLAM, &bp0, NULL, NULL, true, 0); + GetCaster()->CastCustomSpell(SPELL_WARRIOR_SLAM, SPELLVALUE_BASE_POINT0, GetEffectValue(), GetHitUnit(), TRIGGERED_FULL_MASK); } void Register() OVERRIDE diff --git a/src/server/scripts/World/npcs_special.cpp b/src/server/scripts/World/npcs_special.cpp index 8e103f105c1..4efdf78154d 100644 --- a/src/server/scripts/World/npcs_special.cpp +++ b/src/server/scripts/World/npcs_special.cpp @@ -634,7 +634,7 @@ public: void PatientDied(Location* point) { - Player* player = Unit::GetPlayer(*me, PlayerGUID); + Player* player = ObjectAccessor::GetPlayer(*me, PlayerGUID); if (player && ((player->GetQuestStatus(6624) == QUEST_STATUS_INCOMPLETE) || (player->GetQuestStatus(6622) == QUEST_STATUS_INCOMPLETE))) { ++PatientDiedCount; @@ -1685,7 +1685,7 @@ public: me->MonsterWhisper(whisp.c_str(), player->GetGUID()); if (victimGUID) - if (Player* victim = Unit::GetPlayer(*me, victimGUID)) + if (Player* victim = ObjectAccessor::GetPlayer(*me, victimGUID)) victim->RemoveAura(43906); // remove polymorph frog thing me->AddAura(43906, player); // add polymorph frog thing victimGUID = player->GetGUID(); diff --git a/src/server/shared/Cryptography/BigNumber.cpp b/src/server/shared/Cryptography/BigNumber.cpp index 06ea57b662e..b2fce985f21 100644 --- a/src/server/shared/Cryptography/BigNumber.cpp +++ b/src/server/shared/Cryptography/BigNumber.cpp @@ -22,17 +22,18 @@ #include <openssl/bn.h> #include <openssl/crypto.h> #include <algorithm> +#include <ace/Auto_Ptr.h> BigNumber::BigNumber() - : _bn(BN_new()), _array(NULL) + : _bn(BN_new()) { } BigNumber::BigNumber(BigNumber const& bn) - : _bn(BN_dup(bn._bn)), _array(NULL) + : _bn(BN_dup(bn._bn)) { } BigNumber::BigNumber(uint32 val) - : _bn(BN_new()), _array(NULL) + : _bn(BN_new()) { BN_set_word(_bn, val); } @@ -40,7 +41,6 @@ BigNumber::BigNumber(uint32 val) BigNumber::~BigNumber() { BN_free(_bn); - delete[] _array; } void BigNumber::SetDword(uint32 val) @@ -50,16 +50,21 @@ void BigNumber::SetDword(uint32 val) void BigNumber::SetQword(uint64 val) { - BN_add_word(_bn, (uint32)(val >> 32)); + BN_set_word(_bn, (uint32)(val >> 32)); BN_lshift(_bn, _bn, 32); BN_add_word(_bn, (uint32)(val & 0xFFFFFFFF)); } void BigNumber::SetBinary(uint8 const* bytes, int32 len) { - uint8 t[1000]; - for (int i = 0; i < len; i++) t[i] = bytes[len - 1 - i]; - BN_bin2bn(t, len, _bn); + uint8* array = new uint8[len]; + + for (int i = 0; i < len; i++) + array[i] = bytes[len - 1 - i]; + + BN_bin2bn(array, len, _bn); + + delete[] array; } void BigNumber::SetHexStr(char const* str) @@ -165,29 +170,24 @@ bool BigNumber::isZero() const return BN_is_zero(_bn); } -uint8* BigNumber::AsByteArray(int32 minSize, bool reverse) +ACE_Auto_Array_Ptr<uint8> BigNumber::AsByteArray(int32 minSize, bool littleEndian) { int length = (minSize >= GetNumBytes()) ? minSize : GetNumBytes(); - ACE_GUARD_RETURN(ACE_Mutex, g, _lock, 0); - - if (_array) - { - delete[] _array; - _array = NULL; - } - _array = new uint8[length]; + uint8* array = new uint8[length]; // If we need more bytes than length of BigNumber set the rest to 0 if (length > GetNumBytes()) - memset((void*)_array, 0, length); + memset((void*)array, 0, length); - BN_bn2bin(_bn, (unsigned char *)_array); + BN_bn2bin(_bn, (unsigned char *)array); - if (reverse) - std::reverse(_array, _array + length); + // openssl's BN stores data internally in big endian format, reverse if little endian desired + if (littleEndian) + std::reverse(array, array + length); - return _array; + ACE_Auto_Array_Ptr<uint8> ret(array); + return ret; } char * BigNumber::AsHexStr() const diff --git a/src/server/shared/Cryptography/BigNumber.h b/src/server/shared/Cryptography/BigNumber.h index fe56fd7e6f9..6129a24d1bc 100644 --- a/src/server/shared/Cryptography/BigNumber.h +++ b/src/server/shared/Cryptography/BigNumber.h @@ -20,7 +20,7 @@ #define _AUTH_BIGNUMBER_H #include "Define.h" -#include <ace/Mutex.h> +#include <ace/Auto_Ptr.h> struct bignum_st; @@ -86,17 +86,14 @@ class BigNumber struct bignum_st *BN() { return _bn; } uint32 AsDword(); - uint8* AsByteArray(int32 minSize = 0, bool reverse = true); + + ACE_Auto_Array_Ptr<uint8> AsByteArray(int32 minSize = 0, bool littleEndian = true); char * AsHexStr() const; char * AsDecStr() const; private: struct bignum_st *_bn; - uint8 *_array; - - // This mutex only controls thread-safe access to AsByteArray() and should be replaced with a thread-safe implementation of BigNumber - ACE_Mutex _lock; }; #endif diff --git a/src/server/shared/Cryptography/HMACSHA1.cpp b/src/server/shared/Cryptography/HMACSHA1.cpp index 297b4e90316..62d1997ded2 100644 --- a/src/server/shared/Cryptography/HMACSHA1.cpp +++ b/src/server/shared/Cryptography/HMACSHA1.cpp @@ -45,7 +45,7 @@ void HmacHash::Finalize() uint8 *HmacHash::ComputeHash(BigNumber* bn) { - HMAC_Update(&m_ctx, bn->AsByteArray(), bn->GetNumBytes()); + HMAC_Update(&m_ctx, bn->AsByteArray().get(), bn->GetNumBytes()); Finalize(); return (uint8*)m_digest; } diff --git a/src/server/shared/Cryptography/OpenSSLCrypto.cpp b/src/server/shared/Cryptography/OpenSSLCrypto.cpp new file mode 100644 index 00000000000..417be813347 --- /dev/null +++ b/src/server/shared/Cryptography/OpenSSLCrypto.cpp @@ -0,0 +1,59 @@ +/* + * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +#include <OpenSSLCrypto.h> +#include <openssl/crypto.h> +#include <ace/Thread_Mutex.h> +#include <vector> +#include <ace/Thread.h> + +std::vector<ACE_Thread_Mutex*> cryptoLocks; + +static void lockingCallback(int mode, int type, const char* /*file*/, int /*line*/) +{ + if (mode & CRYPTO_LOCK) + cryptoLocks[type]->acquire(); + else + cryptoLocks[type]->release(); +} + +static void threadIdCallback(CRYPTO_THREADID * id) +{ + CRYPTO_THREADID_set_numeric(id, ACE_Thread::self()); +} + +void OpenSSLCrypto::threadsSetup() +{ + cryptoLocks.resize(CRYPTO_num_locks()); + for(int i = 0 ; i < CRYPTO_num_locks(); ++i) + { + cryptoLocks[i] = new ACE_Thread_Mutex(); + } + CRYPTO_THREADID_set_callback(threadIdCallback); + CRYPTO_set_locking_callback(lockingCallback); +} + +void OpenSSLCrypto::threadsCleanup() +{ + CRYPTO_set_locking_callback(NULL); + CRYPTO_THREADID_set_callback(NULL); + for(int i = 0 ; i < CRYPTO_num_locks(); ++i) + { + delete cryptoLocks[i]; + } + cryptoLocks.resize(0); +}
\ No newline at end of file diff --git a/src/server/shared/Cryptography/OpenSSLCrypto.h b/src/server/shared/Cryptography/OpenSSLCrypto.h new file mode 100644 index 00000000000..70071007c5f --- /dev/null +++ b/src/server/shared/Cryptography/OpenSSLCrypto.h @@ -0,0 +1,33 @@ +/* + * Copyright (C) 2008-2013 TrinityCore <http://www.trinitycore.org/> + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see <http://www.gnu.org/licenses/>. + */ + +#ifndef OPENSSL_CRYPTO_H +#define OPENSSL_CRYPTO_H + +/** +* A group of functions which setup openssl crypto module to work properly in multithreaded enviroment +* If not setup properly - it will crash +*/ +namespace OpenSSLCrypto +{ + /// Needs to be called before threads using openssl are spawned + void threadsSetup(); + /// Needs to be called after threads using openssl are despawned + void threadsCleanup(); +} + +#endif
\ No newline at end of file diff --git a/src/server/shared/Cryptography/SHA1.cpp b/src/server/shared/Cryptography/SHA1.cpp index 00d7e520d51..1f65c88a6f3 100644 --- a/src/server/shared/Cryptography/SHA1.cpp +++ b/src/server/shared/Cryptography/SHA1.cpp @@ -50,7 +50,7 @@ void SHA1Hash::UpdateBigNumbers(BigNumber* bn0, ...) bn = bn0; while (bn) { - UpdateData(bn->AsByteArray(), bn->GetNumBytes()); + UpdateData(bn->AsByteArray().get(), bn->GetNumBytes()); bn = va_arg(v, BigNumber*); } va_end(v); diff --git a/src/server/worldserver/Master.cpp b/src/server/worldserver/Master.cpp index 6fd57179140..b2a6b60ac4f 100644 --- a/src/server/worldserver/Master.cpp +++ b/src/server/worldserver/Master.cpp @@ -44,6 +44,7 @@ #include "RealmList.h" #include "BigNumber.h" +#include "OpenSSLCrypto.h" #ifdef _WIN32 #include "ServiceWin32.h" @@ -121,6 +122,7 @@ public: /// Main function int Master::Run() { + OpenSSLCrypto::threadsSetup(); BigNumber seed1; seed1.SetRand(16 * 8); @@ -368,6 +370,7 @@ int Master::Run() // fixes a memory leak related to detaching threads from the module //UnloadScriptingModule(); + OpenSSLCrypto::threadsCleanup(); // Exit the process with specified return value return World::GetExitCode(); } diff --git a/src/tools/mmaps_generator/TerrainBuilder.cpp b/src/tools/mmaps_generator/TerrainBuilder.cpp index 3a87da3d4f1..5c76161c0d6 100644 --- a/src/tools/mmaps_generator/TerrainBuilder.cpp +++ b/src/tools/mmaps_generator/TerrainBuilder.cpp @@ -260,7 +260,8 @@ namespace MMAP meshData.solidVerts.append(coord[1]); } - int indices[3], loopStart = 0, loopEnd = 0, loopInc = 0; + int indices[] = { 0, 0, 0 }; + int loopStart = 0, loopEnd = 0, loopInc = 0; getLoopVars(portion, loopStart, loopEnd, loopInc); for (int i = loopStart; i < loopEnd; i+=loopInc) for (int j = TOP; j <= BOTTOM; j+=1) @@ -340,7 +341,8 @@ namespace MMAP delete [] liquid_map; - int indices[3], loopStart = 0, loopEnd = 0, loopInc = 0, triInc = BOTTOM-TOP; + int indices[] = { 0, 0, 0 }; + int loopStart = 0, loopEnd = 0, loopInc = 0, triInc = BOTTOM-TOP; getLoopVars(portion, loopStart, loopEnd, loopInc); // generate triangles diff --git a/src/tools/vmap4_extractor/wmo.cpp b/src/tools/vmap4_extractor/wmo.cpp index 7c9f23c5a95..d7bd9ecd2f9 100644 --- a/src/tools/vmap4_extractor/wmo.cpp +++ b/src/tools/vmap4_extractor/wmo.cpp @@ -388,7 +388,7 @@ int WMOGroup::ConvertToVMAPGroupWmo(FILE *output, WMORoot *rootWMO, bool precise fwrite(MoviEx,2,nColTriangles*3,output); // write vertices - int VERT[] = {0x54524556, nColVertices*3*sizeof(float)+4, nColVertices};// "VERT" + int VERT[] = {0x54524556, nColVertices*3*static_cast<int>(sizeof(float))+4, nColVertices};// "VERT" int check = 3*nColVertices; fwrite(VERT,4,3,output); for (uint32 i=0; i<nVertices; ++i) @@ -402,9 +402,9 @@ int WMOGroup::ConvertToVMAPGroupWmo(FILE *output, WMORoot *rootWMO, bool precise } //------LIQU------------------------ - if(LiquEx_size != 0) + if (LiquEx_size != 0) { - int LIQU_h[] = {0x5551494C, sizeof(WMOLiquidHeader) + LiquEx_size + hlq->xtiles*hlq->ytiles};// "LIQU" + int LIQU_h[] = {0x5551494C, static_cast<int>(sizeof(WMOLiquidHeader) + LiquEx_size) + hlq->xtiles*hlq->ytiles};// "LIQU" fwrite(LIQU_h, 4, 2, output); // according to WoW.Dev Wiki: |
