Avoid target requirement checks for spells with caster base target selection (self,pet,around). Author: VladimirMangos
This fix cast fail for some spells, mostly triggered or scripted with unexpected prowided explicit tatrget different from caster. --HG-- branch : trunk
This commit is contained in:
+6
-4
@@ -4354,7 +4354,9 @@ SpellCastResult Spell::CheckCast(bool strict)
|
|||||||
if(!m_IsTriggeredSpell && target == m_caster && m_spellInfo->AttributesEx & SPELL_ATTR_EX_CANT_TARGET_SELF)
|
if(!m_IsTriggeredSpell && target == m_caster && m_spellInfo->AttributesEx & SPELL_ATTR_EX_CANT_TARGET_SELF)
|
||||||
return SPELL_FAILED_BAD_TARGETS;
|
return SPELL_FAILED_BAD_TARGETS;
|
||||||
|
|
||||||
if(target != m_caster)
|
bool non_caster_target = target != m_caster && !spellmgr.IsSpellWithCasterSourceTargetsOnly(m_spellInfo);
|
||||||
|
|
||||||
|
if(non_caster_target)
|
||||||
{
|
{
|
||||||
// target state requirements (apply to non-self only), to allow cast affects to self like Dirty Deeds
|
// target state requirements (apply to non-self only), to allow cast affects to self like Dirty Deeds
|
||||||
if(!m_IsTriggeredSpell && m_spellInfo->TargetAuraState && !target->HasAuraState(AuraState(m_spellInfo->TargetAuraState), m_spellInfo, m_caster))
|
if(!m_IsTriggeredSpell && m_spellInfo->TargetAuraState && !target->HasAuraState(AuraState(m_spellInfo->TargetAuraState), m_spellInfo, m_caster))
|
||||||
@@ -4402,7 +4404,7 @@ SpellCastResult Spell::CheckCast(bool strict)
|
|||||||
|
|
||||||
//check creature type
|
//check creature type
|
||||||
//ignore self casts (including area casts when caster selected as target)
|
//ignore self casts (including area casts when caster selected as target)
|
||||||
if(target != m_caster)
|
if(non_caster_target)
|
||||||
{
|
{
|
||||||
if(!CheckTargetCreatureType(target))
|
if(!CheckTargetCreatureType(target))
|
||||||
{
|
{
|
||||||
@@ -4415,7 +4417,7 @@ SpellCastResult Spell::CheckCast(bool strict)
|
|||||||
|
|
||||||
// TODO: this check can be applied and for player to prevent cheating when IsPositiveSpell will return always correct result.
|
// TODO: this check can be applied and for player to prevent cheating when IsPositiveSpell will return always correct result.
|
||||||
// check target for pet/charmed casts (not self targeted), self targeted cast used for area effects and etc
|
// check target for pet/charmed casts (not self targeted), self targeted cast used for area effects and etc
|
||||||
if(m_caster != target && m_caster->GetTypeId() == TYPEID_UNIT && m_caster->GetCharmerOrOwnerGUID())
|
if(non_caster_target && m_caster->GetTypeId() == TYPEID_UNIT && m_caster->GetCharmerOrOwnerGUID())
|
||||||
{
|
{
|
||||||
// check correctness positive/negative cast target (pet cast real check and cheating check)
|
// check correctness positive/negative cast target (pet cast real check and cheating check)
|
||||||
if(IsPositiveSpell(m_spellInfo->Id))
|
if(IsPositiveSpell(m_spellInfo->Id))
|
||||||
@@ -4454,7 +4456,7 @@ SpellCastResult Spell::CheckCast(bool strict)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// check if target is in combat
|
// check if target is in combat
|
||||||
if (target != m_caster && (m_spellInfo->AttributesEx & SPELL_ATTR_EX_NOT_IN_COMBAT_TARGET) && target->isInCombat())
|
if (non_caster_target && (m_spellInfo->AttributesEx & SPELL_ATTR_EX_NOT_IN_COMBAT_TARGET) && target->isInCombat())
|
||||||
return SPELL_FAILED_TARGET_AFFECTING_COMBAT;
|
return SPELL_FAILED_TARGET_AFFECTING_COMBAT;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -270,6 +270,7 @@ bool IsDispelableBySpell(SpellEntry const * dispelSpell, uint32 spellId, bool de
|
|||||||
bool IsSingleTargetSpell(SpellEntry const *spellInfo);
|
bool IsSingleTargetSpell(SpellEntry const *spellInfo);
|
||||||
bool IsSingleTargetSpells(SpellEntry const *spellInfo1, SpellEntry const *spellInfo2);
|
bool IsSingleTargetSpells(SpellEntry const *spellInfo1, SpellEntry const *spellInfo2);
|
||||||
|
|
||||||
|
|
||||||
extern bool IsAreaEffectTarget[TOTAL_SPELL_TARGETS];
|
extern bool IsAreaEffectTarget[TOTAL_SPELL_TARGETS];
|
||||||
|
|
||||||
inline bool IsAreaOfEffectSpell(SpellEntry const *spellInfo)
|
inline bool IsAreaOfEffectSpell(SpellEntry const *spellInfo)
|
||||||
@@ -1051,6 +1052,28 @@ class SpellMgr
|
|||||||
|
|
||||||
bool IsSrcTargetSpell(SpellEntry const *spellInfo) const;
|
bool IsSrcTargetSpell(SpellEntry const *spellInfo) const;
|
||||||
|
|
||||||
|
inline bool IsCasterSourceTarget(uint32 target)
|
||||||
|
{
|
||||||
|
switch (SpellTargetType[target])
|
||||||
|
{
|
||||||
|
case TARGET_TYPE_UNIT_TARGET:
|
||||||
|
case TARGET_TYPE_DEST_TARGET:
|
||||||
|
return false;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline bool IsSpellWithCasterSourceTargetsOnly(SpellEntry const* spellInfo)
|
||||||
|
{
|
||||||
|
for(int i = 0; i < 3; ++i)
|
||||||
|
if(uint32 target = spellInfo->EffectImplicitTargetA[i])
|
||||||
|
if(!IsCasterSourceTarget(target))
|
||||||
|
return false;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
// Modifiers
|
// Modifiers
|
||||||
public:
|
public:
|
||||||
static SpellMgr& Instance();
|
static SpellMgr& Instance();
|
||||||
|
|||||||
Reference in New Issue
Block a user