refactor(Core/Spells): QAston proc system (#24233)

Co-authored-by: blinkysc <blinkysc@users.noreply.github.com>
Co-authored-by: QAston <qaston@gmail.com>
Co-authored-by: joschiwald <joschiwald@online.de>
Co-authored-by: ariel- <ariel-@users.noreply.github.com>
Co-authored-by: Kitzunu <24550914+Kitzunu@users.noreply.github.com>
Co-authored-by: blinkysc <your-github-email@example.com>
Co-authored-by: Tereneckla <Tereneckla@users.noreply.github.com>
Co-authored-by: Andrew <47818697+Nyeriah@users.noreply.github.com>
This commit is contained in:
blinkysc
2026-02-18 05:31:53 -06:00
committed by GitHub
parent 65a869ea27
commit 4599f26ae9
76 changed files with 22915 additions and 5181 deletions

View File

@@ -157,7 +157,6 @@ public:
{ "spell_loot_template", HandleReloadLootTemplatesSpellCommand, SEC_ADMINISTRATOR, Console::Yes },
{ "spell_linked_spell", HandleReloadSpellLinkedSpellCommand, SEC_ADMINISTRATOR, Console::Yes },
{ "spell_pet_auras", HandleReloadSpellPetAurasCommand, SEC_ADMINISTRATOR, Console::Yes },
{ "spell_proc_event", HandleReloadSpellProcEventCommand, SEC_ADMINISTRATOR, Console::Yes },
{ "spell_proc", HandleReloadSpellProcsCommand, SEC_ADMINISTRATOR, Console::Yes },
{ "spell_scripts", HandleReloadSpellScriptsCommand, SEC_ADMINISTRATOR, Console::Yes },
{ "spell_target_position", HandleReloadSpellTargetPositionCommand, SEC_ADMINISTRATOR, Console::Yes },
@@ -301,7 +300,6 @@ public:
HandleReloadSpellAreaCommand(handler);
HandleReloadSpellGroupsCommand(handler);
HandleReloadSpellLinkedSpellCommand(handler);
HandleReloadSpellProcEventCommand(handler);
HandleReloadSpellProcsCommand(handler);
HandleReloadSpellBonusesCommand(handler);
HandleReloadSpellTargetPositionCommand(handler);
@@ -901,14 +899,6 @@ public:
return true;
}
static bool HandleReloadSpellProcEventCommand(ChatHandler* handler)
{
LOG_INFO("server.loading", "Reloading Spell Proc Event conditions...");
sSpellMgr->LoadSpellProcEvents();
handler->SendGlobalGMSysMessage("DB table `spell_proc_event` (spell proc trigger requirements) reloaded.");
return true;
}
static bool HandleReloadSpellProcsCommand(ChatHandler* handler)
{
LOG_INFO("server.loading", "Reloading Spell Proc conditions and data...");

View File

@@ -28,6 +28,7 @@ enum Spells
SPELL_SLEEP = 31298,
SPELL_INFERNO = 31299,
SPELL_VAMPIRIC_AURA = 31317,
SPELL_VAMPIRIC_AURA_HEAL = 31285,
SPELL_ENRAGE = 26662,
SPELL_INFERNAL_STUN = 31302,
SPELL_INFERNAL_IMMOLATION = 31304
@@ -160,8 +161,37 @@ class spell_anetheron_sleep : public SpellScript
}
};
// 31317 - Vampiric Aura
class spell_anetheron_vampiric_aura : public AuraScript
{
PrepareAuraScript(spell_anetheron_vampiric_aura);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_VAMPIRIC_AURA_HEAL });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
Unit* actor = eventInfo.GetActor();
int32 bp = damageInfo->GetDamage() * 3;
actor->CastCustomSpell(SPELL_VAMPIRIC_AURA_HEAL, SPELLVALUE_BASE_POINT0, bp, actor, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_anetheron_vampiric_aura::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
void AddSC_boss_anetheron()
{
RegisterHyjalAI(boss_anetheron);
RegisterSpellScript(spell_anetheron_sleep);
RegisterSpellScript(spell_anetheron_vampiric_aura);
}

View File

@@ -1342,6 +1342,28 @@ public:
}
};
// 72176 - Blood Beast Blood Link
class spell_deathbringer_blood_beast_blood_link : public AuraScript
{
PrepareAuraScript(spell_deathbringer_blood_beast_blood_link);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_BLOOD_LINK_DUMMY });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
eventInfo.GetActionTarget()->CastCustomSpell(SPELL_BLOOD_LINK_DUMMY, SPELLVALUE_BASE_POINT0, 3, nullptr, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_deathbringer_blood_beast_blood_link::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
void AddSC_boss_deathbringer_saurfang()
{
new boss_deathbringer_saurfang();
@@ -1350,6 +1372,7 @@ void AddSC_boss_deathbringer_saurfang()
new npc_saurfang_event();
RegisterSpellScript(spell_deathbringer_blood_link_aura);
RegisterSpellScript(spell_deathbringer_blood_link_blood_beast_aura);
RegisterSpellScript(spell_deathbringer_blood_beast_blood_link);
RegisterSpellScript(spell_deathbringer_blood_link);
RegisterSpellAndAuraScriptPair(spell_deathbringer_blood_power, spell_deathbringer_blood_power_aura);
RegisterSpellScript(spell_deathbringer_blood_nova_targeting);

View File

@@ -1522,11 +1522,37 @@ class spell_putricide_regurgitated_ooze : public SpellScript
}
};
// 71770 - Ooze Tank Protection
class spell_putricide_ooze_tank_protection : public AuraScript
{
PrepareAuraScript(spell_putricide_ooze_tank_protection);
bool Validate(SpellInfo const* spellInfo) override
{
return ValidateSpellInfo({ spellInfo->Effects[EFFECT_0].TriggerSpell, spellInfo->Effects[EFFECT_1].TriggerSpell });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* actionTarget = eventInfo.GetActionTarget();
actionTarget->CastSpell(nullptr, GetSpellInfo()->Effects[aurEff->GetEffIndex()].TriggerSpell, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_putricide_ooze_tank_protection::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
OnEffectProc += AuraEffectProcFn(spell_putricide_ooze_tank_protection::HandleProc, EFFECT_1, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
void AddSC_boss_professor_putricide()
{
new boss_professor_putricide();
new npc_volatile_ooze();
new npc_gas_cloud();
RegisterSpellScript(spell_putricide_ooze_tank_protection);
RegisterSpellScript(spell_putricide_slime_puddle);
RegisterSpellScript(spell_putricide_slime_puddle_spawn);
RegisterSpellScript(spell_putricide_grow_stacker_aura);

View File

@@ -56,6 +56,9 @@ enum XT002Spells
SPELL_SPARK_SUMMON = 64210,
SPELL_SPARK_DAMAGE = 64227,
SPELL_SPARK_MELEE = 64230,
// ACHIEVEMENT
SPELL_ACHIEVEMENT_CREDIT_NERF_SCRAPBOTS = 65037,
};
enum XT002Events
@@ -946,6 +949,36 @@ public:
}
};
// 65032 - 321 Boombot Aura
class spell_xt002_321_boombot_aura : public AuraScript
{
PrepareAuraScript(spell_xt002_321_boombot_aura);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_ACHIEVEMENT_CREDIT_NERF_SCRAPBOTS });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
if (eventInfo.GetActionTarget()->GetEntry() != NPC_XS013_SCRAPBOT)
return false;
return true;
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
if (InstanceScript* instance = eventInfo.GetActor()->GetInstanceScript())
instance->DoCastSpellOnPlayers(SPELL_ACHIEVEMENT_CREDIT_NERF_SCRAPBOTS);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_xt002_321_boombot_aura::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_xt002_321_boombot_aura::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
void AddSC_boss_xt002()
{
// Npcs
@@ -961,6 +994,7 @@ void AddSC_boss_xt002()
RegisterSpellAndAuraScriptPair(spell_xt002_gravity_bomb, spell_xt002_gravity_bomb_aura);
RegisterSpellScript(spell_xt002_gravity_bomb_damage);
RegisterSpellAndAuraScriptPair(spell_xt002_searing_light_spawn_life_spark, spell_xt002_searing_light_spawn_life_spark_aura);
RegisterSpellScript(spell_xt002_321_boombot_aura);
// Achievements
new achievement_xt002_nerf_engineering();

View File

@@ -203,6 +203,44 @@ enum TickingTimeBomb
SPELL_TICKING_TIME_BOMB_EXPLODE = 59687
};
enum SecondWind
{
SPELL_SECOND_WIND_TRIGGER = 42771
};
// 42770 - Second Wind
class spell_uk_second_wind : public AuraScript
{
PrepareAuraScript(spell_uk_second_wind);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_SECOND_WIND_TRIGGER });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return false;
return (spellInfo->GetAllEffectsMechanicMask() & ((1 << MECHANIC_ROOT) | (1 << MECHANIC_STUN))) != 0;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = eventInfo.GetActionTarget();
caster->CastSpell(caster, SPELL_SECOND_WIND_TRIGGER, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_uk_second_wind::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_uk_second_wind::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
class spell_ticking_time_bomb_aura : public AuraScript
{
PrepareAuraScript(spell_ticking_time_bomb_aura);
@@ -231,5 +269,6 @@ void AddSC_utgarde_keep()
RegisterUtgardeKeepCreatureAI(npc_dragonflayer_forge_master);
RegisterUtgardeKeepCreatureAI(npc_enslaved_proto_drake);
RegisterSpellScript(spell_uk_second_wind);
RegisterSpellScript(spell_ticking_time_bomb_aura);
}

View File

@@ -41,9 +41,10 @@ enum Spells
SPELL_MARK_OF_KAZZAK = 32960,
SPELL_MARK_OF_KAZZAK_DAMAGE = 32961,
SPELL_ENRAGE = 32964,
SPELL_CAPTURE_SOUL = 32966,
SPELL_TWISTED_REFLECTION = 21063,
SPELL_BERSERK = 32965
SPELL_CAPTURE_SOUL = 32966,
SPELL_TWISTED_REFLECTION = 21063,
SPELL_TWISTED_REFLECTION_HEAL = 21064,
SPELL_BERSERK = 32965
};
class boss_doomlord_kazzak : public CreatureScript
@@ -184,8 +185,35 @@ class spell_mark_of_kazzak_aura : public AuraScript
}
};
// 21063 - Twisted Reflection
class spell_twisted_reflection : public AuraScript
{
PrepareAuraScript(spell_twisted_reflection);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_TWISTED_REFLECTION_HEAL });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
eventInfo.GetActionTarget()->CastSpell(eventInfo.GetActor(), SPELL_TWISTED_REFLECTION_HEAL, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_twisted_reflection::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
void AddSC_boss_doomlordkazzak()
{
new boss_doomlord_kazzak();
RegisterSpellScript(spell_mark_of_kazzak_aura);
RegisterSpellScript(spell_twisted_reflection);
}

View File

@@ -23,6 +23,9 @@
#include "CreatureScript.h"
#include "PetDefines.h"
#include "ScriptedCreature.h"
#include "SpellAuraEffects.h"
#include "SpellScript.h"
#include "SpellScriptLoader.h"
enum HunterSpells
{
@@ -33,6 +36,18 @@ enum HunterSpells
SPELL_HUNTER_PET_SCALING = 62915
};
enum PetSpellsMisc
{
SPELL_PET_GUARD_DOG_HAPPINESS = 54445,
SPELL_PET_SILVERBACK_RANK_1 = 62800,
SPELL_PET_SILVERBACK_RANK_2 = 62801,
PET_ICON_ID_GROWL = 201,
PET_ICON_ID_CLAW = 262,
PET_ICON_ID_BITE = 1680,
PET_ICON_ID_SMACK = 473
};
struct npc_pet_hunter_snake_trap : public ScriptedAI
{
npc_pet_hunter_snake_trap(Creature* creature) : ScriptedAI(creature) { _init = false; }
@@ -132,7 +147,131 @@ private:
uint32 _spellTimer;
};
// -53178 - Guard Dog
class spell_pet_guard_dog : public AuraScript
{
PrepareAuraScript(spell_pet_guard_dog);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PET_GUARD_DOG_HAPPINESS });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
// Growl shares family flags with other spells
// filter by spellIcon instead
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo || spellInfo->SpellIconID != PET_ICON_ID_GROWL)
return false;
return true;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = eventInfo.GetActor();
caster->CastSpell(nullptr, SPELL_PET_GUARD_DOG_HAPPINESS, true, nullptr, aurEff);
Unit* target = eventInfo.GetActionTarget();
if (!target->CanHaveThreatList())
return;
SpellInfo const* procSpellInfo = eventInfo.GetSpellInfo();
if (!procSpellInfo)
return;
float addThreat = CalculatePct(static_cast<float>(procSpellInfo->Effects[EFFECT_0].CalcValue(caster)), aurEff->GetAmount());
target->GetThreatMgr().AddThreat(caster, addThreat, SPELL_SCHOOL_MASK_NORMAL, GetSpellInfo());
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pet_guard_dog::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_pet_guard_dog::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -62764 - Silverback
class spell_pet_silverback : public AuraScript
{
PrepareAuraScript(spell_pet_silverback);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PET_SILVERBACK_RANK_1, SPELL_PET_SILVERBACK_RANK_2 });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
// Growl shares family flags with other spells
// filter by spellIcon instead
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo || spellInfo->SpellIconID != PET_ICON_ID_GROWL)
return false;
return true;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
static uint32 const triggerSpell[2] = { SPELL_PET_SILVERBACK_RANK_1, SPELL_PET_SILVERBACK_RANK_2 };
PreventDefaultAction();
uint8 rank = GetSpellInfo()->GetRank();
if (rank > 0 && rank <= 2)
{
uint32 spellId = triggerSpell[rank - 1];
eventInfo.GetActor()->CastSpell(nullptr, spellId, true, nullptr, aurEff);
}
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pet_silverback::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_pet_silverback::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -61680 - Culling the Herd
class spell_pet_culling_the_herd : public AuraScript
{
PrepareAuraScript(spell_pet_culling_the_herd);
bool CheckProc(ProcEventInfo& eventInfo)
{
// Claw, Bite and Smack share FamilyFlags with other spells
// filter by spellIcon instead
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return false;
switch (spellInfo->SpellIconID)
{
case PET_ICON_ID_CLAW:
case PET_ICON_ID_BITE:
case PET_ICON_ID_SMACK:
break;
default:
return false;
}
return true;
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pet_culling_the_herd::CheckProc);
}
};
void AddSC_hunter_pet_scripts()
{
RegisterCreatureAI(npc_pet_hunter_snake_trap);
RegisterSpellScript(spell_pet_guard_dog);
RegisterSpellScript(spell_pet_silverback);
RegisterSpellScript(spell_pet_culling_the_herd);
}

View File

