mirror of
https://github.com/mod-playerbots/azerothcore-wotlk.git
synced 2026-01-16 18:40:28 +00:00
chore(Scripts/BlackTemple): Update Akama, Supremus, Gorefiend and Naj… (#17867)
chore(Scripts/BlackTemple): Update Akama, Supremus, Gorefiend and Najentus to new register method
This commit is contained in:
@@ -105,4 +105,6 @@ inline AI* GetBlackTempleAI(T* obj)
|
||||
return GetInstanceAI<AI>(obj, BlackTempleScriptName);
|
||||
}
|
||||
|
||||
#define RegisterBlackTempleCreatureAI(ai_name) RegisterCreatureAIWithFactory(ai_name, GetBlackTempleAI)
|
||||
|
||||
#endif // BLACK_TEMPLE_H_
|
||||
|
||||
@@ -90,541 +90,477 @@ enum Misc
|
||||
EVENT_AKAMA_SCENE7 = 36
|
||||
};
|
||||
|
||||
class boss_shade_of_akama : public CreatureScript
|
||||
struct boss_shade_of_akama : public BossAI
|
||||
{
|
||||
public:
|
||||
boss_shade_of_akama() : CreatureScript("boss_shade_of_akama") { }
|
||||
|
||||
struct boss_shade_of_akamaAI : public BossAI
|
||||
boss_shade_of_akama(Creature* creature) : BossAI(creature, DATA_SHADE_OF_AKAMA), summonsChanneler(me), summonsGenerator(me)
|
||||
{
|
||||
boss_shade_of_akamaAI(Creature* creature) : BossAI(creature, DATA_SHADE_OF_AKAMA), summonsChanneler(me), summonsGenerator(me)
|
||||
{
|
||||
events2.ScheduleEvent(EVENT_SHADE_GATHER_NPCS, 1000);
|
||||
}
|
||||
events2.ScheduleEvent(EVENT_SHADE_GATHER_NPCS, 1000);
|
||||
}
|
||||
|
||||
SummonList summonsChanneler;
|
||||
SummonList summonsGenerator;
|
||||
EventMap events2;
|
||||
SummonList summonsChanneler;
|
||||
SummonList summonsGenerator;
|
||||
EventMap events2;
|
||||
|
||||
void ChannelersAction(int32 action)
|
||||
{
|
||||
for (SummonList::const_iterator i = summonsChanneler.begin(); i != summonsChanneler.end(); ++i)
|
||||
if (Creature* summon = ObjectAccessor::GetCreature(*me, *i))
|
||||
void ChannelersAction(int32 action)
|
||||
{
|
||||
for (SummonList::const_iterator i = summonsChanneler.begin(); i != summonsChanneler.end(); ++i)
|
||||
if (Creature* summon = ObjectAccessor::GetCreature(*me, *i))
|
||||
{
|
||||
if (action == ACTION_CHANNELERS_START_CHANNEL)
|
||||
{
|
||||
if (action == ACTION_CHANNELERS_START_CHANNEL)
|
||||
{
|
||||
summon->CastSpell(me, SPELL_SHADE_SOUL_CHANNEL, true);
|
||||
summon->SetUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
}
|
||||
else if (action == ACTION_START_ENCOUNTER)
|
||||
{
|
||||
summon->RemoveUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
}
|
||||
else if (action == ACTION_KILL_CHANNELERS)
|
||||
{
|
||||
Unit::Kill(me, summon);
|
||||
}
|
||||
summon->CastSpell(me, SPELL_SHADE_SOUL_CHANNEL, true);
|
||||
summon->SetUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
}
|
||||
}
|
||||
else if (action == ACTION_START_ENCOUNTER)
|
||||
{
|
||||
summon->RemoveUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
}
|
||||
else if (action == ACTION_KILL_CHANNELERS)
|
||||
{
|
||||
Unit::Kill(me, summon);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
BossAI::Reset();
|
||||
me->SetReactState(REACT_PASSIVE);
|
||||
me->SetUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
me->SetImmuneToAll(true);
|
||||
me->SetWalk(true);
|
||||
}
|
||||
void Reset() override
|
||||
{
|
||||
BossAI::Reset();
|
||||
me->SetReactState(REACT_PASSIVE);
|
||||
me->SetUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
me->SetImmuneToAll(true);
|
||||
me->SetWalk(true);
|
||||
}
|
||||
|
||||
void EnterEvadeMode(EvadeReason why) override
|
||||
{
|
||||
BossAI::EnterEvadeMode(why);
|
||||
summonsGenerator.DoAction(ACTION_DESPAWN_ALL);
|
||||
events2.ScheduleEvent(EVENT_SHADE_RESET_ENCOUNTER, 20000);
|
||||
me->SetVisible(false);
|
||||
ChannelersAction(ACTION_KILL_CHANNELERS);
|
||||
}
|
||||
void EnterEvadeMode(EvadeReason why) override
|
||||
{
|
||||
BossAI::EnterEvadeMode(why);
|
||||
summonsGenerator.DoAction(ACTION_DESPAWN_ALL);
|
||||
events2.ScheduleEvent(EVENT_SHADE_RESET_ENCOUNTER, 20000);
|
||||
me->SetVisible(false);
|
||||
ChannelersAction(ACTION_KILL_CHANNELERS);
|
||||
}
|
||||
|
||||
void JustDied(Unit* killer) override
|
||||
void JustDied(Unit* killer) override
|
||||
{
|
||||
BossAI::JustDied(killer);
|
||||
summonsGenerator.DoAction(ACTION_DESPAWN_ALL);
|
||||
summonsChanneler.DespawnAll();
|
||||
me->CastSpell(me, SPELL_SHADE_OF_AKAMA_TRIGGER, true);
|
||||
if (Creature* akama = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_AKAMA_SHADE)))
|
||||
{
|
||||
BossAI::JustDied(killer);
|
||||
summonsGenerator.DoAction(ACTION_DESPAWN_ALL);
|
||||
summonsChanneler.DespawnAll();
|
||||
me->CastSpell(me, SPELL_SHADE_OF_AKAMA_TRIGGER, true);
|
||||
akama->SetHomePosition(*akama);
|
||||
akama->AI()->DoAction(ACTION_SHADE_DIED);
|
||||
}
|
||||
}
|
||||
|
||||
void DoAction(int32 param) override
|
||||
{
|
||||
if (param == ACTION_START_ENCOUNTER)
|
||||
{
|
||||
summonsGenerator.DoAction(ACTION_START_ENCOUNTER);
|
||||
ChannelersAction(ACTION_START_ENCOUNTER);
|
||||
events.ScheduleEvent(EVENT_SHADE_CHECK_DISTANCE, 1000);
|
||||
}
|
||||
else if (param == ACTION_AKAMA_DIED)
|
||||
{
|
||||
EnterEvadeMode(EVADE_REASON_OTHER);
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
events2.Update(diff);
|
||||
switch (events2.ExecuteEvent())
|
||||
{
|
||||
case EVENT_SHADE_GATHER_NPCS:
|
||||
{
|
||||
std::list<Creature*> ChannelerList;
|
||||
me->GetCreaturesWithEntryInRange(ChannelerList, 100.0f, NPC_ASHTONGUE_CHANNELER);
|
||||
for (std::list<Creature*>::const_iterator itr = ChannelerList.begin(); itr != ChannelerList.end(); ++itr)
|
||||
summonsChanneler.Summon(*itr);
|
||||
|
||||
std::list<Creature*> SpawnerList;
|
||||
me->GetCreaturesWithEntryInRange(SpawnerList, 100.0f, NPC_CREATURE_GENERATOR_AKAMA);
|
||||
for (std::list<Creature*>::const_iterator itr = SpawnerList.begin(); itr != SpawnerList.end(); ++itr)
|
||||
summonsGenerator.Summon(*itr);
|
||||
|
||||
summonsChanneler.Respawn();
|
||||
summonsGenerator.Respawn();
|
||||
ChannelersAction(ACTION_CHANNELERS_START_CHANNEL);
|
||||
|
||||
if (Creature* akama = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_AKAMA_SHADE)))
|
||||
{
|
||||
akama->SetHomePosition(*akama);
|
||||
akama->AI()->DoAction(ACTION_SHADE_DIED);
|
||||
}
|
||||
akama->Respawn(true);
|
||||
break;
|
||||
}
|
||||
case EVENT_SHADE_RESET_ENCOUNTER:
|
||||
me->SetVisible(true);
|
||||
summonsGenerator.Respawn();
|
||||
summonsChanneler.Respawn();
|
||||
ChannelersAction(ACTION_CHANNELERS_START_CHANNEL);
|
||||
|
||||
if (Creature* akama = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_AKAMA_SHADE)))
|
||||
akama->Respawn(true);
|
||||
break;
|
||||
}
|
||||
|
||||
void JustEngagedWith(Unit* who) override
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
BossAI::JustEngagedWith(who);
|
||||
}
|
||||
|
||||
void DoAction(int32 param) override
|
||||
{
|
||||
if (param == ACTION_START_ENCOUNTER)
|
||||
case EVENT_SHADE_CHECK_DISTANCE:
|
||||
if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() != POINT_MOTION_TYPE)
|
||||
{
|
||||
summonsGenerator.DoAction(ACTION_START_ENCOUNTER);
|
||||
ChannelersAction(ACTION_START_ENCOUNTER);
|
||||
events.ScheduleEvent(EVENT_SHADE_CHECK_DISTANCE, 1000);
|
||||
int32 slow = me->GetMaxNegativeAuraModifier(SPELL_AURA_MOD_DECREASE_SPEED);
|
||||
if (slow > -100)
|
||||
{
|
||||
me->SetWalk(true);
|
||||
me->GetMotionMaster()->MovePoint(POINT_START, 510.0f, 400.7993f, 112.7837f);
|
||||
}
|
||||
}
|
||||
else if (param == ACTION_AKAMA_DIED)
|
||||
else
|
||||
{
|
||||
EnterEvadeMode(EVADE_REASON_OTHER);
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
events2.Update(diff);
|
||||
switch (events2.ExecuteEvent())
|
||||
{
|
||||
case EVENT_SHADE_GATHER_NPCS:
|
||||
{
|
||||
std::list<Creature*> ChannelerList;
|
||||
me->GetCreaturesWithEntryInRange(ChannelerList, 100.0f, NPC_ASHTONGUE_CHANNELER);
|
||||
for (std::list<Creature*>::const_iterator itr = ChannelerList.begin(); itr != ChannelerList.end(); ++itr)
|
||||
summonsChanneler.Summon(*itr);
|
||||
|
||||
std::list<Creature*> SpawnerList;
|
||||
me->GetCreaturesWithEntryInRange(SpawnerList, 100.0f, NPC_CREATURE_GENERATOR_AKAMA);
|
||||
for (std::list<Creature*>::const_iterator itr = SpawnerList.begin(); itr != SpawnerList.end(); ++itr)
|
||||
summonsGenerator.Summon(*itr);
|
||||
|
||||
summonsChanneler.Respawn();
|
||||
summonsGenerator.Respawn();
|
||||
ChannelersAction(ACTION_CHANNELERS_START_CHANNEL);
|
||||
|
||||
if (Creature* akama = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_AKAMA_SHADE)))
|
||||
akama->Respawn(true);
|
||||
break;
|
||||
}
|
||||
case EVENT_SHADE_RESET_ENCOUNTER:
|
||||
me->SetVisible(true);
|
||||
summonsGenerator.Respawn();
|
||||
summonsChanneler.Respawn();
|
||||
ChannelersAction(ACTION_CHANNELERS_START_CHANNEL);
|
||||
|
||||
if (Creature* akama = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_AKAMA_SHADE)))
|
||||
akama->Respawn(true);
|
||||
break;
|
||||
int32 slow = me->GetMaxNegativeAuraModifier(SPELL_AURA_MOD_DECREASE_SPEED);
|
||||
if (slow < -100)
|
||||
me->GetMotionMaster()->Clear();
|
||||
else if (slow == 0)
|
||||
{
|
||||
summonsGenerator.DoAction(ACTION_NO_SORCERERS);
|
||||
me->SetWalk(false);
|
||||
}
|
||||
}
|
||||
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
if (me->IsWithinMeleeRange(me->GetVictim()))
|
||||
{
|
||||
case EVENT_SHADE_CHECK_DISTANCE:
|
||||
if (me->GetMotionMaster()->GetCurrentMovementGeneratorType() != POINT_MOTION_TYPE)
|
||||
{
|
||||
int32 slow = me->GetMaxNegativeAuraModifier(SPELL_AURA_MOD_DECREASE_SPEED);
|
||||
if (slow > -100)
|
||||
{
|
||||
me->SetWalk(true);
|
||||
me->GetMotionMaster()->MovePoint(POINT_START, 510.0f, 400.7993f, 112.7837f);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
int32 slow = me->GetMaxNegativeAuraModifier(SPELL_AURA_MOD_DECREASE_SPEED);
|
||||
if (slow < -100)
|
||||
me->GetMotionMaster()->Clear();
|
||||
else if (slow == 0)
|
||||
{
|
||||
summonsGenerator.DoAction(ACTION_NO_SORCERERS);
|
||||
me->SetWalk(false);
|
||||
}
|
||||
}
|
||||
|
||||
if (me->IsWithinMeleeRange(me->GetVictim()))
|
||||
{
|
||||
me->SetReactState(REACT_AGGRESSIVE);
|
||||
DoResetThreatList();
|
||||
me->GetVictim()->InterruptNonMeleeSpells(false);
|
||||
me->AddThreat(me->GetVictim(), 1000000.0f);
|
||||
me->RemoveUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
me->SetImmuneToAll(false);
|
||||
summonsGenerator.DoAction(ACTION_STOP_SPAWNING);
|
||||
break;
|
||||
}
|
||||
events.ScheduleEvent(EVENT_SHADE_CHECK_DISTANCE, 1000);
|
||||
break;
|
||||
me->SetReactState(REACT_AGGRESSIVE);
|
||||
DoResetThreatList();
|
||||
me->GetVictim()->InterruptNonMeleeSpells(false);
|
||||
me->AddThreat(me->GetVictim(), 1000000.0f);
|
||||
me->RemoveUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
me->SetImmuneToAll(false);
|
||||
summonsGenerator.DoAction(ACTION_STOP_SPAWNING);
|
||||
break;
|
||||
}
|
||||
|
||||
DoMeleeAttackIfReady();
|
||||
events.ScheduleEvent(EVENT_SHADE_CHECK_DISTANCE, 1000);
|
||||
break;
|
||||
}
|
||||
|
||||
bool CheckEvadeIfOutOfCombatArea() const override
|
||||
{
|
||||
return !SelectTargetFromPlayerList(120.0f);
|
||||
}
|
||||
};
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
bool CheckEvadeIfOutOfCombatArea() const override
|
||||
{
|
||||
return GetBlackTempleAI<boss_shade_of_akamaAI>(creature);
|
||||
return !SelectTargetFromPlayerList(120.0f);
|
||||
}
|
||||
};
|
||||
|
||||
class npc_akama_shade : public CreatureScript
|
||||
struct npc_akama_shade : public ScriptedAI
|
||||
{
|
||||
public:
|
||||
npc_akama_shade() : CreatureScript("npc_akama_shade") { }
|
||||
|
||||
struct npc_akamaAI : public ScriptedAI
|
||||
npc_akama_shade(Creature* creature) : ScriptedAI(creature), summons(me)
|
||||
{
|
||||
npc_akamaAI(Creature* creature) : ScriptedAI(creature), summons(me)
|
||||
instance = creature->GetInstanceScript();
|
||||
}
|
||||
|
||||
InstanceScript* instance;
|
||||
EventMap events;
|
||||
EventMap events2;
|
||||
SummonList summons;
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
if (instance->GetBossState(DATA_SHADE_OF_AKAMA) == DONE)
|
||||
{
|
||||
instance = creature->GetInstanceScript();
|
||||
me->RemoveNpcFlag(UNIT_NPC_FLAG_GOSSIP);
|
||||
return;
|
||||
}
|
||||
|
||||
InstanceScript* instance;
|
||||
EventMap events;
|
||||
EventMap events2;
|
||||
SummonList summons;
|
||||
me->SetNpcFlag(UNIT_NPC_FLAG_GOSSIP);
|
||||
me->CastSpell(me, SPELL_STEALTH, true);
|
||||
events.Reset();
|
||||
events2.Reset();
|
||||
}
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
if (instance->GetBossState(DATA_SHADE_OF_AKAMA) == DONE)
|
||||
{
|
||||
me->RemoveNpcFlag(UNIT_NPC_FLAG_GOSSIP);
|
||||
return;
|
||||
}
|
||||
|
||||
me->SetNpcFlag(UNIT_NPC_FLAG_GOSSIP);
|
||||
me->CastSpell(me, SPELL_STEALTH, true);
|
||||
events.Reset();
|
||||
events2.Reset();
|
||||
}
|
||||
|
||||
void MovementInform(uint32 type, uint32 point) override
|
||||
{
|
||||
if (type != POINT_MOTION_TYPE || point != POINT_CHANNEL_SOUL)
|
||||
return;
|
||||
|
||||
me->SetFacingTo(0.0f);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE1, 1000);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE2, 16500);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE3, 17500);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE4, 27000);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE5, 37000);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE6, 51000);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE7, 56000);
|
||||
}
|
||||
|
||||
void DoAction(int32 param) override
|
||||
{
|
||||
if (param == ACTION_SHADE_DIED)
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE0, 1000);
|
||||
}
|
||||
|
||||
void JustDied(Unit* /*killer*/) override
|
||||
void MovementInform(uint32 type, uint32 point) override
|
||||
{
|
||||
if (type != POINT_MOTION_TYPE || point != POINT_CHANNEL_SOUL)
|
||||
return;
|
||||
|
||||
me->SetFacingTo(0.0f);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE1, 1000);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE2, 16500);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE3, 17500);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE4, 27000);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE5, 37000);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE6, 51000);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE7, 56000);
|
||||
}
|
||||
|
||||
void DoAction(int32 param) override
|
||||
{
|
||||
if (param == ACTION_SHADE_DIED)
|
||||
events2.ScheduleEvent(EVENT_AKAMA_SCENE0, 1000);
|
||||
}
|
||||
|
||||
void JustDied(Unit* /*killer*/) override
|
||||
{
|
||||
if (Creature* shade = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_SHADE_OF_AKAMA)))
|
||||
shade->AI()->DoAction(ACTION_AKAMA_DIED);
|
||||
}
|
||||
|
||||
void JustEngagedWith(Unit* /*who*/) override
|
||||
{
|
||||
events.ScheduleEvent(EVENT_SPELL_CHAIN_LIGHTNING, 2000);
|
||||
events.ScheduleEvent(EVENT_SPELL_DESTRUCTIVE_POISON, 5000);
|
||||
}
|
||||
|
||||
void JustSummoned(Creature* summon) override
|
||||
{
|
||||
float dist = frand(30.0f, 32.0f);
|
||||
summon->SetWalk(true);
|
||||
summon->GetMotionMaster()->MovePoint(POINT_START, summon->GetPositionX() + dist * cos(summon->GetOrientation()), summon->GetPositionY() + dist * std::sin(summon->GetOrientation()), summon->GetPositionZ(), false);
|
||||
summons.Summon(summon);
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
events2.Update(diff);
|
||||
switch (events2.ExecuteEvent())
|
||||
{
|
||||
case EVENT_AKAMA_START_ENCOUNTER:
|
||||
me->RemoveAura(SPELL_STEALTH);
|
||||
me->SetWalk(true);
|
||||
me->GetMotionMaster()->MovePoint(POINT_START, 517.4877f, 400.7993f, 112.7837f, false);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_START_CHANNEL, 11000);
|
||||
break;
|
||||
case EVENT_AKAMA_START_CHANNEL:
|
||||
me->CastSpell(me, SPELL_AKAMA_SOUL_CHANNEL, false);
|
||||
if (Creature* shade = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_SHADE_OF_AKAMA)))
|
||||
shade->AI()->DoAction(ACTION_AKAMA_DIED);
|
||||
}
|
||||
|
||||
void JustEngagedWith(Unit* /*who*/) override
|
||||
{
|
||||
events.ScheduleEvent(EVENT_SPELL_CHAIN_LIGHTNING, 2000);
|
||||
events.ScheduleEvent(EVENT_SPELL_DESTRUCTIVE_POISON, 5000);
|
||||
}
|
||||
|
||||
void JustSummoned(Creature* summon) override
|
||||
{
|
||||
float dist = frand(30.0f, 32.0f);
|
||||
summon->SetWalk(true);
|
||||
summon->GetMotionMaster()->MovePoint(POINT_START, summon->GetPositionX() + dist * cos(summon->GetOrientation()), summon->GetPositionY() + dist * std::sin(summon->GetOrientation()), summon->GetPositionZ(), false);
|
||||
summons.Summon(summon);
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
events2.Update(diff);
|
||||
switch (events2.ExecuteEvent())
|
||||
{
|
||||
case EVENT_AKAMA_START_ENCOUNTER:
|
||||
me->RemoveAura(SPELL_STEALTH);
|
||||
me->SetWalk(true);
|
||||
me->GetMotionMaster()->MovePoint(POINT_START, 517.4877f, 400.7993f, 112.7837f, false);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_START_CHANNEL, 11000);
|
||||
break;
|
||||
case EVENT_AKAMA_START_CHANNEL:
|
||||
me->CastSpell(me, SPELL_AKAMA_SOUL_CHANNEL, false);
|
||||
if (Creature* shade = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_SHADE_OF_AKAMA)))
|
||||
{
|
||||
shade->AI()->AttackStart(me);
|
||||
shade->GetMotionMaster()->Clear();
|
||||
shade->AI()->DoAction(ACTION_START_ENCOUNTER);
|
||||
}
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE0:
|
||||
me->SetWalk(true);
|
||||
me->GetMotionMaster()->MovePoint(POINT_CHANNEL_SOUL, 467.0f, 400.7993f, 118.537f);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE1:
|
||||
me->CastSpell(me, SPELL_AKAMA_SOUL_RETRIEVE, true);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE2:
|
||||
Talk(SAY_BROKEN_FREE_0);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE3:
|
||||
me->SummonCreatureGroup(SUMMON_GROUP_BROKENS);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE4:
|
||||
Talk(SAY_BROKEN_FREE_1);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE5:
|
||||
for (SummonList::const_iterator itr = summons.begin(); itr != summons.end(); ++itr)
|
||||
if (Creature* broken = ObjectAccessor::GetCreature(*me, *itr))
|
||||
broken->SetStandState(UNIT_STAND_STATE_KNEEL);
|
||||
Talk(SAY_BROKEN_FREE_2);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE6:
|
||||
if (Creature* broken = summons.GetCreatureWithEntry(NPC_ASHTONGUE_BROKEN))
|
||||
broken->AI()->Talk(SAY_BROKEN_S1);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE7:
|
||||
for (SummonList::const_iterator itr = summons.begin(); itr != summons.end(); ++itr)
|
||||
if (Creature* broken = ObjectAccessor::GetCreature(*me, *itr))
|
||||
broken->AI()->Talk(SAY_BROKEN_S2);
|
||||
break;
|
||||
shade->AI()->AttackStart(me);
|
||||
shade->GetMotionMaster()->Clear();
|
||||
shade->AI()->DoAction(ACTION_START_ENCOUNTER);
|
||||
}
|
||||
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
case EVENT_SPELL_CHAIN_LIGHTNING:
|
||||
me->CastSpell(me->GetVictim(), SPELL_CHAIN_LIGHTNING, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_CHAIN_LIGHTNING, urand(10000, 15000));
|
||||
break;
|
||||
case EVENT_SPELL_DESTRUCTIVE_POISON:
|
||||
me->CastSpell(me, SPELL_DESTRUCTIVE_POISON, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_DESTRUCTIVE_POISON, urand(4000, 5000));
|
||||
break;
|
||||
}
|
||||
|
||||
DoMeleeAttackIfReady();
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE0:
|
||||
me->SetWalk(true);
|
||||
me->GetMotionMaster()->MovePoint(POINT_CHANNEL_SOUL, 467.0f, 400.7993f, 118.537f);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE1:
|
||||
me->CastSpell(me, SPELL_AKAMA_SOUL_RETRIEVE, true);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE2:
|
||||
Talk(SAY_BROKEN_FREE_0);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE3:
|
||||
me->SummonCreatureGroup(SUMMON_GROUP_BROKENS);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE4:
|
||||
Talk(SAY_BROKEN_FREE_1);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE5:
|
||||
for (SummonList::const_iterator itr = summons.begin(); itr != summons.end(); ++itr)
|
||||
if (Creature* broken = ObjectAccessor::GetCreature(*me, *itr))
|
||||
broken->SetStandState(UNIT_STAND_STATE_KNEEL);
|
||||
Talk(SAY_BROKEN_FREE_2);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE6:
|
||||
if (Creature* broken = summons.GetCreatureWithEntry(NPC_ASHTONGUE_BROKEN))
|
||||
broken->AI()->Talk(SAY_BROKEN_S1);
|
||||
break;
|
||||
case EVENT_AKAMA_SCENE7:
|
||||
for (SummonList::const_iterator itr = summons.begin(); itr != summons.end(); ++itr)
|
||||
if (Creature* broken = ObjectAccessor::GetCreature(*me, *itr))
|
||||
broken->AI()->Talk(SAY_BROKEN_S2);
|
||||
break;
|
||||
}
|
||||
|
||||
void sGossipSelect(Player* player, uint32 /*sender*/, uint32 action) override
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
if (action == 0)
|
||||
{
|
||||
CloseGossipMenuFor(player);
|
||||
me->RemoveNpcFlag(UNIT_NPC_FLAG_GOSSIP);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_START_ENCOUNTER, 0);
|
||||
}
|
||||
case EVENT_SPELL_CHAIN_LIGHTNING:
|
||||
me->CastSpell(me->GetVictim(), SPELL_CHAIN_LIGHTNING, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_CHAIN_LIGHTNING, urand(10000, 15000));
|
||||
break;
|
||||
case EVENT_SPELL_DESTRUCTIVE_POISON:
|
||||
me->CastSpell(me, SPELL_DESTRUCTIVE_POISON, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_DESTRUCTIVE_POISON, urand(4000, 5000));
|
||||
break;
|
||||
}
|
||||
};
|
||||
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
|
||||
void sGossipSelect(Player* player, uint32 /*sender*/, uint32 action) override
|
||||
{
|
||||
return GetBlackTempleAI<npc_akamaAI>(creature);
|
||||
if (action == 0)
|
||||
{
|
||||
CloseGossipMenuFor(player);
|
||||
me->RemoveNpcFlag(UNIT_NPC_FLAG_GOSSIP);
|
||||
events2.ScheduleEvent(EVENT_AKAMA_START_ENCOUNTER, 0);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// ########################################################
|
||||
// Creature Generator Akama
|
||||
// ########################################################
|
||||
|
||||
class npc_creature_generator_akama : public CreatureScript
|
||||
struct npc_creature_generator_akama : public NullCreatureAI
|
||||
{
|
||||
public:
|
||||
npc_creature_generator_akama() : CreatureScript("npc_creature_generator_akama") { }
|
||||
|
||||
struct npc_creature_generator_akamaAI : public NullCreatureAI
|
||||
npc_creature_generator_akama(Creature* creature) : NullCreatureAI(creature), summons(me)
|
||||
{
|
||||
npc_creature_generator_akamaAI(Creature* creature) : NullCreatureAI(creature), summons(me)
|
||||
instance = creature->GetInstanceScript();
|
||||
}
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
events.Reset();
|
||||
summons.DespawnAll();
|
||||
}
|
||||
|
||||
void JustSummoned(Creature* summon) override
|
||||
{
|
||||
summons.Summon(summon);
|
||||
if (summon->GetEntry() == NPC_ASHTONGUE_SORCERER)
|
||||
{
|
||||
instance = creature->GetInstanceScript();
|
||||
std::list<Creature*> channelerList;
|
||||
me->GetCreaturesWithEntryInRange(channelerList, 120.0f, NPC_ASHTONGUE_CHANNELER);
|
||||
for (std::list<Creature*>::const_iterator itr = channelerList.begin(); itr != channelerList.end(); ++itr)
|
||||
{
|
||||
if ((*itr)->IsAlive() || (*itr)->HasUnitFlag(UNIT_FLAG_NOT_SELECTABLE))
|
||||
continue;
|
||||
|
||||
summon->SetInCombatWithZone();
|
||||
summon->SetReactState(REACT_PASSIVE);
|
||||
summon->GetMotionMaster()->MovePoint(POINT_START, **itr);
|
||||
(*itr)->SetUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
void Reset() override
|
||||
summon->SetInCombatWithZone();
|
||||
if (Unit* akama = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_AKAMA_SHADE)))
|
||||
{
|
||||
summon->AddThreat(akama, 500.0f);
|
||||
summon->AI()->AttackStart(akama);
|
||||
}
|
||||
}
|
||||
|
||||
void SummonedCreatureDies(Creature* summon, Unit*) override
|
||||
{
|
||||
summon->DespawnOrUnsummon(10000);
|
||||
summons.Despawn(summon);
|
||||
}
|
||||
|
||||
void DoAction(int32 param) override
|
||||
{
|
||||
if (param == ACTION_STOP_SPAWNING || param == ACTION_DESPAWN_ALL)
|
||||
{
|
||||
events.Reset();
|
||||
summons.DespawnAll();
|
||||
}
|
||||
|
||||
void JustSummoned(Creature* summon) override
|
||||
{
|
||||
summons.Summon(summon);
|
||||
if (summon->GetEntry() == NPC_ASHTONGUE_SORCERER)
|
||||
for (SummonList::const_iterator itr = summons.begin(); itr != summons.end(); ++itr)
|
||||
{
|
||||
std::list<Creature*> channelerList;
|
||||
me->GetCreaturesWithEntryInRange(channelerList, 120.0f, NPC_ASHTONGUE_CHANNELER);
|
||||
for (std::list<Creature*>::const_iterator itr = channelerList.begin(); itr != channelerList.end(); ++itr)
|
||||
if (Creature* summon = ObjectAccessor::GetCreature(*me, *itr))
|
||||
{
|
||||
if ((*itr)->IsAlive() || (*itr)->HasUnitFlag(UNIT_FLAG_NOT_SELECTABLE))
|
||||
if (summon->GetEntry() != NPC_ASHTONGUE_SORCERER)
|
||||
continue;
|
||||
|
||||
summon->InterruptNonMeleeSpells(false);
|
||||
summon->GetMotionMaster()->Clear();
|
||||
summon->SetInCombatWithZone();
|
||||
summon->SetReactState(REACT_PASSIVE);
|
||||
summon->GetMotionMaster()->MovePoint(POINT_START, **itr);
|
||||
(*itr)->SetUnitFlag(UNIT_FLAG_NOT_SELECTABLE);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
summon->SetInCombatWithZone();
|
||||
if (Unit* akama = ObjectAccessor::GetCreature(*me, instance->GetGuidData(NPC_AKAMA_SHADE)))
|
||||
{
|
||||
summon->AddThreat(akama, 500.0f);
|
||||
summon->AI()->AttackStart(akama);
|
||||
}
|
||||
}
|
||||
|
||||
void SummonedCreatureDies(Creature* summon, Unit*) override
|
||||
if (param == ACTION_DESPAWN_ALL)
|
||||
summons.DespawnAll();
|
||||
else if (param == ACTION_NO_SORCERERS)
|
||||
events.CancelEvent(EVENT_SUMMON_ASHTONGUE_SORCERER);
|
||||
else if (param == ACTION_START_ENCOUNTER)
|
||||
{
|
||||
summon->DespawnOrUnsummon(10000);
|
||||
summons.Despawn(summon);
|
||||
events.ScheduleEvent(EVENT_SUMMON_WAVE_B, 5000);
|
||||
events.ScheduleEvent(EVENT_SUMMON_ASHTONGUE_DEFENDER, 20000);
|
||||
events.ScheduleEvent(EVENT_SUMMON_ASHTONGUE_SORCERER, 35000);
|
||||
}
|
||||
}
|
||||
|
||||
void DoAction(int32 param) override
|
||||
{
|
||||
if (param == ACTION_STOP_SPAWNING || param == ACTION_DESPAWN_ALL)
|
||||
{
|
||||
events.Reset();
|
||||
for (SummonList::const_iterator itr = summons.begin(); itr != summons.end(); ++itr)
|
||||
{
|
||||
if (Creature* summon = ObjectAccessor::GetCreature(*me, *itr))
|
||||
{
|
||||
if (summon->GetEntry() != NPC_ASHTONGUE_SORCERER)
|
||||
continue;
|
||||
summon->InterruptNonMeleeSpells(false);
|
||||
summon->GetMotionMaster()->Clear();
|
||||
summon->SetInCombatWithZone();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (param == ACTION_DESPAWN_ALL)
|
||||
summons.DespawnAll();
|
||||
else if (param == ACTION_NO_SORCERERS)
|
||||
events.CancelEvent(EVENT_SUMMON_ASHTONGUE_SORCERER);
|
||||
else if (param == ACTION_START_ENCOUNTER)
|
||||
{
|
||||
events.ScheduleEvent(EVENT_SUMMON_WAVE_B, 5000);
|
||||
events.ScheduleEvent(EVENT_SUMMON_ASHTONGUE_DEFENDER, 20000);
|
||||
events.ScheduleEvent(EVENT_SUMMON_ASHTONGUE_SORCERER, 35000);
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
events.Update(diff);
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
case EVENT_SUMMON_WAVE_B:
|
||||
me->CastSpell(me, SPELL_ASHTONGUE_WAVE_B, true);
|
||||
events.ScheduleEvent(EVENT_SUMMON_WAVE_B, 45000);
|
||||
break;
|
||||
case EVENT_SUMMON_ASHTONGUE_SORCERER: // left
|
||||
me->CastSpell(me, SPELL_SUMMON_ASHTONGUE_SORCERER, true);
|
||||
events.ScheduleEvent(EVENT_SUMMON_ASHTONGUE_SORCERER, 45000);
|
||||
break;
|
||||
case EVENT_SUMMON_ASHTONGUE_DEFENDER: // right
|
||||
me->CastSpell(me, SPELL_SUMMON_ASHTONGUE_DEFENDER, true);
|
||||
events.ScheduleEvent(EVENT_SUMMON_ASHTONGUE_DEFENDER, 45000);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
EventMap events;
|
||||
SummonList summons;
|
||||
InstanceScript* instance;
|
||||
};
|
||||
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
return GetBlackTempleAI<npc_creature_generator_akamaAI>(creature);
|
||||
events.Update(diff);
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
case EVENT_SUMMON_WAVE_B:
|
||||
me->CastSpell(me, SPELL_ASHTONGUE_WAVE_B, true);
|
||||
events.ScheduleEvent(EVENT_SUMMON_WAVE_B, 45000);
|
||||
break;
|
||||
case EVENT_SUMMON_ASHTONGUE_SORCERER: // left
|
||||
me->CastSpell(me, SPELL_SUMMON_ASHTONGUE_SORCERER, true);
|
||||
events.ScheduleEvent(EVENT_SUMMON_ASHTONGUE_SORCERER, 45000);
|
||||
break;
|
||||
case EVENT_SUMMON_ASHTONGUE_DEFENDER: // right
|
||||
me->CastSpell(me, SPELL_SUMMON_ASHTONGUE_DEFENDER, true);
|
||||
events.ScheduleEvent(EVENT_SUMMON_ASHTONGUE_DEFENDER, 45000);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
EventMap events;
|
||||
SummonList summons;
|
||||
InstanceScript* instance;
|
||||
};
|
||||
|
||||
class spell_shade_of_akama_shade_soul_channel : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_shade_of_akama_shade_soul_channel);
|
||||
|
||||
void HandleEffectApply(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
if (Unit* caster = GetCaster())
|
||||
caster->SetFacingToObject(GetTarget());
|
||||
}
|
||||
|
||||
void HandleEffectRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
if (Aura* aura = GetTarget()->GetAura(GetSpellInfo()->Effects[EFFECT_1].TriggerSpell))
|
||||
aura->ModStackAmount(-1);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
AfterEffectApply += AuraEffectApplyFn(spell_shade_of_akama_shade_soul_channel::HandleEffectApply, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
AfterEffectRemove += AuraEffectRemoveFn(spell_shade_of_akama_shade_soul_channel::HandleEffectRemove, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_shade_of_akama_shade_soul_channel : public SpellScriptLoader
|
||||
class spell_shade_of_akama_akama_soul_expel : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_shade_of_akama_shade_soul_channel() : SpellScriptLoader("spell_shade_of_akama_shade_soul_channel") { }
|
||||
PrepareSpellScript(spell_shade_of_akama_akama_soul_expel);
|
||||
|
||||
class spell_shade_of_akama_shade_soul_channel_AuraScript : public AuraScript
|
||||
void SetDest(SpellDestination& dest)
|
||||
{
|
||||
PrepareAuraScript(spell_shade_of_akama_shade_soul_channel_AuraScript)
|
||||
|
||||
void HandleEffectApply(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
if (Unit* caster = GetCaster())
|
||||
caster->SetFacingToObject(GetTarget());
|
||||
}
|
||||
|
||||
void HandleEffectRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
if (Aura* aura = GetTarget()->GetAura(GetSpellInfo()->Effects[EFFECT_1].TriggerSpell))
|
||||
aura->ModStackAmount(-1);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
AfterEffectApply += AuraEffectApplyFn(spell_shade_of_akama_shade_soul_channel_AuraScript::HandleEffectApply, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
AfterEffectRemove += AuraEffectRemoveFn(spell_shade_of_akama_shade_soul_channel_AuraScript::HandleEffectRemove, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_shade_of_akama_shade_soul_channel_AuraScript();
|
||||
// Adjust effect summon position
|
||||
Position const offset = { 0.0f, 0.0f, 25.0f, 0.0f };
|
||||
dest.RelocateOffset(offset);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_shade_of_akama_akama_soul_expel : public SpellScriptLoader
|
||||
{
|
||||
public:
|
||||
spell_shade_of_akama_akama_soul_expel() : SpellScriptLoader("spell_shade_of_akama_akama_soul_expel") { }
|
||||
|
||||
class spell_shade_of_akama_akama_soul_expel_SpellScript : public SpellScript
|
||||
void Register() override
|
||||
{
|
||||
PrepareSpellScript(spell_shade_of_akama_akama_soul_expel_SpellScript);
|
||||
|
||||
void SetDest(SpellDestination& dest)
|
||||
{
|
||||
// Adjust effect summon position
|
||||
Position const offset = { 0.0f, 0.0f, 25.0f, 0.0f };
|
||||
dest.RelocateOffset(offset);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnDestinationTargetSelect += SpellDestinationTargetSelectFn(spell_shade_of_akama_akama_soul_expel_SpellScript::SetDest, EFFECT_0, TARGET_DEST_CASTER_RADIUS);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_shade_of_akama_akama_soul_expel_SpellScript();
|
||||
OnDestinationTargetSelect += SpellDestinationTargetSelectFn(spell_shade_of_akama_akama_soul_expel::SetDest, EFFECT_0, TARGET_DEST_CASTER_RADIUS);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_shade_of_akama()
|
||||
{
|
||||
new boss_shade_of_akama();
|
||||
new npc_akama_shade();
|
||||
new npc_creature_generator_akama();
|
||||
new spell_shade_of_akama_shade_soul_channel();
|
||||
new spell_shade_of_akama_akama_soul_expel();
|
||||
RegisterBlackTempleCreatureAI(boss_shade_of_akama);
|
||||
RegisterBlackTempleCreatureAI(npc_akama_shade);
|
||||
RegisterBlackTempleCreatureAI(npc_creature_generator_akama);
|
||||
RegisterSpellScript(spell_shade_of_akama_shade_soul_channel);
|
||||
RegisterSpellScript(spell_shade_of_akama_akama_soul_expel);
|
||||
}
|
||||
|
||||
@@ -46,164 +46,141 @@ enum Supremus
|
||||
EVENT_GROUP_ABILITIES = 1
|
||||
};
|
||||
|
||||
class boss_supremus : public CreatureScript
|
||||
struct boss_supremus : public BossAI
|
||||
{
|
||||
public:
|
||||
boss_supremus() : CreatureScript("boss_supremus") { }
|
||||
boss_supremus(Creature* creature) : BossAI(creature, DATA_SUPREMUS) { }
|
||||
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
void JustEngagedWith(Unit* who) override
|
||||
{
|
||||
return GetBlackTempleAI<boss_supremusAI>(creature);
|
||||
BossAI::JustEngagedWith(who);
|
||||
|
||||
SchedulePhase(false);
|
||||
events.ScheduleEvent(EVENT_SPELL_BERSERK, 900000);
|
||||
events.ScheduleEvent(EVENT_SPELL_MOLTEN_FLAMES, 4000);
|
||||
}
|
||||
|
||||
struct boss_supremusAI : public BossAI
|
||||
void SchedulePhase(bool run)
|
||||
{
|
||||
boss_supremusAI(Creature* creature) : BossAI(creature, DATA_SUPREMUS)
|
||||
events.CancelEventGroup(EVENT_GROUP_ABILITIES);
|
||||
events.ScheduleEvent(EVENT_SWITCH_PHASE, 60000);
|
||||
DoResetThreatList();
|
||||
|
||||
if (!run)
|
||||
{
|
||||
events.ScheduleEvent(EVENT_SPELL_HATEFUL_STRIKE, 5000, EVENT_GROUP_ABILITIES);
|
||||
me->ApplySpellImmune(0, IMMUNITY_STATE, SPELL_AURA_MOD_TAUNT, false);
|
||||
me->ApplySpellImmune(0, IMMUNITY_EFFECT, SPELL_EFFECT_ATTACK_ME, false);
|
||||
me->RemoveAurasDueToSpell(SPELL_SNARE_SELF);
|
||||
}
|
||||
else
|
||||
{
|
||||
events.ScheduleEvent(EVENT_SPELL_VOLCANIC_ERUPTION, 5000, EVENT_GROUP_ABILITIES);
|
||||
events.ScheduleEvent(EVENT_SWITCH_TARGET, 0, EVENT_GROUP_ABILITIES);
|
||||
events.ScheduleEvent(EVENT_CHECK_DIST, 0, EVENT_GROUP_ABILITIES);
|
||||
me->ApplySpellImmune(0, IMMUNITY_STATE, SPELL_AURA_MOD_TAUNT, true);
|
||||
me->ApplySpellImmune(0, IMMUNITY_EFFECT, SPELL_EFFECT_ATTACK_ME, true);
|
||||
me->CastSpell(me, SPELL_SNARE_SELF, true);
|
||||
}
|
||||
}
|
||||
|
||||
void JustSummoned(Creature* summon) override
|
||||
{
|
||||
summons.Summon(summon);
|
||||
if (summon->GetEntry() == NPC_SUPREMUS_PUNCH_STALKER)
|
||||
{
|
||||
summon->ToTempSummon()->InitStats(20000);
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0, 100.0f, true))
|
||||
summon->GetMotionMaster()->MoveFollow(target, 0.0f, 0.0f, MOTION_SLOT_CONTROLLED);
|
||||
}
|
||||
else
|
||||
summon->CastSpell(summon, SPELL_VOLCANIC_ERUPTION_TRIGGER, true);
|
||||
}
|
||||
|
||||
void SummonedCreatureDespawn(Creature* summon) override
|
||||
{
|
||||
summons.Despawn(summon);
|
||||
}
|
||||
|
||||
Unit* FindHatefulStrikeTarget()
|
||||
{
|
||||
Unit* target = nullptr;
|
||||
ThreatContainer::StorageType const& threatlist = me->GetThreatMgr().GetThreatList();
|
||||
for (ThreatContainer::StorageType::const_iterator i = threatlist.begin(); i != threatlist.end(); ++i)
|
||||
{
|
||||
Unit* unit = ObjectAccessor::GetUnit(*me, (*i)->getUnitGuid());
|
||||
if (unit && me->IsWithinMeleeRange(unit))
|
||||
if (!target || unit->GetHealth() > target->GetHealth())
|
||||
target = unit;
|
||||
}
|
||||
|
||||
void Reset() override
|
||||
return target;
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
BossAI::Reset();
|
||||
}
|
||||
|
||||
void JustEngagedWith(Unit* who) override
|
||||
{
|
||||
BossAI::JustEngagedWith(who);
|
||||
|
||||
SchedulePhase(false);
|
||||
events.ScheduleEvent(EVENT_SPELL_BERSERK, 900000);
|
||||
events.ScheduleEvent(EVENT_SPELL_MOLTEN_FLAMES, 4000);
|
||||
}
|
||||
|
||||
void SchedulePhase(bool run)
|
||||
{
|
||||
events.CancelEventGroup(EVENT_GROUP_ABILITIES);
|
||||
events.ScheduleEvent(EVENT_SWITCH_PHASE, 60000);
|
||||
DoResetThreatList();
|
||||
|
||||
if (!run)
|
||||
case EVENT_SPELL_BERSERK:
|
||||
me->CastSpell(me, SPELL_BERSERK, true);
|
||||
break;
|
||||
case EVENT_SPELL_HATEFUL_STRIKE:
|
||||
if (Unit* target = FindHatefulStrikeTarget())
|
||||
me->CastSpell(target, SPELL_HATEFUL_STRIKE, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_HATEFUL_STRIKE, urand(1500, 3000), EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
case EVENT_SPELL_MOLTEN_FLAMES:
|
||||
me->CastSpell(me, SPELL_MOLTEN_PUNCH, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_MOLTEN_FLAMES, 20000, EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
case EVENT_SWITCH_PHASE:
|
||||
SchedulePhase(!me->HasAura(SPELL_SNARE_SELF));
|
||||
break;
|
||||
case EVENT_SWITCH_TARGET:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0, 100, true))
|
||||
{
|
||||
events.ScheduleEvent(EVENT_SPELL_HATEFUL_STRIKE, 5000, EVENT_GROUP_ABILITIES);
|
||||
me->ApplySpellImmune(0, IMMUNITY_STATE, SPELL_AURA_MOD_TAUNT, false);
|
||||
me->ApplySpellImmune(0, IMMUNITY_EFFECT, SPELL_EFFECT_ATTACK_ME, false);
|
||||
me->RemoveAurasDueToSpell(SPELL_SNARE_SELF);
|
||||
DoResetThreatList();
|
||||
me->AddThreat(target, 5000000.0f);
|
||||
Talk(EMOTE_NEW_TARGET);
|
||||
}
|
||||
else
|
||||
events.ScheduleEvent(EVENT_SWITCH_TARGET, 10000, EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
case EVENT_CHECK_DIST:
|
||||
if (me->GetDistance(me->GetVictim()) > 40.0f)
|
||||
{
|
||||
events.ScheduleEvent(EVENT_SPELL_VOLCANIC_ERUPTION, 5000, EVENT_GROUP_ABILITIES);
|
||||
events.ScheduleEvent(EVENT_SWITCH_TARGET, 0, EVENT_GROUP_ABILITIES);
|
||||
events.ScheduleEvent(EVENT_CHECK_DIST, 0, EVENT_GROUP_ABILITIES);
|
||||
me->ApplySpellImmune(0, IMMUNITY_STATE, SPELL_AURA_MOD_TAUNT, true);
|
||||
me->ApplySpellImmune(0, IMMUNITY_EFFECT, SPELL_EFFECT_ATTACK_ME, true);
|
||||
me->CastSpell(me, SPELL_SNARE_SELF, true);
|
||||
Talk(EMOTE_PUNCH_GROUND);
|
||||
me->CastSpell(me->GetVictim(), SPELL_CHARGE, true);
|
||||
events.ScheduleEvent(EVENT_CHECK_DIST, 5000, EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void JustDied(Unit* killer) override
|
||||
{
|
||||
BossAI::JustDied(killer);
|
||||
}
|
||||
|
||||
void JustSummoned(Creature* summon) override
|
||||
{
|
||||
summons.Summon(summon);
|
||||
if (summon->GetEntry() == NPC_SUPREMUS_PUNCH_STALKER)
|
||||
events.ScheduleEvent(EVENT_CHECK_DIST, 1, EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
case EVENT_SPELL_VOLCANIC_ERUPTION:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0, 100, true))
|
||||
{
|
||||
summon->ToTempSummon()->InitStats(20000);
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0, 100.0f, true))
|
||||
summon->GetMotionMaster()->MoveFollow(target, 0.0f, 0.0f, MOTION_SLOT_CONTROLLED);
|
||||
me->CastSpell(target, SPELL_VOLCANIC_ERUPTION, true);
|
||||
Talk(EMOTE_GROUND_CRACK);
|
||||
}
|
||||
else
|
||||
summon->CastSpell(summon, SPELL_VOLCANIC_ERUPTION_TRIGGER, true);
|
||||
events.ScheduleEvent(EVENT_SPELL_VOLCANIC_ERUPTION, urand(10000, 18000), EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
}
|
||||
|
||||
void SummonedCreatureDespawn(Creature* summon) override
|
||||
{
|
||||
summons.Despawn(summon);
|
||||
}
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
|
||||
Unit* FindHatefulStrikeTarget()
|
||||
{
|
||||
Unit* target = nullptr;
|
||||
ThreatContainer::StorageType const& threatlist = me->GetThreatMgr().GetThreatList();
|
||||
for (ThreatContainer::StorageType::const_iterator i = threatlist.begin(); i != threatlist.end(); ++i)
|
||||
{
|
||||
Unit* unit = ObjectAccessor::GetUnit(*me, (*i)->getUnitGuid());
|
||||
if (unit && me->IsWithinMeleeRange(unit))
|
||||
if (!target || unit->GetHealth() > target->GetHealth())
|
||||
target = unit;
|
||||
}
|
||||
|
||||
return target;
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
case EVENT_SPELL_BERSERK:
|
||||
me->CastSpell(me, SPELL_BERSERK, true);
|
||||
break;
|
||||
case EVENT_SPELL_HATEFUL_STRIKE:
|
||||
if (Unit* target = FindHatefulStrikeTarget())
|
||||
me->CastSpell(target, SPELL_HATEFUL_STRIKE, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_HATEFUL_STRIKE, urand(1500, 3000), EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
case EVENT_SPELL_MOLTEN_FLAMES:
|
||||
me->CastSpell(me, SPELL_MOLTEN_PUNCH, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_MOLTEN_FLAMES, 20000, EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
case EVENT_SWITCH_PHASE:
|
||||
SchedulePhase(!me->HasAura(SPELL_SNARE_SELF));
|
||||
break;
|
||||
case EVENT_SWITCH_TARGET:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0, 100, true))
|
||||
{
|
||||
DoResetThreatList();
|
||||
me->AddThreat(target, 5000000.0f);
|
||||
Talk(EMOTE_NEW_TARGET);
|
||||
}
|
||||
events.ScheduleEvent(EVENT_SWITCH_TARGET, 10000, EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
case EVENT_CHECK_DIST:
|
||||
if (me->GetDistance(me->GetVictim()) > 40.0f)
|
||||
{
|
||||
Talk(EMOTE_PUNCH_GROUND);
|
||||
me->CastSpell(me->GetVictim(), SPELL_CHARGE, true);
|
||||
events.ScheduleEvent(EVENT_CHECK_DIST, 5000, EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
}
|
||||
events.ScheduleEvent(EVENT_CHECK_DIST, 1, EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
case EVENT_SPELL_VOLCANIC_ERUPTION:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0, 100, true))
|
||||
{
|
||||
me->CastSpell(target, SPELL_VOLCANIC_ERUPTION, true);
|
||||
Talk(EMOTE_GROUND_CRACK);
|
||||
}
|
||||
events.ScheduleEvent(EVENT_SPELL_VOLCANIC_ERUPTION, urand(10000, 18000), EVENT_GROUP_ABILITIES);
|
||||
break;
|
||||
}
|
||||
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
|
||||
bool CheckEvadeIfOutOfCombatArea() const override
|
||||
{
|
||||
return me->GetPositionX() < 565 || me->GetPositionX() > 865 || me->GetPositionY() < 545 || me->GetPositionY() > 1000;
|
||||
}
|
||||
};
|
||||
bool CheckEvadeIfOutOfCombatArea() const override
|
||||
{
|
||||
return me->GetPositionX() < 565 || me->GetPositionX() > 865 || me->GetPositionY() < 545 || me->GetPositionY() > 1000;
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_supremus()
|
||||
{
|
||||
new boss_supremus();
|
||||
RegisterBlackTempleCreatureAI(boss_supremus);
|
||||
}
|
||||
|
||||
@@ -70,276 +70,213 @@ struct ShadowOfDeathSelector
|
||||
}
|
||||
};
|
||||
|
||||
class boss_teron_gorefiend : public CreatureScript
|
||||
struct boss_teron_gorefiend : public BossAI
|
||||
{
|
||||
public:
|
||||
boss_teron_gorefiend() : CreatureScript("boss_teron_gorefiend") { }
|
||||
boss_teron_gorefiend(Creature* creature) : BossAI(creature, DATA_TERON_GOREFIEND), intro(false) { }
|
||||
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
bool intro;
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
return GetBlackTempleAI<boss_teron_gorefiendAI>(creature);
|
||||
BossAI::Reset();
|
||||
me->CastSpell(me, SPELL_SHADOW_OF_DEATH_REMOVE, true);
|
||||
}
|
||||
|
||||
struct boss_teron_gorefiendAI : public BossAI
|
||||
void SetData(uint32 type, uint32 id) override
|
||||
{
|
||||
boss_teron_gorefiendAI(Creature* creature) : BossAI(creature, DATA_TERON_GOREFIEND)
|
||||
if (type || !me->IsAlive())
|
||||
return;
|
||||
|
||||
if (id == SET_DATA_INTRO && !intro)
|
||||
{
|
||||
intro = false;
|
||||
intro = true;
|
||||
Talk(SAY_INTRO);
|
||||
}
|
||||
}
|
||||
|
||||
bool intro;
|
||||
void JustEngagedWith(Unit* who) override
|
||||
{
|
||||
BossAI::JustEngagedWith(who);
|
||||
events.ScheduleEvent(EVENT_SPELL_INCINERATE, 24000);
|
||||
events.ScheduleEvent(EVENT_SPELL_DOOM_BLOSSOM, 10000);
|
||||
events.ScheduleEvent(EVENT_SPELL_CRUSHING_SHADOWS, 17000);
|
||||
events.ScheduleEvent(EVENT_SPELL_SHADOW_OF_DEATH, 20000);
|
||||
}
|
||||
|
||||
void Reset() override
|
||||
void KilledUnit(Unit* /*victim*/) override
|
||||
{
|
||||
if (events.GetNextEventTime(EVENT_TALK_KILL) == 0)
|
||||
{
|
||||
BossAI::Reset();
|
||||
me->CastSpell(me, SPELL_SHADOW_OF_DEATH_REMOVE, true);
|
||||
Talk(SAY_SLAY);
|
||||
events.ScheduleEvent(EVENT_TALK_KILL, 6000);
|
||||
}
|
||||
}
|
||||
|
||||
void SetData(uint32 type, uint32 id) override
|
||||
void JustSummoned(Creature* summon) override
|
||||
{
|
||||
summons.Summon(summon);
|
||||
}
|
||||
|
||||
void JustDied(Unit* killer) override
|
||||
{
|
||||
BossAI::JustDied(killer);
|
||||
Talk(SAY_DEATH);
|
||||
me->CastSpell(me, SPELL_SHADOW_OF_DEATH_REMOVE, true);
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
if (type || !me->IsAlive())
|
||||
return;
|
||||
|
||||
if (id == SET_DATA_INTRO && !intro)
|
||||
case EVENT_SPELL_INCINERATE:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0))
|
||||
{
|
||||
intro = true;
|
||||
Talk(SAY_INTRO);
|
||||
if (roll_chance_i(50))
|
||||
Talk(SAY_INCINERATE);
|
||||
me->CastSpell(target, SPELL_INCINERATE, false);
|
||||
}
|
||||
events.ScheduleEvent(EVENT_SPELL_INCINERATE, 25000);
|
||||
break;
|
||||
case EVENT_SPELL_DOOM_BLOSSOM:
|
||||
if (roll_chance_i(50))
|
||||
Talk(SAY_BLOSSOM);
|
||||
|
||||
me->CastSpell(me, SPELL_SUMMON_DOOM_BLOSSOM, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_DOOM_BLOSSOM, 40000);
|
||||
break;
|
||||
case EVENT_SPELL_CRUSHING_SHADOWS:
|
||||
if (roll_chance_i(20))
|
||||
Talk(SAY_CRUSHING);
|
||||
me->CastCustomSpell(SPELL_CRUSHING_SHADOWS, SPELLVALUE_MAX_TARGETS, 5, me, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_CRUSHING_SHADOWS, 15000);
|
||||
break;
|
||||
case EVENT_SPELL_SHADOW_OF_DEATH:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 1, ShadowOfDeathSelector()))
|
||||
me->CastSpell(target, SPELL_SHADOW_OF_DEATH, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_SHADOW_OF_DEATH, 30000);
|
||||
break;
|
||||
}
|
||||
|
||||
void JustEngagedWith(Unit* who) override
|
||||
{
|
||||
BossAI::JustEngagedWith(who);
|
||||
events.ScheduleEvent(EVENT_SPELL_INCINERATE, 24000);
|
||||
events.ScheduleEvent(EVENT_SPELL_DOOM_BLOSSOM, 10000);
|
||||
events.ScheduleEvent(EVENT_SPELL_CRUSHING_SHADOWS, 17000);
|
||||
events.ScheduleEvent(EVENT_SPELL_SHADOW_OF_DEATH, 20000);
|
||||
}
|
||||
|
||||
void KilledUnit(Unit* /*victim*/) override
|
||||
{
|
||||
if (events.GetNextEventTime(EVENT_TALK_KILL) == 0)
|
||||
{
|
||||
Talk(SAY_SLAY);
|
||||
events.ScheduleEvent(EVENT_TALK_KILL, 6000);
|
||||
}
|
||||
}
|
||||
|
||||
void JustSummoned(Creature* summon) override
|
||||
{
|
||||
summons.Summon(summon);
|
||||
}
|
||||
|
||||
void JustDied(Unit* killer) override
|
||||
{
|
||||
BossAI::JustDied(killer);
|
||||
Talk(SAY_DEATH);
|
||||
me->CastSpell(me, SPELL_SHADOW_OF_DEATH_REMOVE, true);
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
if (!UpdateVictim() )
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
case EVENT_SPELL_INCINERATE:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0))
|
||||
{
|
||||
if (roll_chance_i(50))
|
||||
Talk(SAY_INCINERATE);
|
||||
me->CastSpell(target, SPELL_INCINERATE, false);
|
||||
}
|
||||
events.ScheduleEvent(EVENT_SPELL_INCINERATE, 25000);
|
||||
break;
|
||||
case EVENT_SPELL_DOOM_BLOSSOM:
|
||||
if (roll_chance_i(50))
|
||||
Talk(SAY_BLOSSOM);
|
||||
|
||||
me->CastSpell(me, SPELL_SUMMON_DOOM_BLOSSOM, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_DOOM_BLOSSOM, 40000);
|
||||
break;
|
||||
case EVENT_SPELL_CRUSHING_SHADOWS:
|
||||
if (roll_chance_i(20))
|
||||
Talk(SAY_CRUSHING);
|
||||
me->CastCustomSpell(SPELL_CRUSHING_SHADOWS, SPELLVALUE_MAX_TARGETS, 5, me, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_CRUSHING_SHADOWS, 15000);
|
||||
break;
|
||||
case EVENT_SPELL_SHADOW_OF_DEATH:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 1, ShadowOfDeathSelector()))
|
||||
me->CastSpell(target, SPELL_SHADOW_OF_DEATH, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_SHADOW_OF_DEATH, 30000);
|
||||
break;
|
||||
}
|
||||
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
|
||||
bool CheckEvadeIfOutOfCombatArea() const override
|
||||
{
|
||||
return me->GetDistance(me->GetHomePosition()) > 100.0f;
|
||||
}
|
||||
};
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
};
|
||||
|
||||
class spell_teron_gorefiend_shadow_of_death : public SpellScriptLoader
|
||||
class spell_teron_gorefiend_shadow_of_death : public AuraScript
|
||||
{
|
||||
public:
|
||||
spell_teron_gorefiend_shadow_of_death() : SpellScriptLoader("spell_teron_gorefiend_shadow_of_death") { }
|
||||
PrepareAuraScript(spell_teron_gorefiend_shadow_of_death);
|
||||
|
||||
class spell_teron_gorefiend_shadow_of_death_AuraScript : public AuraScript
|
||||
void Absorb(AuraEffect* /*aurEff*/, DamageInfo& /*dmgInfo*/, uint32& /*absorbAmount*/)
|
||||
{
|
||||
PrepareAuraScript(spell_teron_gorefiend_shadow_of_death_AuraScript)
|
||||
PreventDefaultAction();
|
||||
}
|
||||
|
||||
void Absorb(AuraEffect* /*aurEff*/, DamageInfo& /*dmgInfo*/, uint32& /*absorbAmount*/)
|
||||
{
|
||||
PreventDefaultAction();
|
||||
}
|
||||
void HandleEffectRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
InstanceScript* instance = GetTarget()->GetInstanceScript();
|
||||
if (!GetCaster() || !instance || !instance->IsEncounterInProgress())
|
||||
return;
|
||||
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SPIRIT, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_POSSESS_SPIRIT_IMMUNE, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SPIRITUAL_VENGEANCE, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SKELETON1, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SKELETON2, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SKELETON3, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SKELETON4, true);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectAbsorb += AuraEffectAbsorbFn(spell_teron_gorefiend_shadow_of_death::Absorb, EFFECT_0);
|
||||
AfterEffectRemove += AuraEffectRemoveFn(spell_teron_gorefiend_shadow_of_death::HandleEffectRemove, EFFECT_0, SPELL_AURA_SCHOOL_ABSORB, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_teron_gorefiend_spirit_lance : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_teron_gorefiend_spirit_lance);
|
||||
|
||||
void CalculateAmount(AuraEffect const* /*aurEff*/, int32& amount, bool& /*canBeRecalculated*/)
|
||||
{
|
||||
if (AuraEffect* effect = GetAura()->GetEffect(EFFECT_2))
|
||||
amount -= (amount / effect->GetTotalTicks()) * effect->GetTickNumber();
|
||||
}
|
||||
|
||||
void Update(AuraEffect const* /*effect*/)
|
||||
{
|
||||
PreventDefaultAction();
|
||||
if (AuraEffect* effect = GetAura()->GetEffect(EFFECT_1))
|
||||
effect->RecalculateAmount();
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
DoEffectCalcAmount += AuraEffectCalcAmountFn(spell_teron_gorefiend_spirit_lance::CalculateAmount, EFFECT_1, SPELL_AURA_MOD_DECREASE_SPEED);
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_teron_gorefiend_spirit_lance::Update, EFFECT_2, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_teron_gorefiend_spiritual_vengeance : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_teron_gorefiend_spiritual_vengeance);
|
||||
|
||||
void HandleEffectRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
InstanceScript* instance = GetTarget()->GetInstanceScript();
|
||||
if (!GetCaster() || !instance || !instance->IsEncounterInProgress())
|
||||
return;
|
||||
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SPIRIT, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_POSSESS_SPIRIT_IMMUNE, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SPIRITUAL_VENGEANCE, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SKELETON1, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SKELETON2, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SKELETON3, true);
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_SUMMON_SKELETON4, true);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectAbsorb += AuraEffectAbsorbFn(spell_teron_gorefiend_shadow_of_death_AuraScript::Absorb, EFFECT_0);
|
||||
AfterEffectRemove += AuraEffectRemoveFn(spell_teron_gorefiend_shadow_of_death_AuraScript::HandleEffectRemove, EFFECT_0, SPELL_AURA_SCHOOL_ABSORB, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_teron_gorefiend_shadow_of_death_AuraScript();
|
||||
Unit::Kill(nullptr, GetTarget());
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
AfterEffectRemove += AuraEffectRemoveFn(spell_teron_gorefiend_spiritual_vengeance::HandleEffectRemove, EFFECT_2, SPELL_AURA_MOD_PACIFY_SILENCE, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_teron_gorefiend_spirit_lance : public SpellScriptLoader
|
||||
class spell_teron_gorefiend_shadowy_construct : public AuraScript
|
||||
{
|
||||
public:
|
||||
spell_teron_gorefiend_spirit_lance() : SpellScriptLoader("spell_teron_gorefiend_spirit_lance") { }
|
||||
PrepareAuraScript(spell_teron_gorefiend_shadowy_construct);
|
||||
|
||||
class spell_teron_gorefiend_spirit_lance_AuraScript : public AuraScript
|
||||
bool Load() override
|
||||
{
|
||||
PrepareAuraScript(spell_teron_gorefiend_spirit_lance_AuraScript);
|
||||
|
||||
void CalculateAmount(AuraEffect const* /*aurEff*/, int32& amount, bool& /*canBeRecalculated*/)
|
||||
{
|
||||
if (AuraEffect* effect = GetAura()->GetEffect(EFFECT_2))
|
||||
amount -= (amount / effect->GetTotalTicks()) * effect->GetTickNumber();
|
||||
}
|
||||
|
||||
void Update(AuraEffect const* /*effect*/)
|
||||
{
|
||||
PreventDefaultAction();
|
||||
if (AuraEffect* effect = GetAura()->GetEffect(EFFECT_1))
|
||||
effect->RecalculateAmount();
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
DoEffectCalcAmount += AuraEffectCalcAmountFn(spell_teron_gorefiend_spirit_lance_AuraScript::CalculateAmount, EFFECT_1, SPELL_AURA_MOD_DECREASE_SPEED);
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_teron_gorefiend_spirit_lance_AuraScript::Update, EFFECT_2, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_teron_gorefiend_spirit_lance_AuraScript();
|
||||
return GetUnitOwner()->GetTypeId() == TYPEID_UNIT;
|
||||
}
|
||||
};
|
||||
|
||||
class spell_teron_gorefiend_spiritual_vengeance : public SpellScriptLoader
|
||||
{
|
||||
public:
|
||||
spell_teron_gorefiend_spiritual_vengeance() : SpellScriptLoader("spell_teron_gorefiend_spiritual_vengeance") { }
|
||||
|
||||
class spell_teron_gorefiend_spiritual_vengeance_AuraScript : public AuraScript
|
||||
void HandleEffectApply(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
PrepareAuraScript(spell_teron_gorefiend_spiritual_vengeance_AuraScript)
|
||||
GetUnitOwner()->ApplySpellImmune(0, IMMUNITY_SCHOOL, SPELL_SCHOOL_MASK_NORMAL, true);
|
||||
GetUnitOwner()->ApplySpellImmune(0, IMMUNITY_ALLOW_ID, SPELL_SPIRIT_LANCE, true);
|
||||
GetUnitOwner()->ApplySpellImmune(0, IMMUNITY_ALLOW_ID, SPELL_SPIRIT_CHAINS, true);
|
||||
GetUnitOwner()->ApplySpellImmune(0, IMMUNITY_ALLOW_ID, SPELL_SPIRIT_VOLLEY, true);
|
||||
|
||||
void HandleEffectRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
Unit::Kill(nullptr, GetTarget());
|
||||
}
|
||||
GetUnitOwner()->ToCreature()->SetInCombatWithZone();
|
||||
Map::PlayerList const& playerList = GetUnitOwner()->GetMap()->GetPlayers();
|
||||
for (Map::PlayerList::const_iterator i = playerList.begin(); i != playerList.end(); ++i)
|
||||
if (Player* player = i->GetSource())
|
||||
{
|
||||
if (GetUnitOwner()->IsValidAttackTarget(player))
|
||||
GetUnitOwner()->AddThreat(player, 1000000.0f);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
AfterEffectRemove += AuraEffectRemoveFn(spell_teron_gorefiend_spiritual_vengeance_AuraScript::HandleEffectRemove, EFFECT_2, SPELL_AURA_MOD_PACIFY_SILENCE, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_teron_gorefiend_spiritual_vengeance_AuraScript();
|
||||
GetUnitOwner()->CastSpell(GetUnitOwner(), SPELL_BRIEF_STUN, true);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_teron_gorefiend_shadowy_construct : public SpellScriptLoader
|
||||
{
|
||||
public:
|
||||
spell_teron_gorefiend_shadowy_construct() : SpellScriptLoader("spell_teron_gorefiend_shadowy_construct") { }
|
||||
|
||||
class spell_teron_gorefiend_shadowy_construct_AuraScript : public AuraScript
|
||||
void Register() override
|
||||
{
|
||||
PrepareAuraScript(spell_teron_gorefiend_shadowy_construct_AuraScript)
|
||||
|
||||
bool Load() override
|
||||
{
|
||||
return GetUnitOwner()->GetTypeId() == TYPEID_UNIT;
|
||||
}
|
||||
|
||||
void HandleEffectApply(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
GetUnitOwner()->ApplySpellImmune(0, IMMUNITY_SCHOOL, SPELL_SCHOOL_MASK_NORMAL, true);
|
||||
GetUnitOwner()->ApplySpellImmune(0, IMMUNITY_ALLOW_ID, SPELL_SPIRIT_LANCE, true);
|
||||
GetUnitOwner()->ApplySpellImmune(0, IMMUNITY_ALLOW_ID, SPELL_SPIRIT_CHAINS, true);
|
||||
GetUnitOwner()->ApplySpellImmune(0, IMMUNITY_ALLOW_ID, SPELL_SPIRIT_VOLLEY, true);
|
||||
|
||||
GetUnitOwner()->ToCreature()->SetInCombatWithZone();
|
||||
Map::PlayerList const& playerList = GetUnitOwner()->GetMap()->GetPlayers();
|
||||
for (Map::PlayerList::const_iterator i = playerList.begin(); i != playerList.end(); ++i)
|
||||
if (Player* player = i->GetSource())
|
||||
{
|
||||
if (GetUnitOwner()->IsValidAttackTarget(player))
|
||||
GetUnitOwner()->AddThreat(player, 1000000.0f);
|
||||
}
|
||||
|
||||
GetUnitOwner()->CastSpell(GetUnitOwner(), SPELL_BRIEF_STUN, true);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
AfterEffectApply += AuraEffectApplyFn(spell_teron_gorefiend_shadowy_construct_AuraScript::HandleEffectApply, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_teron_gorefiend_shadowy_construct_AuraScript();
|
||||
AfterEffectApply += AuraEffectApplyFn(spell_teron_gorefiend_shadowy_construct::HandleEffectApply, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_teron_gorefiend()
|
||||
{
|
||||
new boss_teron_gorefiend();
|
||||
new spell_teron_gorefiend_shadow_of_death();
|
||||
new spell_teron_gorefiend_spirit_lance();
|
||||
new spell_teron_gorefiend_spiritual_vengeance();
|
||||
new spell_teron_gorefiend_shadowy_construct();
|
||||
RegisterBlackTempleCreatureAI(boss_teron_gorefiend);
|
||||
RegisterSpellScript(spell_teron_gorefiend_shadow_of_death);
|
||||
RegisterSpellScript(spell_teron_gorefiend_spirit_lance);
|
||||
RegisterSpellScript(spell_teron_gorefiend_spiritual_vengeance);
|
||||
RegisterSpellScript(spell_teron_gorefiend_shadowy_construct);
|
||||
}
|
||||
|
||||
@@ -50,158 +50,118 @@ enum Events
|
||||
EVENT_KILL_SPEAK = 6
|
||||
};
|
||||
|
||||
class boss_najentus : public CreatureScript
|
||||
struct boss_najentus : public BossAI
|
||||
{
|
||||
public:
|
||||
boss_najentus() : CreatureScript("boss_najentus") { }
|
||||
boss_najentus(Creature* creature) : BossAI(creature, DATA_HIGH_WARLORD_NAJENTUS) { }
|
||||
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
void KilledUnit(Unit* victim) override
|
||||
{
|
||||
return GetBlackTempleAI<boss_najentusAI>(creature);
|
||||
if (victim->GetTypeId() == TYPEID_PLAYER && events.GetNextEventTime(EVENT_KILL_SPEAK) == 0)
|
||||
{
|
||||
Talk(SAY_SLAY);
|
||||
events.ScheduleEvent(EVENT_KILL_SPEAK, 5000);
|
||||
}
|
||||
}
|
||||
|
||||
struct boss_najentusAI : public BossAI
|
||||
void JustDied(Unit* killer) override
|
||||
{
|
||||
boss_najentusAI(Creature* creature) : BossAI(creature, DATA_HIGH_WARLORD_NAJENTUS)
|
||||
{
|
||||
}
|
||||
BossAI::JustDied(killer);
|
||||
Talk(SAY_DEATH);
|
||||
}
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
BossAI::Reset();
|
||||
}
|
||||
void JustEngagedWith(Unit* who) override
|
||||
{
|
||||
BossAI::JustEngagedWith(who);
|
||||
Talk(SAY_AGGRO);
|
||||
events.ScheduleEvent(EVENT_SPELL_BERSERK, 480000);
|
||||
events.ScheduleEvent(EVENT_YELL, urand(25000, 100000));
|
||||
events.RescheduleEvent(EVENT_SPELL_NEEDLE, 10000);
|
||||
events.RescheduleEvent(EVENT_SPELL_SPINE, 20001);
|
||||
events.RescheduleEvent(EVENT_SPELL_SHIELD, 60000);
|
||||
}
|
||||
|
||||
void KilledUnit(Unit* victim) override
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
if (victim->GetTypeId() == TYPEID_PLAYER && events.GetNextEventTime(EVENT_KILL_SPEAK) == 0)
|
||||
case EVENT_SPELL_SHIELD:
|
||||
me->CastSpell(me, SPELL_TIDAL_SHIELD, false);
|
||||
events.DelayEvents(10000);
|
||||
events.ScheduleEvent(EVENT_SPELL_SHIELD, 60000);
|
||||
break;
|
||||
case EVENT_SPELL_BERSERK:
|
||||
Talk(SAY_ENRAGE);
|
||||
me->CastSpell(me, SPELL_BERSERK, true);
|
||||
break;
|
||||
case EVENT_SPELL_NEEDLE:
|
||||
me->CastCustomSpell(SPELL_NEEDLE_SPINE, SPELLVALUE_MAX_TARGETS, 3, me, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_NEEDLE, 15000);
|
||||
break;
|
||||
case EVENT_SPELL_SPINE:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 1))
|
||||
{
|
||||
Talk(SAY_SLAY);
|
||||
events.ScheduleEvent(EVENT_KILL_SPEAK, 5000);
|
||||
me->CastSpell(target, SPELL_IMPALING_SPINE, false);
|
||||
target->CastSpell(target, SPELL_SUMMON_IMPALING_SPINE, true);
|
||||
Talk(SAY_NEEDLE);
|
||||
}
|
||||
}
|
||||
|
||||
void JustDied(Unit* killer) override
|
||||
{
|
||||
BossAI::JustDied(killer);
|
||||
Talk(SAY_DEATH);
|
||||
}
|
||||
|
||||
void JustEngagedWith(Unit* who) override
|
||||
{
|
||||
BossAI::JustEngagedWith(who);
|
||||
Talk(SAY_AGGRO);
|
||||
events.ScheduleEvent(EVENT_SPELL_BERSERK, 480000);
|
||||
events.ScheduleEvent(EVENT_SPELL_SPINE, 20000);
|
||||
return;
|
||||
case EVENT_YELL:
|
||||
Talk(SAY_SPECIAL);
|
||||
events.ScheduleEvent(EVENT_YELL, urand(25000, 100000));
|
||||
events.RescheduleEvent(EVENT_SPELL_NEEDLE, 10000);
|
||||
events.RescheduleEvent(EVENT_SPELL_SPINE, 20001);
|
||||
events.RescheduleEvent(EVENT_SPELL_SHIELD, 60000);
|
||||
break;
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
case EVENT_SPELL_SHIELD:
|
||||
me->CastSpell(me, SPELL_TIDAL_SHIELD, false);
|
||||
events.DelayEvents(10000);
|
||||
events.ScheduleEvent(EVENT_SPELL_SHIELD, 60000);
|
||||
break;
|
||||
case EVENT_SPELL_BERSERK:
|
||||
Talk(SAY_ENRAGE);
|
||||
me->CastSpell(me, SPELL_BERSERK, true);
|
||||
break;
|
||||
case EVENT_SPELL_NEEDLE:
|
||||
me->CastCustomSpell(SPELL_NEEDLE_SPINE, SPELLVALUE_MAX_TARGETS, 3, me, false);
|
||||
events.ScheduleEvent(EVENT_SPELL_NEEDLE, 15000);
|
||||
break;
|
||||
case EVENT_SPELL_SPINE:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 1))
|
||||
{
|
||||
me->CastSpell(target, SPELL_IMPALING_SPINE, false);
|
||||
target->CastSpell(target, SPELL_SUMMON_IMPALING_SPINE, true);
|
||||
Talk(SAY_NEEDLE);
|
||||
}
|
||||
events.ScheduleEvent(EVENT_SPELL_SPINE, 20000);
|
||||
return;
|
||||
case EVENT_YELL:
|
||||
Talk(SAY_SPECIAL);
|
||||
events.ScheduleEvent(EVENT_YELL, urand(25000, 100000));
|
||||
break;
|
||||
}
|
||||
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
class spell_najentus_needle_spine : public SpellScriptLoader
|
||||
{
|
||||
public:
|
||||
spell_najentus_needle_spine() : SpellScriptLoader("spell_najentus_needle_spine") { }
|
||||
|
||||
class spell_najentus_needle_spine_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_najentus_needle_spine_SpellScript);
|
||||
|
||||
void HandleDummy(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
if (Unit* target = GetHitUnit())
|
||||
GetCaster()->CastSpell(target, SPELL_NEEDLE_SPINE_DAMAGE, true);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectHitTarget += SpellEffectFn(spell_najentus_needle_spine_SpellScript::HandleDummy, EFFECT_0, SPELL_EFFECT_DUMMY);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_najentus_needle_spine_SpellScript();
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
};
|
||||
|
||||
class spell_najentus_hurl_spine : public SpellScriptLoader
|
||||
class spell_najentus_needle_spine : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_najentus_hurl_spine() : SpellScriptLoader("spell_najentus_hurl_spine") { }
|
||||
PrepareSpellScript(spell_najentus_needle_spine);
|
||||
|
||||
class spell_najentus_hurl_spine_SpellScript : public SpellScript
|
||||
void HandleDummy(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
PrepareSpellScript(spell_najentus_hurl_spine_SpellScript);
|
||||
if (Unit* target = GetHitUnit())
|
||||
GetCaster()->CastSpell(target, SPELL_NEEDLE_SPINE_DAMAGE, true);
|
||||
}
|
||||
|
||||
void HandleSchoolDamage(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Unit* target = GetHitUnit();
|
||||
if (target && target->HasAura(SPELL_TIDAL_SHIELD))
|
||||
{
|
||||
target->RemoveAurasDueToSpell(SPELL_TIDAL_SHIELD);
|
||||
target->CastSpell(target, SPELL_TIDAL_BURST, true);
|
||||
}
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectHitTarget += SpellEffectFn(spell_najentus_hurl_spine_SpellScript::HandleSchoolDamage, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
void Register() override
|
||||
{
|
||||
return new spell_najentus_hurl_spine_SpellScript();
|
||||
OnEffectHitTarget += SpellEffectFn(spell_najentus_needle_spine::HandleDummy, EFFECT_0, SPELL_EFFECT_DUMMY);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_najentus_hurl_spine : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_najentus_hurl_spine);
|
||||
|
||||
void HandleSchoolDamage(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Unit* target = GetHitUnit();
|
||||
if (target && target->HasAura(SPELL_TIDAL_SHIELD))
|
||||
{
|
||||
target->RemoveAurasDueToSpell(SPELL_TIDAL_SHIELD);
|
||||
target->CastSpell(target, SPELL_TIDAL_BURST, true);
|
||||
}
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectHitTarget += SpellEffectFn(spell_najentus_hurl_spine::HandleSchoolDamage, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_najentus()
|
||||
{
|
||||
new boss_najentus();
|
||||
new spell_najentus_needle_spine();
|
||||
new spell_najentus_hurl_spine();
|
||||
RegisterBlackTempleCreatureAI(boss_najentus);
|
||||
RegisterSpellScript(spell_najentus_needle_spine);
|
||||
RegisterSpellScript(spell_najentus_hurl_spine);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user