diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/game/Unit.cpp | 119 | ||||
-rw-r--r-- | src/game/Unit.h | 3 |
2 files changed, 55 insertions, 67 deletions
diff --git a/src/game/Unit.cpp b/src/game/Unit.cpp index c93a9dd6a1d..5594793337c 100644 --- a/src/game/Unit.cpp +++ b/src/game/Unit.cpp @@ -3933,7 +3933,7 @@ void Unit::RemoveAura(uint32 spellId, uint64 caster ,AuraRemoveMode removeMode) void Unit::RemoveAura(Aura * aur ,AuraRemoveMode mode) { // no need to remove - if (aur->IsRemoved()) + if (!aur || aur->IsRemoved()) return; for(AuraMap::iterator iter = m_Auras.lower_bound(aur->GetId()); iter != m_Auras.upper_bound(aur->GetId());) { @@ -4244,6 +4244,21 @@ bool Unit::HasAura(uint32 spellId, uint64 caster) const return false; } +bool Unit::HasAura(Aura * aur) const +{ + // no need to find aura + if (!aur || aur->IsRemoved()) + return false; + for(AuraMap::const_iterator iter = m_Auras.lower_bound(aur->GetId()); iter != m_Auras.upper_bound(aur->GetId());) + { + if (aur == iter->second) + return true; + else + ++iter; + } + return false; +} + bool Unit::HasAuraEffect(uint32 spellId, uint8 effIndex, uint64 caster) const { if (Aura * aur = GetAura(spellId, caster)) @@ -11265,34 +11280,18 @@ bool Unit::isFrozen() const struct ProcTriggeredData { - ProcTriggeredData(SpellProcEventEntry const * _spellProcEvent, AuraEffect* _triggeredByAura) - : spellProcEvent(_spellProcEvent), triggeredByAura(_triggeredByAura) - {} - SpellProcEventEntry const *spellProcEvent; - AuraEffect* triggeredByAura; -}; -struct ProcTriggerringAura -{ - ProcTriggerringAura(uint32 _spellId, uint64 _casterGUID) : spellId(_spellId), casterGUID(_casterGUID) - { - triggeringAura[0]=NULL; - triggeringAura[1]=NULL; - triggeringAura[2]=NULL; - } - ProcTriggeredData * triggeringAura[3]; - uint32 spellId; - uint64 casterGUID; - ~ProcTriggerringAura() + ProcTriggeredData(Aura* _aura) + : aura(_aura) { - for (uint8 i = 0;i<3;++i) - if (triggeringAura[i]) - delete triggeringAura[i]; + effMask = 0; + spellProcEvent = NULL; } + SpellProcEventEntry const *spellProcEvent; + Aura * aura; + uint32 effMask; }; -//typedef std::list< ProcTriggeredData > ProcTriggeredList; -typedef std::list< ProcTriggerringAura > ProcTriggeredList; -typedef std::list< uint32> RemoveSpellList; +typedef std::list< ProcTriggeredData > ProcTriggeredList; // List of auras that CAN be trigger but may not exist in spell_proc_event // in most case need for drop charges @@ -11448,65 +11447,60 @@ void Unit::ProcDamageAndSpellFor( bool isVictim, Unit * pTarget, uint32 procFlag } } - RemoveSpellList removedSpells; ProcTriggeredList procTriggered; // Fill procTriggered list for(AuraMap::const_iterator itr = GetAuras().begin(); itr!= GetAuras().end(); ++itr) { - bool first = true; - ProcTriggeredList::iterator aurItr; + ProcTriggeredData triggerData(itr->second); + + if(!IsTriggeredAtSpellProcEvent(pTarget, triggerData.aura, procSpell, procFlag, procExtra, attType, isVictim, (damage > 0), triggerData.spellProcEvent)) + continue; + for (uint8 i=0; i<MAX_SPELL_EFFECTS;++i) { if (AuraEffect * aurEff = itr->second->GetPartAura(i)) { - SpellProcEventEntry const* spellProcEvent = NULL; - if(!IsTriggeredAtSpellProcEvent(pTarget, aurEff, procSpell, procFlag, procExtra, attType, isVictim, (damage > 0), spellProcEvent)) + // Skip this auras + if (isNonTriggerAura[aurEff->GetAuraName()]) continue; - if (first) - { - first = false; - ProcTriggerringAura procAur(itr->second->GetId(), itr->second->GetCasterGUID()); - procTriggered.push_front(procAur); - aurItr = procTriggered.begin(); - } - aurItr->triggeringAura[i] = new ProcTriggeredData(spellProcEvent, aurEff); + // If not trigger by default and spellProcEvent==NULL - skip + if (!isTriggerAura[aurEff->GetAuraName()] && triggerData.spellProcEvent==NULL) + continue; + + triggerData.effMask |= 1<<i; } } + if (triggerData.effMask) + procTriggered.push_front(triggerData); } // Nothing found if (procTriggered.empty()) return; - Aura * parentAura = NULL; // Handle effects proceed this time for(ProcTriggeredList::iterator i = procTriggered.begin(); i != procTriggered.end(); ++i) { - // look for parent aura in auras list, it may be removed while proc even processing - parentAura = GetAura(i->spellId, i->casterGUID); - if (!parentAura) + // look for aura in auras list, it may be removed while proc event processing + if (!HasAura(i->aura)) continue; - bool useCharges= parentAura->GetAuraCharges()>0; + bool useCharges= i->aura->GetAuraCharges()>0; bool takeCharges = false; - for (uint8 j = 0; j<MAX_SPELL_EFFECTS;++j) - { - if (!i->triggeringAura[j]) - continue; + // For players set spell cooldown if need + uint32 cooldown = 0; + if (GetTypeId() == TYPEID_PLAYER && i->spellProcEvent && i->spellProcEvent->cooldown) + cooldown = i->spellProcEvent->cooldown; - // possible for stacked auras from same caster, skip then - if (parentAura->GetPartAura(j)!=i->triggeringAura[j]->triggeredByAura) + for (uint8 effIndex = 0; effIndex<MAX_SPELL_EFFECTS;++effIndex) + { + if (!(i->effMask & (1<<effIndex))) continue; - SpellProcEventEntry const *spellProcEvent = i->triggeringAura[j]->spellProcEvent; - AuraEffect *triggeredByAura =triggeredByAura = i->triggeringAura[j]->triggeredByAura; + AuraEffect *triggeredByAura = i->aura->GetPartAura(effIndex); + assert(triggeredByAura); SpellEntry const *spellInfo = triggeredByAura->GetSpellProto(); - uint32 effIndex = triggeredByAura->GetEffIndex(); - // For players set spell cooldown if need - uint32 cooldown = 0; - if (GetTypeId() == TYPEID_PLAYER && spellProcEvent && spellProcEvent->cooldown) - cooldown = spellProcEvent->cooldown; switch(triggeredByAura->GetAuraName()) { @@ -11621,8 +11615,8 @@ void Unit::ProcDamageAndSpellFor( bool isVictim, Unit * pTarget, uint32 procFlag // Remove charge (aura can be removed by triggers) if(useCharges && takeCharges) { - if (parentAura->DropAuraCharge()) - RemoveAura(parentAura->GetId(),parentAura->GetCasterGUID()); + if (i->aura->DropAuraCharge()) + RemoveAura(i->aura); } } } @@ -12242,20 +12236,13 @@ Pet* Unit::CreateTamedPetFrom(Creature* creatureTarget,uint32 spell_id) return pet; } -bool Unit::IsTriggeredAtSpellProcEvent(Unit *pVictim, AuraEffect * aura, SpellEntry const* procSpell, uint32 procFlag, uint32 procExtra, WeaponAttackType attType, bool isVictim, bool active, SpellProcEventEntry const*& spellProcEvent ) +bool Unit::IsTriggeredAtSpellProcEvent(Unit *pVictim, Aura * aura, SpellEntry const* procSpell, uint32 procFlag, uint32 procExtra, WeaponAttackType attType, bool isVictim, bool active, SpellProcEventEntry const*& spellProcEvent ) { SpellEntry const* spellProto = aura->GetSpellProto (); // Get proc Event Entry spellProcEvent = spellmgr.GetSpellProcEvent(spellProto->Id); - // Skip this auras - if (isNonTriggerAura[aura->GetAuraName()]) - return false; - // If not trigger by default and spellProcEvent==NULL - skip - if (!isTriggerAura[aura->GetAuraName()] && spellProcEvent==NULL) - return false; - // Get EventProcFlag uint32 EventProcFlag; if (spellProcEvent && spellProcEvent->procFlags) // if exist get custom spellProcEvent->procFlags diff --git a/src/game/Unit.h b/src/game/Unit.h index 2fd577c873b..7632de82abc 100644 --- a/src/game/Unit.h +++ b/src/game/Unit.h @@ -1395,6 +1395,7 @@ class TRINITY_DLL_SPEC Unit : public WorldObject AuraEffect* GetAura(AuraType type, uint32 family, uint32 familyFlag1 , uint32 familyFlag2=0, uint32 familyFlag3=0, uint64 casterGUID=0); bool HasAuraEffect(uint32 spellId, uint8 effIndex, uint64 caster = 0) const; bool HasAura(uint32 spellId, uint64 caster = 0) const; + bool HasAura(Aura * aur) const; bool HasAuraType(AuraType auraType) const; bool HasAuraTypeWithMiscvalue(AuraType auratype, uint32 miscvalue) const; @@ -1610,7 +1611,7 @@ class TRINITY_DLL_SPEC Unit : public WorldObject void SendAttackStop(Unit* victim); // only from AttackStop(Unit*) //void SendAttackStart(Unit* pVictim); // only from Unit::AttackStart(Unit*) - bool IsTriggeredAtSpellProcEvent(Unit *pVictim, AuraEffect* aura, SpellEntry const* procSpell, uint32 procFlag, uint32 procExtra, WeaponAttackType attType, bool isVictim, bool active, SpellProcEventEntry const*& spellProcEvent ); + bool IsTriggeredAtSpellProcEvent(Unit *pVictim, Aura* aura, SpellEntry const* procSpell, uint32 procFlag, uint32 procExtra, WeaponAttackType attType, bool isVictim, bool active, SpellProcEventEntry const*& spellProcEvent ); bool HandleDummyAuraProc( Unit *pVictim, uint32 damage, AuraEffect* triggeredByAura, SpellEntry const *procSpell, uint32 procFlag, uint32 procEx, uint32 cooldown); bool HandleObsModEnergyAuraProc( Unit *pVictim, uint32 damage, AuraEffect* triggeredByAura, SpellEntry const *procSpell, uint32 procFlag, uint32 procEx, uint32 cooldown); bool HandleHasteAuraProc( Unit *pVictim, uint32 damage, AuraEffect* triggeredByAura, SpellEntry const *procSpell, uint32 procFlag, uint32 procEx, uint32 cooldown); |