@@ -81,11 +81,43 @@ enum DeathKnightSpells
SPELL_DK_RAISE_ALLY = 46619,
SPELL_DK_THRASH = 47480,
SPELL_GHOUL_FRENZY = 62218,
// Proc system spells
SPELL_DK_ACCLIMATION_HOLY = 50490,
SPELL_DK_ACCLIMATION_FIRE = 50362,
SPELL_DK_ACCLIMATION_FROST = 50485,
SPELL_DK_ACCLIMATION_ARCANE = 50486,
SPELL_DK_ACCLIMATION_SHADOW = 50489,
SPELL_DK_ACCLIMATION_NATURE = 50488,
SPELL_DK_ADVANTAGE_T10_4P_MELEE = 70657,
SPELL_DK_BUTCHERY_RUNIC_POWER = 50163,
SPELL_DK_MARK_OF_BLOOD_HEAL = 61607,
SPELL_DK_UNHOLY_BLIGHT_DOT = 50536,
SPELL_DK_GLYPH_OF_UNHOLY_BLIGHT = 63332,
SPELL_DK_VENDETTA_HEAL = 50181,
SPELL_DK_NECROSIS_DAMAGE = 51460,
SPELL_DK_RUNIC_RETURN = 61258,
SPELL_DK_DEATH_COIL_R1 = 47541,
SPELL_DK_DEATH_GRIP_INITIAL = 49576,
SPELL_DK_GLYPH_OF_SCOURGE_STRIKE_SCRIPT = 69961,
SPELL_DK_HOWLING_BLAST_R1 = 49184,
SPELL_DK_OBLITERATE_OFF_HAND_R1 = 66198,
SPELL_DK_FROST_STRIKE_OFF_HAND_R1 = 66196,
SPELL_DK_PLAGUE_STRIKE_OFF_HAND_R1 = 66216,
SPELL_DK_DEATH_STRIKE_OFF_HAND_R1 = 66188,
SPELL_DK_RUNE_STRIKE_OFF_HAND_R1 = 66217,
SPELL_DK_BLOOD_STRIKE_OFF_HAND_R1 = 66215,
SPELL_DK_KILLING_MACHINE = 51124,
};
enum DeathKnightSpellIcons
{
DK_ICON_ID_IMPROVED_DEATH_STRIKE = 2751
DK_ICON_ID_IMPROVED_DEATH_STRIKE = 2751,
DK_ICON_ID_IMPROVED_BLOOD_PRESENCE = 2636,
DK_ICON_ID_BUTCHERY = 2664,
DK_ICON_ID_NECROSIS = 2709,
DK_ICON_ID_THREAT_OF_THASSARIAN = 2023,
DK_ICON_ID_SUDDEN_DOOM = 1939,
DK_ICON_ID_EPIDEMIC = 234
};
enum Misc
@@ -494,10 +526,14 @@ class spell_dk_wandering_plague_aura : public AuraScript
}
// xinef: prevent default proc with castItem passed, which applies 30 sec cooldown to procing of the aura
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
void HandleProc(ProcEventInfo& eventInfo)
{
PreventDefaultAction();
AuraEffect const* aurEff = GetEffect(EFFECT_0);
if (!aurEff)
return;
eventInfo.GetActor()->AddSpellCooldown(SPELL_DK_WANDERING_PLAGUE_TRIGGER, 0, 1000);
eventInfo.GetActor()->CastCustomSpell(SPELL_DK_WANDERING_PLAGUE_TRIGGER, SPELLVALUE_BASE_POINT0, CalculatePct<int32, int32>(eventInfo.GetDamageInfo()->GetDamage(), aurEff->GetAmount()), eventInfo.GetActionTarget(), TRIGGERED_FULL_MASK);
}
@@ -505,7 +541,7 @@ class spell_dk_wandering_plague_aura : public AuraScript
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dk_wandering_plague_aura::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dk_wandering_plague_aura::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
OnProc += AuraProcFn(spell_dk_wandering_plague_aura::HandleProc);
}
};
@@ -881,6 +917,119 @@ class spell_dk_pet_scaling : public AuraScript
}
};
// -49200 - Acclimation
class spell_dk_acclimation : public AuraScript
{
PrepareAuraScript(spell_dk_acclimation);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_DK_ACCLIMATION_HOLY,
SPELL_DK_ACCLIMATION_FIRE,
SPELL_DK_ACCLIMATION_NATURE,
SPELL_DK_ACCLIMATION_FROST,
SPELL_DK_ACCLIMATION_SHADOW,
SPELL_DK_ACCLIMATION_ARCANE
});
}
bool CheckProc(ProcEventInfo& eventInfo)
{
if (DamageInfo* damageInfo = eventInfo.GetDamageInfo())
{
switch (GetFirstSchoolInMask(damageInfo->GetSchoolMask()))
{
case SPELL_SCHOOL_HOLY:
case SPELL_SCHOOL_FIRE:
case SPELL_SCHOOL_NATURE:
case SPELL_SCHOOL_FROST:
case SPELL_SCHOOL_SHADOW:
case SPELL_SCHOOL_ARCANE:
return true;
default:
break;
}
}
return false;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
uint32 triggerspell = 0;
switch (GetFirstSchoolInMask(eventInfo.GetDamageInfo()->GetSchoolMask()))
{
case SPELL_SCHOOL_HOLY:
triggerspell = SPELL_DK_ACCLIMATION_HOLY;
break;
case SPELL_SCHOOL_FIRE:
triggerspell = SPELL_DK_ACCLIMATION_FIRE;
break;
case SPELL_SCHOOL_NATURE:
triggerspell = SPELL_DK_ACCLIMATION_NATURE;
break;
case SPELL_SCHOOL_FROST:
triggerspell = SPELL_DK_ACCLIMATION_FROST;
break;
case SPELL_SCHOOL_SHADOW:
triggerspell = SPELL_DK_ACCLIMATION_SHADOW;
break;
case SPELL_SCHOOL_ARCANE:
triggerspell = SPELL_DK_ACCLIMATION_ARCANE;
break;
default:
return;
}
if (Unit* target = eventInfo.GetActionTarget())
target->CastSpell(target, triggerspell, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dk_acclimation::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dk_acclimation::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// 70656 - Advantage T10 4P (DK)
class spell_dk_advantage_t10_4p : public AuraScript
{
PrepareAuraScript(spell_dk_advantage_t10_4p);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_ADVANTAGE_T10_4P_MELEE });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
if (Unit* caster = eventInfo.GetActor())
{
Player* player = caster->ToPlayer();
if (!player || player->getClass() != CLASS_DEATH_KNIGHT)
return false;
for (uint8 i = 0; i < MAX_RUNES; ++i)
if (player->GetRuneCooldown(i) == 0)
return false;
return true;
}
return false;
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dk_advantage_t10_4p::CheckProc);
}
};
// 50462 - Anti-Magic Zone (on raid member)
class spell_dk_anti_magic_shell_raid : public AuraScript
{
@@ -2314,16 +2463,164 @@ class spell_dk_army_of_the_dead_passive : public AuraScript
}
};
// -50163 - Butchery
class spell_dk_butchery : public AuraScript
{
PrepareAuraScript(spell_dk_butchery);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_BUTCHERY_RUNIC_POWER });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->CastCustomSpell(SPELL_DK_BUTCHERY_RUNIC_POWER, SPELLVALUE_BASE_POINT0, aurEff->GetAmount(), GetTarget(), true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dk_butchery::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 49005 - Mark of Blood
class spell_dk_mark_of_blood : public AuraScript
{
PrepareAuraScript(spell_dk_mark_of_blood);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_MARK_OF_BLOOD_HEAL });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
// Heal the target that the marked enemy attacked (from TrinityCore)
eventInfo.GetActor()->CastSpell(eventInfo.GetActionTarget(), SPELL_DK_MARK_OF_BLOOD_HEAL, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dk_mark_of_blood::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 49194 - Unholy Blight
class spell_dk_unholy_blight : public AuraScript
{
PrepareAuraScript(spell_dk_unholy_blight);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_UNHOLY_BLIGHT_DOT, SPELL_DK_GLYPH_OF_UNHOLY_BLIGHT });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
return damageInfo && damageInfo->GetDamage();
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = GetCaster();
Unit* target = eventInfo.GetActionTarget();
if (!caster || !target)
return;
SpellInfo const* unholyBlight = sSpellMgr->GetSpellInfo(SPELL_DK_UNHOLY_BLIGHT_DOT);
if (!unholyBlight)
return;
int32 bp = CalculatePct(static_cast<int32>(eventInfo.GetDamageInfo()->GetDamage()), aurEff->GetAmount());
// Glyph of Unholy Blight
if (AuraEffect* glyph = caster->GetAuraEffect(SPELL_DK_GLYPH_OF_UNHOLY_BLIGHT, EFFECT_0))
AddPct(bp, glyph->GetAmount());
bp = bp / (unholyBlight->GetMaxDuration() / unholyBlight->Effects[EFFECT_0].Amplitude);
target->CastDelayedSpellWithPeriodicAmount(caster, SPELL_DK_UNHOLY_BLIGHT_DOT, SPELL_AURA_PERIODIC_DAMAGE, bp);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dk_unholy_blight::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dk_unholy_blight::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -50181 - Vendetta
class spell_dk_vendetta : public AuraScript
{
PrepareAuraScript(spell_dk_vendetta);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_VENDETTA_HEAL });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Unit* target = GetTarget();
int32 bp = target->CountPctFromMaxHealth(aurEff->GetAmount());
target->CastCustomSpell(SPELL_DK_VENDETTA_HEAL, SPELLVALUE_BASE_POINT0, bp, target, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dk_vendetta::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -51459 - Necrosis
class spell_dk_necrosis : public AuraScript
{
PrepareAuraScript(spell_dk_necrosis);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_NECROSIS_DAMAGE });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
return damageInfo && damageInfo->GetDamage();
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = GetTarget();
Unit* target = eventInfo.GetActionTarget();
int32 bp = CalculatePct(static_cast<int32>(eventInfo.GetDamageInfo()->GetDamage()), aurEff->GetAmount());
caster->CastCustomSpell(SPELL_DK_NECROSIS_DAMAGE, SPELLVALUE_BASE_POINT0, bp, target, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dk_necrosis::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dk_necrosis::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -49182 Blade Barrier
class spell_dk_blade_barrier : public AuraScript
{
PrepareAuraScript(spell_dk_blade_barrier);
bool CheckProc(ProcEventInfo& /*eventInfo*/)
bool CheckProc(ProcEventInfo& eventInfo)
{
if (Player* player = GetCaster()->ToPlayer())
if (player->getClass() == CLASS_DEATH_KNIGHT && player->IsBaseRuneSlotsOnCooldown(RUNE_BLOOD))
return true;
if (eventInfo.GetSpellInfo())
if (Player* player = eventInfo.GetActor()->ToPlayer())
if (player->getClass() == CLASS_DEATH_KNIGHT && player->IsBaseRuneSlotsOnCooldown(RUNE_BLOOD))
return true;
return false;
}
@@ -2334,6 +2631,359 @@ class spell_dk_blade_barrier : public AuraScript
}
};
// -49208, -49467, -54639 - Death Rune
class spell_dk_death_rune : public AuraScript
{
PrepareAuraScript(spell_dk_death_rune);
bool Load() override
{
return GetUnitOwner()->IsPlayer() && GetUnitOwner()->ToPlayer()->getClass() == CLASS_DEATH_KNIGHT;
}
bool CheckProc(ProcEventInfo& eventInfo)
{
Unit* caster = eventInfo.GetActor();
if (!caster || !caster->IsPlayer())
return false;
Player* player = caster->ToPlayer();
if (player->getClass() != CLASS_DEATH_KNIGHT)
return false;
return true;
}
void HandleProc(ProcEventInfo& eventInfo)
{
Player* player = eventInfo.GetActor()->ToPlayer();
AuraEffect* aurEff = GetEffect(EFFECT_0);
if (!aurEff)
return;
// Reset amplitude - set death rune remove timer to 30s
aurEff->ResetPeriodic(true);
uint32 runesLeft = 1;
// Death Rune Mastery (SpellIconID 2622)
if (GetSpellInfo()->SpellIconID == 2622)
runesLeft = 2;
for (uint8 i = 0; i < MAX_RUNES && runesLeft; ++i)
{
if (GetSpellInfo()->SpellIconID == 2622)
{
if (player->GetBaseRune(i) == RUNE_BLOOD)
continue;
}
else
{
if (player->GetBaseRune(i) != RUNE_BLOOD)
continue;
}
// Check if rune just went on cooldown
if (player->GetRuneCooldown(i) != player->GetRuneBaseCooldown(i, false))
continue;
--runesLeft;
player->AddRuneByAuraEffect(i, RUNE_DEATH, aurEff);
}
}
void PeriodicTick(AuraEffect const* aurEff)
{
GetTarget()->ToPlayer()->RemoveRunesByAuraEffect(aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dk_death_rune::CheckProc);
OnProc += AuraProcFn(spell_dk_death_rune::HandleProc);
OnEffectPeriodic += AuraEffectPeriodicFn(spell_dk_death_rune::PeriodicTick, EFFECT_0, SPELL_AURA_PERIODIC_DUMMY);
}
};
// -49188 - Rime
class spell_dk_rime : public AuraScript
{
PrepareAuraScript(spell_dk_rime);
bool CheckProc(ProcEventInfo& /*eventInfo*/)
{
return GetTarget()->IsPlayer();
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& /*eventInfo*/)
{
Player* player = GetTarget()->ToPlayer();
if (!player)
return;
// Reset cooldown of Howling Blast (all ranks)
SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(SPELL_DK_HOWLING_BLAST_R1);
while (spellInfo)
{
player->RemoveSpellCooldown(spellInfo->Id, true);
spellInfo = spellInfo->GetNextRankSpell();
}
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dk_rime::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dk_rime::HandleProc, EFFECT_1, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// 51124 - Killing Machine
class spell_dk_killing_machine : public AuraScript
{
PrepareAuraScript(spell_dk_killing_machine);
void HandleEffectCalcSpellMod(AuraEffect const* /*aurEff*/, SpellModifier*& spellMod)
{
if (spellMod)
{
// Icy Touch (mask0=2), Frost Strike (mask1=4), Howling Blast (mask1=2)
spellMod->mask = flag96(2, 6, 0);
}
}
void Register() override
{
DoEffectCalcSpellMod += AuraEffectCalcSpellModFn(spell_dk_killing_machine::HandleEffectCalcSpellMod, EFFECT_0, SPELL_AURA_ADD_FLAT_MODIFIER);
}
};
// -49018 - Sudden Doom
class spell_dk_sudden_doom : public AuraScript
{
PrepareAuraScript(spell_dk_sudden_doom);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_DEATH_COIL_R1 });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = eventInfo.GetActor();
SpellInfo const* spellInfo = sSpellMgr->AssertSpellInfo(SPELL_DK_DEATH_COIL_R1);
uint32 spellId = 0;
while (spellInfo)
{
if (!caster->HasSpell(spellInfo->Id))
break;
spellId = spellInfo->Id;
spellInfo = spellInfo->GetNextRankSpell();
}
if (!spellId)
return;
caster->CastSpell(eventInfo.GetActionTarget(), spellId, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dk_sudden_doom::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -65661 - Threat of Thassarian
class spell_dk_threat_of_thassarian : public AuraScript
{
PrepareAuraScript(spell_dk_threat_of_thassarian);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({
SPELL_DK_OBLITERATE_OFF_HAND_R1,
SPELL_DK_FROST_STRIKE_OFF_HAND_R1,
SPELL_DK_PLAGUE_STRIKE_OFF_HAND_R1,
SPELL_DK_DEATH_STRIKE_OFF_HAND_R1,
SPELL_DK_RUNE_STRIKE_OFF_HAND_R1,
SPELL_DK_BLOOD_STRIKE_OFF_HAND_R1
});
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
if (!roll_chance_i(aurEff->GetAmount()))
return;
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return;
Unit* caster = eventInfo.GetActor();
if (!caster->haveOffhandWeapon())
return;
uint32 spellId = 0;
// Plague Strike
if (spellInfo->SpellFamilyFlags[0] & 0x00000001)
spellId = SPELL_DK_PLAGUE_STRIKE_OFF_HAND_R1;
// Death Strike
else if (spellInfo->SpellFamilyFlags[0] & 0x00000010)
spellId = SPELL_DK_DEATH_STRIKE_OFF_HAND_R1;
// Blood Strike
else if (spellInfo->SpellFamilyFlags[0] & 0x00400000)
spellId = SPELL_DK_BLOOD_STRIKE_OFF_HAND_R1;
// Frost Strike
else if (spellInfo->SpellFamilyFlags[1] & 0x00000004)
spellId = SPELL_DK_FROST_STRIKE_OFF_HAND_R1;
// Obliterate
else if (spellInfo->SpellFamilyFlags[1] & 0x00020000)
spellId = SPELL_DK_OBLITERATE_OFF_HAND_R1;
// Rune Strike
else if (spellInfo->SpellFamilyFlags[1] & 0x20000000)
spellId = SPELL_DK_RUNE_STRIKE_OFF_HAND_R1;
if (!spellId)
return;
Unit* target = eventInfo.GetActionTarget();
if (!target)
return;
spellId = sSpellMgr->GetSpellWithRank(spellId, spellInfo->GetRank());
caster->CastSpell(target, spellId, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dk_threat_of_thassarian::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 62259 - Glyph of Death Grip
class spell_dk_glyph_of_death_grip : public AuraScript
{
PrepareAuraScript(spell_dk_glyph_of_death_grip);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_DEATH_GRIP_INITIAL });
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
if (Player* player = eventInfo.GetActor()->ToPlayer())
player->RemoveSpellCooldown(SPELL_DK_DEATH_GRIP_INITIAL, true);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dk_glyph_of_death_grip::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// 58642 - Glyph of Scourge Strike
class spell_dk_glyph_of_scourge_strike : public AuraScript
{
PrepareAuraScript(spell_dk_glyph_of_scourge_strike);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_GLYPH_OF_SCOURGE_STRIKE_SCRIPT });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
eventInfo.GetActor()->CastSpell(eventInfo.GetActionTarget(), SPELL_DK_GLYPH_OF_SCOURGE_STRIKE_SCRIPT, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dk_glyph_of_scourge_strike::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 69961 - Glyph of Scourge Strike (script effect)
class spell_dk_glyph_of_scourge_strike_script : public SpellScript
{
PrepareSpellScript(spell_dk_glyph_of_scourge_strike_script);
void HandleScriptEffect(SpellEffIndex /*effIndex*/)
{
Unit* caster = GetCaster();
Unit* target = GetHitUnit();
Unit::AuraEffectList const& mPeriodic = target->GetAuraEffectsByType(SPELL_AURA_PERIODIC_DAMAGE);
for (Unit::AuraEffectList::const_iterator i = mPeriodic.begin(); i != mPeriodic.end(); ++i)
{
AuraEffect const* aurEff = *i;
SpellInfo const* spellInfo = aurEff->GetSpellInfo();
// Search Blood Plague and Frost Fever on target
if (spellInfo->SpellFamilyName == SPELLFAMILY_DEATHKNIGHT && (spellInfo->SpellFamilyFlags[2] & 0x2) &&
aurEff->GetCasterGUID() == caster->GetGUID())
{
uint32 countMin = aurEff->GetBase()->GetMaxDuration();
uint32 countMax = spellInfo->GetMaxDuration();
// this Glyph
countMax += 9000;
// talent Epidemic
if (AuraEffect const* epidemic = caster->GetAuraEffect(SPELL_AURA_ADD_FLAT_MODIFIER, SPELLFAMILY_DEATHKNIGHT, DK_ICON_ID_EPIDEMIC, EFFECT_0))
countMax += epidemic->GetAmount();
if (countMin < countMax)
{
aurEff->GetBase()->SetDuration(aurEff->GetBase()->GetDuration() + 3000);
aurEff->GetBase()->SetMaxDuration(countMin + 3000);
}
}
}
}
void Register() override
{
OnEffectHitTarget += SpellEffectFn(spell_dk_glyph_of_scourge_strike_script::HandleScriptEffect, EFFECT_0, SPELL_EFFECT_SCRIPT_EFFECT);
}
};
// 61257 - PvP 4P Bonus (Runic Power on Snare/Root)
class spell_dk_pvp_4p_bonus : public AuraScript
{
PrepareAuraScript(spell_dk_pvp_4p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DK_RUNIC_RETURN });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return false;
return (spellInfo->GetAllEffectsMechanicMask() & ((1 << MECHANIC_ROOT) | (1 << MECHANIC_SNARE))) != 0;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
eventInfo.GetActionTarget()->CastSpell(nullptr, SPELL_DK_RUNIC_RETURN, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dk_pvp_4p_bonus::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dk_pvp_4p_bonus::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
void AddSC_deathknight_spell_scripts()
{
RegisterSpellScript(spell_dk_wandering_plague);
@@ -2355,6 +3005,8 @@ void AddSC_deathknight_spell_scripts()
RegisterSpellScript(spell_dk_dancing_rune_weapon_visual);
RegisterSpellScript(spell_dk_scent_of_blood_trigger);
RegisterSpellScript(spell_dk_pet_scaling);
RegisterSpellScript(spell_dk_acclimation);
RegisterSpellScript(spell_dk_advantage_t10_4p);
RegisterSpellScript(spell_dk_anti_magic_shell_raid);
RegisterSpellScript(spell_dk_anti_magic_shell_self);
RegisterSpellScript(spell_dk_anti_magic_zone);
@@ -2382,5 +3034,20 @@ void AddSC_deathknight_spell_scripts()
RegisterSpellScript(spell_dk_will_of_the_necropolis);
RegisterSpellScript(spell_dk_ghoul_thrash);
RegisterSpellScript(spell_dk_army_of_the_dead_passive);
// Proc system scripts
RegisterSpellScript(spell_dk_butchery);
RegisterSpellScript(spell_dk_mark_of_blood);
RegisterSpellScript(spell_dk_unholy_blight);
RegisterSpellScript(spell_dk_vendetta);
RegisterSpellScript(spell_dk_necrosis);
RegisterSpellScript(spell_dk_blade_barrier);
RegisterSpellScript(spell_dk_death_rune);
RegisterSpellScript(spell_dk_rime);
RegisterSpellScript(spell_dk_killing_machine);
RegisterSpellScript(spell_dk_sudden_doom);
RegisterSpellScript(spell_dk_threat_of_thassarian);
RegisterSpellScript(spell_dk_glyph_of_death_grip);
RegisterSpellScript(spell_dk_glyph_of_scourge_strike);
RegisterSpellScript(spell_dk_glyph_of_scourge_strike_script);
RegisterSpellScript(spell_dk_pvp_4p_bonus);
}

View File

@@ -17,6 +17,7 @@
#include "Containers.h"
#include "CreatureScript.h"
#include "GameTime.h"
#include "GridNotifiers.h"
#include "Player.h"
#include "SpellAuraEffects.h"
@@ -60,12 +61,52 @@ enum DruidSpells
SPELL_DRUID_ENRAGE = 5229,
SPELL_DRUID_ENRAGED_DEFENSE = 70725,
SPELL_DRUID_ITEM_T10_FERAL_4P_BONUS = 70726,
SPELL_DRUID_MOONGLADE_2P_BONUS = 37286
SPELL_DRUID_MAIM_INTERRUPT = 32747,
SPELL_DRUID_MOONGLADE_2P_BONUS = 37286,
// Proc system spells
SPELL_DRUID_GLYPH_OF_INNERVATE_MANA = 54833,
SPELL_DRUID_GLYPH_OF_STARFIRE_PROC = 54846,
SPELL_DRUID_GLYPH_OF_RAKE_STUN = 54820,
SPELL_DRUID_LEADER_OF_THE_PACK_HEAL = 34299,
SPELL_DRUID_LEADER_OF_THE_PACK_MANA = 68285,
SPELL_DRUID_GLYPH_OF_REJUV_HEAL = 54755,
SPELL_DRUID_ECLIPSE_LUNAR = 48518,
SPELL_DRUID_ECLIPSE_SOLAR = 48517,
SPELL_DRUID_T3_PROC_ENERGIZE_MANA = 28722,
SPELL_DRUID_T3_PROC_ENERGIZE_RAGE = 28723,
SPELL_DRUID_T3_PROC_ENERGIZE_ENERGY = 28724,
SPELL_DRUID_BLESSING_OF_THE_CLAW = 28750,
SPELL_DRUID_EXHILARATE = 28742,
SPELL_DRUID_INFUSION = 37238,
SPELL_DRUID_BLESSING_OF_REMULOS = 40445,
SPELL_DRUID_BLESSING_OF_ELUNE = 40446,
SPELL_DRUID_BLESSING_OF_CENARIUS = 40452,
SPELL_DRUID_REVITALIZE_ENERGIZE_MANA = 48542,
SPELL_DRUID_REVITALIZE_ENERGIZE_RAGE = 48541,
SPELL_DRUID_REVITALIZE_ENERGIZE_ENERGY = 48540,
SPELL_DRUID_REVITALIZE_ENERGIZE_RP = 48543,
SPELL_DRUID_GLYPH_OF_RIP = 54818,
SPELL_DRUID_RIP_DURATION_LACERATE_DMG = 60141,
SPELL_DRUID_REJUVENATION_T10_PROC = 70691,
SPELL_DRUID_LANGUISH = 71023,
// T9 Feral Relic
SPELL_DRUID_T9_FERAL_RELIC_BEAR = 67354,
SPELL_DRUID_T9_FERAL_RELIC_CAT = 67355,
// Frenzied Regeneration
SPELL_DRUID_FRENZIED_REGENERATION_HEAL = 22845,
// Insect Swarm
SPELL_DRUID_ITEM_T8_BALANCE_RELIC = 64950,
// Nourish
SPELL_DRUID_GLYPH_OF_NOURISH = 62971,
// Wild Growth
SPELL_DRUID_RESTORATION_T10_2P_BONUS = 70658
};
enum DruidIcons
{
SPELL_ICON_REVITALIZE = 2862
SPELL_ICON_REVITALIZE = 2862,
SPELL_ICON_ECLIPSE = 2856,
SPELL_ICON_INNERVATE = 62
};
// 1178 - Bear Form (Passive)
@@ -113,27 +154,27 @@ class spell_dru_t10_balance_4p_bonus : public AuraScript
{
PrepareAuraScript(spell_dru_t10_balance_4p_bonus);
bool CheckProc(ProcEventInfo& eventInfo)
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return eventInfo.GetActor() && eventInfo.GetProcTarget();
return ValidateSpellInfo({ SPELL_DRUID_LANGUISH });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
uint32 triggered_spell_id = 71023;
SpellInfo const* triggeredSpell = sSpellMgr->GetSpellInfo(triggered_spell_id);
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
int32 amount = CalculatePct(eventInfo.GetDamageInfo()->GetDamage(), aurEff->GetAmount()) / triggeredSpell->GetMaxTicks();
eventInfo.GetProcTarget()->CastDelayedSpellWithPeriodicAmount(GetTarget(), triggered_spell_id, SPELL_AURA_PERIODIC_DAMAGE, amount, EFFECT_0);
SpellInfo const* triggeredSpell = sSpellMgr->GetSpellInfo(SPELL_DRUID_LANGUISH);
//GetTarget()->CastCustomSpell(triggered_spell_id, SPELLVALUE_BASE_POINT0, amount, eventInfo.GetProcTarget(), true, nullptr, aurEff);
int32 amount = CalculatePct(static_cast<int32>(damageInfo->GetDamage()), aurEff->GetAmount()) / triggeredSpell->GetMaxTicks();
eventInfo.GetProcTarget()->CastDelayedSpellWithPeriodicAmount(GetTarget(), SPELL_DRUID_LANGUISH, SPELL_AURA_PERIODIC_DAMAGE, amount, EFFECT_0);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dru_t10_balance_4p_bonus::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dru_t10_balance_4p_bonus::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
@@ -286,21 +327,41 @@ class spell_dru_barkskin : public AuraScript
{
PrepareAuraScript(spell_dru_barkskin);
void AfterApply(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
bool Validate(SpellInfo const* /*spellInfo*/) override
{
if (GetUnitOwner()->HasAura(SPELL_DRUID_GLYPH_OF_BARKSKIN, GetUnitOwner()->GetGUID()))
GetUnitOwner()->CastSpell(GetUnitOwner(), SPELL_DRUID_GLYPH_OF_BARKSKIN_TRIGGER, true);
return ValidateSpellInfo({ SPELL_DRUID_GLYPH_OF_BARKSKIN_TRIGGER });
}
void AfterRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
void OnRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
{
GetUnitOwner()->RemoveAurasDueToSpell(SPELL_DRUID_GLYPH_OF_BARKSKIN_TRIGGER, GetUnitOwner()->GetGUID());
GetTarget()->RemoveAurasDueToSpell(SPELL_DRUID_GLYPH_OF_BARKSKIN_TRIGGER);
}
void Register() override
{
AfterEffectApply += AuraEffectApplyFn(spell_dru_barkskin::AfterApply, EFFECT_0, SPELL_AURA_ANY, AURA_EFFECT_HANDLE_REAL);
AfterEffectRemove += AuraEffectRemoveFn(spell_dru_barkskin::AfterRemove, EFFECT_0, SPELL_AURA_ANY, AURA_EFFECT_HANDLE_REAL);
AfterEffectRemove += AuraEffectRemoveFn(spell_dru_barkskin::OnRemove, EFFECT_1, SPELL_AURA_MOD_DAMAGE_PERCENT_TAKEN, AURA_EFFECT_HANDLE_REAL);
}
};
// 63057 - Glyph of Barkskin
class spell_dru_glyph_of_barkskin : public AuraScript
{
PrepareAuraScript(spell_dru_glyph_of_barkskin);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_GLYPH_OF_BARKSKIN_TRIGGER });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
eventInfo.GetActor()->CastSpell(eventInfo.GetActor(), SPELL_DRUID_GLYPH_OF_BARKSKIN_TRIGGER, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_glyph_of_barkskin::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
@@ -1265,6 +1326,773 @@ private:
ObjectGuid _casterGUID;
};
// 54832 - Glyph of Innervate
class spell_dru_glyph_of_innervate : public AuraScript
{
PrepareAuraScript(spell_dru_glyph_of_innervate);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_GLYPH_OF_INNERVATE_MANA });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
return spellInfo && spellInfo->SpellIconID == SPELL_ICON_INNERVATE;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Unit* caster = GetTarget();
int32 manaPercent = aurEff->GetAmount();
int32 bp = caster->GetCreatePowers(POWER_MANA) * manaPercent / 100 / 10;
caster->CastCustomSpell(SPELL_DRUID_GLYPH_OF_INNERVATE_MANA, SPELLVALUE_BASE_POINT0, bp, caster, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dru_glyph_of_innervate::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dru_glyph_of_innervate::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 54821 - Glyph of Rake
class spell_dru_glyph_of_rake : public AuraScript
{
PrepareAuraScript(spell_dru_glyph_of_rake);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_GLYPH_OF_RAKE_STUN });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return false;
// Check if it's Rake (SpellVisual 750 and Effect 1 is periodic damage)
if (spellInfo->SpellVisual[0] != 750 || spellInfo->Effects[EFFECT_1].ApplyAuraName != SPELL_AURA_PERIODIC_DAMAGE)
return false;
Unit* target = eventInfo.GetActionTarget();
return target && target->IsCreature();
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
GetTarget()->CastSpell(eventInfo.GetActionTarget(), SPELL_DRUID_GLYPH_OF_RAKE_STUN, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dru_glyph_of_rake::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dru_glyph_of_rake::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 24932 - Leader of the Pack
class spell_dru_leader_of_the_pack : public AuraScript
{
PrepareAuraScript(spell_dru_leader_of_the_pack);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_LEADER_OF_THE_PACK_HEAL, SPELL_DRUID_LEADER_OF_THE_PACK_MANA });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Unit* target = GetTarget();
int32 healAmount = aurEff->GetAmount();
if (healAmount <= 0)
return;
// 6 second internal cooldown
if (target->IsPlayer() && target->ToPlayer()->HasSpellCooldown(SPELL_DRUID_LEADER_OF_THE_PACK_HEAL))
return;
int32 bp = target->CountPctFromMaxHealth(healAmount);
target->CastCustomSpell(SPELL_DRUID_LEADER_OF_THE_PACK_HEAL, SPELLVALUE_BASE_POINT0, bp, target, true, nullptr, aurEff);
if (target->IsPlayer())
target->ToPlayer()->AddSpellCooldown(SPELL_DRUID_LEADER_OF_THE_PACK_HEAL, 0, 6 * IN_MILLISECONDS);
// Improved Leader of the Pack - mana regen (only for self-cast aura)
if (aurEff->GetCasterGUID() == target->GetGUID())
{
int32 manaAmount = CalculatePct(target->GetMaxPower(POWER_MANA), healAmount * 2);
target->CastCustomSpell(SPELL_DRUID_LEADER_OF_THE_PACK_MANA, SPELLVALUE_BASE_POINT0, manaAmount, target, true, nullptr, aurEff);
}
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_leader_of_the_pack::HandleProc, EFFECT_1, SPELL_AURA_DUMMY);
}
};
// 54754 - Glyph of Rejuvenation
class spell_dru_glyph_of_rejuvenation : public AuraScript
{
PrepareAuraScript(spell_dru_glyph_of_rejuvenation);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_GLYPH_OF_REJUV_HEAL });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
Unit* target = eventInfo.GetActionTarget();
if (!target)
return false;
// Only proc if target is below health threshold
return target->HealthBelowPct(GetSpellInfo()->Effects[EFFECT_0].CalcValue());
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
int32 bp = CalculatePct(static_cast<int32>(eventInfo.GetHealInfo()->GetHeal()), aurEff->GetAmount());
GetTarget()->CastCustomSpell(SPELL_DRUID_GLYPH_OF_REJUV_HEAL, SPELLVALUE_BASE_POINT0, bp, eventInfo.GetActionTarget(), true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dru_glyph_of_rejuvenation::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dru_glyph_of_rejuvenation::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -48516 - Eclipse
class spell_dru_eclipse : public AuraScript
{
PrepareAuraScript(spell_dru_eclipse);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_ECLIPSE_LUNAR, SPELL_DRUID_ECLIPSE_SOLAR });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return false;
Unit* target = GetTarget();
if (!target->IsPlayer())
return false;
bool isWrathSpell = (spellInfo->SpellFamilyFlags[0] & 1);
bool isStarfireSpell = (spellInfo->SpellFamilyFlags[0] & 4);
// Must be Wrath or Starfire
if (!isWrathSpell && !isStarfireSpell)
return false;
// Check 30 second internal cooldown
uint32 now = GameTime::GetGameTimeMS().count();
if (isWrathSpell && _lunarProcCooldownEnd > now)
return false;
if (isStarfireSpell && _solarProcCooldownEnd > now)
return false;
// Don't proc if already have any eclipse aura
if (target->HasAura(SPELL_DRUID_ECLIPSE_LUNAR) || target->HasAura(SPELL_DRUID_ECLIPSE_SOLAR))
return false;
// Check proc chance (60% for Wrath, 100% for Starfire)
if (!roll_chance_f(GetSpellInfo()->ProcChance * (isWrathSpell ? 0.6f : 1.0f)))
return false;
return true;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
bool isWrathSpell = (spellInfo->SpellFamilyFlags[0] & 1);
uint32 triggeredSpell = isWrathSpell ? SPELL_DRUID_ECLIPSE_LUNAR : SPELL_DRUID_ECLIPSE_SOLAR;
// Set 30 second internal cooldown
uint32 now = GameTime::GetGameTimeMS().count();
if (isWrathSpell)
_lunarProcCooldownEnd = now + 30000;
else
_solarProcCooldownEnd = now + 30000;
GetTarget()->CastSpell(GetTarget(), triggeredSpell, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dru_eclipse::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dru_eclipse::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
private:
uint32 _lunarProcCooldownEnd = 0;
uint32 _solarProcCooldownEnd = 0;
};
// -48539 - Revitalize
class spell_dru_revitalize : public AuraScript
{
PrepareAuraScript(spell_dru_revitalize);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({
SPELL_DRUID_REVITALIZE_ENERGIZE_MANA,
SPELL_DRUID_REVITALIZE_ENERGIZE_RAGE,
SPELL_DRUID_REVITALIZE_ENERGIZE_ENERGY,
SPELL_DRUID_REVITALIZE_ENERGIZE_RP
});
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
if (!roll_chance_i(aurEff->GetAmount()))
return;
Unit* target = eventInfo.GetActionTarget();
uint32 spellId;
switch (target->getPowerType())
{
case POWER_MANA:
spellId = SPELL_DRUID_REVITALIZE_ENERGIZE_MANA;
break;
case POWER_RAGE:
spellId = SPELL_DRUID_REVITALIZE_ENERGIZE_RAGE;
break;
case POWER_ENERGY:
spellId = SPELL_DRUID_REVITALIZE_ENERGIZE_ENERGY;
break;
case POWER_RUNIC_POWER:
spellId = SPELL_DRUID_REVITALIZE_ENERGIZE_RP;
break;
default:
return;
}
eventInfo.GetActor()->CastSpell(target, spellId, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_revitalize::HandleProc, EFFECT_0, SPELL_AURA_OVERRIDE_CLASS_SCRIPTS);
}
};
// 28716 - Rejuvenation (T3 2P Bonus)
class spell_dru_t3_2p_bonus : public AuraScript
{
PrepareAuraScript(spell_dru_t3_2p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({
SPELL_DRUID_T3_PROC_ENERGIZE_MANA,
SPELL_DRUID_T3_PROC_ENERGIZE_RAGE,
SPELL_DRUID_T3_PROC_ENERGIZE_ENERGY
});
}
bool CheckProc(ProcEventInfo& /*eventInfo*/)
{
return roll_chance_i(50);
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* target = eventInfo.GetActionTarget();
uint32 spellId;
switch (target->getPowerType())
{
case POWER_MANA:
spellId = SPELL_DRUID_T3_PROC_ENERGIZE_MANA;
break;
case POWER_RAGE:
spellId = SPELL_DRUID_T3_PROC_ENERGIZE_RAGE;
break;
case POWER_ENERGY:
spellId = SPELL_DRUID_T3_PROC_ENERGIZE_ENERGY;
break;
default:
return;
}
eventInfo.GetActor()->CastSpell(target, spellId, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dru_t3_2p_bonus::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dru_t3_2p_bonus::HandleProc, EFFECT_0, SPELL_AURA_OVERRIDE_CLASS_SCRIPTS);
}
};
// 28744 - Regrowth (T3 6P Bonus)
class spell_dru_t3_6p_bonus : public AuraScript
{
PrepareAuraScript(spell_dru_t3_6p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_BLESSING_OF_THE_CLAW });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
eventInfo.GetActor()->CastSpell(eventInfo.GetActionTarget(), SPELL_DRUID_BLESSING_OF_THE_CLAW, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_t3_6p_bonus::HandleProc, EFFECT_0, SPELL_AURA_OVERRIDE_CLASS_SCRIPTS);
}
};
// 28719 - Healing Touch (T3 8P Bonus)
class spell_dru_t3_8p_bonus : public AuraScript
{
PrepareAuraScript(spell_dru_t3_8p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_EXHILARATE });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return;
Unit* caster = eventInfo.GetActor();
int32 amount = CalculatePct(spellInfo->CalcPowerCost(caster, spellInfo->GetSchoolMask()), aurEff->GetAmount());
caster->CastCustomSpell(SPELL_DRUID_EXHILARATE, SPELLVALUE_BASE_POINT0, amount, caster, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_t3_8p_bonus::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 37288, 37295 - Mana Restore (T4 2P Bonus)
class spell_dru_t4_2p_bonus : public AuraScript
{
PrepareAuraScript(spell_dru_t4_2p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_INFUSION });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->CastSpell(nullptr, SPELL_DRUID_INFUSION, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_t4_2p_bonus::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 40442 - Druid Tier 6 Trinket
class spell_dru_item_t6_trinket : public AuraScript
{
PrepareAuraScript(spell_dru_item_t6_trinket);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({
SPELL_DRUID_BLESSING_OF_REMULOS,
SPELL_DRUID_BLESSING_OF_ELUNE,
SPELL_DRUID_BLESSING_OF_CENARIUS
});
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return;
uint32 spellId;
int32 chance;
// Starfire
if (spellInfo->SpellFamilyFlags[0] & 0x00000004)
{
spellId = SPELL_DRUID_BLESSING_OF_REMULOS;
chance = 25;
}
// Rejuvenation
else if (spellInfo->SpellFamilyFlags[0] & 0x00000010)
{
spellId = SPELL_DRUID_BLESSING_OF_ELUNE;
chance = 25;
}
// Mangle (Bear) and Mangle (Cat)
else if (spellInfo->SpellFamilyFlags[1] & 0x00000440)
{
spellId = SPELL_DRUID_BLESSING_OF_CENARIUS;
chance = 40;
}
else
return;
if (roll_chance_i(chance))
eventInfo.GetActor()->CastSpell(nullptr, spellId, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_item_t6_trinket::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 54815 - Glyph of Shred
class spell_dru_glyph_of_shred : public AuraScript
{
PrepareAuraScript(spell_dru_glyph_of_shred);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({
SPELL_DRUID_GLYPH_OF_RIP,
SPELL_DRUID_RIP_DURATION_LACERATE_DMG
});
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = eventInfo.GetActor();
// Try to find Rip on the target
if (AuraEffect const* rip = eventInfo.GetActionTarget()->GetAuraEffect(SPELL_AURA_PERIODIC_DAMAGE, SPELLFAMILY_DRUID, 0x00800000, 0x0, 0x0, caster->GetGUID()))
{
// Rip's max duration, includes modifiers like Glyph of Rip
uint32 countMin = rip->GetBase()->GetMaxDuration();
// Just Rip's max duration without other spells
uint32 countMax = rip->GetSpellInfo()->GetMaxDuration();
// Add possible auras' and Glyph of Shred's max duration
countMax += 3 * aurEff->GetAmount() * IN_MILLISECONDS; // Glyph of Shred -> +6 seconds
countMax += caster->HasAura(SPELL_DRUID_GLYPH_OF_RIP) ? 4 * IN_MILLISECONDS : 0; // Glyph of Rip -> +4 seconds
countMax += caster->HasAura(SPELL_DRUID_RIP_DURATION_LACERATE_DMG) ? 4 * IN_MILLISECONDS : 0; // T7 set bonus -> +4 seconds
// If min < max that means caster didn't cast 3 shred yet
if (countMin < countMax)
{
rip->GetBase()->SetDuration(rip->GetBase()->GetDuration() + aurEff->GetAmount() * IN_MILLISECONDS);
rip->GetBase()->SetMaxDuration(countMin + aurEff->GetAmount() * IN_MILLISECONDS);
}
}
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_glyph_of_shred::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 54845 - Glyph of Starfire (Dummy)
class spell_dru_glyph_of_starfire_dummy : public AuraScript
{
PrepareAuraScript(spell_dru_glyph_of_starfire_dummy);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_GLYPH_OF_STARFIRE_PROC });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
eventInfo.GetActor()->CastSpell(eventInfo.GetActionTarget(), SPELL_DRUID_GLYPH_OF_STARFIRE_PROC, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_glyph_of_starfire_dummy::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 70664 - Item - Druid T10 Restoration 4P Bonus (Rejuvenation)
class spell_dru_t10_restoration_4p_bonus_dummy : public AuraScript
{
PrepareAuraScript(spell_dru_t10_restoration_4p_bonus_dummy);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_REJUVENATION_T10_PROC });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo || spellInfo->Id == SPELL_DRUID_REJUVENATION_T10_PROC)
return false;
HealInfo* healInfo = eventInfo.GetHealInfo();
if (!healInfo || !healInfo->GetHeal())
return false;
Player* caster = eventInfo.GetActor()->ToPlayer();
if (!caster)
return false;
return caster->GetGroup() || caster != eventInfo.GetActionTarget();
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
int32 amount = eventInfo.GetHealInfo()->GetHeal();
eventInfo.GetActor()->CastCustomSpell(SPELL_DRUID_REJUVENATION_T10_PROC, SPELLVALUE_BASE_POINT0, amount, nullptr, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dru_t10_restoration_4p_bonus_dummy::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dru_t10_restoration_4p_bonus_dummy::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 44835 - Maim Interrupt
class spell_dru_maim_interrupt : public AuraScript
{
PrepareAuraScript(spell_dru_maim_interrupt);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_MAIM_INTERRUPT });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->CastSpell(GetTarget(), SPELL_DRUID_MAIM_INTERRUPT, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_dru_maim_interrupt::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 67353 - T9 Feral Relic (Idol of Mutilation)
class spell_dru_t9_feral_relic : public AuraScript
{
PrepareAuraScript(spell_dru_t9_feral_relic);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({
SPELL_DRUID_T9_FERAL_RELIC_BEAR,
SPELL_DRUID_T9_FERAL_RELIC_CAT
});
}
bool CheckProc(ProcEventInfo& eventInfo)
{
Unit* target = eventInfo.GetActor();
switch (target->GetShapeshiftForm())
{
case FORM_BEAR:
case FORM_DIREBEAR:
case FORM_CAT:
return true;
default:
break;
}
return false;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
uint32 triggerspell = 0;
Unit* target = eventInfo.GetActor();
switch (target->GetShapeshiftForm())
{
case FORM_BEAR:
case FORM_DIREBEAR:
triggerspell = SPELL_DRUID_T9_FERAL_RELIC_BEAR;
break;
case FORM_CAT:
triggerspell = SPELL_DRUID_T9_FERAL_RELIC_CAT;
break;
default:
return;
}
target->CastSpell(target, triggerspell, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_dru_t9_feral_relic::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_dru_t9_feral_relic::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// 22842 - Frenzied Regeneration
class spell_dru_frenzied_regeneration : public AuraScript
{
PrepareAuraScript(spell_dru_frenzied_regeneration);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_FRENZIED_REGENERATION_HEAL });
}
void HandlePeriodic(AuraEffect const* aurEff)
{
Unit* target = GetTarget();
if (target->getPowerType() != POWER_RAGE)
return;
uint32 rage = target->GetPower(POWER_RAGE);
if (!rage)
return;
int32 const mod = std::min(static_cast<int32>(rage), 100);
int32 const points = GetSpellInfo()->Effects[EFFECT_1].CalcValue(target);
int32 const regen = CalculatePct(target->GetMaxHealth(), points * mod / 100.f);
target->CastCustomSpell(SPELL_DRUID_FRENZIED_REGENERATION_HEAL, SPELLVALUE_BASE_POINT0, regen, target, true, nullptr, aurEff);
target->SetPower(POWER_RAGE, rage - mod);
}
void Register() override
{
OnEffectPeriodic += AuraEffectPeriodicFn(spell_dru_frenzied_regeneration::HandlePeriodic, EFFECT_0, SPELL_AURA_PERIODIC_DUMMY);
}
};
// -5570 - Insect Swarm
class spell_dru_insect_swarm : public AuraScript
{
PrepareAuraScript(spell_dru_insect_swarm);
void CalculateAmount(AuraEffect const* aurEff, int32& amount, bool& /*canBeRecalculated*/)
{
if (Unit* caster = GetCaster())
if (AuraEffect const* relicAurEff = caster->GetAuraEffect(SPELL_DRUID_ITEM_T8_BALANCE_RELIC, EFFECT_0))
amount += relicAurEff->GetAmount() / aurEff->GetTotalTicks();
}
void Register() override
{
DoEffectCalcAmount += AuraEffectCalcAmountFn(spell_dru_insect_swarm::CalculateAmount, EFFECT_0, SPELL_AURA_PERIODIC_DAMAGE);
}
};
// 50464 - Nourish
class spell_dru_nourish : public SpellScript
{
PrepareSpellScript(spell_dru_nourish);
void HandleHeal(SpellEffIndex /*effIndex*/)
{
Unit* caster = GetCaster();
Unit* target = GetHitUnit();
if (!target)
return;
int32 heal = GetHitHeal();
// Glyph of Nourish
if (AuraEffect const* aurEff = caster->GetAuraEffect(SPELL_DRUID_GLYPH_OF_NOURISH, EFFECT_0))
{
uint32 auraCount = 0;
Unit::AuraEffectList const& periodicHeals = target->GetAuraEffectsByType(SPELL_AURA_PERIODIC_HEAL);
for (AuraEffect const* hot : periodicHeals)
{
if (caster->GetGUID() == hot->GetCasterGUID())
++auraCount;
}
AddPct(heal, aurEff->GetAmount() * auraCount);
}
SetHitHeal(heal);
}
void Register() override
{
OnEffectHitTarget += SpellEffectFn(spell_dru_nourish::HandleHeal, EFFECT_0, SPELL_EFFECT_HEAL);
}
};
// -48438 - Wild Growth (AuraScript)
class spell_dru_wild_growth_aura : public AuraScript
{
PrepareAuraScript(spell_dru_wild_growth_aura);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_DRUID_RESTORATION_T10_2P_BONUS });
}
void SetTickHeal(AuraEffect const* /*aurEff*/, int32& amount, bool& /*canBeRecalculated*/)
{
_baseTick = amount;
if (Unit* caster = GetCaster())
if (AuraEffect const* bonus = caster->GetAuraEffect(SPELL_DRUID_RESTORATION_T10_2P_BONUS, EFFECT_0))
AddPct(_baseReduction, -bonus->GetAmount());
}
void HandleTickUpdate(AuraEffect* aurEff)
{
// Wild Growth = first tick gains a 6% bonus, reduced by 2% each tick
float reduction = _baseReduction;
reduction *= (aurEff->GetTickNumber() - 1);
float const bonus = 6.f - reduction;
int32 const amount = int32(_baseTick + CalculatePct(_baseTick, bonus));
aurEff->SetAmount(amount);
}
void Register() override
{
DoEffectCalcAmount += AuraEffectCalcAmountFn(spell_dru_wild_growth_aura::SetTickHeal, EFFECT_0, SPELL_AURA_PERIODIC_HEAL);
OnEffectUpdatePeriodic += AuraEffectUpdatePeriodicFn(spell_dru_wild_growth_aura::HandleTickUpdate, EFFECT_0, SPELL_AURA_PERIODIC_HEAL);
}
float _baseTick = 0.f;
float _baseReduction = 2.f;
};
void AddSC_druid_spell_scripts()
{
RegisterSpellScript(spell_dru_bear_form_passive);
@@ -1274,6 +2102,7 @@ void AddSC_druid_spell_scripts()
RegisterSpellScript(spell_dru_omen_of_clarity);
RegisterSpellScript(spell_dru_brambles_treant);
RegisterSpellScript(spell_dru_barkskin);
RegisterSpellScript(spell_dru_glyph_of_barkskin);
RegisterSpellScript(spell_dru_treant_scaling);
RegisterSpellScript(spell_dru_berserk);
RegisterSpellAndAuraScriptPair(spell_dru_dash, spell_dru_dash_aura);
@@ -1298,7 +2127,27 @@ void AddSC_druid_spell_scripts()
RegisterSpellScript(spell_dru_tiger_s_fury);
RegisterSpellScript(spell_dru_typhoon);
RegisterSpellScript(spell_dru_t10_restoration_4p_bonus);
RegisterSpellScript(spell_dru_wild_growth);
RegisterSpellAndAuraScriptPair(spell_dru_wild_growth, spell_dru_wild_growth_aura);
RegisterSpellScript(spell_dru_moonkin_form_passive_proc);
RegisterSpellScript(spell_dru_rejuvenation_moonglade_2_set);
// Proc system scripts
RegisterSpellScript(spell_dru_glyph_of_innervate);
RegisterSpellScript(spell_dru_glyph_of_rake);
RegisterSpellScript(spell_dru_leader_of_the_pack);
RegisterSpellScript(spell_dru_glyph_of_rejuvenation);
RegisterSpellScript(spell_dru_eclipse);
RegisterSpellScript(spell_dru_revitalize);
RegisterSpellScript(spell_dru_t3_2p_bonus);
RegisterSpellScript(spell_dru_t3_6p_bonus);
RegisterSpellScript(spell_dru_t3_8p_bonus);
RegisterSpellScript(spell_dru_t4_2p_bonus);
RegisterSpellScript(spell_dru_item_t6_trinket);
RegisterSpellScript(spell_dru_glyph_of_shred);
RegisterSpellScript(spell_dru_glyph_of_starfire_dummy);
RegisterSpellScript(spell_dru_t10_restoration_4p_bonus_dummy);
RegisterSpellScript(spell_dru_maim_interrupt);
RegisterSpellScript(spell_dru_t9_feral_relic);
RegisterSpellScript(spell_dru_frenzied_regeneration);
RegisterSpellScript(spell_dru_insect_swarm);
RegisterSpellScript(spell_dru_nourish);
}

