From 5365bd25fae59a6ae225534b779bd6c14779599a Mon Sep 17 00:00:00 2001 From: QAston Date: Thu, 9 Feb 2012 23:27:22 +0100 Subject: Core/Spells: remove some workarounds about transform spells in corpse explosion script. --- src/server/game/Entities/Unit/Unit.cpp | 8 -------- src/server/scripts/Spells/spell_dk.cpp | 10 +++++----- 2 files changed, 5 insertions(+), 13 deletions(-) (limited to 'src') diff --git a/src/server/game/Entities/Unit/Unit.cpp b/src/server/game/Entities/Unit/Unit.cpp index 5b18713740f..3859c8dcafe 100755 --- a/src/server/game/Entities/Unit/Unit.cpp +++ b/src/server/game/Entities/Unit/Unit.cpp @@ -12704,14 +12704,6 @@ void Unit::setDeathState(DeathState s) } else if (s == JUST_ALIVED) RemoveFlag (UNIT_FIELD_FLAGS, UNIT_FLAG_SKINNABLE); // clear skinnable for creature and player (at battleground) - - if (oldDeathState != ALIVE && s == ALIVE) - { - // Reset display id on resurection - needed by corpse explosion to cleanup after display change - // TODO: fix this - if (!HasAuraType(SPELL_AURA_TRANSFORM)) - SetDisplayId(GetNativeDisplayId()); - } } /*######################################## diff --git a/src/server/scripts/Spells/spell_dk.cpp b/src/server/scripts/Spells/spell_dk.cpp index f62d62c671a..5c0f6bcce59 100644 --- a/src/server/scripts/Spells/spell_dk.cpp +++ b/src/server/scripts/Spells/spell_dk.cpp @@ -29,8 +29,8 @@ enum DeathKnightSpells DK_SPELL_RUNIC_POWER_ENERGIZE = 49088, DK_SPELL_ANTI_MAGIC_SHELL_TALENT = 51052, DK_SPELL_CORPSE_EXPLOSION_TRIGGERED = 43999, + DK_SPELL_CORPSE_EXPLOSION_VISUAL = 51270, DK_SPELL_GHOUL_EXPLODE = 47496, - DISPLAY_GHOUL_CORPSE = 25537, DK_SPELL_SCOURGE_STRIKE_TRIGGERED = 70890, DK_SPELL_BLOOD_BOIL_TRIGGERED = 65658, DK_SPELL_WILL_OF_THE_NECROPOLIS_TALENT_R1 = 49189, @@ -208,6 +208,8 @@ class spell_dk_corpse_explosion : public SpellScriptLoader return false; if (!sSpellMgr->GetSpellInfo(DK_SPELL_GHOUL_EXPLODE)) return false; + if (!sSpellMgr->GetSpellInfo(DK_SPELL_CORPSE_EXPLOSION_VISUAL)) + return false; return true; } @@ -227,9 +229,9 @@ class spell_dk_corpse_explosion : public SpellScriptLoader GetCaster()->CastCustomSpell(unitTarget, GetSpellInfo()->Effects[EFFECT_1].CalcValue(), &bp, NULL, NULL, true); // Corpse Explosion (Suicide) unitTarget->CastSpell(unitTarget, DK_SPELL_CORPSE_EXPLOSION_TRIGGERED, true); - // Set corpse look - unitTarget->SetDisplayId(DISPLAY_GHOUL_CORPSE + urand(0, 3)); } + // Set corpse look + GetCaster()->CastSpell(unitTarget, DK_SPELL_CORPSE_EXPLOSION_VISUAL, true); } } @@ -261,8 +263,6 @@ class spell_dk_ghoul_explode : public SpellScriptLoader { // Corpse Explosion (Suicide) unitTarget->CastSpell(unitTarget, DK_SPELL_CORPSE_EXPLOSION_TRIGGERED, true); - // Set corpse look - unitTarget->SetDisplayId(DISPLAY_GHOUL_CORPSE + urand(0, 3)); } } -- cgit v1.2.3 From 806733550c915eaa6733be585760c29ca7021b12 Mon Sep 17 00:00:00 2001 From: Shauren Date: Fri, 10 Feb 2012 10:24:56 +0100 Subject: Core/GameObjects: Fixed crashes in GameObject::SetLootState and GameObject::SetGoState for summoned objects Closes #5166 --- src/server/game/Entities/GameObject/GameObject.cpp | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'src') diff --git a/src/server/game/Entities/GameObject/GameObject.cpp b/src/server/game/Entities/GameObject/GameObject.cpp index c36dbc35249..040bd8b70dd 100755 --- a/src/server/game/Entities/GameObject/GameObject.cpp +++ b/src/server/game/Entities/GameObject/GameObject.cpp @@ -220,7 +220,7 @@ bool GameObject::Create(uint32 guidlow, uint32 name_id, Map* map, uint32 phaseMa SetGoArtKit(0); // unknown what this is SetByteValue(GAMEOBJECT_BYTES_1, 2, artKit); - + switch (goinfo->type) { @@ -1901,8 +1901,8 @@ void GameObject::SetLootState(LootState state, Unit* unit) { // startOpen determines whether we are going to add or remove the LoS on activation bool startOpen = (GetGoType() == GAMEOBJECT_TYPE_DOOR || GetGoType() == GAMEOBJECT_TYPE_BUTTON ? GetGOInfo()->door.startOpen : false); - - if (GetGOData()->go_state == GO_NOT_READY) + + if (GetGOData() && GetGOData()->go_state == GO_NOT_READY) startOpen = !startOpen; if (state == GO_ACTIVATED || state == GO_JUST_DEACTIVATED) @@ -1923,7 +1923,7 @@ void GameObject::SetGoState(GOState state) // startOpen determines whether we are going to add or remove the LoS on activation bool startOpen = (GetGoType() == GAMEOBJECT_TYPE_DOOR || GetGoType() == GAMEOBJECT_TYPE_BUTTON ? GetGOInfo()->door.startOpen : false); - if (GetGOData()->go_state == GO_NOT_READY) + if (GetGOData() && GetGOData()->go_state == GO_NOT_READY) startOpen = !startOpen; if (state == GO_STATE_ACTIVE || state == GO_STATE_ACTIVE_ALTERNATIVE) @@ -1949,7 +1949,7 @@ void GameObject::EnableCollision(bool enable) { if (!m_model) return; - + /*if (enable && !GetMap()->Contains(*m_model)) GetMap()->Insert(*m_model);*/ -- cgit v1.2.3 From 5251daf01a9991c97d4e350397033da4f0231466 Mon Sep 17 00:00:00 2001 From: Shauren Date: Fri, 10 Feb 2012 11:32:33 +0100 Subject: Core/Spells: Summoning players will now teleport them directly on summoner, not near him --- src/server/game/Spells/SpellEffects.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/server/game/Spells/SpellEffects.cpp b/src/server/game/Spells/SpellEffects.cpp index d3fd3a6b117..6802cbdd90d 100755 --- a/src/server/game/Spells/SpellEffects.cpp +++ b/src/server/game/Spells/SpellEffects.cpp @@ -3048,7 +3048,7 @@ void Spell::EffectSummonType(SpellEffIndex effIndex) uint32 numSummons; // some spells need to summon many units, for those spells number of summons is stored in effect value - // however so far noone found a generic check to find all of those (there's no related data in summonproperties.dbc + // however so far noone found a generic check to find all of those (there's no related data in summonproperties.dbc // and in spell attributes, possibly we need to add a table for those) // so here's a list of MiscValueB values, which is currently most generic check switch (properties->Id) @@ -5691,7 +5691,7 @@ void Spell::EffectSummonPlayer(SpellEffIndex /*effIndex*/) return; float x, y, z; - m_caster->GetClosePoint(x, y, z, unitTarget->GetObjectSize()); + m_caster->GetPosition(x, y, z); unitTarget->ToPlayer()->SetSummonPoint(m_caster->GetMapId(), x, y, z); @@ -7142,7 +7142,7 @@ void Spell::SummonGuardian(uint32 i, uint32 entry, SummonPropertiesEntry const* float radius = 5.0f; int32 duration = m_spellInfo->GetDuration(); - + if (Player* modOwner = m_originalCaster->GetSpellModOwner()) modOwner->ApplySpellMod(m_spellInfo->Id, SPELLMOD_DURATION, duration); -- cgit v1.2.3 From 03b27179318f7371d47808589f10131aa0887bd5 Mon Sep 17 00:00:00 2001 From: kaelima Date: Fri, 10 Feb 2012 12:43:13 +0100 Subject: Core/Map: - Fixed crash when a player was disconnected during a transfer to another map. - Only call OnPlayerLeaveMap if player is removed from map. (Ty QAston) --- src/server/game/Entities/Transport/Transport.cpp | 2 +- src/server/game/Entities/Vehicle/Vehicle.cpp | 3 +-- src/server/game/Maps/Map.cpp | 3 ++- src/server/game/Server/WorldSession.cpp | 4 ++-- 4 files changed, 6 insertions(+), 6 deletions(-) (limited to 'src') diff --git a/src/server/game/Entities/Transport/Transport.cpp b/src/server/game/Entities/Transport/Transport.cpp index 891cf6b6697..a425640e36d 100755 --- a/src/server/game/Entities/Transport/Transport.cpp +++ b/src/server/game/Entities/Transport/Transport.cpp @@ -496,7 +496,7 @@ void Transport::TeleportTransport(uint32 newMapid, float x, float y, float z) ResetMap(); Map* newMap = sMapMgr->CreateBaseMap(newMapid); SetMap(newMap); - ASSERT (GetMap()); + ASSERT(GetMap()); AddToWorld(); if (oldMap != newMap) diff --git a/src/server/game/Entities/Vehicle/Vehicle.cpp b/src/server/game/Entities/Vehicle/Vehicle.cpp index fc6c6cb063e..286605f0057 100755 --- a/src/server/game/Entities/Vehicle/Vehicle.cpp +++ b/src/server/game/Entities/Vehicle/Vehicle.cpp @@ -433,8 +433,7 @@ void Vehicle::RemovePassenger(Unit* unit) void Vehicle::RelocatePassengers(float x, float y, float z, float ang) { - Map* map = _me->GetMap(); - ASSERT(map != NULL); + ASSERT(_me->IsInWorld()); // not sure that absolute position calculation is correct, it must depend on vehicle orientation and pitch angle for (SeatMap::const_iterator itr = Seats.begin(); itr != Seats.end(); ++itr) diff --git a/src/server/game/Maps/Map.cpp b/src/server/game/Maps/Map.cpp index 71fc2ef00a1..6e13e70d1cd 100755 --- a/src/server/game/Maps/Map.cpp +++ b/src/server/game/Maps/Map.cpp @@ -668,7 +668,8 @@ void Map::RemovePlayerFromMap(Player* player, bool remove) if (remove) DeleteFromWorld(player); - sScriptMgr->OnPlayerLeaveMap(this, player); + if (remove) + sScriptMgr->OnPlayerLeaveMap(this, player); } template diff --git a/src/server/game/Server/WorldSession.cpp b/src/server/game/Server/WorldSession.cpp index 6bd09f2b3a7..ab107fd0599 100755 --- a/src/server/game/Server/WorldSession.cpp +++ b/src/server/game/Server/WorldSession.cpp @@ -519,8 +519,8 @@ void WorldSession::LogoutPlayer(bool Save) // calls to GetMap in this case may cause crashes _player->CleanupsBeforeDelete(); sLog->outChar("Account: %d (IP: %s) Logout Character:[%s] (GUID: %u)", GetAccountId(), GetRemoteAddress().c_str(), _player->GetName(), _player->GetGUIDLow()); - Map* _map = _player->GetMap(); - _map->RemovePlayerFromMap(_player, true); + if (Map* _map = _player->FindMap()) + _map->RemovePlayerFromMap(_player, true); SetPlayer(NULL); // deleted in Remove call ///- Send the 'logout complete' packet to the client -- cgit v1.2.3 From a7fc2586e765a39371d49bf3f2b0b81d9c9df69a Mon Sep 17 00:00:00 2001 From: QAston Date: Fri, 10 Feb 2012 12:44:07 +0100 Subject: Core/Db/Conditions: Add NegativeCondition column to conditions table which allows to check whenever player does not meet condition specified by ConditionTypeOrReference column (ConditionTypeOrReference and ConditionValue3 set to reference id are not affected by the change) --- sql/updates/world/2012_02_10_00_world_conditions.sql | 1 + src/server/game/Conditions/ConditionMgr.cpp | 10 ++++++++-- src/server/game/Conditions/ConditionMgr.h | 2 ++ 3 files changed, 11 insertions(+), 2 deletions(-) create mode 100644 sql/updates/world/2012_02_10_00_world_conditions.sql (limited to 'src') diff --git a/sql/updates/world/2012_02_10_00_world_conditions.sql b/sql/updates/world/2012_02_10_00_world_conditions.sql new file mode 100644 index 00000000000..508011609cf --- /dev/null +++ b/sql/updates/world/2012_02_10_00_world_conditions.sql @@ -0,0 +1 @@ +ALTER TABLE `conditions` ADD COLUMN `NegativeCondition` tinyint(3) UNSIGNED NOT NULL default '0' AFTER `ConditionValue3`; diff --git a/src/server/game/Conditions/ConditionMgr.cpp b/src/server/game/Conditions/ConditionMgr.cpp index 8562c66c29f..b05643529ec 100755 --- a/src/server/game/Conditions/ConditionMgr.cpp +++ b/src/server/game/Conditions/ConditionMgr.cpp @@ -215,11 +215,14 @@ bool Condition::Meets(Player* player, Unit* invoker) break; } + if (mNegativeCondition) + condMeets = !condMeets; + bool refMeets = false; if (condMeets && refId)//only have to check references if 'this' is met { ConditionList ref = sConditionMgr->GetConditionReferences(refId); - refMeets = sConditionMgr->IsPlayerMeetToConditions(player, ref); + refMeets = sConditionMgr->IsPlayerMeetToConditions(player, ref, invoker); } else refMeets = true; @@ -391,7 +394,7 @@ void ConditionMgr::LoadConditions(bool isReload) } QueryResult result = WorldDatabase.Query("SELECT SourceTypeOrReferenceId, SourceGroup, SourceEntry, SourceId, ElseGroup, ConditionTypeOrReference, " - " ConditionValue1, ConditionValue2, ConditionValue3, ErrorTextId, ScriptName FROM conditions"); + " ConditionValue1, ConditionValue2, ConditionValue3, ErrorTextId, ScriptName, NegateCondition FROM conditions"); if (!result) { @@ -419,6 +422,7 @@ void ConditionMgr::LoadConditions(bool isReload) cond->mConditionValue3 = fields[8].GetUInt32(); cond->ErrorTextd = fields[9].GetUInt32(); cond->mScriptId = sObjectMgr->GetScriptId(fields[10].GetCString()); + cond->mNegativeCondition = fields[11].GetUInt8(); if (iConditionTypeOrReference >= 0) cond->mConditionType = ConditionType(iConditionTypeOrReference); @@ -443,6 +447,8 @@ void ConditionMgr::LoadConditions(bool isReload) sLog->outErrorDb("Condition %s %i has useless data in value2 (%u)!", rowType, iSourceTypeOrReferenceId, cond->mConditionValue2); if (cond->mConditionValue3) sLog->outErrorDb("Condition %s %i has useless data in value3 (%u)!", rowType, iSourceTypeOrReferenceId, cond->mConditionValue3); + if (cond->mNegativeCondition) + sLog->outErrorDb("Condition %s %i has useless data in NegativeCondition (%u)!", rowType, iSourceTypeOrReferenceId, cond->mNegativeCondition); if (cond->mSourceGroup && iSourceTypeOrReferenceId < 0) sLog->outErrorDb("Condition %s %i has useless data in SourceGroup (%u)!", rowType, iSourceTypeOrReferenceId, cond->mSourceGroup); if (cond->mSourceEntry && iSourceTypeOrReferenceId < 0) diff --git a/src/server/game/Conditions/ConditionMgr.h b/src/server/game/Conditions/ConditionMgr.h index 1641642dd86..4e371997d73 100755 --- a/src/server/game/Conditions/ConditionMgr.h +++ b/src/server/game/Conditions/ConditionMgr.h @@ -114,6 +114,7 @@ struct Condition uint32 ErrorTextd; uint32 mReferenceId; uint32 mScriptId; + bool mNegativeCondition; Condition() { @@ -128,6 +129,7 @@ struct Condition mReferenceId = 0; ErrorTextd = 0; mScriptId = 0; + mNegativeCondition = false; } bool Meets(Player* player, Unit* invoker = NULL); -- cgit v1.2.3 From 5684f39d58602f1abf0b718da6cc5fb3f52b9dfe Mon Sep 17 00:00:00 2001 From: kaelima Date: Fri, 10 Feb 2012 12:51:56 +0100 Subject: Core/Protocol: Remove useless ResetInstances call inside WorldSession::HandleResetInstancesOpcode. --- src/server/game/Entities/Vehicle/Vehicle.cpp | 2 +- src/server/game/Handlers/MiscHandler.cpp | 20 ++++++-------------- 2 files changed, 7 insertions(+), 15 deletions(-) (limited to 'src') diff --git a/src/server/game/Entities/Vehicle/Vehicle.cpp b/src/server/game/Entities/Vehicle/Vehicle.cpp index 286605f0057..348ce132da8 100755 --- a/src/server/game/Entities/Vehicle/Vehicle.cpp +++ b/src/server/game/Entities/Vehicle/Vehicle.cpp @@ -433,7 +433,7 @@ void Vehicle::RemovePassenger(Unit* unit) void Vehicle::RelocatePassengers(float x, float y, float z, float ang) { - ASSERT(_me->IsInWorld()); + ASSERT(_me->GetMap()); // not sure that absolute position calculation is correct, it must depend on vehicle orientation and pitch angle for (SeatMap::const_iterator itr = Seats.begin(); itr != Seats.end(); ++itr) diff --git a/src/server/game/Handlers/MiscHandler.cpp b/src/server/game/Handlers/MiscHandler.cpp index f109332e235..dbe2fc871bc 100755 --- a/src/server/game/Handlers/MiscHandler.cpp +++ b/src/server/game/Handlers/MiscHandler.cpp @@ -1470,20 +1470,14 @@ void WorldSession::HandleTimeSyncResp(WorldPacket & recv_data) void WorldSession::HandleResetInstancesOpcode(WorldPacket & /*recv_data*/) { sLog->outDebug(LOG_FILTER_NETWORKIO, "WORLD: CMSG_RESET_INSTANCES"); - Group* group = _player->GetGroup(); - if (group) + + if (Group* group = _player->GetGroup()) { if (group->IsLeader(_player->GetGUID())) - { group->ResetInstances(INSTANCE_RESET_ALL, false, _player); - group->ResetInstances(INSTANCE_RESET_ALL, true, _player); - } } else - { _player->ResetInstances(INSTANCE_RESET_ALL, false); - _player->ResetInstances(INSTANCE_RESET_ALL, true); - } } void WorldSession::HandleSetDungeonDifficultyOpcode(WorldPacket & recv_data) @@ -1503,7 +1497,7 @@ void WorldSession::HandleSetDungeonDifficultyOpcode(WorldPacket & recv_data) return; // cannot reset while in an instance - Map* map = _player->GetMap(); + Map* map = _player->FindMap(); if (map && map->IsDungeon()) { sLog->outError("WorldSession::HandleSetDungeonDifficultyOpcode: player (Name: %s, GUID: %u) tried to reset the instance while player is inside!", _player->GetName(), _player->GetGUIDLow()); @@ -1524,8 +1518,7 @@ void WorldSession::HandleSetDungeonDifficultyOpcode(WorldPacket & recv_data) if (!pGroupGuy->IsInMap(pGroupGuy)) return; - map = pGroupGuy->GetMap(); - if (map && map->IsNonRaidDungeon()) + if (pGroupGuy->GetMap()->IsNonRaidDungeon()) { sLog->outError("WorldSession::HandleSetDungeonDifficultyOpcode: player %d tried to reset the instance while group member (Name: %s, GUID: %u) is inside!", _player->GetGUIDLow(), pGroupGuy->GetName(), pGroupGuy->GetGUIDLow()); return; @@ -1558,7 +1551,7 @@ void WorldSession::HandleSetRaidDifficultyOpcode(WorldPacket & recv_data) } // cannot reset while in an instance - Map* map = _player->GetMap(); + Map* map = _player->FindMap(); if (map && map->IsDungeon()) { sLog->outError("WorldSession::HandleSetRaidDifficultyOpcode: player %d tried to reset the instance while inside!", _player->GetGUIDLow()); @@ -1582,8 +1575,7 @@ void WorldSession::HandleSetRaidDifficultyOpcode(WorldPacket & recv_data) if (!pGroupGuy->IsInMap(pGroupGuy)) return; - map = pGroupGuy->GetMap(); - if (map && map->IsRaid()) + if (pGroupGuy->GetMap()->IsRaid()) { sLog->outError("WorldSession::HandleSetRaidDifficultyOpcode: player %d tried to reset the instance while inside!", _player->GetGUIDLow()); return; -- cgit v1.2.3 From e0ad0f0e8d391e0f71894c2b49232aa301773058 Mon Sep 17 00:00:00 2001 From: QAston Date: Fri, 10 Feb 2012 12:54:06 +0100 Subject: Minor correction to a7fc2586e765a39371d49bf3f2b0b81d9c9df69a - load columns from db in the same order they're stored. --- src/server/game/Conditions/ConditionMgr.cpp | 8 ++++---- src/server/game/Entities/Pet/Pet.cpp | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) (limited to 'src') diff --git a/src/server/game/Conditions/ConditionMgr.cpp b/src/server/game/Conditions/ConditionMgr.cpp index b05643529ec..964abe6ae57 100755 --- a/src/server/game/Conditions/ConditionMgr.cpp +++ b/src/server/game/Conditions/ConditionMgr.cpp @@ -394,7 +394,7 @@ void ConditionMgr::LoadConditions(bool isReload) } QueryResult result = WorldDatabase.Query("SELECT SourceTypeOrReferenceId, SourceGroup, SourceEntry, SourceId, ElseGroup, ConditionTypeOrReference, " - " ConditionValue1, ConditionValue2, ConditionValue3, ErrorTextId, ScriptName, NegateCondition FROM conditions"); + " ConditionValue1, ConditionValue2, ConditionValue3, NegativeCondition, ErrorTextId, ScriptName FROM conditions"); if (!result) { @@ -420,9 +420,9 @@ void ConditionMgr::LoadConditions(bool isReload) cond->mConditionValue1 = fields[6].GetUInt32(); cond->mConditionValue2 = fields[7].GetUInt32(); cond->mConditionValue3 = fields[8].GetUInt32(); - cond->ErrorTextd = fields[9].GetUInt32(); - cond->mScriptId = sObjectMgr->GetScriptId(fields[10].GetCString()); - cond->mNegativeCondition = fields[11].GetUInt8(); + cond->mNegativeCondition = fields[9].GetUInt8(); + cond->ErrorTextd = fields[10].GetUInt32(); + cond->mScriptId = sObjectMgr->GetScriptId(fields[11].GetCString()); if (iConditionTypeOrReference >= 0) cond->mConditionType = ConditionType(iConditionTypeOrReference); diff --git a/src/server/game/Entities/Pet/Pet.cpp b/src/server/game/Entities/Pet/Pet.cpp index bf6dc3b67d9..566ee06218e 100755 --- a/src/server/game/Entities/Pet/Pet.cpp +++ b/src/server/game/Entities/Pet/Pet.cpp @@ -1243,7 +1243,7 @@ void Pet::_SaveAuras(SQLTransaction& trans) } // don't save guid of caster in case we are caster of the spell - guid for pet is generated every pet load, so it won't match saved guid anyways - uint64 casterGUID = (itr->second->GetCasterGUID() == GetGUID()) ? NULL : itr->second->GetCasterGUID(); + uint64 casterGUID = (itr->second->GetCasterGUID() == GetGUID()) ? 0 : itr->second->GetCasterGUID(); trans->PAppend("INSERT INTO pet_aura (guid, caster_guid, spell, effect_mask, recalculate_mask, stackcount, amount0, amount1, amount2, base_amount0, base_amount1, base_amount2, maxduration, remaintime, remaincharges) " "VALUES ('%u', '" UI64FMTD "', '%u', '%u', '%u', '%u', '%d', '%d', '%d', '%d', '%d', '%d', '%d', '%d', '%u')", -- cgit v1.2.3 From 8713b44ee71941212fa6a12c5553e92f869cfa46 Mon Sep 17 00:00:00 2001 From: QAston Date: Fri, 10 Feb 2012 14:18:59 +0100 Subject: Core/Db/Conditions: Prepare conditions system to work on objects of different type than players. Warning: API has changed a bit: ConditionScript::OnConditionCheck(Condition* condition, Player* player, Unit* invoker) is now ConditionScript::OnConditionCheck(Condition* condition, WorldObject* object, WorldObject* invoker) --- src/server/game/AI/CoreAI/CombatAI.cpp | 2 +- src/server/game/AI/SmartScripts/SmartScript.cpp | 2 +- src/server/game/Conditions/ConditionMgr.cpp | 224 ++++++++++++++++-------- src/server/game/Conditions/ConditionMgr.h | 6 +- src/server/game/Entities/Player/Player.cpp | 8 +- src/server/game/Handlers/QuestHandler.cpp | 4 +- src/server/game/Loot/LootMgr.cpp | 2 +- src/server/game/Scripting/ScriptMgr.cpp | 6 +- src/server/game/Scripting/ScriptMgr.h | 4 +- src/server/game/Spells/Spell.cpp | 2 +- 10 files changed, 166 insertions(+), 94 deletions(-) (limited to 'src') diff --git a/src/server/game/AI/CoreAI/CombatAI.cpp b/src/server/game/AI/CoreAI/CombatAI.cpp index 6ce8ce330cf..d8def36f999 100755 --- a/src/server/game/AI/CoreAI/CombatAI.cpp +++ b/src/server/game/AI/CoreAI/CombatAI.cpp @@ -326,7 +326,7 @@ void VehicleAI::CheckConditions(const uint32 diff) { if (Player* player = passenger->ToPlayer()) { - if (!sConditionMgr->IsPlayerMeetToConditions(player, conditions)) + if (!sConditionMgr->IsObjectMeetToConditions(player, conditions)) { player->ExitVehicle(); return;//check other pessanger in next tick diff --git a/src/server/game/AI/SmartScripts/SmartScript.cpp b/src/server/game/AI/SmartScripts/SmartScript.cpp index a6923ea19e0..42a23236182 100644 --- a/src/server/game/AI/SmartScripts/SmartScript.cpp +++ b/src/server/game/AI/SmartScripts/SmartScript.cpp @@ -90,7 +90,7 @@ void SmartScript::ProcessEventsFor(SMART_EVENT e, Unit* unit, uint32 var0, uint3 if (Player* player = unit->ToPlayer()) { ConditionList conds = sConditionMgr->GetConditionsForSmartEvent((*i).entryOrGuid, (*i).event_id, (*i).source_type); - meets = sConditionMgr->IsPlayerMeetToConditions(player, conds); + meets = sConditionMgr->IsObjectMeetToConditions(player, conds); } } diff --git a/src/server/game/Conditions/ConditionMgr.cpp b/src/server/game/Conditions/ConditionMgr.cpp index 964abe6ae57..81db61171a3 100755 --- a/src/server/game/Conditions/ConditionMgr.cpp +++ b/src/server/game/Conditions/ConditionMgr.cpp @@ -27,14 +27,15 @@ #include "ScriptMgr.h" #include "ScriptedCreature.h" -// Checks if player meets the condition +// Checks if object meets the condition // Can have CONDITION_SOURCE_TYPE_NONE && !mReferenceId if called from a special event (ie: eventAI) -bool Condition::Meets(Player* player, Unit* invoker) +bool Condition::Meets(WorldObject* object, WorldObject* invoker) { - if (!player) + // object not present, return false + if (!object) { - sLog->outDebug(LOG_FILTER_CONDITIONSYS, "Condition player not found"); - return false; // player not present, return false + sLog->outDebug(LOG_FILTER_CONDITIONSYS, "Condition object not found"); + return false; } uint32 refId = mConditionValue3;//value 3 can be a 'quick' reference bool condMeets = false; @@ -45,72 +46,119 @@ bool Condition::Meets(Player* player, Unit* invoker) condMeets = true; // empty condition, always met break; case CONDITION_AURA: - refId = 0; - if (!mConditionValue3) - condMeets = player->HasAuraEffect(mConditionValue1, mConditionValue2); - else if (Unit* target = player->GetSelectedUnit()) - condMeets = target->HasAuraEffect(mConditionValue1, mConditionValue2); + { + if (Unit* unit = object->ToUnit()) + { + refId = 0; + if (!mConditionValue3) + condMeets = unit->HasAuraEffect(mConditionValue1, mConditionValue2); + else if (Player* player = unit->ToPlayer()) + { + if (Unit* target = player->GetSelectedUnit()) + condMeets = target->HasAuraEffect(mConditionValue1, mConditionValue2); + } + } break; + } case CONDITION_ITEM: - condMeets = (mConditionValue2 && player->HasItemCount(mConditionValue1, mConditionValue2)) || (!mConditionValue2 && !player->HasItemCount(mConditionValue1, mConditionValue2));//HasItemCount returns false if 0 count is used + { + if (Player* player = object->ToPlayer()) + condMeets = (mConditionValue2 && player->HasItemCount(mConditionValue1, mConditionValue2)) || (!mConditionValue2 && !player->HasItemCount(mConditionValue1, mConditionValue2));//HasItemCount returns false if 0 count is used break; + } case CONDITION_ITEM_EQUIPPED: - condMeets = player->HasItemOrGemWithIdEquipped(mConditionValue1, 1); + { + if (Player* player = object->ToPlayer()) + condMeets = player->HasItemOrGemWithIdEquipped(mConditionValue1, 1); break; + } case CONDITION_ZONEID: - condMeets = player->GetZoneId() == mConditionValue1; + condMeets = object->GetZoneId() == mConditionValue1; break; case CONDITION_REPUTATION_RANK: { - if (FactionEntry const* faction = sFactionStore.LookupEntry(mConditionValue1)) - condMeets = (mConditionValue2 & (1 << player->GetReputationMgr().GetRank(faction))); + if (Player* player = object->ToPlayer()) + { + if (FactionEntry const* faction = sFactionStore.LookupEntry(mConditionValue1)) + condMeets = (mConditionValue2 & (1 << player->GetReputationMgr().GetRank(faction))); + } break; } case CONDITION_ACHIEVEMENT: - condMeets = player->GetAchievementMgr().HasAchieved(mConditionValue1); + { + if (Player* player = object->ToPlayer()) + condMeets = player->GetAchievementMgr().HasAchieved(mConditionValue1); break; + } case CONDITION_TEAM: - condMeets = player->GetTeam() == mConditionValue1; + { + if (Player* player = object->ToPlayer()) + condMeets = player->GetTeam() == mConditionValue1; break; + } case CONDITION_CLASS: - condMeets = player->getClassMask() & mConditionValue1; + { + if (Player* player = object->ToPlayer()) + condMeets = player->getClassMask() & mConditionValue1; break; + } case CONDITION_RACE: - condMeets = player->getRaceMask() & mConditionValue1; + { + if (Player* player = object->ToPlayer()) + condMeets = player->getRaceMask() & mConditionValue1; break; + } case CONDITION_SKILL: - condMeets = player->HasSkill(mConditionValue1) && player->GetBaseSkillValue(mConditionValue1) >= mConditionValue2; + { + if (Player* player = object->ToPlayer()) + condMeets = player->HasSkill(mConditionValue1) && player->GetBaseSkillValue(mConditionValue1) >= mConditionValue2; break; + } case CONDITION_QUESTREWARDED: - condMeets = (player->GetQuestRewardStatus(mConditionValue1) == !mConditionValue2); + { + if (Player* player = object->ToPlayer()) + condMeets = (player->GetQuestRewardStatus(mConditionValue1) == !mConditionValue2); break; + } case CONDITION_QUESTTAKEN: { - QuestStatus status = player->GetQuestStatus(mConditionValue1); - condMeets = ((status == QUEST_STATUS_INCOMPLETE) == !mConditionValue2); + if (Player* player = object->ToPlayer()) + { + QuestStatus status = player->GetQuestStatus(mConditionValue1); + condMeets = ((status == QUEST_STATUS_INCOMPLETE) == !mConditionValue2); + } break; } case CONDITION_QUEST_COMPLETE: { - QuestStatus status = player->GetQuestStatus(mConditionValue1); - condMeets = ((status == QUEST_STATUS_COMPLETE && !player->GetQuestRewardStatus(mConditionValue1)) == !mConditionValue2); + if (Player* player = object->ToPlayer()) + { + QuestStatus status = player->GetQuestStatus(mConditionValue1); + condMeets = ((status == QUEST_STATUS_COMPLETE && !player->GetQuestRewardStatus(mConditionValue1)) == !mConditionValue2); + } break; } case CONDITION_QUEST_NONE: { - QuestStatus status = player->GetQuestStatus(mConditionValue1); - condMeets = ((status == QUEST_STATUS_NONE) == !mConditionValue2); + if (Player* player = object->ToPlayer()) + { + QuestStatus status = player->GetQuestStatus(mConditionValue1); + condMeets = ((status == QUEST_STATUS_NONE) == !mConditionValue2); + } break; } case CONDITION_NO_AURA: - condMeets = !player->HasAuraEffect(mConditionValue1, mConditionValue2); + { + if (Unit* unit = object->ToUnit()) + condMeets = !unit->HasAuraEffect(mConditionValue1, mConditionValue2); break; + } case CONDITION_ACTIVE_EVENT: condMeets = sGameEventMgr->IsActiveEvent(mConditionValue1); break; case CONDITION_INSTANCE_DATA: { - Map* map = player->GetMap(); + Map* map = object->GetMap(); if (map && map->IsDungeon() && ((InstanceMap*)map)->GetInstanceScript()) condMeets = ((InstanceMap*)map)->GetInstanceScript()->GetData(mConditionValue1) == mConditionValue2; break; @@ -121,32 +169,41 @@ bool Condition::Meets(Player* player, Unit* invoker) break; case CONDITION_CREATURE_TARGET: { - Unit* target = player->GetSelectedUnit(); - if (target) - if (Creature* cTarget = target->ToCreature()) - if (cTarget->GetEntry() == mConditionValue1) - condMeets = true; + if (Player* player = object->ToPlayer()) + { + Unit* target = player->GetSelectedUnit(); + if (target) + if (Creature* cTarget = target->ToCreature()) + if (cTarget->GetEntry() == mConditionValue1) + condMeets = true; + } break; } case CONDITION_TARGET_HEALTH_BELOW_PCT: { - Unit* target = player->GetSelectedUnit(); - if (target) - condMeets = !target->HealthAbovePct(mConditionValue1); - break; + if (Player* player = object->ToPlayer()) + { + Unit* target = player->GetSelectedUnit(); + if (target) + condMeets = !target->HealthAbovePct(mConditionValue1); + break; + } } case CONDITION_TARGET_RANGE: { - if (Unit* target = player->GetSelectedUnit()) - if (player->GetDistance(target) >= mConditionValue1 && (!mConditionValue2 || player->GetDistance(target) <= mConditionValue2)) - condMeets = true; + if (Player* player = object->ToPlayer()) + { + if (Unit* target = player->GetSelectedUnit()) + if (player->GetDistance(target) >= mConditionValue1 && (!mConditionValue2 || player->GetDistance(target) <= mConditionValue2)) + condMeets = true; + } break; } case CONDITION_MAPID: - condMeets = player->GetMapId() == mConditionValue1; + condMeets = object->GetMapId() == mConditionValue1; break; case CONDITION_AREAID: - condMeets = player->GetAreaId() == mConditionValue1; + condMeets = object->GetAreaId() == mConditionValue1; break; case CONDITION_ITEM_TARGET: { @@ -155,49 +212,61 @@ bool Condition::Meets(Player* player, Unit* invoker) break; } case CONDITION_SPELL: - if (mConditionValue2 == 1) - condMeets = player->HasSpell(mConditionValue1); - else - condMeets = !player->HasSpell(mConditionValue1); + { + if (Player* player = object->ToPlayer()) + { + if (mConditionValue2 == 1) + condMeets = player->HasSpell(mConditionValue1); + else + condMeets = !player->HasSpell(mConditionValue1); + } break; + } case CONDITION_NOITEM: - condMeets = !player->HasItemCount(mConditionValue1, 1, mConditionValue2 ? true : false); + { + if (Player* player = object->ToPlayer()) + condMeets = !player->HasItemCount(mConditionValue1, 1, mConditionValue2 ? true : false); break; + } case CONDITION_LEVEL: { - switch (mConditionValue2) + if (Unit* unit = object->ToUnit()) { - case LVL_COND_EQ: - condMeets = player->getLevel() == mConditionValue1; - break; - case LVL_COND_HIGH: - condMeets = player->getLevel() > mConditionValue1; - break; - case LVL_COND_LOW: - condMeets = player->getLevel() < mConditionValue1; - break; - case LVL_COND_HIGH_EQ: - condMeets = player->getLevel() >= mConditionValue1; - break; - case LVL_COND_LOW_EQ: - condMeets = player->getLevel() <= mConditionValue1; - break; + switch (mConditionValue2) + { + case LVL_COND_EQ: + condMeets = unit->getLevel() == mConditionValue1; + break; + case LVL_COND_HIGH: + condMeets = unit->getLevel() > mConditionValue1; + break; + case LVL_COND_LOW: + condMeets = unit->getLevel() < mConditionValue1; + break; + case LVL_COND_HIGH_EQ: + condMeets = unit->getLevel() >= mConditionValue1; + break; + case LVL_COND_LOW_EQ: + condMeets = unit->getLevel() <= mConditionValue1; + break; + } } break; } case CONDITION_DRUNKENSTATE: { - condMeets = (uint32)Player::GetDrunkenstateByValue(player->GetDrunkValue()) >= mConditionValue1; + if (Player* player = object->ToPlayer()) + condMeets = (uint32)Player::GetDrunkenstateByValue(player->GetDrunkValue()) >= mConditionValue1; break; } case CONDITION_NEAR_CREATURE: { - condMeets = GetClosestCreatureWithEntry(player, mConditionValue1, (float)mConditionValue2) ? true : false; + condMeets = GetClosestCreatureWithEntry(object, mConditionValue1, (float)mConditionValue2) ? true : false; break; } case CONDITION_NEAR_GAMEOBJECT: { - condMeets = GetClosestGameObjectWithEntry(player, mConditionValue1, (float)mConditionValue2) ? true : false; + condMeets = GetClosestGameObjectWithEntry(object, mConditionValue1, (float)mConditionValue2) ? true : false; break; } default: @@ -222,15 +291,16 @@ bool Condition::Meets(Player* player, Unit* invoker) if (condMeets && refId)//only have to check references if 'this' is met { ConditionList ref = sConditionMgr->GetConditionReferences(refId); - refMeets = sConditionMgr->IsPlayerMeetToConditions(player, ref, invoker); + refMeets = sConditionMgr->IsObjectMeetToConditions(object, ref, invoker); } else refMeets = true; - if (sendErrorMsg && ErrorTextd && (!condMeets || !refMeets))//send special error from DB - player->m_ConditionErrorMsgId = ErrorTextd; + if (Player* player = object->ToPlayer()) + if (sendErrorMsg && ErrorTextd && (!condMeets || !refMeets))//send special error from DB + player->m_ConditionErrorMsgId = ErrorTextd; - bool script = sScriptMgr->OnConditionCheck(this, player, invoker); // Returns true by default. + bool script = sScriptMgr->OnConditionCheck(this, object, invoker); // Returns true by default. return condMeets && refMeets && script; } @@ -252,7 +322,7 @@ ConditionList ConditionMgr::GetConditionReferences(uint32 refId) return conditions; } -bool ConditionMgr::IsPlayerMeetToConditionList(Player* player, ConditionList const& conditions, Unit* invoker /*= NULL*/) +bool ConditionMgr::IsObjectMeetToConditionList(WorldObject* object, ConditionList const& conditions, WorldObject* invoker /*= NULL*/) { std::map ElseGroupStore; for (ConditionList::const_iterator i = conditions.begin(); i != conditions.end(); ++i) @@ -271,7 +341,7 @@ bool ConditionMgr::IsPlayerMeetToConditionList(Player* player, ConditionList con ConditionReferenceContainer::const_iterator ref = ConditionReferenceStore.find((*i)->mReferenceId); if (ref != ConditionReferenceStore.end()) { - if (!IsPlayerMeetToConditionList(player, (*ref).second, invoker)) + if (!IsObjectMeetToConditionList(object, (*ref).second, invoker)) ElseGroupStore[(*i)->mElseGroup] = false; } else @@ -283,7 +353,7 @@ bool ConditionMgr::IsPlayerMeetToConditionList(Player* player, ConditionList con } else //handle normal condition { - if (!(*i)->Meets(player, invoker)) + if (!(*i)->Meets(object, invoker)) ElseGroupStore[(*i)->mElseGroup] = false; } } @@ -295,16 +365,18 @@ bool ConditionMgr::IsPlayerMeetToConditionList(Player* player, ConditionList con return false; } -bool ConditionMgr::IsPlayerMeetToConditions(Player* player, ConditionList const& conditions, Unit* invoker /*= NULL*/) +bool ConditionMgr::IsObjectMeetToConditions(WorldObject* object, ConditionList const& conditions, WorldObject* invoker /*= NULL*/) { if (conditions.empty()) return true; + Player* player = object ? object->ToPlayer() : NULL; + if (player) player->m_ConditionErrorMsgId = 0; sLog->outDebug(LOG_FILTER_CONDITIONSYS, "ConditionMgr::IsPlayerMeetToConditions"); - bool result = IsPlayerMeetToConditionList(player, conditions, invoker); + bool result = IsObjectMeetToConditionList(player, conditions, invoker); if (player && player->m_ConditionErrorMsgId && player->GetSession() && !result) player->GetSession()->SendNotification(player->m_ConditionErrorMsgId); //m_ConditionErrorMsgId is set only if a condition was not met diff --git a/src/server/game/Conditions/ConditionMgr.h b/src/server/game/Conditions/ConditionMgr.h index 4e371997d73..b3ba27db7b5 100755 --- a/src/server/game/Conditions/ConditionMgr.h +++ b/src/server/game/Conditions/ConditionMgr.h @@ -132,7 +132,7 @@ struct Condition mNegativeCondition = false; } - bool Meets(Player* player, Unit* invoker = NULL); + bool Meets(WorldObject* player, WorldObject* invoker = NULL); bool isLoaded() const { return mConditionType > CONDITION_NONE || mReferenceId; } }; @@ -157,7 +157,7 @@ class ConditionMgr bool isConditionTypeValid(Condition* cond); ConditionList GetConditionReferences(uint32 refId); - bool IsPlayerMeetToConditions(Player* player, ConditionList const& conditions, Unit* invoker = NULL); + bool IsObjectMeetToConditions(WorldObject* object, ConditionList const& conditions, WorldObject* invoker = NULL); ConditionList GetConditionsForNotGroupedEntry(ConditionSourceType sourceType, uint32 entry); ConditionList GetConditionsForSmartEvent(int32 entryOrGuid, uint32 eventId, uint32 sourceType); ConditionList GetConditionsForVehicleSpell(uint32 creatureID, uint32 spellID); @@ -167,7 +167,7 @@ class ConditionMgr bool addToLootTemplate(Condition* cond, LootTemplate* loot); bool addToGossipMenus(Condition* cond); bool addToGossipMenuItems(Condition* cond); - bool IsPlayerMeetToConditionList(Player* player, ConditionList const& conditions, Unit* invoker = NULL); + bool IsObjectMeetToConditionList(WorldObject* player, ConditionList const& conditions, WorldObject* invoker = NULL); bool isGroupable(ConditionSourceType sourceType) const { diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp index 38af97f61cb..c6ea26a2dfd 100755 --- a/src/server/game/Entities/Player/Player.cpp +++ b/src/server/game/Entities/Player/Player.cpp @@ -14088,7 +14088,7 @@ void Player::PrepareGossipMenu(WorldObject* source, uint32 menuId /*= 0*/, bool for (GossipMenuItemsMap::const_iterator itr = menuItemBounds.first; itr != menuItemBounds.second; ++itr) { bool canTalk = true; - if (!sConditionMgr->IsPlayerMeetToConditions(this, itr->second.Conditions)) + if (!sConditionMgr->IsObjectMeetToConditions(this, itr->second.Conditions)) continue; if (source->GetTypeId() == TYPEID_UNIT) @@ -14390,7 +14390,7 @@ uint32 Player::GetGossipTextId(uint32 menuId) GossipMenusMapBounds menuBounds = sObjectMgr->GetGossipMenusMapBounds(menuId); for (GossipMenusMap::const_iterator itr = menuBounds.first; itr != menuBounds.second; ++itr) - if (sConditionMgr->IsPlayerMeetToConditions(this, itr->second.conditions)) + if (sConditionMgr->IsObjectMeetToConditions(this, itr->second.conditions)) textId = itr->second.text_id; return textId; @@ -15378,7 +15378,7 @@ bool Player::SatisfyQuestStatus(Quest const* qInfo, bool msg) bool Player::SatisfyQuestConditions(Quest const* qInfo, bool msg) { ConditionList conditions = sConditionMgr->GetConditionsForNotGroupedEntry(CONDITION_SOURCE_TYPE_QUEST_ACCEPT, qInfo->GetQuestId()); - if (!sConditionMgr->IsPlayerMeetToConditions(this, conditions)) + if (!sConditionMgr->IsObjectMeetToConditions(this, conditions)) { if (msg) SendCanTakeQuestResponse(INVALIDREASON_DONT_HAVE_REQ); @@ -19861,7 +19861,7 @@ void Player::VehicleSpellInitialize() } ConditionList conditions = sConditionMgr->GetConditionsForVehicleSpell(veh->GetEntry(), spellId); - if (!sConditionMgr->IsPlayerMeetToConditions(this, conditions)) + if (!sConditionMgr->IsObjectMeetToConditions(this, conditions)) { sLog->outDebug(LOG_FILTER_CONDITIONSYS, "VehicleSpellInitialize: conditions not met for Vehicle entry %u spell %u", veh->ToCreature()->GetEntry(), spellId); data << uint16(0) << uint8(0) << uint8(i+8); diff --git a/src/server/game/Handlers/QuestHandler.cpp b/src/server/game/Handlers/QuestHandler.cpp index f9aa40cdcda..05d945d3a93 100755 --- a/src/server/game/Handlers/QuestHandler.cpp +++ b/src/server/game/Handlers/QuestHandler.cpp @@ -651,7 +651,7 @@ uint32 WorldSession::getDialogStatus(Player* player, Object* questgiver, uint32 if (!pQuest) continue; ConditionList conditions = sConditionMgr->GetConditionsForNotGroupedEntry(CONDITION_SOURCE_TYPE_QUEST_SHOW_MARK, pQuest->GetQuestId()); - if (!sConditionMgr->IsPlayerMeetToConditions(player, conditions)) + if (!sConditionMgr->IsObjectMeetToConditions(player, conditions)) continue; QuestStatus status = player->GetQuestStatus(quest_id); @@ -679,7 +679,7 @@ uint32 WorldSession::getDialogStatus(Player* player, Object* questgiver, uint32 continue; ConditionList conditions = sConditionMgr->GetConditionsForNotGroupedEntry(CONDITION_SOURCE_TYPE_QUEST_SHOW_MARK, pQuest->GetQuestId()); - if (!sConditionMgr->IsPlayerMeetToConditions(player, conditions)) + if (!sConditionMgr->IsObjectMeetToConditions(player, conditions)) continue; QuestStatus status = player->GetQuestStatus(quest_id); diff --git a/src/server/game/Loot/LootMgr.cpp b/src/server/game/Loot/LootMgr.cpp index c9e8f68af52..89c13dd6b5c 100755 --- a/src/server/game/Loot/LootMgr.cpp +++ b/src/server/game/Loot/LootMgr.cpp @@ -341,7 +341,7 @@ LootItem::LootItem(LootStoreItem const& li) bool LootItem::AllowedForPlayer(Player const* player) const { // DB conditions check - if (!sConditionMgr->IsPlayerMeetToConditions(const_cast(player), conditions)) + if (!sConditionMgr->IsObjectMeetToConditions(const_cast(player), conditions)) return false; ItemTemplate const* pProto = sObjectMgr->GetItemTemplate(itemid); diff --git a/src/server/game/Scripting/ScriptMgr.cpp b/src/server/game/Scripting/ScriptMgr.cpp index d5e8f71e1fd..eccf12aa7e1 100755 --- a/src/server/game/Scripting/ScriptMgr.cpp +++ b/src/server/game/Scripting/ScriptMgr.cpp @@ -1036,14 +1036,14 @@ void ScriptMgr::OnAuctionExpire(AuctionHouseObject* ah, AuctionEntry* entry) FOREACH_SCRIPT(AuctionHouseScript)->OnAuctionExpire(ah, entry); } -bool ScriptMgr::OnConditionCheck(Condition* condition, Player* player, Unit* invoker) +bool ScriptMgr::OnConditionCheck(Condition* condition, WorldObject* object, WorldObject* invoker) { ASSERT(condition); - ASSERT(player); + ASSERT(object); // invoker can be NULL. GET_SCRIPT_RET(ConditionScript, condition->mScriptId, tmpscript, true); - return tmpscript->OnConditionCheck(condition, player, invoker); + return tmpscript->OnConditionCheck(condition, object, invoker); } void ScriptMgr::OnInstall(Vehicle* veh) diff --git a/src/server/game/Scripting/ScriptMgr.h b/src/server/game/Scripting/ScriptMgr.h index 60052bea0ea..853db564a6d 100755 --- a/src/server/game/Scripting/ScriptMgr.h +++ b/src/server/game/Scripting/ScriptMgr.h @@ -572,7 +572,7 @@ class ConditionScript : public ScriptObject bool IsDatabaseBound() const { return true; } // Called when a single condition is checked for a player. - virtual bool OnConditionCheck(Condition* /*condition*/, Player* /*player*/, Unit* /*invoker*/) { return true; } + virtual bool OnConditionCheck(Condition* /*condition*/, WorldObject* /*object*/, WorldObject* /*invoker*/) { return true; } }; class VehicleScript : public ScriptObject @@ -938,7 +938,7 @@ class ScriptMgr public: /* ConditionScript */ - bool OnConditionCheck(Condition* condition, Player* player, Unit* invoker); + bool OnConditionCheck(Condition* condition, WorldObject* object, WorldObject* invoker); public: /* VehicleScript */ diff --git a/src/server/game/Spells/Spell.cpp b/src/server/game/Spells/Spell.cpp index 45cf64266e1..9dccb0ff341 100755 --- a/src/server/game/Spells/Spell.cpp +++ b/src/server/game/Spells/Spell.cpp @@ -4720,7 +4720,7 @@ SpellCastResult Spell::CheckCast(bool strict) if (Player* plrCaster = m_caster->GetCharmerOrOwnerPlayerOrPlayerItself()) { ConditionList conditions = sConditionMgr->GetConditionsForNotGroupedEntry(CONDITION_SOURCE_TYPE_SPELL, m_spellInfo->Id); - if (!conditions.empty() && !sConditionMgr->IsPlayerMeetToConditions(plrCaster, conditions)) + if (!conditions.empty() && !sConditionMgr->IsObjectMeetToConditions(plrCaster, conditions)) return SPELL_FAILED_DONT_REPORT; } -- cgit v1.2.3 From 676151f6ace7cc01406a990bcbe975d2f27c3774 Mon Sep 17 00:00:00 2001 From: QAston Date: Fri, 10 Feb 2012 15:30:33 +0100 Subject: Core/Db/Conditions: Don't use ConditionValue3 as a reference id for template conditions - ConditionTypeOrReference serves this purpose. --- src/server/game/Conditions/ConditionMgr.cpp | 82 +++++++++++++++++++++-------- src/server/game/Conditions/ConditionMgr.h | 56 ++++++++++---------- 2 files changed, 87 insertions(+), 51 deletions(-) (limited to 'src') diff --git a/src/server/game/Conditions/ConditionMgr.cpp b/src/server/game/Conditions/ConditionMgr.cpp index 81db61171a3..831452e50f6 100755 --- a/src/server/game/Conditions/ConditionMgr.cpp +++ b/src/server/game/Conditions/ConditionMgr.cpp @@ -37,7 +37,6 @@ bool Condition::Meets(WorldObject* object, WorldObject* invoker) sLog->outDebug(LOG_FILTER_CONDITIONSYS, "Condition object not found"); return false; } - uint32 refId = mConditionValue3;//value 3 can be a 'quick' reference bool condMeets = false; bool sendErrorMsg = false; switch (mConditionType) @@ -49,7 +48,6 @@ bool Condition::Meets(WorldObject* object, WorldObject* invoker) { if (Unit* unit = object->ToUnit()) { - refId = 0; if (!mConditionValue3) condMeets = unit->HasAuraEffect(mConditionValue1, mConditionValue2); else if (Player* player = unit->ToPlayer()) @@ -207,8 +205,7 @@ bool Condition::Meets(WorldObject* object, WorldObject* invoker) break; case CONDITION_ITEM_TARGET: { - condMeets = true;//handled in Item::IsTargetValidForItemUse - refId = 0;//cant have references for now + condMeets = true; //handled in Item::IsTargetValidForItemUse break; } case CONDITION_SPELL: @@ -271,7 +268,6 @@ bool Condition::Meets(WorldObject* object, WorldObject* invoker) } default: condMeets = false; - refId = 0; break; } switch (mSourceType) @@ -287,15 +283,6 @@ bool Condition::Meets(WorldObject* object, WorldObject* invoker) if (mNegativeCondition) condMeets = !condMeets; - bool refMeets = false; - if (condMeets && refId)//only have to check references if 'this' is met - { - ConditionList ref = sConditionMgr->GetConditionReferences(refId); - refMeets = sConditionMgr->IsObjectMeetToConditions(object, ref, invoker); - } - else - refMeets = true; - if (Player* player = object->ToPlayer()) if (sendErrorMsg && ErrorTextd && (!condMeets || !refMeets))//send special error from DB player->m_ConditionErrorMsgId = ErrorTextd; @@ -1156,6 +1143,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("Item condition has 0 set for item count in value2 (%u), skipped", cond->mConditionValue2); return false; } + if (cond->mConditionValue3) + sLog->outErrorDb("Item condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_ITEM_EQUIPPED: @@ -1169,6 +1158,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) if (cond->mConditionValue2) sLog->outErrorDb("ItemEquipped condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("ItemEquipped condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_ZONEID: @@ -1176,18 +1167,20 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) AreaTableEntry const* areaEntry = GetAreaEntryByAreaID(cond->mConditionValue1); if (!areaEntry) { - sLog->outErrorDb("Zone condition has non existing area (%u), skipped", cond->mConditionValue1); + sLog->outErrorDb("ZoneID condition has non existing area (%u), skipped", cond->mConditionValue1); return false; } if (areaEntry->zone != 0) { - sLog->outErrorDb("Zone condition requires to be in area (%u) which is a subzone but zone expected, skipped", cond->mConditionValue1); + sLog->outErrorDb("ZoneID condition requires to be in area (%u) which is a subzone but zone expected, skipped", cond->mConditionValue1); return false; } if (cond->mConditionValue2) - sLog->outErrorDb("Zone condition has useless data in value2 (%u)!", cond->mConditionValue2); + sLog->outErrorDb("ZoneID condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("ZoneID condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_REPUTATION_RANK: @@ -1198,6 +1191,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("Reputation condition has non existing faction (%u), skipped", cond->mConditionValue1); return false; } + if (cond->mConditionValue3) + sLog->outErrorDb("Reputation condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_TEAM: @@ -1210,6 +1205,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) if (cond->mConditionValue2) sLog->outErrorDb("Team condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("Team condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_SKILL: @@ -1226,6 +1223,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("Skill condition specifies invalid skill value (%u), skipped", cond->mConditionValue2); return false; } + if (cond->mConditionValue3) + sLog->outErrorDb("Skill condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_QUESTREWARDED: @@ -1241,21 +1240,25 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) if (cond->mConditionValue2 > 1) sLog->outErrorDb("Quest condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("Quest condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_NO_AURA: { if (!sSpellMgr->GetSpellInfo(cond->mConditionValue1)) { - sLog->outErrorDb("Aura condition has non existing spell (Id: %d), skipped", cond->mConditionValue1); + sLog->outErrorDb("NoAura condition has non existing spell (Id: %d), skipped", cond->mConditionValue1); return false; } if (cond->mConditionValue2 > 2) { - sLog->outErrorDb("Aura condition has non existing effect index (%u) in value2 (must be 0..2), skipped", cond->mConditionValue2); + sLog->outErrorDb("NoAura condition has non existing effect index (%u) in value2 (must be 0..2), skipped", cond->mConditionValue2); return false; } + if (cond->mConditionValue3) + sLog->outErrorDb("NoAura condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_ACTIVE_EVENT: @@ -1263,12 +1266,14 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) GameEventMgr::GameEventDataMap const& events = sGameEventMgr->GetEventMap(); if (cond->mConditionValue1 >=events.size() || !events[cond->mConditionValue1].isValid()) { - sLog->outErrorDb("Active event condition has non existing event id (%u), skipped", cond->mConditionValue1); + sLog->outErrorDb("ActiveEvent condition has non existing event id (%u), skipped", cond->mConditionValue1); return false; } if (cond->mConditionValue2) - sLog->outErrorDb("Active event condition has useless data in value2 (%u)!", cond->mConditionValue2); + sLog->outErrorDb("ActiveEvent condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("ActiveEvent condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_ACHIEVEMENT: @@ -1276,12 +1281,14 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) AchievementEntry const* achievement = GetAchievementStore()->LookupEntry(cond->mConditionValue1); if (!achievement) { - sLog->outErrorDb("Achivemen condition has non existing achivement id (%u), skipped", cond->mConditionValue1); + sLog->outErrorDb("Achivement condition has non existing achivement id (%u), skipped", cond->mConditionValue1); return false; } if (cond->mConditionValue2) - sLog->outErrorDb("Achivemen condition has useless data in value2 (%u)!", cond->mConditionValue2); + sLog->outErrorDb("Achivement condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("Achivement condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_CLASS: @@ -1294,6 +1301,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) if (cond->mConditionValue2) sLog->outErrorDb("Class condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("Class condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_RACE: @@ -1306,6 +1315,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) if (cond->mConditionValue2) sLog->outErrorDb("Race condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("Race condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_SPELL_SCRIPT_TARGET: @@ -1358,6 +1369,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) if (cond->mConditionValue2) sLog->outErrorDb("CreatureTarget condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("CreatureTarget condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_TARGET_HEALTH_BELOW_PCT: @@ -1370,6 +1383,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) if (cond->mConditionValue2) sLog->outErrorDb("TargetHealthBelowPct condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("TargetHealthBelowPct condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_TARGET_RANGE: @@ -1379,6 +1394,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("TargetRange condition has max distance closer then min distance, skipped"); return false; } + if (cond->mConditionValue3) + sLog->outErrorDb("TargetRange condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_MAPID: @@ -1392,6 +1409,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) if (cond->mConditionValue2) sLog->outErrorDb("Map condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("Map condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_ITEM_TARGET: @@ -1422,6 +1441,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) if (cond->mConditionValue2) sLog->outErrorDb("Spell condition has useless data in value2 (%u)!", cond->mConditionValue2); + if (cond->mConditionValue3) + sLog->outErrorDb("Spell condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_NOITEM: @@ -1432,6 +1453,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("NoItem condition has non existing item (%u), skipped", cond->mConditionValue1); return false; } + if (cond->mConditionValue3) + sLog->outErrorDb("NoItem condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_LEVEL: @@ -1441,6 +1464,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("Level condition has invalid option (%u), skipped", cond->mConditionValue2); return false; } + if (cond->mConditionValue3) + sLog->outErrorDb("Level condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_DRUNKENSTATE: @@ -1450,6 +1475,13 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("DrunkState condition has invalid state (%u), skipped", cond->mConditionValue1); return false; } + if (cond->mConditionValue2) + { + sLog->outErrorDb("DrunkState condition has useless data in value2 (%u)!", cond->mConditionValue3); + return false; + } + if (cond->mConditionValue3) + sLog->outErrorDb("DrunkState condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_NEAR_CREATURE: @@ -1459,6 +1491,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("NearCreature condition has non existing creature template entry (%u), skipped", cond->mConditionValue1); return false; } + if (cond->mConditionValue3) + sLog->outErrorDb("NearCreature condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_NEAR_GAMEOBJECT: @@ -1468,6 +1502,8 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("NearGameObject condition has non existing gameobject template entry (%u), skipped", cond->mConditionValue1); return false; } + if (cond->mConditionValue3) + sLog->outErrorDb("NearGameObject condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_AREAID: diff --git a/src/server/game/Conditions/ConditionMgr.h b/src/server/game/Conditions/ConditionMgr.h index b3ba27db7b5..19bdd929b58 100755 --- a/src/server/game/Conditions/ConditionMgr.h +++ b/src/server/game/Conditions/ConditionMgr.h @@ -30,35 +30,35 @@ enum ConditionType { // value1 value2 value3 CONDITION_NONE = 0, // 0 0 0 always true CONDITION_AURA = 1, // spell_id effindex use target? true if player (or target, if value3) has aura of spell_id with effect effindex - CONDITION_ITEM = 2, // item_id count +referenceID true if has #count of item_ids - CONDITION_ITEM_EQUIPPED = 3, // item_id 0 +referenceID true if has item_id equipped - CONDITION_ZONEID = 4, // zone_id 0 +referenceID true if in zone_id - CONDITION_REPUTATION_RANK = 5, // faction_id min_rank +referenceID true if has min_rank for faction_id - CONDITION_TEAM = 6, // player_team 0, +referenceID 469 - Alliance, 67 - Horde) - CONDITION_SKILL = 7, // skill_id skill_value +referenceID true if has skill_value for skill_id - CONDITION_QUESTREWARDED = 8, // quest_id 0 +referenceID true if quest_id was rewarded before - CONDITION_QUESTTAKEN = 9, // quest_id 0, +referenceID true while quest active - CONDITION_DRUNKENSTATE = 10, // DrunkenState 0, +referenceID true if player is drunk enough - CONDITION_NO_AURA = 11, // spell_id effindex +referenceID true if does not have aura of spell_id with effect effindex - CONDITION_ACTIVE_EVENT = 12, // event_id 0 +referenceID true if event is active - CONDITION_INSTANCE_DATA = 13, // entry data +referenceID true if data is set in current instance - CONDITION_QUEST_NONE = 14, // quest_id 0 +referenceID true if doesn't have quest saved - CONDITION_CLASS = 15, // class 0 +referenceID true if player's class is equal to class - CONDITION_RACE = 16, // race 0 +referenceID true if player's race is equal to race - CONDITION_ACHIEVEMENT = 17, // achievement_id 0 +referenceID true if achievement is complete - CONDITION_SPELL_SCRIPT_TARGET = 18, // SpellScriptTargetType, TargetEntry, 0 - CONDITION_CREATURE_TARGET = 19, // creature entry 0 +referenceID true if current target is creature with value1 entry - CONDITION_TARGET_HEALTH_BELOW_PCT = 20, // 0-100 0 +referenceID true if target's health is below value1 percent, false if over or no target - CONDITION_TARGET_RANGE = 21, // minDistance maxDist +referenceID true if target is closer then minDist and further then maxDist or if max is 0 then max dist is infinit - CONDITION_MAPID = 22, // map_id 0 +referenceID true if in map_id - CONDITION_AREAID = 23, // area_id 0 +referenceID true if in area_id + CONDITION_ITEM = 2, // item_id count 0 true if has #count of item_ids + CONDITION_ITEM_EQUIPPED = 3, // item_id 0 0 true if has item_id equipped + CONDITION_ZONEID = 4, // zone_id 0 0 true if in zone_id + CONDITION_REPUTATION_RANK = 5, // faction_id min_rank 0 true if has min_rank for faction_id + CONDITION_TEAM = 6, // player_team 0, 0 469 - Alliance, 67 - Horde) + CONDITION_SKILL = 7, // skill_id skill_value 0 true if has skill_value for skill_id + CONDITION_QUESTREWARDED = 8, // quest_id 0 0 true if quest_id was rewarded before + CONDITION_QUESTTAKEN = 9, // quest_id 0, 0 true while quest active + CONDITION_DRUNKENSTATE = 10, // DrunkenState 0, 0 true if player is drunk enough + CONDITION_NO_AURA = 11, // spell_id effindex 0 true if does not have aura of spell_id with effect effindex + CONDITION_ACTIVE_EVENT = 12, // event_id 0 0 true if event is active + CONDITION_INSTANCE_DATA = 13, // entry data 0 true if data is set in current instance + CONDITION_QUEST_NONE = 14, // quest_id 0 0 true if doesn't have quest saved + CONDITION_CLASS = 15, // class 0 0 true if player's class is equal to class + CONDITION_RACE = 16, // race 0 0 true if player's race is equal to race + CONDITION_ACHIEVEMENT = 17, // achievement_id 0 0 true if achievement is complete + CONDITION_SPELL_SCRIPT_TARGET = 18, // SpellScriptTargetType, TargetEntry, 0 + CONDITION_CREATURE_TARGET = 19, // creature entry 0 0 true if current target is creature with value1 entry + CONDITION_TARGET_HEALTH_BELOW_PCT = 20, // 0-100 0 0 true if target's health is below value1 percent, false if over or no target + CONDITION_TARGET_RANGE = 21, // minDistance maxDist 0 true if target is closer then minDist and further then maxDist or if max is 0 then max dist is infinit + CONDITION_MAPID = 22, // map_id 0 0 true if in map_id + CONDITION_AREAID = 23, // area_id 0 0 true if in area_id CONDITION_ITEM_TARGET = 24, // ItemRequiredTargetType, TargetEntry, 0 - CONDITION_SPELL = 25, // spell_id bool +referenceID bool 1 for true 0 for false - CONDITION_NOITEM = 26, // item_id bank +referenceID true if player does not have any of the item (if 'bank' is set it searches in bank slots too) - CONDITION_LEVEL = 27, // level opt +referenceID true if player's level is equal to param1 (param2 can modify the statement) - CONDITION_QUEST_COMPLETE = 28, // quest_id 0 +referenceID true if player has quest_id with all objectives complete, but not yet rewarded - CONDITION_NEAR_CREATURE = 29, // creature entry distance +referenceID true if there is a creature of entry in range - CONDITION_NEAR_GAMEOBJECT = 30, // gameobject entry distance +referenceID true if there is a gameobject of entry in range + CONDITION_SPELL = 25, // spell_id bool 0 bool 1 for true 0 for false + CONDITION_NOITEM = 26, // item_id bank 0 true if player does not have any of the item (if 'bank' is set it searches in bank slots too) + CONDITION_LEVEL = 27, // level opt 0 true if player's level is equal to param1 (param2 can modify the statement) + CONDITION_QUEST_COMPLETE = 28, // quest_id 0 0 true if player has quest_id with all objectives complete, but not yet rewarded + CONDITION_NEAR_CREATURE = 29, // creature entry distance 0 true if there is a creature of entry in range + CONDITION_NEAR_GAMEOBJECT = 30, // gameobject entry distance 0 true if there is a gameobject of entry in range CONDITION_MAX = 31 // MAX }; -- cgit v1.2.3 From f2f11507614b8c482fce67d4ef4dda1bce1fe623 Mon Sep 17 00:00:00 2001 From: QAston Date: Fri, 10 Feb 2012 15:43:19 +0100 Subject: Fixed build. --- src/server/game/Conditions/ConditionMgr.cpp | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/server/game/Conditions/ConditionMgr.cpp b/src/server/game/Conditions/ConditionMgr.cpp index 831452e50f6..e2027e8884e 100755 --- a/src/server/game/Conditions/ConditionMgr.cpp +++ b/src/server/game/Conditions/ConditionMgr.cpp @@ -163,7 +163,6 @@ bool Condition::Meets(WorldObject* object, WorldObject* invoker) } case CONDITION_SPELL_SCRIPT_TARGET: condMeets = true;//spell target condition is handled in spellsystem, here it is always true - refId = 0;//cant have references! use CONDITION_SOURCE_TYPE_SPELL for it break; case CONDITION_CREATURE_TARGET: { @@ -284,11 +283,11 @@ bool Condition::Meets(WorldObject* object, WorldObject* invoker) condMeets = !condMeets; if (Player* player = object->ToPlayer()) - if (sendErrorMsg && ErrorTextd && (!condMeets || !refMeets))//send special error from DB + if (sendErrorMsg && ErrorTextd && (!condMeets))//send special error from DB player->m_ConditionErrorMsgId = ErrorTextd; bool script = sScriptMgr->OnConditionCheck(this, object, invoker); // Returns true by default. - return condMeets && refMeets && script; + return condMeets && script; } ConditionMgr::ConditionMgr() @@ -1477,7 +1476,7 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) } if (cond->mConditionValue2) { - sLog->outErrorDb("DrunkState condition has useless data in value2 (%u)!", cond->mConditionValue3); + sLog->outErrorDb("DrunkState condition has useless data in value2 (%u)!", cond->mConditionValue2); return false; } if (cond->mConditionValue3) -- cgit v1.2.3 From 9155d21b649589df729b1a5a0f4828678059f7dd Mon Sep 17 00:00:00 2001 From: Shauren Date: Fri, 10 Feb 2012 16:40:02 +0100 Subject: Scripts/Icecrown Citadel: Fixed crash in spell_frostwarden_handler_order_whelp Closes #5129 --- src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp b/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp index fb04d9ce7a4..6bbc028e90c 100644 --- a/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp +++ b/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp @@ -1344,6 +1344,9 @@ class spell_frostwarden_handler_order_whelp : public SpellScriptLoader ++itr; } + if (unitList.empty()) + return; + Unit* target = SelectRandomContainerElement(unitList); unitList.clear(); unitList.push_back(target); @@ -1356,7 +1359,10 @@ class spell_frostwarden_handler_order_whelp : public SpellScriptLoader std::list unitList; GetCreatureListWithEntryInGrid(unitList, GetCaster(), NPC_FROSTWING_WHELP, 150.0f); if (Creature* creature = GetCaster()->ToCreature()) - unitList.remove_if (OrderWhelpTargetSelector(creature)); + unitList.remove_if(OrderWhelpTargetSelector(creature)); + + if (unitList.empty()) + return; SelectRandomContainerElement(unitList)->CastSpell(GetHitUnit(), uint32(GetEffectValue()), true); } -- cgit v1.2.3 From 05b18ca9ba81c9a6a656e4476e132807489894bf Mon Sep 17 00:00:00 2001 From: Shauren Date: Fri, 10 Feb 2012 16:44:02 +0100 Subject: Scripts/Icecrown Citadel: Attempt to fix Sindragosa spawning --- .../Northrend/IcecrownCitadel/boss_sindragosa.cpp | 23 ++++++++++++++++++++++ .../IcecrownCitadel/instance_icecrown_citadel.cpp | 4 ---- 2 files changed, 23 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp b/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp index 6bbc028e90c..1d9c3c14897 100644 --- a/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp +++ b/src/server/scripts/Northrend/IcecrownCitadel/boss_sindragosa.cpp @@ -597,6 +597,16 @@ class npc_spinestalker : public CreatureScript { } + void InitializeAI() + { + // Increase add count + if (!me->isDead()) + { + _instance->SetData(DATA_SINDRAGOSA_FROSTWYRMS, 1); // this cannot be in Reset because reset also happens on evade + Reset(); + } + } + void Reset() { _events.Reset(); @@ -712,6 +722,16 @@ class npc_rimefang : public CreatureScript { } + void InitializeAI() + { + // Increase add count + if (!me->isDead()) + { + _instance->SetData(DATA_SINDRAGOSA_FROSTWYRMS, 1); // this cannot be in Reset because reset also happens on evade + Reset(); + } + } + void Reset() { _events.Reset(); @@ -860,7 +880,10 @@ class npc_sindragosa_trash : public CreatureScript _frostwyrmId = (me->GetHomePosition().GetPositionY() < 2484.35f) ? DATA_RIMEFANG : DATA_SPINESTALKER; // Increase add count if (!me->isDead()) + { _instance->SetData(_frostwyrmId, 1); // this cannot be in Reset because reset also happens on evade + Reset(); + } } void Reset() diff --git a/src/server/scripts/Northrend/IcecrownCitadel/instance_icecrown_citadel.cpp b/src/server/scripts/Northrend/IcecrownCitadel/instance_icecrown_citadel.cpp index 2a61d00d119..98f5c04ba42 100755 --- a/src/server/scripts/Northrend/IcecrownCitadel/instance_icecrown_citadel.cpp +++ b/src/server/scripts/Northrend/IcecrownCitadel/instance_icecrown_citadel.cpp @@ -279,13 +279,9 @@ class instance_icecrown_citadel : public InstanceMapScript break; case NPC_SPINESTALKER: SpinestalkerGUID = creature->GetGUID(); - if (!creature->isDead()) - ++FrostwyrmCount; break; case NPC_RIMEFANG: RimefangGUID = creature->GetGUID(); - if (!creature->isDead()) - ++FrostwyrmCount; break; case NPC_THE_LICH_KING: TheLichKingGUID = creature->GetGUID(); -- cgit v1.2.3 From 586a76e3a0345a86f0e372f59aef082580bd266a Mon Sep 17 00:00:00 2001 From: QAston Date: Fri, 10 Feb 2012 16:47:22 +0100 Subject: Core/Db/Conditions: Add 3rd parameter to CONDITION_ITEM so it can now perform a check if item exists in bank aswell as in equipment. --- src/server/game/Conditions/ConditionMgr.cpp | 9 ++++++--- src/server/game/Conditions/ConditionMgr.h | 2 +- 2 files changed, 7 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/server/game/Conditions/ConditionMgr.cpp b/src/server/game/Conditions/ConditionMgr.cpp index e2027e8884e..9391636c619 100755 --- a/src/server/game/Conditions/ConditionMgr.cpp +++ b/src/server/game/Conditions/ConditionMgr.cpp @@ -61,7 +61,12 @@ bool Condition::Meets(WorldObject* object, WorldObject* invoker) case CONDITION_ITEM: { if (Player* player = object->ToPlayer()) - condMeets = (mConditionValue2 && player->HasItemCount(mConditionValue1, mConditionValue2)) || (!mConditionValue2 && !player->HasItemCount(mConditionValue1, mConditionValue2));//HasItemCount returns false if 0 count is used + { + // don't allow 0 items (it's checked during table load) + ASSERT(mConditionValue2); + bool checkBank = mConditionValue3 ? true : false; + condMeets = player->HasItemCount(mConditionValue1, mConditionValue2, checkBank); + } break; } case CONDITION_ITEM_EQUIPPED: @@ -1142,8 +1147,6 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) sLog->outErrorDb("Item condition has 0 set for item count in value2 (%u), skipped", cond->mConditionValue2); return false; } - if (cond->mConditionValue3) - sLog->outErrorDb("Item condition has useless data in value3 (%u)!", cond->mConditionValue3); break; } case CONDITION_ITEM_EQUIPPED: diff --git a/src/server/game/Conditions/ConditionMgr.h b/src/server/game/Conditions/ConditionMgr.h index 19bdd929b58..1a666abbf2b 100755 --- a/src/server/game/Conditions/ConditionMgr.h +++ b/src/server/game/Conditions/ConditionMgr.h @@ -30,7 +30,7 @@ enum ConditionType { // value1 value2 value3 CONDITION_NONE = 0, // 0 0 0 always true CONDITION_AURA = 1, // spell_id effindex use target? true if player (or target, if value3) has aura of spell_id with effect effindex - CONDITION_ITEM = 2, // item_id count 0 true if has #count of item_ids + CONDITION_ITEM = 2, // item_id count bank true if has #count of item_ids (if 'bank' is set it searches in bank slots too) CONDITION_ITEM_EQUIPPED = 3, // item_id 0 0 true if has item_id equipped CONDITION_ZONEID = 4, // zone_id 0 0 true if in zone_id CONDITION_REPUTATION_RANK = 5, // faction_id min_rank 0 true if has min_rank for faction_id -- cgit v1.2.3