[7190] Rewrite code for Unit::SpellHealingBonus (no big changes)

Implement SPELL_AURA_OVERRIDE_CLASS_SCRIPTS auras for healing mod
Remove dead code
Implement SPELL_AURA_MOD_HEALING_RECEIVED aura

Signed-off-by: DiSlord <dislord@nomail.com>
This commit is contained in:
DiSlord 2009-01-26 22:10:37 +03:00
parent 32cbef4291
commit 170a0aaf3b
3 changed files with 114 additions and 43 deletions

View file

@ -333,7 +333,7 @@ pAuraHandler AuraHandler[TOTAL_AURAS]=
&Aura::HandleNULL, //280 SPELL_AURA_MOD_TARGET_ARMOR_PCT &Aura::HandleNULL, //280 SPELL_AURA_MOD_TARGET_ARMOR_PCT
&Aura::HandleNULL, //281 SPELL_AURA_MOD_HONOR_GAIN &Aura::HandleNULL, //281 SPELL_AURA_MOD_HONOR_GAIN
&Aura::HandleAuraIncreaseBaseHealthPercent, //282 SPELL_AURA_INCREASE_BASE_HEALTH_PERCENT &Aura::HandleAuraIncreaseBaseHealthPercent, //282 SPELL_AURA_INCREASE_BASE_HEALTH_PERCENT
&Aura::HandleNULL //283 SPD/heal from AP? &Aura::HandleNoImmediateEffect //283 SPELL_AURA_MOD_HEALING_RECEIVED implemented in Unit::SpellHealingBonus
}; };
Aura::Aura(SpellEntry const* spellproto, uint32 eff, int32 *currentBasePoints, Unit *target, Unit *caster, Item* castItem) : Aura::Aura(SpellEntry const* spellproto, uint32 eff, int32 *currentBasePoints, Unit *target, Unit *caster, Item* castItem) :

View file