View File

@@ -69,6 +69,89 @@ class spell_gen_5000_gold : public SpellScript
}
};
// 430, 431, 432, 1133, 1135, 1137, 10250, 22734, 27089, 34291, 43182, 43183, 46755, 49472, 57073, 61830, 72623 - Drink
class spell_gen_arena_drink : public AuraScript
{
PrepareAuraScript(spell_gen_arena_drink);
bool Load() override
{
return GetCaster() && GetCaster()->IsPlayer();
}
bool Validate(SpellInfo const* spellInfo) override
{
if (spellInfo->Effects[EFFECT_0].ApplyAuraName != SPELL_AURA_MOD_POWER_REGEN)
{
LOG_ERROR("spells", "Aura {} structure has been changed - first aura is no longer SPELL_AURA_MOD_POWER_REGEN", spellInfo->Id);
return false;
}
return true;
}
void CalcPeriodic(AuraEffect const* /*aurEff*/, bool& isPeriodic, int32& /*amplitude*/)
{
AuraEffect* regen = GetAura()->GetEffect(EFFECT_0);
if (!regen)
return;
// default case - not in arena
if (!GetCaster()->ToPlayer()->InArena())
isPeriodic = false;
}
void CalcAmount(AuraEffect const* /*aurEff*/, int32& amount, bool& /*canBeRecalculated*/)
{
AuraEffect* regen = GetAura()->GetEffect(EFFECT_0);
if (!regen)
return;
// default case - not in arena
if (!GetCaster()->ToPlayer()->InArena())
regen->ChangeAmount(amount);
}
void UpdatePeriodic(AuraEffect* aurEff)
{
AuraEffect* regen = GetAura()->GetEffect(EFFECT_0);
if (!regen)
return;
// This feature used only in arenas
// Here need increase mana regen per tick (6 second rule)
// on 0 tick - 0 (handled in 2 second)
// on 1 tick - 166% (handled in 4 second)
// on 2 tick - 133% (handled in 6 second)
// Apply bonus for 1 - 4 tick
switch (aurEff->GetTickNumber())
{
case 1: // 0%
regen->ChangeAmount(0);
break;
case 2: // 166%
regen->ChangeAmount(aurEff->GetAmount() * 5 / 3);
break;
case 3: // 133%
regen->ChangeAmount(aurEff->GetAmount() * 4 / 3);
break;
default: // 100% - normal regen
regen->ChangeAmount(aurEff->GetAmount());
// No need to update after 4th tick
aurEff->SetPeriodic(false);
break;
}
}
void Register() override
{
DoEffectCalcPeriodic += AuraEffectCalcPeriodicFn(spell_gen_arena_drink::CalcPeriodic, EFFECT_1, SPELL_AURA_PERIODIC_DUMMY);
DoEffectCalcAmount += AuraEffectCalcAmountFn(spell_gen_arena_drink::CalcAmount, EFFECT_1, SPELL_AURA_PERIODIC_DUMMY);
OnEffectUpdatePeriodic += AuraEffectUpdatePeriodicFn(spell_gen_arena_drink::UpdatePeriodic, EFFECT_1, SPELL_AURA_PERIODIC_DUMMY);
}
};
// 24401 - Test Pet Passive
class spell_gen_model_visible : public AuraScript
{
@@ -5696,6 +5779,307 @@ class spell_gen_whisper_to_controller : public SpellScript
}
};
enum VampiricTouchSpells
{
SPELL_VAMPIRIC_TOUCH_HEAL = 52724
};
// 52723 - Vampiric Touch (proc)
class spell_gen_vampiric_touch : public AuraScript
{
PrepareAuraScript(spell_gen_vampiric_touch);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_VAMPIRIC_TOUCH_HEAL });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
Unit* caster = eventInfo.GetActor();
int32 bp = damageInfo->GetDamage() / 2;
caster->CastCustomSpell(SPELL_VAMPIRIC_TOUCH_HEAL, SPELLVALUE_BASE_POINT0, bp, caster, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_gen_vampiric_touch::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 62337, 62933 - Petrified Bark (Freya)
class spell_gen_petrified_bark : public AuraScript
{
PrepareAuraScript(spell_gen_petrified_bark);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ 62379 });
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
Unit* victim = eventInfo.GetActor();
if (!victim)
return;
int32 damage = damageInfo->GetDamage();
victim->CastCustomSpell(GetTarget(), 62379, &damage, nullptr, nullptr, true);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_gen_petrified_bark::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 67534 - Earth Shield (Trial of the Champion)
class spell_gen_earth_shield_toc : public AuraScript
{
PrepareAuraScript(spell_gen_earth_shield_toc);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ 67535 });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
int32 damage = damageInfo->GetDamage();
GetTarget()->CastCustomSpell(GetTarget(), 67535, &damage, nullptr, nullptr, true, nullptr, aurEff, GetCasterGUID());
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_gen_earth_shield_toc::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 65932 - Retaliation (Faction Champions)
class spell_gen_retaliation_toc : public AuraScript
{
PrepareAuraScript(spell_gen_retaliation_toc);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ 65934 });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
Unit* attacker = eventInfo.GetActor();
return attacker && GetTarget()->HasInArc(M_PI, attacker);
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* attacker = eventInfo.GetActor();
if (attacker)
GetTarget()->CastSpell(attacker, 65934, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_gen_retaliation_toc::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_gen_retaliation_toc::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 69172 - Overlord's Brand (damage/heal redirect - non-DoT)
class spell_gen_overlords_brand : public AuraScript
{
PrepareAuraScript(spell_gen_overlords_brand);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ 69189, 69190 });
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = GetCaster();
if (!caster)
return;
if (eventInfo.GetTypeMask() & (PROC_FLAG_DONE_SPELL_NONE_DMG_CLASS_POS | PROC_FLAG_DONE_SPELL_MAGIC_DMG_CLASS_POS))
{
HealInfo* healInfo = eventInfo.GetHealInfo();
if (!healInfo || !healInfo->GetHeal())
return;
int32 heal = static_cast<int32>(healInfo->GetHeal() * 5.5f);
GetTarget()->CastCustomSpell(caster, 69190, &heal, nullptr, nullptr, true);
}
else
{
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
if (Unit* victim = caster->GetVictim())
{
int32 damage = damageInfo->GetDamage();
GetTarget()->CastCustomSpell(victim, 69189, &damage, nullptr, nullptr, true);
}
}
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_gen_overlords_brand::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 69173 - Overlord's Brand (damage/heal redirect - DoT only)
class spell_gen_overlords_brand_dot : public AuraScript
{
PrepareAuraScript(spell_gen_overlords_brand_dot);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ 69189, 69190 });
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = GetCaster();
if (!caster)
return;
if (eventInfo.GetHitMask() & PROC_EX_INTERNAL_HOT)
{
HealInfo* healInfo = eventInfo.GetHealInfo();
if (!healInfo || !healInfo->GetHeal())
return;
int32 heal = static_cast<int32>(healInfo->GetHeal() * 5.5f);
GetTarget()->CastCustomSpell(caster, 69190, &heal, nullptr, nullptr, true);
}
else
{
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
if (Unit* victim = caster->GetVictim())
{
int32 damage = damageInfo->GetDamage();
GetTarget()->CastCustomSpell(victim, 69189, &damage, nullptr, nullptr, true);
}
}
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_gen_overlords_brand_dot::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 70674 - Vampiric Might (Lady Deathwhisper)
class spell_gen_vampiric_might : public AuraScript
{
PrepareAuraScript(spell_gen_vampiric_might);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ 70677 });
}
void HandleProc(ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = GetCaster();
if (!caster)
return;
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
int32 heal = damageInfo->GetDamage() * 3;
caster->CastCustomSpell(caster, 70677, &heal, nullptr, nullptr, true);
}
void Register() override
{
OnProc += AuraProcFn(spell_gen_vampiric_might::HandleProc);
}
};
// 69023 - Mirrored Soul (Devourer of Souls)
class spell_gen_mirrored_soul : public AuraScript
{
PrepareAuraScript(spell_gen_mirrored_soul);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ 69034 });
}
void HandleProc(ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
Unit* caster = GetCaster();
if (!caster)
return;
int32 damage = static_cast<int32>(damageInfo->GetDamage() * 0.45f);
if (damage > 0)
GetTarget()->CastCustomSpell(caster, 69034, &damage, nullptr, nullptr, true);
}
void Register() override
{
OnProc += AuraProcFn(spell_gen_mirrored_soul::HandleProc);
}
};
// 27522, 40336, 46939 - Black Bow of the Betrayer / Mana Drain Trigger
class spell_gen_black_bow_of_the_betrayer : public AuraScript
{
PrepareAuraScript(spell_gen_black_bow_of_the_betrayer);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ 29471, 27526 });
}
void HandleProc(ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* target = GetTarget();
Unit* victim = eventInfo.GetActionTarget();
if (target->IsAlive())
target->CastSpell(target, 29471, true);
if (victim && victim->IsAlive())
target->CastSpell(victim, 27526, true);
}
void Register() override
{
OnProc += AuraProcFn(spell_gen_black_bow_of_the_betrayer::HandleProc);
}
};
// 35475 Drums of War
// 35476 Drums of Battle
// 35478 Drums of Restoration
@@ -5722,6 +6106,7 @@ void AddSC_generic_spell_scripts()
{
RegisterSpellScript(spell_silithyst);
RegisterSpellScript(spell_gen_5000_gold);
RegisterSpellScript(spell_gen_arena_drink);
RegisterSpellScript(spell_gen_model_visible);
RegisterSpellScript(spell_the_flag_of_ownership);
RegisterSpellScript(spell_gen_have_item_auras);
@@ -5893,5 +6278,15 @@ void AddSC_generic_spell_scripts()
RegisterSpellScript(spell_gen_bm_on);
RegisterSpellScript(spell_gen_bm_off);
RegisterSpellScript(spell_gen_whisper_to_controller);
RegisterSpellScript(spell_gen_vampiric_touch);
// Boss and item proc scripts
RegisterSpellScript(spell_gen_petrified_bark);
RegisterSpellScript(spell_gen_earth_shield_toc);
RegisterSpellScript(spell_gen_retaliation_toc);
RegisterSpellScript(spell_gen_overlords_brand);
RegisterSpellScript(spell_gen_overlords_brand_dot);
RegisterSpellScript(spell_gen_vampiric_might);
RegisterSpellScript(spell_gen_mirrored_soul);
RegisterSpellScript(spell_gen_black_bow_of_the_betrayer);
RegisterSpellScript(spell_gen_filter_party_level_80);
}

