aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/server/game/Spells/Auras/SpellAuraEffects.cpp14
-rw-r--r--src/server/game/Spells/SpellInfo.cpp102
-rw-r--r--src/server/game/Spells/SpellInfo.h36
3 files changed, 103 insertions, 49 deletions
diff --git a/src/server/game/Spells/Auras/SpellAuraEffects.cpp b/src/server/game/Spells/Auras/SpellAuraEffects.cpp
index eb6ffc3012b..f420d1debd3 100644
--- a/src/server/game/Spells/Auras/SpellAuraEffects.cpp
+++ b/src/server/game/Spells/Auras/SpellAuraEffects.cpp
@@ -3118,7 +3118,7 @@ void AuraEffect::HandleModMechanicImmunityMask(AuraApplication const* aurApp, ui
return;
Unit* target = aurApp->GetTarget();
- m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetEffIndex(), apply);
+ m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetSpellEffectInfo(), apply);
}
void AuraEffect::HandleModMechanicImmunity(AuraApplication const* aurApp, uint8 mode, bool apply) const
@@ -3127,7 +3127,7 @@ void AuraEffect::HandleModMechanicImmunity(AuraApplication const* aurApp, uint8
return;
Unit* target = aurApp->GetTarget();
- m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetEffIndex(), apply);
+ m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetSpellEffectInfo(), apply);
}
void AuraEffect::HandleAuraModEffectImmunity(AuraApplication const* aurApp, uint8 mode, bool apply) const
@@ -3136,7 +3136,7 @@ void AuraEffect::HandleAuraModEffectImmunity(AuraApplication const* aurApp, uint
return;
Unit* target = aurApp->GetTarget();
- m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetEffIndex(), apply);
+ m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetSpellEffectInfo(), apply);
// when removing flag aura, handle flag drop
Player* player = target->ToPlayer();
@@ -3158,7 +3158,7 @@ void AuraEffect::HandleAuraModStateImmunity(AuraApplication const* aurApp, uint8
return;
Unit* target = aurApp->GetTarget();
- m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetEffIndex(), apply);
+ m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetSpellEffectInfo(), apply);
}
void AuraEffect::HandleAuraModSchoolImmunity(AuraApplication const* aurApp, uint8 mode, bool apply) const
@@ -3167,7 +3167,7 @@ void AuraEffect::HandleAuraModSchoolImmunity(AuraApplication const* aurApp, uint
return;
Unit* target = aurApp->GetTarget();
- m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetEffIndex(), apply);
+ m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetSpellEffectInfo(), apply);
if (GetSpellInfo()->Mechanic == MECHANIC_BANISH)
{
@@ -3219,7 +3219,7 @@ void AuraEffect::HandleAuraModDmgImmunity(AuraApplication const* aurApp, uint8 m
return;
Unit* target = aurApp->GetTarget();
- m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetEffIndex(), apply);
+ m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetSpellEffectInfo(), apply);
if (apply)
{
@@ -3241,7 +3241,7 @@ void AuraEffect::HandleAuraModDispelImmunity(AuraApplication const* aurApp, uint
return;
Unit* target = aurApp->GetTarget();
- m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetEffIndex(), apply);
+ m_spellInfo->ApplyAllSpellImmunitiesTo(target, GetSpellEffectInfo(), apply);
}
/*********************************************************/
diff --git a/src/server/game/Spells/SpellInfo.cpp b/src/server/game/Spells/SpellInfo.cpp
index 38347a1bae5..dd3c8ede288 100644
--- a/src/server/game/Spells/SpellInfo.cpp
+++ b/src/server/game/Spells/SpellInfo.cpp
@@ -30,6 +30,7 @@
#include "SpellAuraEffects.h"
#include "SpellMgr.h"
#include "Vehicle.h"
+#include <boost/container/flat_set.hpp>
uint32 GetTargetFlagMask(SpellTargetObjectTypes objType)
{
@@ -211,6 +212,26 @@ uint32 SpellImplicitTargetInfo::GetExplicitTargetMask(bool& srcSet, bool& dstSet
return targetMask;
}
+struct SpellEffectInfo::ImmunityInfo
+{
+ ImmunityInfo() = default;
+ ~ImmunityInfo() = default;
+
+ ImmunityInfo(ImmunityInfo const&) = delete;
+ ImmunityInfo(ImmunityInfo&&) noexcept = delete;
+ ImmunityInfo& operator=(ImmunityInfo const&) = delete;
+ ImmunityInfo& operator=(ImmunityInfo&&) noexcept = delete;
+
+ uint32 SchoolImmuneMask = 0;
+ uint32 ApplyHarmfulAuraImmuneMask = 0;
+ uint32 MechanicImmuneMask = 0;
+ uint32 DispelImmune = 0;
+ uint32 DamageSchoolMask = 0;
+
+ boost::container::flat_set<AuraType> AuraTypeImmune;
+ boost::container::flat_set<SpellEffects> SpellEffectImmune;
+};
+
std::array<SpellImplicitTargetInfo::StaticData, TOTAL_SPELL_TARGETS> SpellImplicitTargetInfo::_data =
{ {
{TARGET_OBJECT_TYPE_NONE, TARGET_REFERENCE_TYPE_NONE, TARGET_SELECT_CATEGORY_NYI, TARGET_CHECK_DEFAULT, TARGET_DIR_NONE}, //
@@ -326,6 +347,13 @@ std::array<SpellImplicitTargetInfo::StaticData, TOTAL_SPELL_TARGETS> SpellImplic
{TARGET_OBJECT_TYPE_DEST, TARGET_REFERENCE_TYPE_NONE, TARGET_SELECT_CATEGORY_NYI, TARGET_CHECK_ENTRY, TARGET_DIR_NONE}, // 110 TARGET_UNIT_CONE_ENTRY_110
} };
+SpellEffectInfo::SpellEffectInfo() : _spellInfo(nullptr), EffectIndex(EFFECT_0), Effect(SPELL_EFFECT_NONE), ApplyAuraName(SPELL_AURA_NONE),
+ Amplitude(0), DieSides(0), RealPointsPerLevel(0), BasePoints(0), PointsPerComboPoint(0), ValueMultiplier(0), DamageMultiplier(0),
+ BonusMultiplier(0), MiscValue(0), MiscValueB(0), Mechanic(MECHANIC_NONE), RadiusEntry(nullptr), ChainTarget(0), ItemType(0),
+ TriggerSpell(0), ImplicitTargetConditions(nullptr), _immunityInfo(nullptr)
+{
+}
+
SpellEffectInfo::SpellEffectInfo(SpellEntry const* spellEntry, SpellInfo const* spellInfo, uint8 effIndex)
{
_spellInfo = spellInfo;
@@ -351,6 +379,17 @@ SpellEffectInfo::SpellEffectInfo(SpellEntry const* spellEntry, SpellInfo const*
TriggerSpell = spellEntry->EffectTriggerSpell[effIndex];
SpellClassMask = spellEntry->EffectSpellClassMask[effIndex];
ImplicitTargetConditions = nullptr;
+ _immunityInfo = nullptr;
+}
+
+SpellEffectInfo::SpellEffectInfo(SpellEffectInfo const&) = default;
+SpellEffectInfo::SpellEffectInfo(SpellEffectInfo&&) noexcept = default;
+SpellEffectInfo& SpellEffectInfo::operator=(SpellEffectInfo const&) = default;
+SpellEffectInfo& SpellEffectInfo::operator=(SpellEffectInfo&&) noexcept = default;
+
+SpellEffectInfo::~SpellEffectInfo()
+{
+ delete _immunityInfo;
}
bool SpellEffectInfo::IsEffect() const
@@ -2545,6 +2584,8 @@ int32 SpellInfo::GetDiminishingReturnsLimitDuration(bool triggered) const
void SpellInfo::_LoadImmunityInfo()
{
+ std::unique_ptr<SpellEffectInfo::ImmunityInfo> workBuffer = std::make_unique<SpellEffectInfo::ImmunityInfo>();
+
for (SpellEffectInfo& effect : _GetEffects())
{
uint32 schoolImmunityMask = 0;
@@ -2556,7 +2597,7 @@ void SpellInfo::_LoadImmunityInfo()
int32 miscVal = effect.MiscValue;
int32 amount = effect.CalcValue();
- ImmunityInfo& immuneInfo = _immunityInfo[effect.EffectIndex];
+ SpellEffectInfo::ImmunityInfo& immuneInfo = *workBuffer;
switch (effect.ApplyAuraName)
{
@@ -2736,7 +2777,7 @@ void SpellInfo::_LoadImmunityInfo()
break;
default:
if (miscVal < 1)
- continue;
+ break;
mechanicImmunityMask |= 1 << miscVal;
break;
@@ -2786,6 +2827,18 @@ void SpellInfo::_LoadImmunityInfo()
immuneInfo.AuraTypeImmune.shrink_to_fit();
immuneInfo.SpellEffectImmune.shrink_to_fit();
+ if (immuneInfo.SchoolImmuneMask
+ || immuneInfo.ApplyHarmfulAuraImmuneMask
+ || immuneInfo.MechanicImmuneMask
+ || immuneInfo.DispelImmune
+ || immuneInfo.DamageSchoolMask
+ || !immuneInfo.AuraTypeImmune.empty()
+ || !immuneInfo.SpellEffectImmune.empty())
+ {
+ effect._immunityInfo = workBuffer.release();
+ workBuffer = std::make_unique<SpellEffectInfo::ImmunityInfo>();
+ }
+
_allowedMechanicMask |= immuneInfo.MechanicImmuneMask;
}
@@ -2827,11 +2880,13 @@ void SpellInfo::_LoadImmunityInfo()
}
}
-void SpellInfo::ApplyAllSpellImmunitiesTo(Unit* target, uint8 effIndex, bool apply) const
+void SpellInfo::ApplyAllSpellImmunitiesTo(Unit* target, SpellEffectInfo const& spellEffectInfo, bool apply) const
{
- ImmunityInfo const& immuneInfo = _immunityInfo[effIndex];
+ SpellEffectInfo::ImmunityInfo const* immuneInfo = spellEffectInfo.GetImmunityInfo();
+ if (!immuneInfo)
+ return;
- if (uint32 schoolImmunity = immuneInfo.SchoolImmuneMask)
+ if (uint32 schoolImmunity = immuneInfo->SchoolImmuneMask)
{
target->ApplySpellImmune(Id, IMMUNITY_SCHOOL, schoolImmunity, apply);
@@ -2849,7 +2904,7 @@ void SpellInfo::ApplyAllSpellImmunitiesTo(Unit* target, uint8 effIndex, bool app
}
}
- if (uint32 mechanicImmunity = immuneInfo.MechanicImmuneMask)
+ if (uint32 mechanicImmunity = immuneInfo->MechanicImmuneMask)
{
for (uint32 i = 0; i < MAX_MECHANIC; ++i)
if (mechanicImmunity & (1 << i))
@@ -2878,7 +2933,7 @@ void SpellInfo::ApplyAllSpellImmunitiesTo(Unit* target, uint8 effIndex, bool app
}
}
- if (uint32 dispelImmunity = immuneInfo.DispelImmune)
+ if (uint32 dispelImmunity = immuneInfo->DispelImmune)
{
target->ApplySpellImmune(Id, IMMUNITY_DISPEL, dispelImmunity, apply);
@@ -2895,10 +2950,10 @@ void SpellInfo::ApplyAllSpellImmunitiesTo(Unit* target, uint8 effIndex, bool app
}
}
- if (uint32 damageImmunity = immuneInfo.DamageSchoolMask)
+ if (uint32 damageImmunity = immuneInfo->DamageSchoolMask)
target->ApplySpellImmune(Id, IMMUNITY_DAMAGE, damageImmunity, apply);
- for (AuraType auraType : immuneInfo.AuraTypeImmune)
+ for (AuraType auraType : immuneInfo->AuraTypeImmune)
{
target->ApplySpellImmune(Id, IMMUNITY_STATE, auraType, apply);
if (apply && HasAttribute(SPELL_ATTR1_DISPEL_AURAS_ON_IMMUNITY))
@@ -2909,7 +2964,7 @@ void SpellInfo::ApplyAllSpellImmunitiesTo(Unit* target, uint8 effIndex, bool app
});
}
- for (SpellEffects effectType : immuneInfo.SpellEffectImmune)
+ for (SpellEffects effectType : immuneInfo->SpellEffectImmune)
target->ApplySpellImmune(Id, IMMUNITY_EFFECT, effectType, apply);
}
@@ -2918,20 +2973,27 @@ bool SpellInfo::CanSpellProvideImmunityAgainstAura(SpellInfo const* auraSpellInf
if (!auraSpellInfo)
return false;
- for (ImmunityInfo const& immuneInfo : _immunityInfo)
+ for (SpellEffectInfo const& effectInfo : _effects)
{
+ if (!effectInfo.IsEffect())
+ continue;
+
+ SpellEffectInfo::ImmunityInfo const* immuneInfo = effectInfo.GetImmunityInfo();
+ if (!immuneInfo)
+ continue;
+
if (!auraSpellInfo->HasAttribute(SPELL_ATTR1_UNAFFECTED_BY_SCHOOL_IMMUNE) && !auraSpellInfo->HasAttribute(SPELL_ATTR2_UNAFFECTED_BY_AURA_SCHOOL_IMMUNE))
{
- if (uint32 schoolImmunity = immuneInfo.SchoolImmuneMask)
+ if (uint32 schoolImmunity = immuneInfo->SchoolImmuneMask)
if ((auraSpellInfo->SchoolMask & schoolImmunity) != 0)
return true;
}
- if (uint32 mechanicImmunity = immuneInfo.MechanicImmuneMask)
+ if (uint32 mechanicImmunity = immuneInfo->MechanicImmuneMask)
if ((mechanicImmunity & (1 << auraSpellInfo->Mechanic)) != 0)
return true;
- if (uint32 dispelImmunity = immuneInfo.DispelImmune)
+ if (uint32 dispelImmunity = immuneInfo->DispelImmune)
if (auraSpellInfo->Dispel == dispelImmunity)
return true;
@@ -2941,8 +3003,8 @@ bool SpellInfo::CanSpellProvideImmunityAgainstAura(SpellInfo const* auraSpellInf
if (!auraSpellEffectInfo.IsEffect())
continue;
- auto spellImmuneItr = immuneInfo.SpellEffectImmune.find(auraSpellEffectInfo.Effect);
- if (spellImmuneItr == immuneInfo.SpellEffectImmune.cend())
+ auto spellImmuneItr = immuneInfo->SpellEffectImmune.find(auraSpellEffectInfo.Effect);
+ if (spellImmuneItr == immuneInfo->SpellEffectImmune.cend())
{
immuneToAllEffects = false;
break;
@@ -2950,7 +3012,7 @@ bool SpellInfo::CanSpellProvideImmunityAgainstAura(SpellInfo const* auraSpellInf
if (uint32 mechanic = auraSpellEffectInfo.Mechanic)
{
- if (!(immuneInfo.MechanicImmuneMask & (1 << mechanic)))
+ if (!(immuneInfo->MechanicImmuneMask & (1 << mechanic)))
{
immuneToAllEffects = false;
break;
@@ -2962,13 +3024,13 @@ bool SpellInfo::CanSpellProvideImmunityAgainstAura(SpellInfo const* auraSpellInf
if (AuraType auraName = auraSpellEffectInfo.ApplyAuraName)
{
bool isImmuneToAuraEffectApply = false;
- auto auraImmuneItr = immuneInfo.AuraTypeImmune.find(auraName);
- if (auraImmuneItr != immuneInfo.AuraTypeImmune.cend())
+ auto auraImmuneItr = immuneInfo->AuraTypeImmune.find(auraName);
+ if (auraImmuneItr != immuneInfo->AuraTypeImmune.cend())
isImmuneToAuraEffectApply = true;
if (!isImmuneToAuraEffectApply && !auraSpellInfo->IsPositiveEffect(auraSpellEffectInfo.EffectIndex) && !auraSpellInfo->HasAttribute(SPELL_ATTR2_UNAFFECTED_BY_AURA_SCHOOL_IMMUNE))
{
- if (uint32 applyHarmfulAuraImmunityMask = immuneInfo.ApplyHarmfulAuraImmuneMask)
+ if (uint32 applyHarmfulAuraImmunityMask = immuneInfo->ApplyHarmfulAuraImmuneMask)
if ((auraSpellInfo->GetSchoolMask() & applyHarmfulAuraImmunityMask) != 0)
isImmuneToAuraEffectApply = true;
}
diff --git a/src/server/game/Spells/SpellInfo.h b/src/server/game/Spells/SpellInfo.h
index 51d34e2d443..426c067317a 100644
--- a/src/server/game/Spells/SpellInfo.h
+++ b/src/server/game/Spells/SpellInfo.h
@@ -24,8 +24,6 @@
#include "Object.h"
#include "SpellAuraDefines.h"
-#include <boost/container/flat_set.hpp>
-
class AuraEffect;
class Item;
class Player;
@@ -208,6 +206,7 @@ private:
class TC_GAME_API SpellEffectInfo
{
+ friend class SpellInfo;
SpellInfo const* _spellInfo;
public:
SpellEffIndex EffectIndex;
@@ -233,11 +232,13 @@ public:
flag96 SpellClassMask;
std::vector<Condition*>* ImplicitTargetConditions;
- SpellEffectInfo() : _spellInfo(nullptr), EffectIndex(EFFECT_0), Effect(SPELL_EFFECT_NONE), ApplyAuraName(SPELL_AURA_NONE), Amplitude(0), DieSides(0),
- RealPointsPerLevel(0), BasePoints(0), PointsPerComboPoint(0), ValueMultiplier(0), DamageMultiplier(0),
- BonusMultiplier(0), MiscValue(0), MiscValueB(0), Mechanic(MECHANIC_NONE), RadiusEntry(nullptr), ChainTarget(0),
- ItemType(0), TriggerSpell(0), ImplicitTargetConditions(nullptr) {}
- SpellEffectInfo(SpellEntry const* spellEntry, SpellInfo const* spellInfo, uint8 effIndex);
+ SpellEffectInfo();
+ explicit SpellEffectInfo(SpellEntry const* spellEntry, SpellInfo const* spellInfo, uint8 effIndex);
+ SpellEffectInfo(SpellEffectInfo const&);
+ SpellEffectInfo(SpellEffectInfo&&) noexcept;
+ SpellEffectInfo& operator=(SpellEffectInfo const&);
+ SpellEffectInfo& operator=(SpellEffectInfo&&) noexcept;
+ ~SpellEffectInfo();
bool IsEffect() const;
bool IsEffect(SpellEffects effectName) const;
@@ -261,6 +262,9 @@ public:
SpellEffectImplicitTargetTypes GetImplicitTargetType() const;
SpellTargetObjectTypes GetUsedTargetObjectType() const;
+ struct ImmunityInfo;
+ ImmunityInfo const* GetImmunityInfo() const { return _immunityInfo; }
+
private:
struct StaticData
{
@@ -268,6 +272,8 @@ private:
SpellTargetObjectTypes UsedTargetObjectType; // defines valid target object type for spell effect
};
static std::array<StaticData, TOTAL_SPELL_EFFECTS> _data;
+
+ ImmunityInfo* _immunityInfo;
};
struct TC_GAME_API SpellDiminishInfo
@@ -278,18 +284,6 @@ struct TC_GAME_API SpellDiminishInfo
int32 DiminishDurationLimit = 0;
};
-struct TC_GAME_API ImmunityInfo
-{
- uint32 SchoolImmuneMask = 0;
- uint32 ApplyHarmfulAuraImmuneMask = 0;
- uint32 MechanicImmuneMask = 0;
- uint32 DispelImmune = 0;
- uint32 DamageSchoolMask = 0;
-
- boost::container::flat_set<AuraType> AuraTypeImmune;
- boost::container::flat_set<SpellEffects> SpellEffectImmune;
-};
-
class TC_GAME_API SpellInfo
{
friend class SpellMgr;
@@ -498,7 +492,7 @@ class TC_GAME_API SpellInfo
int32 GetDiminishingReturnsLimitDuration(bool triggered) const;
// spell immunities
- void ApplyAllSpellImmunitiesTo(Unit* target, uint8 effIndex, bool apply) const;
+ void ApplyAllSpellImmunitiesTo(Unit* target, SpellEffectInfo const& spellEffectInfo, bool apply) const;
bool CanSpellProvideImmunityAgainstAura(SpellInfo const* auraSpellInfo) const;
bool SpellCancelsAuraEffect(AuraEffect const* aurEff) const;
@@ -528,8 +522,6 @@ class TC_GAME_API SpellInfo
SpellDiminishInfo _diminishInfoTriggered;
uint32 _allowedMechanicMask;
-
- std::array<ImmunityInfo, MAX_SPELL_EFFECTS> _immunityInfo;
};
#endif // _SPELLINFO_H