@ -8110,33 +8110,101 @@ uint32 Unit::SpellHealingBonus(SpellEntry const *spellProto, uint32 healamount,
spellProto->Id == 38395 || spellProto->Id == 40972) spellProto->Id == 38395 || spellProto->Id == 40972)
return healamount; return healamount;
int32 AdvertisedBenefit = SpellBaseHealingBonus(GetSpellSchoolMask(spellProto)); // Taken/Done total percent damage auras
uint32 CastingTime = GetSpellCastTime(spellProto); float DoneTotalMod = 1.0f;
float TakenTotalMod = 1.0f;
uint32 DoneTotal = 0;
uint32 TakenTotal = 0;
// Healing Taken // Healing done percent
AdvertisedBenefit += SpellBaseHealingBonusForVictim(GetSpellSchoolMask(spellProto), pVictim); AuraList const& mHealingDonePct = GetAurasByType(SPELL_AURA_MOD_HEALING_DONE_PERCENT);
for(AuraList::const_iterator i = mHealingDonePct.begin();i != mHealingDonePct.end(); ++i)
DoneTotalMod *= (100.0f + (*i)->GetModifier()->m_amount) / 100.0f;
// Blessing of Light dummy effects healing taken from Holy Light and Flash of Light // done scripted mod (take it from owner)
if (spellProto->SpellFamilyName == SPELLFAMILY_PALADIN && (spellProto->SpellFamilyFlags & 0x00000000C0000000LL)) Unit *owner = GetOwner();
if (!owner) owner = this;
AuraList const& mOverrideClassScript= owner->GetAurasByType(SPELL_AURA_OVERRIDE_CLASS_SCRIPTS);
for(AuraList::const_iterator i = mOverrideClassScript.begin(); i != mOverrideClassScript.end(); ++i)
{ {
AuraList const& mDummyAuras = pVictim->GetAurasByType(SPELL_AURA_DUMMY); if (!(*i)->isAffectedOnSpell(spellProto))
for(AuraList::const_iterator i = mDummyAuras.begin();i != mDummyAuras.end(); ++i) continue;
switch((*i)->GetModifier()->m_miscvalue)
{ {
if((*i)->GetSpellProto()->SpellVisual[0] == 9180) case 4415: // Increased Rejuvenation Healing
case 4953:
case 3736: // Hateful Totem of the Third Wind / Increased Lesser Healing Wave / LK Arena (4/5/6) Totem of the Third Wind / Savage Totem of the Third Wind
DoneTotal+=(*i)->GetModifier()->m_amount;
break;
case 7997: // Renewed Hope
case 7998:
if (pVictim->HasAura(6788))
DoneTotalMod *=((*i)->GetModifier()->m_amount + 100.0f)/100.0f;
break;
case 21: // Test of Faith
case 6935:
case 6918:
if (pVictim->GetHealth() < pVictim->GetMaxHealth()/2)
DoneTotalMod *=((*i)->GetModifier()->m_amount + 100.0f)/100.0f;
break;
case 7798: // Glyph of Regrowth
{ {
// Flash of Light AuraList const& auras = pVictim->GetAurasByType(SPELL_AURA_PERIODIC_HEAL);
if ((spellProto->SpellFamilyFlags & 0x0000000040000000LL) && (*i)->GetEffIndex() == 1) for(AuraList::const_iterator itr = auras.begin(); itr != auras.end(); ++itr)
AdvertisedBenefit += (*i)->GetModifier()->m_amount; {
// Holy Light SpellEntry const* m_spell = (*itr)->GetSpellProto();
else if ((spellProto->SpellFamilyFlags & 0x0000000080000000LL) && (*i)->GetEffIndex() == 0) if (m_spell->SpellFamilyName == SPELLFAMILY_DRUID &&
AdvertisedBenefit += (*i)->GetModifier()->m_amount; m_spell->SpellFamilyFlags & 0x0000000000000040LL)
{
DoneTotalMod *= ((*i)->GetModifier()->m_amount+100.0f)/100.0f;
break;
}
}
break;
} }
case 8477: // Nourish Heal Boost
{
int32 stepPercent = (*i)->GetModifier()->m_amount;
int32 modPercent = 0;
AuraMap const& victimAuras = pVictim->GetAuras();
for (AuraMap::const_iterator itr = victimAuras.begin(); itr != victimAuras.end(); ++itr)
{
if (itr->second->GetCasterGUID()!=GetGUID())
continue;
SpellEntry const* m_spell = itr->second->GetSpellProto();
if ( m_spell->SpellFamilyName != SPELLFAMILY_DRUID ||
!(m_spell->SpellFamilyFlags & 0x0000001000000050LL))
continue;
modPercent += stepPercent * itr->second->GetStackAmount();
}
DoneTotalMod *= (modPercent+100.0f)/100.0f;
break;
}
case 7871: // Glyph of Lesser Healing Wave
{
AuraList const& auras = pVictim->GetAurasByType(SPELL_AURA_DUMMY);
for(AuraList::const_iterator itr = auras.begin(); itr != auras.end(); ++itr)
{
if ((*itr)->GetCasterGUID()!=GetGUID())
continue;
SpellEntry const* m_spell = (*itr)->GetSpellProto();
if (m_spell->SpellFamilyName == SPELLFAMILY_SHAMAN &&
m_spell->SpellFamilyFlags & 0x0000040000000000LL)
{
DoneTotalMod *= ((*i)->GetModifier()->m_amount+100.0f)/100.0f;
break;
}
}
break;
}
default:
break;
} }
} }
float ActualBenefit = 0.0f; int32 DoneAdvertisedBenefit = SpellBaseHealingBonus(GetSpellSchoolMask(spellProto));
int32 TakenAdvertisedBenefit = SpellBaseHealingBonusForVictim(GetSpellSchoolMask(spellProto), pVictim);
if (AdvertisedBenefit != 0) if (DoneAdvertisedBenefit != 0 && TakenAdvertisedBenefit!=0)
{ {
// Healing over Time spells // Healing over Time spells
float DotFactor = 1.0f; float DotFactor = 1.0f;
@ -8163,9 +8231,13 @@ uint32 Unit::SpellHealingBonus(SpellEntry const *spellProto, uint32 healamount,
if(spellProto->EffectAmplitude[x] != 0) if(spellProto->EffectAmplitude[x] != 0)
DotTicks = DotDuration / spellProto->EffectAmplitude[x]; DotTicks = DotDuration / spellProto->EffectAmplitude[x];
if(DotTicks) if(DotTicks)
AdvertisedBenefit /= DotTicks; {
DoneAdvertisedBenefit /= DotTicks;
TakenAdvertisedBenefit /= DotTicks;
}
} }
} }
uint32 CastingTime = GetSpellCastTime(spellProto);
// distribute healing to all effects, reduce AoE damage // distribute healing to all effects, reduce AoE damage
CastingTime = GetCastingTimeForBonus( spellProto, damagetype, CastingTime ); CastingTime = GetCastingTimeForBonus( spellProto, damagetype, CastingTime );
@ -8184,12 +8256,15 @@ uint32 Unit::SpellHealingBonus(SpellEntry const *spellProto, uint32 healamount,
// Exception // Exception
switch (spellProto->SpellFamilyName) switch (spellProto->SpellFamilyName)
{ {
case SPELLFAMILY_SHAMAN: case SPELLFAMILY_GENERIC:
// Healing stream from totem (add 6% per tick from hill bonus owner) // Healing stream from totem (add 6% per tick from hill bonus owner)
if (spellProto->SpellFamilyFlags & 0x000000002000LL) // Possibly need do it on apply dummy aura
if (spellProto->Id == 52042)
CastingTime = 210; CastingTime = 210;
break;
case SPELLFAMILY_SHAMAN:
// Earth Shield 30% per charge // Earth Shield 30% per charge
else if (spellProto->SpellFamilyFlags & 0x40000000000LL) if (spellProto->SpellFamilyFlags & 0x40000000000LL)
CastingTime = 1050; CastingTime = 1050;
break; break;
case SPELLFAMILY_DRUID: case SPELLFAMILY_DRUID:
@ -8239,48 +8314,44 @@ uint32 Unit::SpellHealingBonus(SpellEntry const *spellProto, uint32 healamount,
SpellModSpellDamage /= 100.0f; SpellModSpellDamage /= 100.0f;
ActualBenefit = (float)AdvertisedBenefit * ((float)CastingTime / 3500.0f) * DotFactor * SpellModSpellDamage * LvlPenalty; DoneTotal += (float)DoneAdvertisedBenefit * ((float)CastingTime / 3500.0f) * DotFactor * SpellModSpellDamage * LvlPenalty;
TakenTotal += (float)TakenAdvertisedBenefit * ((float)CastingTime / 3500.0f) * DotFactor * SpellModSpellDamage * LvlPenalty;
} }
// use float as more appropriate for negative values and percent applying // use float as more appropriate for negative values and percent applying
float heal = healamount + ActualBenefit; float heal = (healamount + DoneTotal)*DoneTotalMod;
// TODO: check for ALL/SPELLS type
// Healing done percent
AuraList const& mHealingDonePct = GetAurasByType(SPELL_AURA_MOD_HEALING_DONE_PERCENT);
for(AuraList::const_iterator i = mHealingDonePct.begin();i != mHealingDonePct.end(); ++i)
heal *= (100.0f + (*i)->GetModifier()->m_amount) / 100.0f;
// apply spellmod to Done amount // apply spellmod to Done amount
if(Player* modOwner = GetSpellModOwner()) if(Player* modOwner = GetSpellModOwner())
modOwner->ApplySpellMod(spellProto->Id, damagetype == DOT ? SPELLMOD_DOT : SPELLMOD_DAMAGE, heal); modOwner->ApplySpellMod(spellProto->Id, damagetype == DOT ? SPELLMOD_DOT : SPELLMOD_DAMAGE, heal);
// Taken mods
// Healing Wave cast // Healing Wave cast
if (spellProto->SpellFamilyName == SPELLFAMILY_SHAMAN && spellProto->SpellFamilyFlags & 0x0000000000000040LL) if (spellProto->SpellFamilyName == SPELLFAMILY_SHAMAN && spellProto->SpellFamilyFlags & 0x0000000000000040LL)
{ {
// Search for Healing Way on Victim (stack up to 3 time) // Search for Healing Way on Victim
int32 pctMod = 0;
Unit::AuraList const& auraDummy = pVictim->GetAurasByType(SPELL_AURA_DUMMY); Unit::AuraList const& auraDummy = pVictim->GetAurasByType(SPELL_AURA_DUMMY);
for(Unit::AuraList::const_iterator itr = auraDummy.begin(); itr!=auraDummy.end(); ++itr) for(Unit::AuraList::const_iterator itr = auraDummy.begin(); itr!=auraDummy.end(); ++itr)
if((*itr)->GetId() == 29203) if((*itr)->GetId() == 29203)
pctMod += (*itr)->GetModifier()->m_amount; TakenTotalMod *= (*itr)->GetModifier()->m_amount;
// Apply bonus
if (pctMod)
heal = heal * (100 + pctMod) / 100;
} }
// Healing taken percent // Healing taken percent
float minval = pVictim->GetMaxNegativeAuraModifier(SPELL_AURA_MOD_HEALING_PCT); float minval = pVictim->GetMaxNegativeAuraModifier(SPELL_AURA_MOD_HEALING_PCT);
if(minval) if(minval)
heal *= (100.0f + minval) / 100.0f; TakenTotalMod *= (100.0f + minval) / 100.0f;
float maxval = pVictim->GetMaxPositiveAuraModifier(SPELL_AURA_MOD_HEALING_PCT); float maxval = pVictim->GetMaxPositiveAuraModifier(SPELL_AURA_MOD_HEALING_PCT);
if(maxval) if(maxval)
heal *= (100.0f + maxval) / 100.0f; TakenTotalMod *= (100.0f + maxval) / 100.0f;
if (heal < 0) heal = 0; AuraList const& mHealingGet= pVictim->GetAurasByType(SPELL_AURA_MOD_HEALING_RECEIVED);
for(AuraList::const_iterator i = mHealingGet.begin(); i != mHealingGet.end(); ++i)
if ((*i)->isAffectedOnSpell(spellProto))
TakenTotalMod *= ((*i)->GetModifier()->m_amount + 100.0f) / 100.0f;
return uint32(heal); heal = (heal + TakenTotal) * TakenTotalMod;
return heal < 0 ? 0 : uint32(heal);
} }
int32 Unit::SpellBaseHealingBonus(SpellSchoolMask schoolMask) int32 Unit::SpellBaseHealingBonus(SpellSchoolMask schoolMask)

View file

@ -1,4 +1,4 @@
#ifndef __REVISION_NR_H__ #ifndef __REVISION_NR_H__
#define __REVISION_NR_H__ #define __REVISION_NR_H__
#define REVISION_NR "7189" #define REVISION_NR "7190"
#endif // __REVISION_NR_H__ #endif // __REVISION_NR_H__