View File

@@ -68,6 +68,25 @@ enum HunterSpells
SPELL_LOCK_AND_LOAD_TRIGGER = 56453,
SPELL_LOCK_AND_LOAD_MARKER = 67544,
SPELL_HUNTER_PET_LEGGINGS_OF_BEAST_MASTERY = 38297, // Leggings of Beast Mastery
// Proc system spells
SPELL_HUNTER_THRILL_OF_THE_HUNT_MANA = 34720,
SPELL_HUNTER_REPLENISHMENT = 57669,
SPELL_HUNTER_RAPID_RECUPERATION_R1 = 56654,
SPELL_HUNTER_RAPID_RECUPERATION_R2 = 58882,
SPELL_HUNTER_GLYPH_OF_MEND_PET_HAPPINESS = 57894,
SPELL_HUNTER_KILL_COMMAND_HUNTER = 34026,
SPELL_HUNTER_RAPID_RECUPERATION_MANA_R1 = 56654,
SPELL_HUNTER_RAPID_RECUPERATION_MANA_R2 = 58882,
SPELL_HUNTER_PIERCING_SHOTS = 63468,
SPELL_HUNTER_T9_4P_GREATNESS = 68130
};
enum HunterSpellIcons
{
HUNTER_ICON_THRILL_OF_THE_HUNT = 2236,
HUNTER_ICON_HUNTING_PARTY = 3406,
HUNTER_ICON_RAPID_RECUPERATION = 3560
};
class spell_hun_check_pet_los : public SpellScript
@@ -738,18 +757,15 @@ class spell_hun_sniper_training : public AuraScript
PreventDefaultAction();
if (aurEff->GetAmount() <= 0)
{
if (!GetCaster() || !GetTarget())
{
return;
}
Unit* target = GetTarget();
uint32 spellId = SPELL_HUNTER_SNIPER_TRAINING_BUFF_R1 + GetId() - SPELL_HUNTER_SNIPER_TRAINING_R1;
if (SpellInfo const* triggeredSpellInfo = sSpellMgr->GetSpellInfo(spellId))
target->CastSpell(target, spellId, true, nullptr, aurEff);
if (Player* playerTarget = GetUnitOwner()->ToPlayer())
{
Unit* triggerCaster = triggeredSpellInfo->NeedsToBeTriggeredByCaster(GetSpellInfo()) ? GetCaster() : target;
triggerCaster->CastSpell(target, triggeredSpellInfo, true, 0, aurEff);
int32 baseAmount = aurEff->GetBaseAmount();
int32 amount = playerTarget->CalculateSpellDamage(playerTarget, GetSpellInfo(), aurEff->GetEffIndex(), &baseAmount);
GetEffect(EFFECT_0)->SetAmount(amount);
}
}
}
@@ -759,7 +775,7 @@ class spell_hun_sniper_training : public AuraScript
if (Player* playerTarget = GetUnitOwner()->ToPlayer())
{
int32 baseAmount = aurEff->GetBaseAmount();
int32 amount = playerTarget->isMoving() || aurEff->GetAmount() <= 0 ?
int32 amount = playerTarget->isMoving() ?
playerTarget->CalculateSpellDamage(playerTarget, GetSpellInfo(), aurEff->GetEffIndex(), &baseAmount) :
aurEff->GetAmount() - 1;
aurEff->SetAmount(amount);
@@ -1151,11 +1167,6 @@ private:
WorldObject* _target = nullptr;
};
enum LocknLoadSpells
{
SPELL_FROST_TRAP_SLOW = 67035
};
// -56342 - Lock and Load
class spell_hun_lock_and_load : public AuraScript
{
@@ -1163,103 +1174,58 @@ class spell_hun_lock_and_load : public AuraScript
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_LOCK_AND_LOAD_TRIGGER, SPELL_LOCK_AND_LOAD_MARKER, SPELL_FROST_TRAP_SLOW });
return ValidateSpellInfo(
{
SPELL_LOCK_AND_LOAD_TRIGGER,
SPELL_LOCK_AND_LOAD_MARKER
});
}
bool CheckTrapProc(ProcEventInfo& eventInfo)
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo || !eventInfo.GetActor())
{
if (eventInfo.GetActor()->HasAura(SPELL_LOCK_AND_LOAD_MARKER))
return false;
}
// Black Arrow and Fire traps may trigger on periodic tick only.
if (((spellInfo->GetSchoolMask() & SPELL_SCHOOL_MASK_FIRE) || (spellInfo->GetSchoolMask() & SPELL_SCHOOL_MASK_SHADOW))
&& (spellInfo->Effects[0].ApplyAuraName == SPELL_AURA_PERIODIC_DAMAGE || spellInfo->Effects[1].ApplyAuraName == SPELL_AURA_PERIODIC_DAMAGE))
{
return true;
}
return IsTargetValid(spellInfo, eventInfo.GetProcTarget()) && !eventInfo.GetActor()->HasAura(SPELL_LOCK_AND_LOAD_MARKER);
}
bool IsTargetValid(SpellInfo const* spellInfo, Unit* target)
{
if (!spellInfo || !target)
{
return false;
}
// Don't check it for fire traps and black arrow, they proc on periodic only and not spell hit.
// So it's wrong to check for immunity, it was already checked when the spell was applied.
if ((spellInfo->GetSchoolMask() & SPELL_SCHOOL_MASK_FIRE) || (spellInfo->GetSchoolMask() & SPELL_SCHOOL_MASK_SHADOW))
{
return false;
}
// HitMask for Frost Trap can't be checked correctly as it is.
// That's because the talent is triggered by the spell that fires the trap (63487)...
// ...and not the actual spell that applies the slow effect (67035).
// So the IMMUNE result is never sent by the spell that triggers this.
if (spellInfo->GetSchoolMask() & SPELL_SCHOOL_MASK_NATURE)
{
if (SpellInfo const* triggerSpell = sSpellMgr->GetSpellInfo(SPELL_FROST_TRAP_SLOW))
{
return !target->IsImmunedToSpell(triggerSpell);
}
}
return true;
}
template <uint32 mask>
void HandleProcs(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
bool CheckTrapProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
if (!(eventInfo.GetTypeMask() & PROC_FLAG_DONE_TRAP_ACTIVATION))
return false;
// Do not proc on traps for immolation/explosive trap
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo || !(spellInfo->GetSchoolMask() & SPELL_SCHOOL_MASK_FROST))
return false;
return roll_chance_i(aurEff->GetAmount());
}
bool CheckPeriodicProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
if (!(eventInfo.GetTypeMask() & PROC_FLAG_DONE_PERIODIC))
return false;
return roll_chance_i(aurEff->GetAmount());
}
void HandleProc(ProcEventInfo& eventInfo)
{
PreventDefaultAction();
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!(eventInfo.GetTypeMask() & mask) || !spellInfo)
{
return;
}
// Also check if the proc from the fire traps and black arrow actually comes from the periodic ticks here.
// Normally this wouldn't be required, but we are circumventing the current proc system limitations.
if (((spellInfo->GetSchoolMask() & SPELL_SCHOOL_MASK_FIRE) || (spellInfo->GetSchoolMask() & SPELL_SCHOOL_MASK_SHADOW))
&& (spellInfo->Effects[0].ApplyAuraName == SPELL_AURA_PERIODIC_DAMAGE || spellInfo->Effects[1].ApplyAuraName == SPELL_AURA_PERIODIC_DAMAGE)
&& !(mask & PROC_FLAG_DONE_PERIODIC))
{
return;
}
if (!roll_chance_i(aurEff->GetAmount()))
{
return;
}
Unit* caster = eventInfo.GetActor();
caster->CastSpell(caster, SPELL_LOCK_AND_LOAD_TRIGGER, true);
}
void ApplyMarker(ProcEventInfo& eventInfo)
{
if (IsTargetValid(eventInfo.GetSpellInfo(), eventInfo.GetProcTarget()))
{
Unit* caster = eventInfo.GetActor();
caster->CastSpell(caster, SPELL_LOCK_AND_LOAD_MARKER, true);
}
caster->CastSpell(caster, SPELL_LOCK_AND_LOAD_MARKER, true);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_hun_lock_and_load::CheckTrapProc);
DoCheckProc += AuraCheckProcFn(spell_hun_lock_and_load::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_hun_lock_and_load::HandleProcs<PROC_FLAG_DONE_TRAP_ACTIVATION>, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
OnEffectProc += AuraEffectProcFn(spell_hun_lock_and_load::HandleProcs<PROC_FLAG_DONE_PERIODIC>, EFFECT_1, SPELL_AURA_DUMMY);
DoCheckEffectProc += AuraCheckEffectProcFn(spell_hun_lock_and_load::CheckTrapProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
DoCheckEffectProc += AuraCheckEffectProcFn(spell_hun_lock_and_load::CheckPeriodicProc, EFFECT_1, SPELL_AURA_DUMMY);
AfterProc += AuraProcFn(spell_hun_lock_and_load::ApplyMarker);
OnProc += AuraProcFn(spell_hun_lock_and_load::HandleProc);
}
};
@@ -1343,6 +1309,159 @@ class spell_hun_target_self_and_pet : public SpellScript
}
};
// -34497 - Thrill of the Hunt
class spell_hun_thrill_of_the_hunt : public AuraScript
{
PrepareAuraScript(spell_hun_thrill_of_the_hunt);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_HUNTER_THRILL_OF_THE_HUNT_MANA });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
SpellInfo const* procSpell = eventInfo.GetSpellInfo();
if (!procSpell)
return;
Unit* caster = GetTarget();
if (!caster->IsPlayer())
return;
int32 mana = 0;
Spell* spell = caster->ToPlayer()->m_spellModTakingSpell;
// Disable charge drop because of Lock and Load
if (spell)
caster->ToPlayer()->SetSpellModTakingSpell(spell, false);
// Explosive Shot
if (procSpell->SpellFamilyFlags[2] & 0x200)
{
Unit* victim = eventInfo.GetActionTarget();
if (!victim)
{
if (spell)
caster->ToPlayer()->SetSpellModTakingSpell(spell, true);
return;
}
if (AuraEffect const* pEff = victim->GetAuraEffect(SPELL_AURA_PERIODIC_DUMMY, SPELLFAMILY_HUNTER, 0x0, 0x80000000, 0x0, caster->GetGUID()))
mana = pEff->GetSpellInfo()->CalcPowerCost(caster, SpellSchoolMask(pEff->GetSpellInfo()->SchoolMask)) * 4 / 10 / 3;
}
else
mana = procSpell->CalcPowerCost(caster, SpellSchoolMask(procSpell->SchoolMask)) * 4 / 10;
if (spell)
caster->ToPlayer()->SetSpellModTakingSpell(spell, true);
if (mana <= 0)
return;
caster->CastCustomSpell(SPELL_HUNTER_THRILL_OF_THE_HUNT_MANA, SPELLVALUE_BASE_POINT0, mana, caster, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_hun_thrill_of_the_hunt::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -53290 - Hunting Party
class spell_hun_hunting_party : public AuraScript
{
PrepareAuraScript(spell_hun_hunting_party);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_HUNTER_REPLENISHMENT });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
eventInfo.GetActor()->CastSpell(nullptr, SPELL_HUNTER_REPLENISHMENT, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_hun_hunting_party::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -53228 - Rapid Recuperation
class spell_hun_rapid_recuperation : public AuraScript
{
PrepareAuraScript(spell_hun_rapid_recuperation);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_HUNTER_RAPID_RECUPERATION_R1, SPELL_HUNTER_RAPID_RECUPERATION_R2 });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* procSpell = eventInfo.GetSpellInfo();
if (!procSpell)
return false;
// This effect only from Rapid Killing (mana regen)
return (procSpell->SpellFamilyFlags[1] & 0x01000000) != 0;
}
void HandleProc(ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
uint32 triggeredSpell = 0;
switch (GetSpellInfo()->Id)
{
case 53228: // Rank 1
triggeredSpell = SPELL_HUNTER_RAPID_RECUPERATION_R1;
break;
case 53232: // Rank 2
triggeredSpell = SPELL_HUNTER_RAPID_RECUPERATION_R2;
break;
default:
return;
}
GetTarget()->CastSpell(GetTarget(), triggeredSpell, true);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_hun_rapid_recuperation::CheckProc);
OnProc += AuraProcFn(spell_hun_rapid_recuperation::HandleProc);
}
};
// 57870 - Glyph of Mend Pet
class spell_hun_glyph_of_mend_pet : public AuraScript
{
PrepareAuraScript(spell_hun_glyph_of_mend_pet);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_HUNTER_GLYPH_OF_MEND_PET_HAPPINESS });
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* target = eventInfo.GetActionTarget();
if (!target)
return;
target->CastSpell(target, SPELL_HUNTER_GLYPH_OF_MEND_PET_HAPPINESS, true, nullptr, nullptr, GetTarget()->GetGUID());
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_hun_glyph_of_mend_pet::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -53301 - Explosive Shot
class spell_hun_explosive_shot : public SpellScript
{
@@ -1364,6 +1483,153 @@ class spell_hun_explosive_shot : public SpellScript
}
};
// 58914 - Kill Command (Pet Aura)
class spell_hun_kill_command_pet : public AuraScript
{
PrepareAuraScript(spell_hun_kill_command_pet);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_HUNTER_KILL_COMMAND_HUNTER });
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
// prevent charge drop (aura has both proc charge and stacks)
PreventDefaultAction();
if (Unit* owner = eventInfo.GetActor()->GetOwner())
owner->RemoveAuraFromStack(SPELL_HUNTER_KILL_COMMAND_HUNTER);
ModStackAmount(-1);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_hun_kill_command_pet::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -53228 - Rapid Recuperation (trigger)
class spell_hun_rapid_recuperation_trigger : public AuraScript
{
PrepareAuraScript(spell_hun_rapid_recuperation_trigger);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_HUNTER_RAPID_RECUPERATION_MANA_R1,
SPELL_HUNTER_RAPID_RECUPERATION_MANA_R2
});
}
void HandleRapidFireProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
// Proc only from Rapid Fire
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo || !(spellInfo->SpellFamilyFlags[0] & 0x00000020))
{
PreventDefaultAction();
return;
}
}
void HandleRapidKillingProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
static uint32 const triggerSpells[2] = { SPELL_HUNTER_RAPID_RECUPERATION_MANA_R1, SPELL_HUNTER_RAPID_RECUPERATION_MANA_R2 };
PreventDefaultAction();
// Proc only from Rapid Killing
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo || !(spellInfo->SpellFamilyFlags[1] & 0x01000000))
return;
uint8 rank = GetSpellInfo()->GetRank();
if (rank > 0 && rank <= 2)
GetTarget()->CastSpell(GetTarget(), triggerSpells[rank - 1], true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_hun_rapid_recuperation_trigger::HandleRapidFireProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
OnEffectProc += AuraEffectProcFn(spell_hun_rapid_recuperation_trigger::HandleRapidKillingProc, EFFECT_1, SPELL_AURA_DUMMY);
}
};
// -53234 - Piercing Shots
class spell_hun_piercing_shots : public AuraScript
{
PrepareAuraScript(spell_hun_piercing_shots);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_HUNTER_PIERCING_SHOTS });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
return eventInfo.GetActionTarget() != nullptr;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* dmgInfo = eventInfo.GetDamageInfo();
if (!dmgInfo || !dmgInfo->GetDamage())
return;
Unit* caster = eventInfo.GetActor();
Unit* target = eventInfo.GetActionTarget();
SpellInfo const* piercingShots = sSpellMgr->AssertSpellInfo(SPELL_HUNTER_PIERCING_SHOTS);
int32 bp = CalculatePct(static_cast<int32>(dmgInfo->GetDamage()), aurEff->GetAmount());
ASSERT(piercingShots->GetMaxTicks() > 0);
bp /= piercingShots->GetMaxTicks();
caster->CastCustomSpell(target, SPELL_HUNTER_PIERCING_SHOTS, &bp, nullptr, nullptr, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_hun_piercing_shots::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_hun_piercing_shots::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// 67151 - Item - Hunter T9 4P Bonus (Steady Shot)
class spell_hun_t9_4p_bonus : public AuraScript
{
PrepareAuraScript(spell_hun_t9_4p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_HUNTER_T9_4P_GREATNESS });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
Unit* actor = eventInfo.GetActor();
return actor && actor->IsPlayer() && actor->ToPlayer()->GetPet();
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = eventInfo.GetActor();
caster->CastSpell(caster->ToPlayer()->GetPet(), SPELL_HUNTER_T9_4P_GREATNESS, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_hun_t9_4p_bonus::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_hun_t9_4p_bonus::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
void AddSC_hunter_spell_scripts()
{
RegisterSpellScript(spell_hun_check_pet_los);
@@ -1396,4 +1662,13 @@ void AddSC_hunter_spell_scripts()
RegisterSpellScript(spell_hun_bestial_wrath);
RegisterSpellScript(spell_hun_target_self_and_pet);
RegisterSpellScript(spell_hun_explosive_shot);
RegisterSpellScript(spell_hun_thrill_of_the_hunt);
RegisterSpellScript(spell_hun_hunting_party);
RegisterSpellScript(spell_hun_rapid_recuperation);
RegisterSpellScript(spell_hun_glyph_of_mend_pet);
// Proc system scripts
RegisterSpellScript(spell_hun_kill_command_pet);
RegisterSpellScript(spell_hun_piercing_shots);
RegisterSpellScript(spell_hun_rapid_recuperation_trigger);
RegisterSpellScript(spell_hun_t9_4p_bonus);
}

File diff suppressed because it is too large Load Diff

View File

@@ -31,6 +31,9 @@
enum MageSpells
{
SPELL_MAGE_ARCANE_MISSILES_R1 = 5143,
SPELL_MAGE_BLAZING_SPEED = 31643,
SPELL_MAGE_MAGIC_ABSORPTION_MANA = 29442,
SPELL_MAGE_BURNOUT_TRIGGER = 44450,
SPELL_MAGE_IMPROVED_BLIZZARD_CHILLED = 12486,
SPELL_MAGE_COMBUSTION = 11129,
@@ -42,6 +45,7 @@ enum MageSpells
SPELL_MAGE_INCANTERS_ABSORBTION_TRIGGERED = 44413,
SPELL_MAGE_IGNITE = 12654,
SPELL_MAGE_MASTER_OF_ELEMENTS_ENERGIZE = 29077,
SPELL_MAGE_PERMAFROST_AURA = 68391,
SPELL_MAGE_SQUIRREL_FORM = 32813,
SPELL_MAGE_GIRAFFE_FORM = 32816,
SPELL_MAGE_SERPENT_FORM = 32817,
@@ -52,7 +56,28 @@ enum MageSpells
SPELL_MAGE_SUMMON_WATER_ELEMENTAL_PERMANENT = 70908,
SPELL_MAGE_SUMMON_WATER_ELEMENTAL_TEMPORARY = 70907,
SPELL_MAGE_GLYPH_OF_BLAST_WAVE = 62126,
SPELL_MAGE_FINGERS_OF_FROST = 44543
SPELL_MAGE_FINGERS_OF_FROST = 44543,
SPELL_MAGE_FINGERS_OF_FROST_AURASTATE_AURA = 44544,
SPELL_MAGE_ARCANE_POTENCY_RANK_1 = 57529,
SPELL_MAGE_ARCANE_POTENCY_RANK_2 = 57531,
SPELL_MAGE_EMPOWERED_FIRE_PROC = 67545,
SPELL_MAGE_T10_2P_BONUS = 70752,
SPELL_MAGE_T10_2P_BONUS_EFFECT = 70753,
SPELL_MAGE_T8_4P_BONUS = 64869,
SPELL_MAGE_HOT_STREAK_PROC = 48108,
SPELL_MAGE_CHILLED_R1 = 12484,
SPELL_MAGE_CHILLED_R2 = 12485,
SPELL_MAGE_CHILLED_R3 = 12486,
SPELL_MAGE_MANA_SURGE = 37445,
SPELL_MAGE_FROST_NOVA = 122
};
enum MageSpellIcons
{
MAGE_ICON_MAGIC_ABSORPTION = 459,
MAGE_ICON_CLEARCASTING = 212,
MAGE_ICON_PRESENCE_OF_MIND = 139,
MAGE_ICON_LIVING_BOMB = 3000
};
class spell_mage_arcane_blast : public SpellScript
@@ -112,7 +137,7 @@ class spell_mage_burning_determination : public AuraScript
return true;
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& /*eventInfo*/)
void HandleProc(ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetUnitOwner()->CastSpell(GetUnitOwner(), 54748, true);
@@ -121,7 +146,7 @@ class spell_mage_burning_determination : public AuraScript
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_mage_burning_determination::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_mage_burning_determination::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
OnProc += AuraProcFn(spell_mage_burning_determination::HandleProc);
}
};
@@ -784,44 +809,11 @@ class spell_mage_master_of_elements : public AuraScript
return ValidateSpellInfo({ SPELL_MAGE_MASTER_OF_ELEMENTS_ENERGIZE });
}
bool AfterCheckProc(ProcEventInfo& eventInfo, bool isTriggeredAtSpellProcEvent)
bool CheckProc(ProcEventInfo& eventInfo)
{
if (!isTriggeredAtSpellProcEvent || !eventInfo.GetActor() || !eventInfo.GetActionTarget())
{
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetSpellInfo())
return false;
}
_spellInfo = eventInfo.GetSpellInfo();
bool selectCaster = false;
// Triggered spells cost no mana so we need triggering spellInfo
if (SpellInfo const* triggeredByAuraSpellInfo = eventInfo.GetTriggerAuraSpell())
{
_spellInfo = triggeredByAuraSpellInfo;
selectCaster = true;
}
if (!_spellInfo)
{
return false;
}
_ticksModifier = 1;
// If spell is periodic, mana amount is divided by tick number
if (eventInfo.GetTriggerAuraEffectIndex() >= EFFECT_0)
{
if (Unit* caster = GetCaster())
{
if (Unit* target = (selectCaster ? eventInfo.GetActor() : eventInfo.GetActionTarget()))
{
if (AuraEffect const* aurEff = target->GetAuraEffect(_spellInfo->Id, eventInfo.GetTriggerAuraEffectIndex(), caster->GetGUID()))
{
_ticksModifier = std::max(1, aurEff->GetTotalTicks());
}
}
}
}
return true;
}
@@ -830,30 +822,20 @@ class spell_mage_master_of_elements : public AuraScript
{
PreventDefaultAction();
if (!_spellInfo)
return;
int32 mana = eventInfo.GetDamageInfo()->GetSpellInfo()->CalcPowerCost(GetTarget(), eventInfo.GetDamageInfo()->GetSchoolMask());
mana = CalculatePct(mana, aurEff->GetAmount());
if (Unit* target = GetTarget())
if (mana > 0)
{
int32 mana = int32(_spellInfo->CalcPowerCost(target, eventInfo.GetSchoolMask()) / _ticksModifier);
mana = CalculatePct(mana, aurEff->GetAmount());
if (mana > 0)
{
target->CastCustomSpell(SPELL_MAGE_MASTER_OF_ELEMENTS_ENERGIZE, SPELLVALUE_BASE_POINT0, mana, target, true, nullptr, aurEff);
}
GetTarget()->CastCustomSpell(SPELL_MAGE_MASTER_OF_ELEMENTS_ENERGIZE, SPELLVALUE_BASE_POINT0, mana, GetTarget(), true, nullptr, aurEff);
}
}
void Register() override
{
DoAfterCheckProc += AuraAfterCheckProcFn(spell_mage_master_of_elements::AfterCheckProc);
DoCheckProc += AuraCheckProcFn(spell_mage_master_of_elements::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_mage_master_of_elements::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
private:
SpellInfo const* _spellInfo = nullptr;
uint8 _ticksModifier = 0;
};
enum SilvermoonPolymorph
@@ -946,125 +928,587 @@ class spell_mage_summon_water_elemental : public SpellScript
}
};
#define FingersOfFrostScriptName "spell_mage_fingers_of_frost_proc_aura"
class spell_mage_fingers_of_frost_proc_aura : public AuraScript
{ PrepareAuraScript(spell_mage_fingers_of_frost_proc_aura);
// 74396 - Fingers of Frost
// Charge consumption is handled by the default proc system in PrepareProcToTrigger
// This script only handles removing the aura state aura (44544) when the buff expires
class spell_mage_fingers_of_frost : public AuraScript
{
PrepareAuraScript(spell_mage_fingers_of_frost);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_FINGERS_OF_FROST_AURASTATE_AURA });
}
void OnRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
{
GetTarget()->RemoveAurasDueToSpell(SPELL_MAGE_FINGERS_OF_FROST_AURASTATE_AURA);
}
void Register() override
{
AfterEffectRemove += AuraEffectRemoveFn(spell_mage_fingers_of_frost::OnRemove, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
}
};
// -31571 - Arcane Potency
class spell_mage_arcane_potency : public AuraScript
{
PrepareAuraScript(spell_mage_arcane_potency);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_MAGE_ARCANE_POTENCY_RANK_1,
SPELL_MAGE_ARCANE_POTENCY_RANK_2
});
}
bool CheckProc(ProcEventInfo& eventInfo)
{
if (eventInfo.GetSpellPhaseMask() != PROC_SPELL_PHASE_CAST)
{
eventInfo.SetProcChance(_chance);
}
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return false;
// Only proc on Clearcasting or Presence of Mind
if (spellInfo->SpellIconID != MAGE_ICON_CLEARCASTING && spellInfo->SpellIconID != MAGE_ICON_PRESENCE_OF_MIND)
return false;
return true;
}
bool AfterCheckProc(ProcEventInfo& eventInfo, bool isTriggeredAtSpellProcEvent)
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
if (eventInfo.GetSpellPhaseMask() != PROC_SPELL_PHASE_CAST)
{
eventInfo.ResetProcChance();
}
return isTriggeredAtSpellProcEvent;
PreventDefaultAction();
uint32 spellId = GetSpellInfo()->GetRank() == 1 ? SPELL_MAGE_ARCANE_POTENCY_RANK_1 : SPELL_MAGE_ARCANE_POTENCY_RANK_2;
GetTarget()->CastSpell(GetTarget(), spellId, true, nullptr, aurEff);
}
void HandleOnEffectProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
void Register() override
{
if (eventInfo.GetSpellPhaseMask() == PROC_SPELL_PHASE_CAST)
DoCheckProc += AuraCheckProcFn(spell_mage_arcane_potency::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_mage_arcane_potency::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 11129 - Combustion
class spell_mage_combustion : public AuraScript
{
PrepareAuraScript(spell_mage_combustion);
bool CheckProc(ProcEventInfo& eventInfo)
{
// Prevent charge consumption on non-crits
return eventInfo.GetHitMask() & PROC_EX_CRITICAL_HIT;
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_mage_combustion::CheckProc);
}
};
// -31656 - Empowered Fire
class spell_mage_empowered_fire : public AuraScript
{
PrepareAuraScript(spell_mage_empowered_fire);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_EMPOWERED_FIRE_PROC });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return false;
// Only proc on Ignite
return spellInfo->Id == SPELL_MAGE_IGNITE;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Unit* target = GetTarget();
// Calculate mana restored: 2% of base mana (percent value comes from spell 67545 effect 0)
uint32 percent = sSpellMgr->GetSpellInfo(SPELL_MAGE_EMPOWERED_FIRE_PROC)->Effects[EFFECT_0].CalcValue();
int32 mana = int32(CalculatePct(target->GetCreateMana(), percent));
target->CastCustomSpell(SPELL_MAGE_EMPOWERED_FIRE_PROC, SPELLVALUE_BASE_POINT0, mana, target, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_mage_empowered_fire::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_mage_empowered_fire::HandleProc, EFFECT_0, SPELL_AURA_ADD_FLAT_MODIFIER);
}
};
// 48108 - Hot Streak, 57761 - Fireball!
class spell_mage_gen_extra_effects : public AuraScript
{
PrepareAuraScript(spell_mage_gen_extra_effects);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_MAGE_T8_4P_BONUS,
SPELL_MAGE_T10_2P_BONUS,
SPELL_MAGE_T10_2P_BONUS_EFFECT
});
}
bool CheckProc(ProcEventInfo& eventInfo)
{
Unit* caster = eventInfo.GetActor();
// T8 4P bonus: prevent double proc on Arcane Missiles
if (GetSpellInfo()->Id == SPELL_MAGE_HOT_STREAK_PROC && caster->HasAura(SPELL_MAGE_T8_4P_BONUS))
{
_chance = 100.f;
_spell = eventInfo.GetProcSpell();
_procSpellDelayMoment = std::nullopt;
if (!_spell || _spell->GetDelayMoment() <= 0)
PreventDefaultAction();
if (_spell)
_procSpellDelayMoment = _spell->GetDelayMoment();
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (spellInfo && spellInfo->SpellFamilyName == SPELLFAMILY_MAGE &&
(spellInfo->SpellFamilyFlags[0] & 0x00000800)) // Arcane Missiles
return false;
}
else
{
if (eventInfo.GetSpellPhaseMask() == PROC_SPELL_PHASE_FINISH || (_procSpellDelayMoment.value_or(0) > 0 || !eventInfo.GetDamageInfo()))
PreventDefaultAction();
return true;
}
ResetProcState();
void HandleProc(ProcEventInfo& eventInfo)
{
Unit* caster = eventInfo.GetActor();
// T10 2P bonus: apply pushing the limit on proc consumption
if (caster->HasAura(SPELL_MAGE_T10_2P_BONUS))
caster->CastSpell(caster, SPELL_MAGE_T10_2P_BONUS_EFFECT, true);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_mage_gen_extra_effects::CheckProc);
OnProc += AuraProcFn(spell_mage_gen_extra_effects::HandleProc);
}
};
// 56372 - Glyph of Ice Block
class spell_mage_glyph_of_ice_block : public AuraScript
{
PrepareAuraScript(spell_mage_glyph_of_ice_block);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_FROST_NOVA });
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Player* player = GetTarget()->ToPlayer();
if (!player)
return;
// Reset cooldowns on Frost Nova and all its ranks
SpellInfo const* frostNovaInfo = sSpellMgr->GetSpellInfo(SPELL_MAGE_FROST_NOVA);
if (!frostNovaInfo)
return;
PlayerSpellMap const& spellMap = player->GetSpellMap();
for (auto const& itr : spellMap)
{
SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(itr.first);
if (!spellInfo)
continue;
// Frost Nova spell family flags: 0x00000040
if (spellInfo->SpellFamilyName == SPELLFAMILY_MAGE &&
(spellInfo->SpellFamilyFlags[0] & 0x00000040))
{
player->RemoveSpellCooldown(spellInfo->Id, true);
}
}
}
void HandleAfterEffectProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
void Register() override
{
switch (eventInfo.GetSpellPhaseMask())
OnEffectProc += AuraEffectProcFn(spell_mage_glyph_of_ice_block::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 56374 - Glyph of Icy Veins
class spell_mage_glyph_of_icy_veins : public AuraScript
{
PrepareAuraScript(spell_mage_glyph_of_icy_veins);
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Unit* target = GetTarget();
// Remove attack speed slows and haste reducting auras
target->RemoveAurasByType(SPELL_AURA_HASTE_SPELLS);
target->RemoveAurasByType(SPELL_AURA_MOD_DECREASE_SPEED);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_mage_glyph_of_icy_veins::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 56375 - Glyph of Polymorph
class spell_mage_glyph_of_polymorph : public AuraScript
{
PrepareAuraScript(spell_mage_glyph_of_polymorph);
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* target = eventInfo.GetProcTarget();
if (!target)
return;
// Remove DoTs from target
target->RemoveAurasByType(SPELL_AURA_PERIODIC_DAMAGE, ObjectGuid::Empty, nullptr, true);
target->RemoveAurasByType(SPELL_AURA_PERIODIC_DAMAGE_PERCENT, ObjectGuid::Empty, nullptr, true);
target->RemoveAurasByType(SPELL_AURA_PERIODIC_LEECH, ObjectGuid::Empty, nullptr, true);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_mage_glyph_of_polymorph::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -44445 - Hot Streak
class spell_mage_hot_streak : public AuraScript
{
PrepareAuraScript(spell_mage_hot_streak);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_HOT_STREAK_PROC });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
// Non-crit - reset counter
if (!(eventInfo.GetHitMask() & PROC_EX_CRITICAL_HIT))
{
case PROC_SPELL_PHASE_HIT: _chance = 100.f; break;
case PROC_SPELL_PHASE_FINISH: ResetProcState(); break;
default: break;
_critStreak = 0;
return;
}
// Crit - increment counter
++_critStreak;
// Two crits in a row - proc Hot Streak if chance succeeds
if (_critStreak >= 2)
{
_critStreak = 0;
if (roll_chance_i(aurEff->GetAmount()))
GetTarget()->CastSpell(GetTarget(), SPELL_MAGE_HOT_STREAK_PROC, true, nullptr, aurEff);
}
}
void ResetProcState()
void Register() override
{
_chance = 0.f;
_spell = nullptr;
_procSpellDelayMoment = std::nullopt;
OnEffectProc += AuraEffectProcFn(spell_mage_hot_streak::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
void Register()
private:
uint8 _critStreak = 0;
};
// -11185 - Improved Blizzard
class spell_mage_imp_blizzard : public AuraScript
{
PrepareAuraScript(spell_mage_imp_blizzard);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
DoCheckProc += AuraCheckProcFn(spell_mage_fingers_of_frost_proc_aura::CheckProc);
DoAfterCheckProc += AuraAfterCheckProcFn(spell_mage_fingers_of_frost_proc_aura::AfterCheckProc);
OnEffectProc += AuraEffectProcFn(spell_mage_fingers_of_frost_proc_aura::HandleOnEffectProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
AfterEffectProc += AuraEffectProcFn(spell_mage_fingers_of_frost_proc_aura::HandleAfterEffectProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
return ValidateSpellInfo(
{
SPELL_MAGE_CHILLED_R1,
SPELL_MAGE_CHILLED_R2,
SPELL_MAGE_CHILLED_R3
});
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
uint32 spellId;
switch (GetSpellInfo()->GetRank())
{
case 1: spellId = SPELL_MAGE_CHILLED_R1; break;
case 2: spellId = SPELL_MAGE_CHILLED_R2; break;
case 3: spellId = SPELL_MAGE_CHILLED_R3; break;
default: return;
}
if (Unit* target = eventInfo.GetProcTarget())
GetTarget()->CastSpell(target, spellId, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_mage_imp_blizzard::HandleProc, EFFECT_0, SPELL_AURA_OVERRIDE_CLASS_SCRIPTS);
}
};
// 61062, 37447 - Improved Mana Gems
class spell_mage_imp_mana_gems : public AuraScript
{
PrepareAuraScript(spell_mage_imp_mana_gems);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_MANA_SURGE });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->CastSpell(GetTarget(), SPELL_MAGE_MANA_SURGE, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_mage_imp_mana_gems::HandleProc, EFFECT_1, SPELL_AURA_OVERRIDE_CLASS_SCRIPTS);
}
};
// -44404 - Missile Barrage
class spell_mage_missile_barrage : public AuraScript
{
PrepareAuraScript(spell_mage_missile_barrage);
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (!spellInfo)
return false;
// Arcane Blast - full proc chance (100%)
// Arcane Blast spell family flags: 0x20000000
if (spellInfo->SpellFamilyFlags[0] & 0x20000000)
return true;
// Other spells - 50% proc chance
return roll_chance_i(50);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_mage_missile_barrage::CheckProc);
}
};
// -29441 - Magic Absorption
class spell_mage_magic_absorption : public AuraScript
{
PrepareAuraScript(spell_mage_magic_absorption);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_MAGIC_ABSORPTION_MANA });
}
bool CheckProc(ProcEventInfo& /*eventInfo*/)
{
return GetTarget()->HasActivePowerType(POWER_MANA);
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Unit* target = GetTarget();
int32 bp = CalculatePct(int32(target->GetMaxPower(POWER_MANA)), aurEff->GetAmount());
target->CastCustomSpell(SPELL_MAGE_MAGIC_ABSORPTION_MANA, SPELLVALUE_BASE_POINT0, bp, target, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_mage_magic_absorption::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_mage_magic_absorption::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -31641 - Blazing Speed
class spell_mage_blazing_speed : public AuraScript
{
PrepareAuraScript(spell_mage_blazing_speed);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_BLAZING_SPEED });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
if (Unit* target = eventInfo.GetActionTarget())
target->CastSpell(target, SPELL_MAGE_BLAZING_SPEED, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_mage_blazing_speed::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// -5143 - Arcane Missiles
class spell_mage_arcane_missiles : public AuraScript
{
PrepareAuraScript(spell_mage_arcane_missiles);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_T10_2P_BONUS, SPELL_MAGE_T10_2P_BONUS_EFFECT });
}
void OnRemove(AuraEffect const* aurEff, AuraEffectHandleModes /*mode*/)
{
Unit* target = GetTarget();
if (target->HasAura(SPELL_MAGE_T10_2P_BONUS) && _canProcT10)
target->CastSpell(target, SPELL_MAGE_T10_2P_BONUS_EFFECT, true, nullptr, aurEff);
}
void Register() override
{
AfterEffectRemove += AuraEffectRemoveFn(spell_mage_arcane_missiles::OnRemove, EFFECT_1, SPELL_AURA_PERIODIC_TRIGGER_SPELL, AURA_EFFECT_HANDLE_REAL);
}
public:
// May point to a deleted object.
// Dereferencing is unsafe unless validity is guaranteed by the caller.
Spell const* GetProcSpell() const { return _spell; }
void AllowT10Proc() { _canProcT10 = true; }
private:
float _chance = 0.f;
std::optional<uint64> _procSpellDelayMoment = std::nullopt;
// May be dangling; points to memory that might no longer be valid.
Spell const* _spell = nullptr;
bool _canProcT10 = false;
};
typedef spell_mage_fingers_of_frost_proc_aura spell_mage_fingers_of_frost_proc_aura_script;
class spell_mage_fingers_of_frost_proc : public AuraScript
// -31661 - Dragon's Breath
class spell_mage_dragon_breath : public AuraScript
{
PrepareAuraScript(spell_mage_fingers_of_frost_proc);
PrepareAuraScript(spell_mage_dragon_breath);
bool CheckProc(ProcEventInfo& eventInfo)
{
if (Aura* aura = GetCaster()->GetAuraOfRankedSpell(SPELL_MAGE_FINGERS_OF_FROST))
{
if (spell_mage_fingers_of_frost_proc_aura_script* script = dynamic_cast<spell_mage_fingers_of_frost_proc_aura_script*>(aura->GetScriptByName(FingersOfFrostScriptName)))
{
if (Spell const* fofProcSpell = script->GetProcSpell())
{
if (fofProcSpell == eventInfo.GetProcSpell())
{
return false;
}
}
}
}
// Don't proc with Living Bomb explosion
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
if (spellInfo && spellInfo->SpellIconID == MAGE_ICON_LIVING_BOMB && spellInfo->SpellFamilyName == SPELLFAMILY_MAGE)
return false;
return true;
}
void Register()
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_mage_fingers_of_frost_proc::CheckProc);
DoCheckProc += AuraCheckProcFn(spell_mage_dragon_breath::CheckProc);
}
};
// -44614 - Frostfire Bolt
class spell_mage_frostfire_bolt : public AuraScript
{
PrepareAuraScript(spell_mage_frostfire_bolt);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_PERMAFROST_AURA });
}
void ApplyPermafrost(AuraEffect const* aurEff, AuraEffectHandleModes /*mode*/)
{
if (Unit* caster = GetCaster())
caster->CastSpell(GetTarget(), SPELL_MAGE_PERMAFROST_AURA, true, nullptr, aurEff);
}
void RemovePermafrost(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
{
GetTarget()->RemoveAurasDueToSpell(SPELL_MAGE_PERMAFROST_AURA);
}
void Register() override
{
AfterEffectApply += AuraEffectApplyFn(spell_mage_frostfire_bolt::ApplyPermafrost, EFFECT_0, SPELL_AURA_MOD_DECREASE_SPEED, AURA_EFFECT_HANDLE_REAL_OR_REAPPLY_MASK);
AfterEffectRemove += AuraEffectRemoveFn(spell_mage_frostfire_bolt::RemovePermafrost, EFFECT_0, SPELL_AURA_MOD_DECREASE_SPEED, AURA_EFFECT_HANDLE_REAL);
}
};
// 45438 - Ice Block
class spell_mage_ice_block : public SpellScript
{
PrepareSpellScript(spell_mage_ice_block);
bool Validate(SpellInfo const* spellInfo) override
{
return spellInfo->ExcludeCasterAuraSpell && ValidateSpellInfo({ static_cast<uint32>(spellInfo->ExcludeCasterAuraSpell) });
}
void TriggerHypothermia()
{
GetCaster()->CastSpell(GetCaster(), GetSpellInfo()->ExcludeCasterAuraSpell, true);
}
void Register() override
{
AfterHit += SpellHitFn(spell_mage_ice_block::TriggerHypothermia);
}
};
// 44401 - Missile Barrage (proc buff)
class spell_mage_missile_barrage_proc : public AuraScript
{
PrepareAuraScript(spell_mage_missile_barrage_proc);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_MAGE_T10_2P_BONUS, SPELL_MAGE_T8_4P_BONUS, SPELL_MAGE_ARCANE_MISSILES_R1 });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
Unit* caster = eventInfo.GetActor();
// T8 4P bonus: chance to not consume the proc
if (AuraEffect const* aurEff = caster->GetAuraEffect(SPELL_MAGE_T8_4P_BONUS, EFFECT_0))
if (roll_chance_i(aurEff->GetAmount()))
return false;
return true;
}
void OnRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
{
Unit* caster = GetTarget();
// T10 2P bonus: signal Arcane Missiles to proc the bonus when it ends
if (caster->HasAura(SPELL_MAGE_T10_2P_BONUS))
{
if (Aura* aura = caster->GetAuraOfRankedSpell(SPELL_MAGE_ARCANE_MISSILES_R1))
{
if (spell_mage_arcane_missiles* script = dynamic_cast<spell_mage_arcane_missiles*>(aura->GetScriptByName("spell_mage_arcane_missiles")))
script->AllowT10Proc();
}
}
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_mage_missile_barrage_proc::CheckProc);
AfterEffectRemove += AuraEffectRemoveFn(spell_mage_missile_barrage_proc::OnRemove, EFFECT_0, SPELL_AURA_ADD_FLAT_MODIFIER, AURA_EFFECT_HANDLE_REAL);
}
};
void AddSC_mage_spell_scripts()
{
RegisterSpellScript(spell_mage_arcane_blast);
RegisterSpellScript(spell_mage_arcane_missiles);
RegisterSpellScript(spell_mage_arcane_potency);
RegisterSpellScript(spell_mage_blazing_speed);
RegisterSpellScript(spell_mage_burning_determination);
RegisterSpellScript(spell_mage_molten_armor);
RegisterSpellScript(spell_mage_mirror_image);
@@ -1072,19 +1516,33 @@ void AddSC_mage_spell_scripts()
RegisterSpellScript(spell_mage_burnout_trigger);
RegisterSpellScript(spell_mage_pet_scaling);
RegisterSpellScript(spell_mage_brain_freeze);
RegisterSpellScript(spell_mage_combustion);
RegisterSpellScript(spell_mage_glyph_of_eternal_water);
RegisterSpellScript(spell_mage_combustion_proc);
RegisterSpellScript(spell_mage_dragon_breath);
RegisterSpellScript(spell_mage_empowered_fire);
RegisterSpellScript(spell_mage_gen_extra_effects);
RegisterSpellScript(spell_mage_frostfire_bolt);
RegisterSpellScript(spell_mage_glyph_of_ice_block);
RegisterSpellScript(spell_mage_glyph_of_icy_veins);
RegisterSpellScript(spell_mage_glyph_of_polymorph);
RegisterSpellScript(spell_mage_hot_streak);
RegisterSpellScript(spell_mage_ice_barrier);
RegisterSpellScript(spell_mage_ice_block);
RegisterSpellScript(spell_mage_imp_blizzard);
RegisterSpellScript(spell_mage_imp_mana_gems);
RegisterSpellScript(spell_mage_missile_barrage);
RegisterSpellScript(spell_mage_missile_barrage_proc);
RegisterSpellScript(spell_mage_blast_wave);
RegisterSpellScript(spell_mage_cold_snap);
RegisterSpellScript(spell_mage_fire_frost_ward);
RegisterSpellScript(spell_mage_focus_magic);
RegisterSpellScript(spell_mage_ice_barrier);
RegisterSpellScript(spell_mage_ignite);
RegisterSpellScript(spell_mage_living_bomb);
RegisterSpellScript(spell_mage_mana_shield);
RegisterSpellScript(spell_mage_master_of_elements);
RegisterSpellScript(spell_mage_polymorph_cast_visual);
RegisterSpellScript(spell_mage_summon_water_elemental);
RegisterSpellScript(spell_mage_fingers_of_frost_proc_aura);
RegisterSpellScript(spell_mage_fingers_of_frost_proc);
RegisterSpellScript(spell_mage_fingers_of_frost);
RegisterSpellScript(spell_mage_magic_absorption);
}

