aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authormegamage <none@none>2009-08-23 10:22:58 -0500
committermegamage <none@none>2009-08-23 10:22:58 -0500
commit0b06baee4dcbc18534bbfb3becb679ae42103439 (patch)
tree7740eb58fae708062901ae493c48472615f6bd9c
parentd132f7e401ecfc032b33405f6b247807a0754133 (diff)
*Update rules of aura stack.
--HG-- branch : trunk
-rw-r--r--src/game/SharedDefines.h4
-rw-r--r--src/game/SpellAuras.cpp3
-rw-r--r--src/game/SpellMgr.cpp122
-rw-r--r--src/game/SpellMgr.h2
-rw-r--r--src/game/Unit.cpp2
5 files changed, 68 insertions, 65 deletions
diff --git a/src/game/SharedDefines.h b/src/game/SharedDefines.h
index fdd4f6401fe..6a2a9ff334e 100644
--- a/src/game/SharedDefines.h
+++ b/src/game/SharedDefines.h
@@ -266,7 +266,7 @@ enum SpellCategory
#define SPELL_ATTR_EX_UNK11 0x00000800 // 11 aura
#define SPELL_ATTR_EX_UNK12 0x00001000 // 12
#define SPELL_ATTR_EX_UNK13 0x00002000 // 13
-#define SPELL_ATTR_EX_UNK14 0x00004000 // 14
+#define SPELL_ATTR_EX_STACK_FOR_DIFF_CASTERS 0x00004000 // 14
#define SPELL_ATTR_EX_DISPEL_AURAS_ON_IMMUNITY 0x00008000 // 15 remove auras on immunity
#define SPELL_ATTR_EX_UNK16 0x00010000 // 16 on immuniy
#define SPELL_ATTR_EX_UNAUTOCASTABLE_BY_PET 0x00020000 // 17
@@ -325,7 +325,7 @@ enum SpellCategory
#define SPELL_ATTR_EX3_UNK4 0x00000010 // 4 Druid Rebirth only this spell have this flag
#define SPELL_ATTR_EX3_UNK5 0x00000020 // 5
#define SPELL_ATTR_EX3_UNK6 0x00000040 // 6
-#define SPELL_ATTR_EX3_STACKS_FOR_DIFFERENT_CASTERS 0x00000080 // 7 separate stack for every caster
+#define SPELL_ATTR_EX3_STACK_FOR_DIFF_CASTERS 0x00000080 // 7 separate stack for every caster
#define SPELL_ATTR_EX3_PLAYERS_ONLY 0x00000100 // 8 Player only?
#define SPELL_ATTR_EX3_TRIGGERED_CAN_TRIGGER_2 0x00000200 // 9 triggered from effect?
#define SPELL_ATTR_EX3_MAIN_HAND 0x00000400 // 10 Main hand weapon required
diff --git a/src/game/SpellAuras.cpp b/src/game/SpellAuras.cpp
index 27e2c2a9e3a..837b8323a60 100644
--- a/src/game/SpellAuras.cpp
+++ b/src/game/SpellAuras.cpp
@@ -780,8 +780,7 @@ void AreaAuraEffect::Update(uint32 diff)
bool skip = false;
for(Unit::AuraMap::iterator iter = (*tIter)->GetAuras().begin(); iter != (*tIter)->GetAuras().end();++iter)
{
- bool samecaster = iter->second->GetCasterGUID() == GetCasterGUID();
- if(spellmgr.IsNoStackSpellDueToSpell(GetId(), iter->first, samecaster))
+ if(!spellmgr.CanAurasStack(GetSpellProto(), iter->second->GetSpellProto(), iter->second->GetCasterGUID() == GetCasterGUID()))
{
skip = true;
break;
diff --git a/src/game/SpellMgr.cpp b/src/game/SpellMgr.cpp
index 9f21fd442d4..91e11ca90a4 100644
--- a/src/game/SpellMgr.cpp
+++ b/src/game/SpellMgr.cpp
@@ -3002,94 +3002,98 @@ bool SpellArea::IsFitToRequirements(Player const* player, uint32 newZone, uint32
//-----------TRINITY-------------
-bool SpellMgr::IsNoStackSpellDueToSpell(uint32 spellId_1, uint32 spellId_2, bool sameCaster) const
+bool SpellMgr::CanAurasStack(SpellEntry const *spellInfo_1, SpellEntry const *spellInfo_2, bool sameCaster) const
{
- SpellEntry const *spellInfo_1 = sSpellStore.LookupEntry(spellId_1);
- SpellEntry const *spellInfo_2 = sSpellStore.LookupEntry(spellId_2);
-
- if(!spellInfo_1 || !spellInfo_2)
- return false;
-
- SpellSpecific spellId_spec_1 = GetSpellSpecific(spellId_1);
- SpellSpecific spellId_spec_2 = GetSpellSpecific(spellId_2);
- if (spellId_spec_1 && spellId_spec_2)
- if (IsSingleFromSpellSpecificPerTarget(spellId_spec_1, spellId_spec_2)
- ||(sameCaster && IsSingleFromSpellSpecificPerCaster(spellId_spec_1, spellId_spec_2)))
- return true;
+ SpellSpecific spellSpec_1 = GetSpellSpecific(spellInfo_1->Id);
+ SpellSpecific spellSpec_2 = GetSpellSpecific(spellInfo_2->Id);
+ if (spellSpec_1 && spellSpec_2)
+ if (IsSingleFromSpellSpecificPerTarget(spellSpec_1, spellSpec_2)
+ || sameCaster && IsSingleFromSpellSpecificPerCaster(spellSpec_1, spellSpec_2))
+ return false;
if(spellInfo_1->SpellFamilyName != spellInfo_2->SpellFamilyName)
- return false;
+ return true;
if(!sameCaster)
{
+ if(spellInfo_1->AttributesEx & SPELL_ATTR_EX3_STACK_FOR_DIFF_CASTERS
+ || spellInfo_1->AttributesEx3 & SPELL_ATTR_EX3_STACK_FOR_DIFF_CASTERS)
+ return true;
+
+ // check same periodic auras
for(uint32 i = 0; i < 3; ++i)
- if (spellInfo_1->Effect[i] == SPELL_EFFECT_APPLY_AURA
- || spellInfo_1->Effect[i] == SPELL_EFFECT_PERSISTENT_AREA_AURA)
+ {
+ // area auras should not stack (shaman totem)
+ if(spellInfo_1->Effect[i] != SPELL_EFFECT_APPLY_AURA
+ && spellInfo_1->Effect[i] != SPELL_EFFECT_PERSISTENT_AREA_AURA)
+ continue;
+
+ // not channeled AOE effects should not stack (blizzard should, but Consecration should not)
+ if((IsAreaEffectTarget[spellInfo_1->EffectImplicitTargetA[i]] || IsAreaEffectTarget[spellInfo_1->EffectImplicitTargetB[i]])
+ && !IsChanneledSpell(spellInfo_1))
+ continue;
+
+ switch(spellInfo_1->EffectApplyAuraName[i])
{
- // not channeled AOE effects can stack
- if(IsAreaEffectTarget[spellInfo_1->EffectImplicitTargetA[i]] || IsAreaEffectTarget[spellInfo_1->EffectImplicitTargetB[i]]
- && !IsChanneledSpell(spellInfo_1))
- continue;
- // not area auras (shaman totem)
- switch(spellInfo_1->EffectApplyAuraName[i])
- {
- // DOT or HOT from different casters will stack
- case SPELL_AURA_PERIODIC_DAMAGE:
- case SPELL_AURA_PERIODIC_HEAL:
- case SPELL_AURA_PERIODIC_TRIGGER_SPELL:
- case SPELL_AURA_PERIODIC_ENERGIZE:
- case SPELL_AURA_PERIODIC_MANA_LEECH:
- case SPELL_AURA_PERIODIC_LEECH:
- case SPELL_AURA_POWER_BURN_MANA:
- case SPELL_AURA_OBS_MOD_ENERGY:
- case SPELL_AURA_OBS_MOD_HEALTH:
- case SPELL_AURA_PERIODIC_TRIGGER_SPELL_WITH_VALUE:
- return false;
- default:
- break;
- }
+ // DOT or HOT from different casters will stack
+ case SPELL_AURA_PERIODIC_DAMAGE:
+ case SPELL_AURA_PERIODIC_HEAL:
+ case SPELL_AURA_PERIODIC_TRIGGER_SPELL:
+ case SPELL_AURA_PERIODIC_ENERGIZE:
+ case SPELL_AURA_PERIODIC_MANA_LEECH:
+ case SPELL_AURA_PERIODIC_LEECH:
+ case SPELL_AURA_POWER_BURN_MANA:
+ case SPELL_AURA_OBS_MOD_ENERGY:
+ case SPELL_AURA_OBS_MOD_HEALTH:
+ case SPELL_AURA_PERIODIC_TRIGGER_SPELL_WITH_VALUE:
+ return true;
+ default:
+ break;
}
+ }
}
- spellId_2 = GetLastSpellInChain(spellId_2);
- spellId_1 = GetLastSpellInChain(spellId_1);
-
- // Hack for Incanter's Absorption
- if (spellId_1 == spellId_2 && (spellId_1 == 44413 || (!sameCaster && spellInfo_1->AttributesEx3 & SPELL_ATTR_EX3_STACKS_FOR_DIFFERENT_CASTERS)))
- return false;
+ uint32 spellId_1 = GetLastSpellInChain(spellInfo_1->Id);
+ uint32 spellId_2 = GetLastSpellInChain(spellInfo_2->Id);
+ // same spell
if (spellId_1 == spellId_2)
- return true;
+ {
+ // Hack for Incanter's Absorption
+ if(spellId_1 == 44413)
+ return true;
+ // same spell with same caster should not stack
+ return false;
+ }
- // generic spells
+ // use icon to check generic spells
if(!spellInfo_1->SpellFamilyName)
{
- if(!spellInfo_1->SpellIconID
- || spellInfo_1->SpellIconID == 1
+ if(!spellInfo_1->SpellIconID || spellInfo_1->SpellIconID == 1
|| spellInfo_1->SpellIconID != spellInfo_2->SpellIconID)
- return false;
+ return true;
}
- // check for class spells
+ // use familyflag to check class spells
else
{
- if (spellInfo_1->SpellFamilyFlags != spellInfo_2->SpellFamilyFlags)
- return false;
- if (!spellInfo_1->SpellFamilyFlags)
- return false;
+ if(!spellInfo_1->SpellFamilyFlags
+ || spellInfo_1->SpellFamilyFlags != spellInfo_2->SpellFamilyFlags)
+ return true;
}
//use data of highest rank spell(needed for spells which ranks have different effects)
- spellInfo_1=sSpellStore.LookupEntry(spellId_1);
- spellInfo_2=sSpellStore.LookupEntry(spellId_2);
+ spellInfo_1 = sSpellStore.LookupEntry(spellId_1);
+ spellInfo_2 = sSpellStore.LookupEntry(spellId_2);
- //if spells have exactly the same effect they cannot stack
+ //if spells do not have the same effect or aura or miscvalue, they will stack
for(uint32 i = 0; i < 3; ++i)
if(spellInfo_1->Effect[i] != spellInfo_2->Effect[i]
|| spellInfo_1->EffectApplyAuraName[i] != spellInfo_2->EffectApplyAuraName[i]
|| spellInfo_1->EffectMiscValue[i] != spellInfo_2->EffectMiscValue[i]) // paladin resist aura
- return false; // need itemtype check? need an example to add that check
+ return true; // need itemtype check? need an example to add that check
- return (!(!sameCaster && spellInfo_1->AttributesEx3 & SPELL_ATTR_EX3_STACKS_FOR_DIFFERENT_CASTERS));
+ // different spells with same effect
+ return false;
}
bool IsDispelableBySpell(SpellEntry const * dispelSpell, uint32 spellId, bool def)
diff --git a/src/game/SpellMgr.h b/src/game/SpellMgr.h
index 42705f1e7ca..b8dca34edf0 100644
--- a/src/game/SpellMgr.h
+++ b/src/game/SpellMgr.h
@@ -967,7 +967,7 @@ class SpellMgr
bool IsRankSpellDueToSpell(SpellEntry const *spellInfo_1,uint32 spellId_2) const;
static bool canStackSpellRanks(SpellEntry const *spellInfo);
- bool IsNoStackSpellDueToSpell(uint32 spellId_1, uint32 spellId_2, bool sameCaster) const;
+ bool CanAurasStack(SpellEntry const *spellInfo_1, SpellEntry const *spellInfo_2, bool sameCaster) const;
SpellEntry const* SelectAuraRankForPlayerLevel(SpellEntry const* spellInfo, uint32 playerLevel) const;
diff --git a/src/game/Unit.cpp b/src/game/Unit.cpp
index aca48c53e01..be24edb329f 100644
--- a/src/game/Unit.cpp
+++ b/src/game/Unit.cpp
@@ -3865,7 +3865,7 @@ bool Unit::RemoveNoStackAurasDueToAura(Aura *Aur)
if (is_triggered_by_spell)
continue;
- if(!spellmgr.IsNoStackSpellDueToSpell(spellId, i_spellId, sameCaster))
+ if(spellmgr.CanAurasStack(spellProto, i_spellProto, sameCaster))
continue;
//some spells should be not removed by lower rank of them (totem, paladin aura)