File diff suppressed because it is too large Load Diff

View File

@@ -64,6 +64,24 @@ enum PriestSpellIcons
PRIEST_ICON_ID_BORROWED_TIME = 2899,
PRIEST_ICON_ID_EMPOWERED_RENEW_TALENT = 3021,
PRIEST_ICON_ID_PAIN_AND_SUFFERING = 2874,
PRIEST_ICON_ID_BODY_AND_SOUL = 2218
};
// Proc system triggered spells
enum PriestProcSpells
{
SPELL_PRIEST_VAMPIRIC_EMBRACE_HEAL = 15290,
SPELL_PRIEST_GLYPH_OF_DISPEL_MAGIC_HEAL = 56131,
SPELL_PRIEST_BODY_AND_SOUL_SPEED = 64136,
SPELL_PRIEST_ORACULAR_HEAL = 26170,
SPELL_PRIEST_DIVINE_BLESSING = 40440,
SPELL_PRIEST_DIVINE_WRATH = 40441,
SPELL_PRIEST_ARMOR_OF_FAITH = 28810,
SPELL_PRIEST_BLESSED_HEALING = 70772,
SPELL_PRIEST_SHADOW_WORD_DEATH_R1 = 32379,
SPELL_PRIEST_MIND_BLAST_R1 = 8092,
SPELL_PRIEST_MIND_FLAY_DAMAGE = 58381,
SPELL_PRIEST_BLESSED_RECOVERY_R1 = 27813
};
enum Mics
@@ -431,6 +449,27 @@ class spell_pri_lightwell_renew : public AuraScript
}
}
void InitializeAmount(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
{
// Attacks done to you equal to 30% of your total health will cancel the effect
_remainingAmount = GetTarget()->CountPctFromMaxHealth(30);
}
void CheckDropCharge(ProcEventInfo& eventInfo)
{
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo)
return;
uint32 damage = damageInfo->GetDamage();
if (_remainingAmount <= damage)
return;
_remainingAmount -= damage;
// prevent drop charge
PreventDefaultAction();
}
void HandleUpdateSpellclick(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
{
if (Unit* caster = GetCaster())
@@ -448,10 +487,15 @@ class spell_pri_lightwell_renew : public AuraScript
void Register() override
{
DoPrepareProc += AuraProcFn(spell_pri_lightwell_renew::CheckDropCharge);
DoEffectCalcAmount += AuraEffectCalcAmountFn(spell_pri_lightwell_renew::CalculateAmount, EFFECT_0, SPELL_AURA_PERIODIC_HEAL);
AfterEffectApply += AuraEffectApplyFn(spell_pri_lightwell_renew::InitializeAmount, EFFECT_0, SPELL_AURA_PERIODIC_HEAL, AURA_EFFECT_HANDLE_REAL_OR_REAPPLY_MASK);
AfterEffectApply += AuraEffectApplyFn(spell_pri_lightwell_renew::HandleUpdateSpellclick, EFFECT_0, SPELL_AURA_PERIODIC_HEAL, AURA_EFFECT_HANDLE_REAL);
AfterEffectRemove += AuraEffectRemoveFn(spell_pri_lightwell_renew::HandleUpdateSpellclick, EFFECT_0, SPELL_AURA_PERIODIC_HEAL, AURA_EFFECT_HANDLE_REAL);
}
private:
uint32 _remainingAmount = 0;
};
// 8129 - Mana Burn
@@ -983,6 +1027,418 @@ class spell_pri_shadowfiend_death : public AuraScript
}
};
// 15286 - Vampiric Embrace
class spell_pri_vampiric_embrace : public AuraScript
{
PrepareAuraScript(spell_pri_vampiric_embrace);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PRIEST_VAMPIRIC_EMBRACE_HEAL });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
// Not proc from Mind Sear
SpellInfo const* procSpell = eventInfo.GetSpellInfo();
if (!procSpell)
return false;
return !(procSpell->SpellFamilyFlags[1] & 0x80000);
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
int32 selfHeal = CalculatePct(static_cast<int32>(damageInfo->GetDamage()), aurEff->GetAmount());
int32 partyHeal = selfHeal / 5;
GetTarget()->CastCustomSpell(GetTarget(), SPELL_PRIEST_VAMPIRIC_EMBRACE_HEAL, &partyHeal, &selfHeal, nullptr, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pri_vampiric_embrace::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_pri_vampiric_embrace::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 55677 - Glyph of Dispel Magic
class spell_pri_glyph_of_dispel_magic : public AuraScript
{
PrepareAuraScript(spell_pri_glyph_of_dispel_magic);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PRIEST_GLYPH_OF_DISPEL_MAGIC_HEAL });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* procSpell = eventInfo.GetSpellInfo();
if (!procSpell)
return false;
// Dispel Magic shares spellfamilyflag with abolish disease - check icon
if (procSpell->SpellIconID != 74)
return false;
Unit* target = eventInfo.GetActionTarget();
if (!target || !target->IsFriendlyTo(GetTarget()))
return false;
return true;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* target = eventInfo.GetActionTarget();
if (!target)
return;
int32 bp = int32(target->CountPctFromMaxHealth(aurEff->GetAmount()));
GetTarget()->CastCustomSpell(SPELL_PRIEST_GLYPH_OF_DISPEL_MAGIC_HEAL, SPELLVALUE_BASE_POINT0, bp, target, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pri_glyph_of_dispel_magic::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_pri_glyph_of_dispel_magic::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -64127 - Body and Soul
class spell_pri_body_and_soul : public AuraScript
{
PrepareAuraScript(spell_pri_body_and_soul);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PRIEST_BODY_AND_SOUL_SPEED });
}
bool CheckProcTriggerSpell(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
return spellInfo && (spellInfo->SpellFamilyFlags[0] & 0x00000001) != 0;
}
bool CheckProcDummy(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
if (eventInfo.GetActor() != eventInfo.GetActionTarget())
return false;
SpellInfo const* spellInfo = eventInfo.GetSpellInfo();
return spellInfo && spellInfo->Id == 552;
}
void HandleProcDummy(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
if (roll_chance_i(aurEff->GetAmount()))
eventInfo.GetActor()->CastSpell(eventInfo.GetActor(), SPELL_PRIEST_BODY_AND_SOUL_SPEED, true, nullptr, aurEff);
}
void Register() override
{
DoCheckEffectProc += AuraCheckEffectProcFn(spell_pri_body_and_soul::CheckProcTriggerSpell, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
DoCheckEffectProc += AuraCheckEffectProcFn(spell_pri_body_and_soul::CheckProcDummy, EFFECT_1, SPELL_AURA_DUMMY);
OnEffectProc += AuraEffectProcFn(spell_pri_body_and_soul::HandleProcDummy, EFFECT_1, SPELL_AURA_DUMMY);
}
};
// 47569, 47570 - Improved Shadowform
class spell_pri_improved_shadowform : public AuraScript
{
PrepareAuraScript(spell_pri_improved_shadowform);
bool CheckProc(ProcEventInfo& /*eventInfo*/)
{
return roll_chance_i(GetEffect(EFFECT_0)->GetAmount());
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->RemoveMovementImpairingAuras(true);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pri_improved_shadowform::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_pri_improved_shadowform::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 26169 - AQ 3P Bonus
class spell_pri_aq_3p_bonus : public AuraScript
{
PrepareAuraScript(spell_pri_aq_3p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PRIEST_ORACULAR_HEAL });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
if (eventInfo.GetActor() == eventInfo.GetActionTarget())
return false;
HealInfo* healInfo = eventInfo.GetHealInfo();
return healInfo && healInfo->GetHeal();
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
int32 bp0 = CalculatePct(eventInfo.GetHealInfo()->GetHeal(), 10);
eventInfo.GetActor()->CastCustomSpell(SPELL_PRIEST_ORACULAR_HEAL, SPELLVALUE_BASE_POINT0, bp0, eventInfo.GetActor(), true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pri_aq_3p_bonus::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_pri_aq_3p_bonus::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -47569 - Improved Shadowform (talent)
class spell_pri_imp_shadowform : public AuraScript
{
PrepareAuraScript(spell_pri_imp_shadowform);
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
if (roll_chance_i(aurEff->GetAmount()))
GetTarget()->RemoveMovementImpairingAuras(true);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_pri_imp_shadowform::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -15337 - Improved Spirit Tap
class spell_pri_improved_spirit_tap : public AuraScript
{
PrepareAuraScript(spell_pri_improved_spirit_tap);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_PRIEST_SHADOW_WORD_DEATH_R1,
SPELL_PRIEST_MIND_BLAST_R1
});
}
bool CheckProc(ProcEventInfo& eventInfo)
{
if (SpellInfo const* spellInfo = eventInfo.GetSpellInfo())
{
if (spellInfo->IsRankOf(sSpellMgr->AssertSpellInfo(SPELL_PRIEST_SHADOW_WORD_DEATH_R1)) ||
spellInfo->IsRankOf(sSpellMgr->AssertSpellInfo(SPELL_PRIEST_MIND_BLAST_R1)))
return true;
else if (spellInfo->Id == SPELL_PRIEST_MIND_FLAY_DAMAGE)
return roll_chance_i(50);
}
return false;
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pri_improved_spirit_tap::CheckProc);
}
};
// 40438 - Priest Tier 6 Trinket
class spell_pri_item_t6_trinket : public AuraScript
{
PrepareAuraScript(spell_pri_item_t6_trinket);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_PRIEST_DIVINE_BLESSING,
SPELL_PRIEST_DIVINE_WRATH
});
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = eventInfo.GetActor();
if (eventInfo.GetSpellTypeMask() & PROC_SPELL_TYPE_HEAL)
caster->CastSpell(caster, SPELL_PRIEST_DIVINE_BLESSING, true, nullptr, aurEff);
if (eventInfo.GetSpellTypeMask() & PROC_SPELL_TYPE_DAMAGE)
caster->CastSpell(caster, SPELL_PRIEST_DIVINE_WRATH, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_pri_item_t6_trinket::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 28809 - T3 4P Bonus
class spell_pri_t3_4p_bonus : public AuraScript
{
PrepareAuraScript(spell_pri_t3_4p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PRIEST_ARMOR_OF_FAITH });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
eventInfo.GetActor()->CastSpell(eventInfo.GetActionTarget(), SPELL_PRIEST_ARMOR_OF_FAITH, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_pri_t3_4p_bonus::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 37594 - Greater Heal Refund / T5 2P Bonus
class spell_pri_t5_heal_2p_bonus : public AuraScript
{
PrepareAuraScript(spell_pri_t5_heal_2p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PRIEST_ITEM_EFFICIENCY });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
if (HealInfo* healInfo = eventInfo.GetHealInfo())
if (Unit* healTarget = healInfo->GetTarget())
if (healInfo->GetEffectiveHeal())
if (healTarget->GetHealth() >= healTarget->GetMaxHealth())
return true;
return false;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->CastSpell(GetTarget(), SPELL_PRIEST_ITEM_EFFICIENCY, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pri_t5_heal_2p_bonus::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_pri_t5_heal_2p_bonus::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// 70770 - Item - Priest T10 Healer 2P Bonus
class spell_pri_t10_heal_2p_bonus : public AuraScript
{
PrepareAuraScript(spell_pri_t10_heal_2p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PRIEST_BLESSED_HEALING });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
HealInfo* healInfo = eventInfo.GetHealInfo();
return healInfo && healInfo->GetHeal();
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
SpellInfo const* spellInfo = sSpellMgr->AssertSpellInfo(SPELL_PRIEST_BLESSED_HEALING);
int32 amount = CalculatePct(static_cast<int32>(eventInfo.GetHealInfo()->GetHeal()), aurEff->GetAmount());
ASSERT(spellInfo->GetMaxTicks() > 0);
amount /= spellInfo->GetMaxTicks();
Unit* caster = eventInfo.GetActor();
Unit* target = eventInfo.GetActionTarget();
caster->CastCustomSpell(target, SPELL_PRIEST_BLESSED_HEALING, &amount, nullptr, nullptr, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_pri_t10_heal_2p_bonus::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_pri_t10_heal_2p_bonus::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -47580 - Pain and Suffering (dummy aura)
class spell_pri_pain_and_suffering_dummy : public AuraScript
{
PrepareAuraScript(spell_pri_pain_and_suffering_dummy);
bool CheckDummy(AuraEffect const* /*aurEff*/, ProcEventInfo& /*eventInfo*/)
{
return false;
}
void Register() override
{
DoCheckEffectProc += AuraCheckEffectProcFn(spell_pri_pain_and_suffering_dummy::CheckDummy, EFFECT_1, SPELL_AURA_DUMMY);
}
};
// -27811 - Blessed Recovery
class spell_pri_blessed_recovery : public AuraScript
{
PrepareAuraScript(spell_pri_blessed_recovery);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_PRIEST_BLESSED_RECOVERY_R1 });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* dmgInfo = eventInfo.GetDamageInfo();
if (!dmgInfo || !dmgInfo->GetDamage())
return;
Unit* target = eventInfo.GetActionTarget();
uint32 triggerSpell = sSpellMgr->GetSpellWithRank(SPELL_PRIEST_BLESSED_RECOVERY_R1, aurEff->GetSpellInfo()->GetRank());
SpellInfo const* triggerInfo = sSpellMgr->AssertSpellInfo(triggerSpell);
int32 bp = CalculatePct(static_cast<int32>(dmgInfo->GetDamage()), aurEff->GetAmount());
ASSERT(triggerInfo->GetMaxTicks() > 0);
bp /= triggerInfo->GetMaxTicks();
target->CastCustomSpell(target, triggerSpell, &bp, nullptr, nullptr, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_pri_blessed_recovery::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
void AddSC_priest_spell_scripts()
{
RegisterSpellScript(spell_pri_shadowfiend_scaling);
@@ -998,6 +1454,7 @@ void AddSC_priest_spell_scripts()
RegisterSpellScript(spell_pri_mana_burn);
RegisterSpellScript(spell_pri_mana_leech);
RegisterSpellScript(spell_pri_mind_sear);
RegisterSpellScript(spell_pri_pain_and_suffering_dummy);
RegisterSpellScript(spell_pri_pain_and_suffering_proc);
RegisterSpellScript(spell_pri_penance);
RegisterSpellAndAuraScriptPair(spell_pri_power_word_shield, spell_pri_power_word_shield_aura);
@@ -1008,4 +1465,17 @@ void AddSC_priest_spell_scripts()
RegisterSpellScript(spell_pri_mind_control);
RegisterSpellScript(spell_pri_t4_4p_bonus);
RegisterSpellScript(spell_pri_shadowfiend_death);
RegisterSpellScript(spell_pri_vampiric_embrace);
RegisterSpellScript(spell_pri_glyph_of_dispel_magic);
RegisterSpellScript(spell_pri_body_and_soul);
RegisterSpellScript(spell_pri_improved_shadowform);
// Proc system scripts
RegisterSpellScript(spell_pri_aq_3p_bonus);
RegisterSpellScript(spell_pri_blessed_recovery);
RegisterSpellScript(spell_pri_imp_shadowform);
RegisterSpellScript(spell_pri_improved_spirit_tap);
RegisterSpellScript(spell_pri_item_t6_trinket);
RegisterSpellScript(spell_pri_t3_4p_bonus);
RegisterSpellScript(spell_pri_t5_heal_2p_bonus);
RegisterSpellScript(spell_pri_t10_heal_2p_bonus);
}

View File

@@ -18,6 +18,7 @@
#include "AreaDefines.h"
#include "CellImpl.h"
#include "CreatureScript.h"
#include "GameTime.h"
#include "GridNotifiers.h"
#include "SpellAuraEffects.h"
#include "SpellMgr.h"
@@ -43,6 +44,22 @@ enum RogueSpells
SPELL_ROGUE_SHIV_TRIGGERED = 5940,
SPELL_ROGUE_TRICKS_OF_THE_TRADE_DMG_BOOST = 57933,
SPELL_ROGUE_TRICKS_OF_THE_TRADE_PROC = 59628,
// Proc system spells
SPELL_ROGUE_MASTER_OF_SUBTLETY_DAMAGE = 31665,
SPELL_ROGUE_DEADLY_BREW_POISON = 3409,
SPELL_ROGUE_QUICK_RECOVERY_ENERGY = 31663,
SPELL_ROGUE_TURN_THE_TABLES_R1 = 52910,
SPELL_ROGUE_TURN_THE_TABLES_R2 = 52914,
SPELL_ROGUE_TURN_THE_TABLES_R3 = 52915,
SPELL_ROGUE_OVERKILL_TRIGGERED = 58427
};
enum RogueSpellIcons
{
ROGUE_ICON_MASTER_OF_SUBTLETY = 2114,
ROGUE_ICON_CUT_TO_THE_CHASE = 2909,
ROGUE_ICON_DEADLY_BREW = 2963,
ROGUE_ICON_QUICK_RECOVERY = 2116
};
class spell_rog_savage_combat : public AuraScript
@@ -753,6 +770,206 @@ class spell_rog_vanish : public SpellScript
}
};
// 56800 - Glyph of Backstab
class spell_rog_glyph_of_backstab : public AuraScript
{
PrepareAuraScript(spell_rog_glyph_of_backstab);
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* target = eventInfo.GetActionTarget();
if (!target)
return;
// Try to find Rupture on target
if (AuraEffect* ruptureEff = target->GetAuraEffect(SPELL_AURA_PERIODIC_DAMAGE, SPELLFAMILY_ROGUE, 0x100000, 0, 0, GetTarget()->GetGUID()))
{
Aura* rupture = ruptureEff->GetBase();
if (!rupture->IsRemoved() && rupture->GetDuration() > 0)
{
// Check if we can extend (max 5 seconds extension per glyph)
if ((rupture->GetApplyTime() + rupture->GetMaxDuration() / 1000 + 5) > (GameTime::GetGameTime().count() + rupture->GetDuration() / 1000))
{
rupture->SetDuration(rupture->GetDuration() + aurEff->GetAmount() * IN_MILLISECONDS);
}
}
}
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_rog_glyph_of_backstab::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 31666 - Master of Subtlety
// 58428 - Overkill
template <uint32 RemoveSpellId>
class spell_rog_stealth_buff_tracker : public AuraScript
{
PrepareAuraScript(spell_rog_stealth_buff_tracker);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ RemoveSpellId });
}
void AfterApply(AuraEffect const* aurEff, AuraEffectHandleModes /*mode*/)
{
if (Aura* visualAura = GetTarget()->GetAura(RemoveSpellId))
{
int32 duration = aurEff->GetBase()->GetDuration();
visualAura->SetDuration(duration);
visualAura->SetMaxDuration(duration);
}
}
void PeriodicTick(AuraEffect const* /*aurEff*/)
{
GetTarget()->RemoveAurasDueToSpell(RemoveSpellId);
}
void Register() override
{
AfterEffectApply += AuraEffectApplyFn(spell_rog_stealth_buff_tracker::AfterApply, EFFECT_0, SPELL_AURA_PERIODIC_DUMMY, AURA_EFFECT_HANDLE_REAL);
OnEffectPeriodic += AuraEffectPeriodicFn(spell_rog_stealth_buff_tracker::PeriodicTick, EFFECT_0, SPELL_AURA_PERIODIC_DUMMY);
}
};
// -51664 - Cut to the Chase
class spell_rog_cut_to_the_chase : public AuraScript
{
PrepareAuraScript(spell_rog_cut_to_the_chase);
void HandleProc(ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
// Refresh Slice and Dice to 5 combo point max duration
if (AuraEffect const* snDEffect = GetTarget()->GetAuraEffect(SPELL_AURA_MOD_MELEE_HASTE, SPELLFAMILY_ROGUE, 0x40000, 0, 0))
{
snDEffect->GetBase()->SetDuration(snDEffect->GetSpellInfo()->GetMaxDuration(), true);
}
}
void Register() override
{
OnProc += AuraProcFn(spell_rog_cut_to_the_chase::HandleProc);
}
};
// -51625 - Deadly Brew
class spell_rog_deadly_brew : public AuraScript
{
PrepareAuraScript(spell_rog_deadly_brew);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_ROGUE_DEADLY_BREW_POISON });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* target = eventInfo.GetActionTarget();
if (target)
GetTarget()->CastSpell(target, SPELL_ROGUE_DEADLY_BREW_POISON, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_rog_deadly_brew::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -31244 - Quick Recovery
class spell_rog_quick_recovery : public AuraScript
{
PrepareAuraScript(spell_rog_quick_recovery);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_ROGUE_QUICK_RECOVERY_ENERGY });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
return eventInfo.GetSpellInfo() != nullptr;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
int32 energyBack = CalculatePct(static_cast<int32>(eventInfo.GetSpellInfo()->ManaCost), aurEff->GetAmount());
if (energyBack > 0)
GetTarget()->CastCustomSpell(SPELL_ROGUE_QUICK_RECOVERY_ENERGY, SPELLVALUE_BASE_POINT0, energyBack, GetTarget(), true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_rog_quick_recovery::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_rog_quick_recovery::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -13983 - Setup
class spell_rog_setup : public AuraScript
{
PrepareAuraScript(spell_rog_setup);
bool CheckProc(ProcEventInfo& eventInfo)
{
if (Player* target = GetTarget()->ToPlayer())
if (eventInfo.GetActor() == target->GetSelectedUnit())
return true;
return false;
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_rog_setup::CheckProc);
}
};
// -51627 - Turn the Tables
class spell_rog_turn_the_tables : public AuraScript
{
PrepareAuraScript(spell_rog_turn_the_tables);
bool Validate(SpellInfo const* spellInfo) override
{
return ValidateSpellInfo({ spellInfo->Effects[EFFECT_0].TriggerSpell });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Unit* caster = GetCaster();
if (!caster)
return;
caster->CastSpell(caster, GetSpellInfo()->Effects[EFFECT_0].TriggerSpell, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_rog_turn_the_tables::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// 52910, 52914, 52915 - Turn the Tables (proc)
class spell_rog_turn_the_tables_proc : public AuraScript
{
PrepareAuraScript(spell_rog_turn_the_tables_proc);
void Register() override
{
// No special handling needed - default behavior
}
};
void AddSC_rogue_spell_scripts()
{
RegisterSpellScript(spell_rog_savage_combat);
@@ -771,4 +988,14 @@ void AddSC_rogue_spell_scripts()
RegisterSpellScript(spell_rog_pickpocket);
RegisterSpellScript(spell_rog_vanish_purge);
RegisterSpellScript(spell_rog_vanish);
// Proc system scripts
RegisterSpellScript(spell_rog_glyph_of_backstab);
RegisterSpellScriptWithArgs(spell_rog_stealth_buff_tracker<SPELL_ROGUE_MASTER_OF_SUBTLETY_DAMAGE>, "spell_rog_master_of_subtlety");
RegisterSpellScriptWithArgs(spell_rog_stealth_buff_tracker<SPELL_ROGUE_OVERKILL_TRIGGERED>, "spell_rog_overkill");
RegisterSpellScript(spell_rog_cut_to_the_chase);
RegisterSpellScript(spell_rog_deadly_brew);
RegisterSpellScript(spell_rog_quick_recovery);
RegisterSpellScript(spell_rog_setup);
RegisterSpellScript(spell_rog_turn_the_tables);
RegisterSpellScript(spell_rog_turn_the_tables_proc);
}

File diff suppressed because it is too large Load Diff

View File

@@ -36,6 +36,7 @@
enum WarlockSpells
{
SPELL_WARLOCK_SHADOW_TRANCE = 17941,
SPELL_WARLOCK_DRAIN_SOUL_R1 = 1120,
SPELL_WARLOCK_CREATE_SOULSHARD = 43836,
SPELL_WARLOCK_CURSE_OF_DOOM_EFFECT = 18662,
@@ -77,6 +78,22 @@ enum WarlockSpells
SPELL_WARLOCK_PET_VOID_STAR_TALISMAN = 37386, // Void Star Talisman
SPELL_WARLOCK_DEMONIC_PACT_PROC = 48090,
SPELL_WARLOCK_GLYPH_OF_VOIDWALKER = 56247,
SPELL_WARLOCK_GLYPH_OF_LIFE_TAP_TRIGGERED = 63321,
SPELL_WARLOCK_SOUL_LEECH_HEAL = 30294,
SPELL_WARLOCK_IMP_SOUL_LEECH_R1 = 54117,
SPELL_WARLOCK_SOUL_LEECH_PET_MANA_1 = 54607,
SPELL_WARLOCK_SOUL_LEECH_PET_MANA_2 = 59118,
SPELL_WARLOCK_SOUL_LEECH_CASTER_MANA_1 = 54300,
SPELL_WARLOCK_SOUL_LEECH_CASTER_MANA_2 = 59117,
SPELL_WARLOCK_SHADOWFLAME_PROC = 37378,
SPELL_WARLOCK_FLAMESHADOW_PROC = 37379,
SPELL_REPLENISHMENT = 57669,
SPELL_WARLOCK_NETHER_PROTECTION_HOLY = 54370,
SPELL_WARLOCK_NETHER_PROTECTION_FIRE = 54371,
SPELL_WARLOCK_NETHER_PROTECTION_FROST = 54372,
SPELL_WARLOCK_NETHER_PROTECTION_ARCANE = 54373,
SPELL_WARLOCK_NETHER_PROTECTION_SHADOW = 54374,
SPELL_WARLOCK_NETHER_PROTECTION_NATURE = 54375,
};
enum WarlockSpellIcons
@@ -1458,8 +1475,483 @@ class spell_warl_demonic_pact_aura : public AuraScript
}
};
// -980 - Curse of Agony
class spell_warl_curse_of_agony : public AuraScript
{
PrepareAuraScript(spell_warl_curse_of_agony);
void ApplyEffect(AuraEffect const* aurEff, AuraEffectHandleModes /*mode*/)
{
_tick_amount = aurEff->GetAmount();
}
void HandleEffectPeriodicUpdate(AuraEffect* aurEff)
{
switch (aurEff->GetTickNumber())
{
// 1..4 ticks, 1/2 from normal tick damage
case 1:
aurEff->SetAmount(_tick_amount / 2);
break;
// 5..8 ticks have normal tick damage
case 5:
aurEff->SetAmount(_tick_amount);
break;
// 9..12 ticks, 3/2 from normal tick damage
case 9:
aurEff->SetAmount((_tick_amount + 1) * 3 / 2); // +1 prevent 0.5 damage possible lost at 1..4 ticks
break;
// 13 and 14 ticks (glyphed only), twice normal tick damage
case 13:
aurEff->SetAmount(_tick_amount * 2);
break;
}
}
void Register() override
{
AfterEffectApply += AuraEffectApplyFn(spell_warl_curse_of_agony::ApplyEffect, EFFECT_0, SPELL_AURA_PERIODIC_DAMAGE, AURA_EFFECT_HANDLE_REAL_OR_REAPPLY_MASK);
OnEffectUpdatePeriodic += AuraEffectUpdatePeriodicFn(spell_warl_curse_of_agony::HandleEffectPeriodicUpdate, EFFECT_0, SPELL_AURA_PERIODIC_DAMAGE);
}
private:
uint32 _tick_amount = 0;
};
// 56218 - Glyph of Corruption
class spell_warl_glyph_of_corruption_nightfall : public AuraScript
{
PrepareAuraScript(spell_warl_glyph_of_corruption_nightfall);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARLOCK_SHADOW_TRANCE });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = eventInfo.GetActor();
caster->CastSpell(caster, SPELL_WARLOCK_SHADOW_TRANCE, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warl_glyph_of_corruption_nightfall::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 18094, 18095 - Nightfall
class spell_warl_nightfall : public AuraScript
{
PrepareAuraScript(spell_warl_nightfall);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARLOCK_SHADOW_TRANCE });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->CastSpell(GetTarget(), SPELL_WARLOCK_SHADOW_TRANCE, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warl_nightfall::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -63156 - Decimation
class spell_warl_decimation : public AuraScript
{
PrepareAuraScript(spell_warl_decimation);
bool CheckProc(ProcEventInfo& eventInfo)
{
if (SpellInfo const* spellInfo = eventInfo.GetSpellInfo())
if (eventInfo.GetActionTarget()->HasAuraState(AURA_STATE_HEALTHLESS_35_PERCENT, spellInfo, eventInfo.GetActor()))
return true;
return false;
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_warl_decimation::CheckProc);
}
};
// 54909, 53646 - Demonic Pact
class spell_warl_demonic_pact : public AuraScript
{
PrepareAuraScript(spell_warl_demonic_pact);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARLOCK_DEMONIC_PACT_PROC });
}
bool CheckProc(ProcEventInfo& eventInfo)
{
return eventInfo.GetActor() && eventInfo.GetActor()->IsPet();
}
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
if (Unit* owner = eventInfo.GetActor()->GetOwner())
{
if (AuraEffect* aurEff = owner->GetDummyAuraEffect(SPELLFAMILY_WARLOCK, WARLOCK_ICON_ID_DEMONIC_PACT, EFFECT_0))
{
int32 bp = static_cast<int32>((aurEff->GetAmount() * owner->SpellBaseDamageBonusDone(SPELL_SCHOOL_MASK_MAGIC) + 100.0f) / 100.0f);
owner->CastCustomSpell(owner, SPELL_WARLOCK_DEMONIC_PACT_PROC, &bp, &bp, nullptr, true, nullptr, aurEff);
}
}
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_warl_demonic_pact::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_warl_demonic_pact::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// 63320 - Glyph of Life Tap
class spell_warl_glyph_of_life_tap : public AuraScript
{
PrepareAuraScript(spell_warl_glyph_of_life_tap);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARLOCK_GLYPH_OF_LIFE_TAP_TRIGGERED });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Unit* caster = GetTarget();
caster->CastSpell(caster, SPELL_WARLOCK_GLYPH_OF_LIFE_TAP_TRIGGERED, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warl_glyph_of_life_tap::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 18213, 18372 - Improved Drain Soul (proc handler)
class spell_warl_improved_drain_soul : public AuraScript
{
PrepareAuraScript(spell_warl_improved_drain_soul);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_WARLOCK_DRAIN_SOUL_R1,
SPELL_WARLOCK_IMPROVED_DRAIN_SOUL_R1,
SPELL_WARLOCK_IMPROVED_DRAIN_SOUL_PROC
});
}
bool CheckProc(ProcEventInfo& eventInfo)
{
// Make sure that dying unit is afflicted by the caster's Drain Soul debuff
Unit* caster = eventInfo.GetActor();
Unit* victim = eventInfo.GetActionTarget();
return victim->GetAuraApplicationOfRankedSpell(SPELL_WARLOCK_DRAIN_SOUL_R1, caster->GetGUID()) != nullptr;
}
void HandleProc(ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = eventInfo.GetActor();
// Improved Drain Soul - use the current aura (this script is on the talent)
int32 amount = CalculatePct(caster->GetMaxPower(POWER_MANA), GetSpellInfo()->Effects[EFFECT_2].CalcValue());
caster->CastCustomSpell(SPELL_WARLOCK_IMPROVED_DRAIN_SOUL_PROC, SPELLVALUE_BASE_POINT0, amount, caster, true);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_warl_improved_drain_soul::CheckProc);
OnProc += AuraProcFn(spell_warl_improved_drain_soul::HandleProc);
}
};
// -27243 - Seed of Corruption (proc handler)
class spell_warl_seed_of_corruption_dummy : public AuraScript
{
PrepareAuraScript(spell_warl_seed_of_corruption_dummy);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARLOCK_SEED_OF_CORRUPTION_DAMAGE_R1 });
}
void CalculateBuffer(AuraEffect const* aurEff, int32& amount, bool& /*canBeRecalculated*/)
{
Unit* caster = GetCaster();
if (!caster)
return;
amount = caster->SpellDamageBonusDone(GetUnitOwner(), GetSpellInfo(), amount, SPELL_DIRECT_DAMAGE, aurEff->GetEffIndex());
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
int32 amount = aurEff->GetAmount() - damageInfo->GetDamage();
if (amount > 0)
{
const_cast<AuraEffect*>(aurEff)->SetAmount(amount);
if (!GetTarget()->HealthBelowPctDamaged(1, damageInfo->GetDamage()))
return;
}
Remove();
Unit* caster = GetCaster();
if (!caster)
return;
uint32 spellId = sSpellMgr->GetSpellWithRank(SPELL_WARLOCK_SEED_OF_CORRUPTION_DAMAGE_R1, GetSpellInfo()->GetRank());
caster->CastSpell(eventInfo.GetActionTarget(), spellId, true, nullptr, aurEff);
}
void Register() override
{
DoEffectCalcAmount += AuraEffectCalcAmountFn(spell_warl_seed_of_corruption_dummy::CalculateBuffer, EFFECT_1, SPELL_AURA_DUMMY);
OnEffectProc += AuraEffectProcFn(spell_warl_seed_of_corruption_dummy::HandleProc, EFFECT_1, SPELL_AURA_DUMMY);
}
};
// 32863, 36123, 38252, 39367, 44141, 70388 - Seed of Corruption (generic)
class spell_warl_seed_of_corruption_generic : public AuraScript
{
PrepareAuraScript(spell_warl_seed_of_corruption_generic);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARLOCK_SEED_OF_CORRUPTION_DAMAGE_GENERIC });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
int32 amount = aurEff->GetAmount() - damageInfo->GetDamage();
if (amount > 0)
{
const_cast<AuraEffect*>(aurEff)->SetAmount(amount);
return;
}
Remove();
Unit* caster = GetCaster();
if (!caster)
return;
caster->CastSpell(eventInfo.GetActionTarget(), SPELL_WARLOCK_SEED_OF_CORRUPTION_DAMAGE_GENERIC, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warl_seed_of_corruption_generic::HandleProc, EFFECT_1, SPELL_AURA_DUMMY);
}
};
// -30293 - Soul Leech
class spell_warl_soul_leech : public AuraScript
{
PrepareAuraScript(spell_warl_soul_leech);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_WARLOCK_SOUL_LEECH_HEAL,
SPELL_WARLOCK_IMP_SOUL_LEECH_R1,
SPELL_WARLOCK_SOUL_LEECH_PET_MANA_1,
SPELL_WARLOCK_SOUL_LEECH_PET_MANA_2,
SPELL_WARLOCK_SOUL_LEECH_CASTER_MANA_1,
SPELL_WARLOCK_SOUL_LEECH_CASTER_MANA_2,
SPELL_REPLENISHMENT
});
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
static uint32 const casterMana[2] = { SPELL_WARLOCK_SOUL_LEECH_CASTER_MANA_1, SPELL_WARLOCK_SOUL_LEECH_CASTER_MANA_2 };
static uint32 const petMana[2] = { SPELL_WARLOCK_SOUL_LEECH_PET_MANA_1, SPELL_WARLOCK_SOUL_LEECH_PET_MANA_2 };
PreventDefaultAction();
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (!damageInfo || !damageInfo->GetDamage())
return;
Unit* caster = eventInfo.GetActor();
int32 healAmount = CalculatePct(static_cast<int32>(damageInfo->GetDamage()), aurEff->GetAmount());
caster->CastCustomSpell(SPELL_WARLOCK_SOUL_LEECH_HEAL, SPELLVALUE_BASE_POINT0, healAmount, caster, true, nullptr, aurEff);
// Improved Soul Leech code below
AuraEffect const* impSoulLeech = GetTarget()->GetAuraEffectOfRankedSpell(SPELL_WARLOCK_IMP_SOUL_LEECH_R1, EFFECT_1, aurEff->GetCasterGUID());
if (!impSoulLeech)
return;
uint8 impSoulLeechRank = impSoulLeech->GetSpellInfo()->GetRank();
uint32 selfSpellId = casterMana[impSoulLeechRank - 1];
uint32 petSpellId = petMana[impSoulLeechRank - 1];
caster->CastSpell(nullptr, selfSpellId, true, nullptr, aurEff);
caster->CastSpell(nullptr, petSpellId, true, nullptr, aurEff);
if (roll_chance_i(impSoulLeech->GetAmount()))
caster->CastSpell(nullptr, SPELL_REPLENISHMENT, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warl_soul_leech::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 37377 - Shadowflame (T4 2P fire)
class spell_warl_t4_2p_bonus_fire : public AuraScript
{
PrepareAuraScript(spell_warl_t4_2p_bonus_fire);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARLOCK_SHADOWFLAME_PROC });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->CastSpell(GetTarget(), SPELL_WARLOCK_SHADOWFLAME_PROC, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warl_t4_2p_bonus_fire::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// 39437 - Shadowflame Hellfire and RoF (T4 2P shadow)
class spell_warl_t4_2p_bonus_shadow : public AuraScript
{
PrepareAuraScript(spell_warl_t4_2p_bonus_shadow);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARLOCK_FLAMESHADOW_PROC });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->CastSpell(GetTarget(), SPELL_WARLOCK_FLAMESHADOW_PROC, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warl_t4_2p_bonus_shadow::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// -30299 - Nether Protection
class spell_warl_nether_protection : public AuraScript
{
PrepareAuraScript(spell_warl_nether_protection);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_WARLOCK_NETHER_PROTECTION_HOLY,
SPELL_WARLOCK_NETHER_PROTECTION_FIRE,
SPELL_WARLOCK_NETHER_PROTECTION_NATURE,
SPELL_WARLOCK_NETHER_PROTECTION_FROST,
SPELL_WARLOCK_NETHER_PROTECTION_SHADOW,
SPELL_WARLOCK_NETHER_PROTECTION_ARCANE
});
}
bool CheckProc(ProcEventInfo& eventInfo)
{
if (DamageInfo* damageInfo = eventInfo.GetDamageInfo())
{
switch (GetFirstSchoolInMask(damageInfo->GetSchoolMask()))
{
case SPELL_SCHOOL_HOLY:
case SPELL_SCHOOL_FIRE:
case SPELL_SCHOOL_NATURE:
case SPELL_SCHOOL_FROST:
case SPELL_SCHOOL_SHADOW:
case SPELL_SCHOOL_ARCANE:
return true;
default:
break;
}
}
return false;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
uint32 triggerspell = 0;
switch (GetFirstSchoolInMask(eventInfo.GetDamageInfo()->GetSchoolMask()))
{
case SPELL_SCHOOL_HOLY:
triggerspell = SPELL_WARLOCK_NETHER_PROTECTION_HOLY;
break;
case SPELL_SCHOOL_FIRE:
triggerspell = SPELL_WARLOCK_NETHER_PROTECTION_FIRE;
break;
case SPELL_SCHOOL_NATURE:
triggerspell = SPELL_WARLOCK_NETHER_PROTECTION_NATURE;
break;
case SPELL_SCHOOL_FROST:
triggerspell = SPELL_WARLOCK_NETHER_PROTECTION_FROST;
break;
case SPELL_SCHOOL_SHADOW:
triggerspell = SPELL_WARLOCK_NETHER_PROTECTION_SHADOW;
break;
case SPELL_SCHOOL_ARCANE:
triggerspell = SPELL_WARLOCK_NETHER_PROTECTION_ARCANE;
break;
default:
return;
}
if (Unit* target = eventInfo.GetActionTarget())
target->CastSpell(target, triggerspell, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_warl_nether_protection::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_warl_nether_protection::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
void AddSC_warlock_spell_scripts()
{
RegisterSpellScript(spell_warl_nether_protection);
RegisterSpellScript(spell_warl_eye_of_kilrogg);
RegisterSpellScript(spell_warl_shadowflame);
RegisterSpellScript(spell_warl_seduction);
@@ -1493,4 +1985,16 @@ void AddSC_warlock_spell_scripts()
RegisterSpellScript(spell_warl_shadowburn);
RegisterSpellScript(spell_warl_voidwalker_pet_passive);
RegisterSpellScript(spell_warl_demonic_pact_aura);
RegisterSpellScript(spell_warl_curse_of_agony);
RegisterSpellScript(spell_warl_glyph_of_corruption_nightfall);
RegisterSpellScript(spell_warl_nightfall);
RegisterSpellScript(spell_warl_decimation);
RegisterSpellScript(spell_warl_demonic_pact);
RegisterSpellScript(spell_warl_glyph_of_life_tap);
RegisterSpellScript(spell_warl_improved_drain_soul);
RegisterSpellScript(spell_warl_seed_of_corruption_dummy);
RegisterSpellScript(spell_warl_seed_of_corruption_generic);
RegisterSpellScript(spell_warl_soul_leech);
RegisterSpellScript(spell_warl_t4_2p_bonus_fire);
RegisterSpellScript(spell_warl_t4_2p_bonus_shadow);
}

View File

@@ -62,11 +62,22 @@ enum WarriorSpells
SPELL_WARRIOR_WHIRLWIND_MAIN = 50622,
SPELL_WARRIOR_WHIRLWIND_OFF = 44949,
SPELL_WARRIOR_EXECUTE_R1 = 5308,
SPELL_WARRIOR_SECOND_WIND_HEAL_R1 = 29841,
SPELL_WARRIOR_SECOND_WIND_HEAL_R2 = 29842,
SPELL_WARRIOR_SECOND_WIND_UK = 42771,
SPELL_WARRIOR_T10_PROT_4P_ABSORB = 70845,
SPELL_WARRIOR_GLYPH_OF_BLOCKING_BUFF = 58374,
SPELL_WARRIOR_T10_MELEE_4P_BONUS = 70847,
SPELL_WARRIOR_T10_MELEE_4P_EXTRA_CHARGE = 70849,
SPELL_WARRIOR_SLAM_GCD_REDUCED = 71072,
SPELL_WARRIOR_EXECUTE_GCD_REDUCED = 71069,
SPELL_WARRIOR_WARRIORS_WRATH = 21887,
};
enum WarriorSpellIcons
{
WARRIOR_ICON_ID_SUDDEN_DEATH = 1989
WARRIOR_ICON_ID_SUDDEN_DEATH = 1989,
WARRIOR_ICON_ID_SECOND_WIND = 1697
};
enum MiscSpells
@@ -726,17 +737,6 @@ class spell_warr_vigilance : public AuraScript
target->CastSpell(caster, SPELL_WARRIOR_VIGILANCE_REDIRECT_THREAT, true);
}
void HandleAfterApply(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
{
//! WORKAROUND
//! this glyph is a proc
if (Unit* caster = GetCaster())
{
if (AuraEffect const* glyph = caster->GetAuraEffect(SPELL_WARRIOR_GLYPH_OF_VIGILANCE, EFFECT_0))
GetTarget()->ModifyRedirectThreat(glyph->GetAmount());
}
}
void HandleRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
{
Unit* target = GetTarget();
@@ -766,7 +766,6 @@ class spell_warr_vigilance : public AuraScript
void Register() override
{
OnEffectApply += AuraEffectApplyFn(spell_warr_vigilance::HandleApply, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL, AURA_EFFECT_HANDLE_REAL_OR_REAPPLY_MASK);
AfterEffectApply += AuraEffectApplyFn(spell_warr_vigilance::HandleAfterApply, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL, AURA_EFFECT_HANDLE_REAL_OR_REAPPLY_MASK);
OnEffectRemove += AuraEffectRemoveFn(spell_warr_vigilance::HandleRemove, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL, AURA_EFFECT_HANDLE_REAL_OR_REAPPLY_MASK);
DoCheckProc += AuraCheckProcFn(spell_warr_vigilance::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_warr_vigilance::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
@@ -776,6 +775,29 @@ private:
Unit* _procTarget;
};
// 59665 - Vigilance (Redirect Threat)
class spell_warr_vigilance_redirect_threat : public SpellScript
{
PrepareSpellScript(spell_warr_vigilance_redirect_threat);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARRIOR_GLYPH_OF_VIGILANCE });
}
void HandleGlyph(SpellEffIndex /*effIndex*/)
{
if (Unit* warrior = GetHitUnit())
if (AuraEffect const* glyph = warrior->GetAuraEffect(SPELL_WARRIOR_GLYPH_OF_VIGILANCE, EFFECT_0))
SetEffectValue(GetEffectValue() + glyph->GetAmount());
}
void Register() override
{
OnEffectHitTarget += SpellEffectFn(spell_warr_vigilance_redirect_threat::HandleGlyph, EFFECT_0, SPELL_EFFECT_REDIRECT_THREAT);
}
};
// 50725 - Vigilance
class spell_warr_vigilance_trigger : public SpellScript
{
@@ -826,35 +848,27 @@ class spell_warr_glyph_of_sunder_armor : public AuraScript
}
};
// Spell 28845 - Cheat Death
enum CheatDeath
{
SPELL_CHEAT_DEATH_TRIGGER = 28846
};
// 28845 - Cheat Death
class spell_warr_t3_prot_8p_bonus : public AuraScript
{
PrepareAuraScript(spell_warr_t3_prot_8p_bonus);
bool CheckProc(ProcEventInfo& eventInfo)
{
return eventInfo.GetActionTarget() && eventInfo.GetActionTarget()->GetHealthPct() <= 20.0f;
}
if (eventInfo.GetActionTarget()->HealthBelowPct(20))
return true;
void HandleEffectProc(AuraEffect const* /*aurEff*/, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
if (Unit* target = eventInfo.GetActionTarget())
{
target->CastSpell(target, SPELL_CHEAT_DEATH_TRIGGER, true);
}
DamageInfo* damageInfo = eventInfo.GetDamageInfo();
if (damageInfo && damageInfo->GetDamage())
if (GetTarget()->HealthBelowPctDamaged(20, damageInfo->GetDamage()))
return true;
return false;
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_warr_t3_prot_8p_bonus::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_warr_t3_prot_8p_bonus::HandleEffectProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
@@ -980,6 +994,235 @@ class spell_war_sudden_death_aura : public AuraScript
}
};
// Second Wind - triggers health regen when stunned or immobilized
class spell_warr_second_wind : public AuraScript
{
PrepareAuraScript(spell_warr_second_wind);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({
SPELL_WARRIOR_SECOND_WIND_HEAL_R1,
SPELL_WARRIOR_SECOND_WIND_HEAL_R2,
SPELL_WARRIOR_SECOND_WIND_UK
});
}
bool CheckProc(ProcEventInfo& eventInfo)
{
SpellInfo const* procSpell = eventInfo.GetSpellInfo();
if (!procSpell)
return false;
// Must be from stun or root mechanic
if (!(procSpell->GetAllEffectsMechanicMask() & ((1 << MECHANIC_ROOT) | (1 << MECHANIC_STUN))))
return false;
// Not from self
if (eventInfo.GetActionTarget() == eventInfo.GetActor())
return false;
return true;
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
uint32 triggeredSpellId = 0;
switch (GetId())
{
case 29838: triggeredSpellId = SPELL_WARRIOR_SECOND_WIND_HEAL_R2; break;
case 29834: triggeredSpellId = SPELL_WARRIOR_SECOND_WIND_HEAL_R1; break;
case 42770: triggeredSpellId = SPELL_WARRIOR_SECOND_WIND_UK; break;
default:
return;
}
GetTarget()->CastSpell(GetTarget(), triggeredSpellId, true, nullptr, aurEff);
}
void Register() override
{
DoCheckProc += AuraCheckProcFn(spell_warr_second_wind::CheckProc);
OnEffectProc += AuraEffectProcFn(spell_warr_second_wind::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// Deep Wounds - calculates bleed damage based on weapon damage
class spell_warr_deep_wounds_aura : public AuraScript
{
PrepareAuraScript(spell_warr_deep_wounds_aura);
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& eventInfo)
{
PreventDefaultAction();
Unit* caster = GetTarget();
if (!caster->IsPlayer())
return;
int32 basepoints;
if (eventInfo.GetTypeMask() & PROC_FLAG_DONE_OFFHAND_ATTACK)
basepoints = int32((caster->GetFloatValue(UNIT_FIELD_MAXOFFHANDDAMAGE) + caster->GetFloatValue(UNIT_FIELD_MINOFFHANDDAMAGE)) / 2.0f);
else
basepoints = int32((caster->GetFloatValue(UNIT_FIELD_MAXDAMAGE) + caster->GetFloatValue(UNIT_FIELD_MINDAMAGE)) / 2.0f);
uint32 triggeredSpellId = GetSpellInfo()->Effects[EFFECT_0].TriggerSpell;
if (Unit* target = eventInfo.GetActionTarget())
caster->CastCustomSpell(target, triggeredSpellId, &basepoints, nullptr, nullptr, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warr_deep_wounds_aura::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// Warrior T10 Melee 4P Bonus - extra effects for Sudden Death/Bloodsurge procs
class spell_warr_extra_proc : public AuraScript
{
PrepareAuraScript(spell_warr_extra_proc);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({
SPELL_WARRIOR_T10_MELEE_4P_BONUS,
SPELL_WARRIOR_T10_MELEE_4P_EXTRA_CHARGE,
SPELL_WARRIOR_SLAM_GCD_REDUCED,
SPELL_WARRIOR_EXECUTE_GCD_REDUCED
});
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
Unit* caster = GetTarget();
uint32 triggeredSpellId = GetSpellInfo()->Effects[EFFECT_0].TriggerSpell;
// Triggered spell IDs: 46916 = Slam!, 52437 = Sudden Death
bool isBloodsurge = (triggeredSpellId == 46916);
// Item - Warrior T10 Melee 4P Bonus
if (AuraEffect const* t10Bonus = caster->GetAuraEffect(SPELL_WARRIOR_T10_MELEE_4P_BONUS, EFFECT_0))
{
if (!roll_chance_i(t10Bonus->GetAmount()))
{
// Don't allow normal proc to override set one
if (caster->GetAura(isBloodsurge ? SPELL_WARRIOR_SLAM_GCD_REDUCED : SPELL_WARRIOR_EXECUTE_GCD_REDUCED))
{
PreventDefaultAction();
return;
}
// Just to be sure
caster->RemoveAurasDueToSpell(SPELL_WARRIOR_T10_MELEE_4P_EXTRA_CHARGE);
return;
}
PreventDefaultAction();
// Fully remove all auras and reapply once more
caster->RemoveAurasDueToSpell(SPELL_WARRIOR_T10_MELEE_4P_EXTRA_CHARGE);
caster->RemoveAurasDueToSpell(SPELL_WARRIOR_SLAM_GCD_REDUCED);
caster->RemoveAurasDueToSpell(SPELL_WARRIOR_EXECUTE_GCD_REDUCED);
caster->CastSpell(caster, SPELL_WARRIOR_T10_MELEE_4P_EXTRA_CHARGE, true, nullptr, aurEff);
caster->CastSpell(caster, triggeredSpellId, true, nullptr, aurEff);
caster->CastSpell(caster, isBloodsurge ? SPELL_WARRIOR_SLAM_GCD_REDUCED : SPELL_WARRIOR_EXECUTE_GCD_REDUCED, true, nullptr, aurEff);
}
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warr_extra_proc::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// Sword and Board proc - remove Shield Slam cooldown
class spell_warr_sword_and_board : public AuraScript
{
PrepareAuraScript(spell_warr_sword_and_board);
void HandleProc(AuraEffect const* /*aurEff*/, ProcEventInfo& /*eventInfo*/)
{
Unit* caster = GetTarget();
if (caster->IsPlayer())
caster->ToPlayer()->RemoveCategoryCooldown(1209); // Shield Slam category
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warr_sword_and_board::HandleProc, EFFECT_0, SPELL_AURA_PROC_TRIGGER_SPELL);
}
};
// Glyph of Blocking - triggers block value buff
class spell_warr_glyph_of_blocking : public AuraScript
{
PrepareAuraScript(spell_warr_glyph_of_blocking);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARRIOR_GLYPH_OF_BLOCKING_BUFF });
}
void HandleProc(AuraEffect const* aurEff, ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
GetTarget()->CastSpell(GetTarget(), SPELL_WARRIOR_GLYPH_OF_BLOCKING_BUFF, true, nullptr, aurEff);
}
void Register() override
{
OnEffectProc += AuraEffectProcFn(spell_warr_glyph_of_blocking::HandleProc, EFFECT_0, SPELL_AURA_DUMMY);
}
};
// Item - Warrior T10 Protection 4P Bonus
class spell_warr_item_t10_prot_4p_bonus : public AuraScript
{
PrepareAuraScript(spell_warr_item_t10_prot_4p_bonus);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARRIOR_T10_PROT_4P_ABSORB });
}
void HandleProc(ProcEventInfo& /*eventInfo*/)
{
PreventDefaultAction();
Unit* caster = GetTarget();
int32 basepoints = CalculatePct(static_cast<int32>(caster->GetMaxHealth()), GetSpellInfo()->Effects[EFFECT_1].CalcValue());
caster->CastCustomSpell(caster, SPELL_WARRIOR_T10_PROT_4P_ABSORB, &basepoints, nullptr, nullptr, true, nullptr, GetEffect(EFFECT_0));
}
void Register() override
{
OnProc += AuraProcFn(spell_warr_item_t10_prot_4p_bonus::HandleProc);
}
};
// 21977 - Warrior's Wrath (T3 8P Bonus)
class spell_warr_warriors_wrath : public SpellScript
{
PrepareSpellScript(spell_warr_warriors_wrath);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_WARRIOR_WARRIORS_WRATH });
}
void HandleDummy(SpellEffIndex /*effIndex*/)
{
GetCaster()->CastSpell(GetCaster(), SPELL_WARRIOR_WARRIORS_WRATH, true);
}
void Register() override
{
OnEffectHit += SpellEffectFn(spell_warr_warriors_wrath::HandleDummy, EFFECT_0, SPELL_EFFECT_DUMMY);
}
};
void AddSC_warrior_spell_scripts()
{
RegisterSpellScript(spell_warr_mocking_blow);
@@ -1004,8 +1247,16 @@ void AddSC_warrior_spell_scripts()
RegisterSpellScript(spell_warr_slam);
RegisterSpellScript(spell_warr_sweeping_strikes);
RegisterSpellScript(spell_warr_vigilance);
RegisterSpellScript(spell_warr_vigilance_redirect_threat);
RegisterSpellScript(spell_warr_vigilance_trigger);
RegisterSpellScript(spell_warr_warriors_wrath);
RegisterSpellScript(spell_warr_t3_prot_8p_bonus);
RegisterSpellScript(spell_warr_heroic_strike);
RegisterSpellScript(spell_war_sudden_death_aura);
RegisterSpellScript(spell_warr_second_wind);
RegisterSpellScript(spell_warr_deep_wounds_aura);
RegisterSpellScript(spell_warr_extra_proc);
RegisterSpellScript(spell_warr_sword_and_board);
RegisterSpellScript(spell_warr_glyph_of_blocking);
RegisterSpellScript(spell_warr_item_t10_prot_4p_bonus);
}