mirror of
https://github.com/ZhengPeiRu21/mod-individual-progression
synced 2025-11-29 23:44:51 +08:00
update spell scripts, some fixes
This commit is contained in:
@@ -1,4 +1,3 @@
|
||||
|
||||
#include "Player.h"
|
||||
#include "ScriptMgr.h"
|
||||
#include "ScriptedCreature.h"
|
||||
@@ -117,7 +116,6 @@ class npc_omarion : public CreatureScript
|
||||
public:
|
||||
npc_omarion() : CreatureScript("npc_omarion_gossip") { }
|
||||
|
||||
|
||||
bool OnGossipHello(Player* player, Creature* creature) override
|
||||
{
|
||||
ClearGossipMenuFor(player);
|
||||
@@ -311,7 +309,7 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_npc_omarion()
|
||||
void AddSC_omarion_40()
|
||||
{
|
||||
new npc_omarion();
|
||||
}
|
||||
@@ -253,49 +253,7 @@ public:
|
||||
};
|
||||
};
|
||||
|
||||
class spell_anub_locust_swarm_40 : public SpellScriptLoader
|
||||
{
|
||||
public:
|
||||
spell_anub_locust_swarm_40() : SpellScriptLoader("spell_anub_locust_swarm_40") { }
|
||||
|
||||
class spell_anub_locust_swarm_40_AuraScript : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_anub_locust_swarm_40_AuraScript);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
return ValidateSpellInfo({ SPELL_LOCUST_SWARM_TRIGGER });
|
||||
}
|
||||
|
||||
void HandleTriggerSpell(AuraEffect const* /*aurEff*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
PreventDefaultAction();
|
||||
int32 modifiedLocustSwarmDamage = 812;
|
||||
CustomSpellValues values;
|
||||
values.AddSpellMod(SPELLVALUE_BASE_POINT0, modifiedLocustSwarmDamage);
|
||||
values.AddSpellMod(SPELLVALUE_RADIUS_MOD, 3000); // 30yd
|
||||
caster->CastCustomSpell(SPELL_LOCUST_SWARM_TRIGGER, values, caster, TRIGGERED_FULL_MASK, nullptr, nullptr, GetCasterGUID());
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_anub_locust_swarm_40_AuraScript::HandleTriggerSpell, EFFECT_0, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_anub_locust_swarm_40_AuraScript();
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_anubrekhan_40()
|
||||
{
|
||||
new boss_anubrekhan_40();
|
||||
new spell_anub_locust_swarm_40();
|
||||
}
|
||||
|
||||
@@ -25,6 +25,8 @@
|
||||
enum Spells
|
||||
{
|
||||
SPELL_BERSERK = 26662,
|
||||
SPELL_SHIELDWALL = 29061, // Shield Wall - All 4 horsemen will shield wall at 50% hp and 20% hp for 20 seconds
|
||||
SPELL_SUMMON_PLAYER = 25104,
|
||||
// Marks
|
||||
SPELL_MARK_OF_KORTHAZZ = 28832,
|
||||
SPELL_MARK_OF_BLAUMEUX = 28833,
|
||||
@@ -32,21 +34,15 @@ enum Spells
|
||||
SPELL_MARK_OF_ZELIEK = 28835,
|
||||
SPELL_MARK_DAMAGE = 28836,
|
||||
// Korth'azz
|
||||
SPELL_KORTHAZZ_METEOR_10 = 28884,
|
||||
SPELL_KORTHAZZ_METEOR_25 = 57467,
|
||||
SPELL_KORTHAZZ_METEOR = 28884,
|
||||
// Blaumeux
|
||||
SPELL_BLAUMEUX_SHADOW_BOLT_10 = 57374,
|
||||
SPELL_BLAUMEUX_SHADOW_BOLT_25 = 57464,
|
||||
SPELL_BLAUMEUX_VOID_ZONE_10 = 28863,
|
||||
SPELL_BLAUMEUX_VOID_ZONE_25 = 57463,
|
||||
SPELL_BLAUMEUX_SHADOW_BOLT = 57374,
|
||||
SPELL_BLAUMEUX_VOID_ZONE = 28863,
|
||||
// Zeliek
|
||||
SPELL_ZELIEK_HOLY_WRATH_10 = 28883,
|
||||
SPELL_ZELIEK_HOLY_WRATH_25 = 57466,
|
||||
SPELL_ZELIEK_HOLY_BOLT_10 = 57376,
|
||||
SPELL_ZELIEK_HOLY_BOLT_25 = 57465,
|
||||
SPELL_ZELIEK_HOLY_WRATH = 28883,
|
||||
SPELL_ZELIEK_HOLY_BOLT = 57376,
|
||||
// Mograine
|
||||
SPELL_RIVENDARE_UNHOLY_SHADOW_10 = 28882,
|
||||
SPELL_RIVENDARE_UNHOLY_SHADOW_25 = 57369
|
||||
SPELL_RIVENDARE_UNHOLY_SHADOW = 28882,
|
||||
};
|
||||
|
||||
enum Events
|
||||
@@ -54,15 +50,12 @@ enum Events
|
||||
EVENT_MARK_CAST = 1,
|
||||
EVENT_PRIMARY_SPELL = 2,
|
||||
EVENT_SECONDARY_SPELL = 3,
|
||||
EVENT_BERSERK = 4
|
||||
EVENT_BERSERK = 4,
|
||||
EVENT_HEALTH_CHECK = 5
|
||||
};
|
||||
|
||||
enum Misc
|
||||
{
|
||||
// Movement
|
||||
MOVE_PHASE_NONE = 0,
|
||||
MOVE_PHASE_STARTED = 1,
|
||||
MOVE_PHASE_FINISHED = 2,
|
||||
// Horseman
|
||||
HORSEMAN_ZELIEK = 0,
|
||||
HORSEMAN_BLAUMEUX = 1,
|
||||
@@ -70,6 +63,20 @@ enum Misc
|
||||
HORSEMAN_KORTHAZZ = 3
|
||||
};
|
||||
|
||||
enum Spirits
|
||||
{
|
||||
// Spells
|
||||
SPELL_SUMMON_SPIRIT_ZELIEK = 28934,
|
||||
SPELL_SUMMON_SPIRIT_BLAUMEUX = 28931,
|
||||
SPELL_SUMMON_SPIRIT_MOGRAINE = 28928,
|
||||
SPELL_SUMMON_SPIRIT_KORTHAZZ = 28932,
|
||||
// NPCs
|
||||
NPC_SPIRIT_ZELIEK = 16777,
|
||||
NPC_SPIRIT_BLAUMEUX = 16776,
|
||||
NPC_SPIRIT_MOGRAINE = 16775,
|
||||
NPC_SPIRIT_KORTHAZZ = 16778
|
||||
};
|
||||
|
||||
enum FourHorsemen
|
||||
{
|
||||
SAY_AGGRO = 0,
|
||||
@@ -82,26 +89,8 @@ enum FourHorsemen
|
||||
|
||||
// MARKS
|
||||
const uint32 TABLE_SPELL_MARK[4] = {SPELL_MARK_OF_ZELIEK, SPELL_MARK_OF_BLAUMEUX, SPELL_MARK_OF_MOGRAINE, SPELL_MARK_OF_KORTHAZZ};
|
||||
|
||||
const Position WaypointPositions[12] =
|
||||
{
|
||||
// Thane waypoints
|
||||
{2542.3f, -2984.1f, 241.49f, 5.362f},
|
||||
{2547.6f, -2999.4f, 241.34f, 5.049f},
|
||||
{2542.9f, -3015.0f, 241.35f, 4.654f},
|
||||
// Lady waypoints
|
||||
{2498.3f, -2961.8f, 241.28f, 3.267f},
|
||||
{2487.7f, -2959.2f, 241.28f, 2.890f},
|
||||
{2469.4f, -2947.6f, 241.28f, 2.576f},
|
||||
// Mograine waypoints
|
||||
{2553.8f, -2968.4f, 241.33f, 5.757f},
|
||||
{2564.3f, -2972.5f, 241.33f, 5.890f},
|
||||
{2583.9f, -2971.6f, 241.35f, 0.008f},
|
||||
// Sir waypoints
|
||||
{2534.5f, -2921.7f, 241.53f, 1.363f},
|
||||
{2523.5f, -2902.8f, 241.28f, 2.095f},
|
||||
{2517.8f, -2896.6f, 241.28f, 2.315f}
|
||||
};
|
||||
// SPIRITS
|
||||
const uint32 TABLE_SPELL_SUMMON_SPIRIT[4] = {SPELL_SUMMON_SPIRIT_ZELIEK, SPELL_SUMMON_SPIRIT_BLAUMEUX, SPELL_SUMMON_SPIRIT_MOGRAINE, SPELL_SUMMON_SPIRIT_KORTHAZZ};
|
||||
|
||||
class boss_four_horsemen_40 : public CreatureScript
|
||||
{
|
||||
@@ -137,29 +126,8 @@ public:
|
||||
|
||||
EventMap events;
|
||||
InstanceScript* pInstance;
|
||||
uint8 currentWaypoint{};
|
||||
uint8 movementPhase{};
|
||||
uint8 horsemanId;
|
||||
|
||||
void MoveToCorner()
|
||||
{
|
||||
switch(me->GetEntry())
|
||||
{
|
||||
case NPC_THANE_KORTHAZZ_40:
|
||||
currentWaypoint = 0;
|
||||
break;
|
||||
case NPC_LADY_BLAUMEUX_40:
|
||||
currentWaypoint = 3;
|
||||
break;
|
||||
case NPC_HIGHLORD_MOGRAINE_40:
|
||||
currentWaypoint = 6;
|
||||
break;
|
||||
case NPC_SIR_ZELIEK_40:
|
||||
currentWaypoint = 9;
|
||||
break;
|
||||
}
|
||||
me->GetMotionMaster()->MovePoint(currentWaypoint, WaypointPositions[currentWaypoint]);
|
||||
}
|
||||
bool doneFirstShieldWall;
|
||||
|
||||
bool IsInRoom()
|
||||
{
|
||||
@@ -175,12 +143,13 @@ public:
|
||||
{
|
||||
BossAI::Reset();
|
||||
me->SetPosition(me->GetHomePosition());
|
||||
movementPhase = MOVE_PHASE_NONE;
|
||||
currentWaypoint = 0;
|
||||
|
||||
me->SetReactState(REACT_AGGRESSIVE);
|
||||
doneFirstShieldWall = false;
|
||||
events.Reset();
|
||||
events.RescheduleEvent(EVENT_MARK_CAST, 24000);
|
||||
events.RescheduleEvent(EVENT_MARK_CAST, 20000);
|
||||
events.RescheduleEvent(EVENT_BERSERK, 600000);
|
||||
summons.DespawnAll(); // despawn spirits
|
||||
if ((me->GetEntry() != NPC_LADY_BLAUMEUX_40 && me->GetEntry() != NPC_SIR_ZELIEK_40))
|
||||
{
|
||||
events.RescheduleEvent(EVENT_PRIMARY_SPELL, 10000 + rand() % 5000);
|
||||
@@ -201,47 +170,6 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
void MovementInform(uint32 type, uint32 id) override
|
||||
{
|
||||
if (type != POINT_MOTION_TYPE)
|
||||
return;
|
||||
|
||||
// final waypoint
|
||||
if (id % 3 == 2)
|
||||
{
|
||||
movementPhase = MOVE_PHASE_FINISHED;
|
||||
me->SetReactState(REACT_AGGRESSIVE);
|
||||
me->SetInCombatWithZone();
|
||||
if (!UpdateVictim())
|
||||
{
|
||||
EnterEvadeMode();
|
||||
return;
|
||||
}
|
||||
if (me->GetEntry() == NPC_LADY_BLAUMEUX_40 || me->GetEntry() == NPC_SIR_ZELIEK_40)
|
||||
{
|
||||
me->GetMotionMaster()->Clear(false);
|
||||
me->GetMotionMaster()->MoveIdle();
|
||||
}
|
||||
return;
|
||||
}
|
||||
currentWaypoint = id + 1;
|
||||
}
|
||||
|
||||
void AttackStart(Unit* who) override
|
||||
{
|
||||
if (movementPhase == MOVE_PHASE_FINISHED)
|
||||
{
|
||||
if (me->GetEntry() == NPC_LADY_BLAUMEUX_40 || me->GetEntry() == NPC_SIR_ZELIEK_40)
|
||||
{
|
||||
me->Attack(who, false);
|
||||
}
|
||||
else
|
||||
{
|
||||
ScriptedAI::AttackStart(who);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void KilledUnit(Unit* who) override
|
||||
{
|
||||
if (who->GetTypeId() != TYPEID_PLAYER)
|
||||
@@ -254,6 +182,14 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
void SpellHitTarget(Unit* target, SpellInfo const* spellInfo) override
|
||||
{
|
||||
if (spellInfo->Id == TABLE_SPELL_MARK[horsemanId])
|
||||
{
|
||||
DoModifyThreatByPercent(target, -50);
|
||||
}
|
||||
}
|
||||
|
||||
void JustDied(Unit* killer) override
|
||||
{
|
||||
BossAI::JustDied(killer);
|
||||
@@ -261,6 +197,14 @@ public:
|
||||
{
|
||||
if (pInstance->GetBossState(BOSS_HORSEMAN) == DONE)
|
||||
{
|
||||
if (Creature* spirit = GetClosestCreatureWithEntry(me, NPC_SPIRIT_ZELIEK, 200.0f))
|
||||
spirit->DespawnOrUnsummon();
|
||||
if (Creature* spirit = GetClosestCreatureWithEntry(me, NPC_SPIRIT_BLAUMEUX, 200.0f))
|
||||
spirit->DespawnOrUnsummon();
|
||||
if (Creature* spirit = GetClosestCreatureWithEntry(me, NPC_SPIRIT_MOGRAINE, 200.0f))
|
||||
spirit->DespawnOrUnsummon();
|
||||
if (Creature* spirit = GetClosestCreatureWithEntry(me, NPC_SPIRIT_KORTHAZZ, 200.0f))
|
||||
spirit->DespawnOrUnsummon();
|
||||
if (!me->GetMap()->GetPlayers().IsEmpty())
|
||||
{
|
||||
if (Player* player = me->GetMap()->GetPlayers().getFirst()->GetSource())
|
||||
@@ -276,22 +220,30 @@ public:
|
||||
go->SetGoState(GO_STATE_ACTIVE);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Prevent spawning if last horseman killed
|
||||
DoCastSelf(TABLE_SPELL_SUMMON_SPIRIT[horsemanId], true);
|
||||
}
|
||||
}
|
||||
Talk(SAY_DEATH);
|
||||
}
|
||||
|
||||
void JustSummoned(Creature* summon) override
|
||||
{
|
||||
summons.Summon(summon);
|
||||
summons.DoZoneInCombat();
|
||||
summon->SetUnitFlag(UNIT_FLAG_DISABLE_MOVE);
|
||||
}
|
||||
|
||||
void JustEngagedWith(Unit* who) override
|
||||
{
|
||||
BossAI::JustEngagedWith(who);
|
||||
if (movementPhase == MOVE_PHASE_NONE)
|
||||
{
|
||||
Talk(SAY_AGGRO);
|
||||
me->SetReactState(REACT_PASSIVE);
|
||||
movementPhase = MOVE_PHASE_STARTED;
|
||||
me->SetSpeed(MOVE_RUN, me->GetSpeedRate(MOVE_RUN), true);
|
||||
MoveToCorner();
|
||||
}
|
||||
me->SetReactState(REACT_AGGRESSIVE);
|
||||
me->SetInCombatWithZone();
|
||||
if (pInstance)
|
||||
events.ScheduleEvent(EVENT_HEALTH_CHECK, 1s);
|
||||
{
|
||||
if (GameObject* go = me->GetMap()->GetGameObject(pInstance->GetGuidData(DATA_HORSEMEN_GATE)))
|
||||
{
|
||||
@@ -302,18 +254,18 @@ public:
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
if (movementPhase == MOVE_PHASE_STARTED && currentWaypoint)
|
||||
{
|
||||
me->GetMotionMaster()->MovePoint(currentWaypoint, WaypointPositions[currentWaypoint]);
|
||||
currentWaypoint = 0;
|
||||
}
|
||||
|
||||
if (!IsInRoom())
|
||||
return;
|
||||
|
||||
if (movementPhase < MOVE_PHASE_FINISHED || !UpdateVictim())
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
if (Unit* victim = me->GetVictim())
|
||||
{
|
||||
if (!me->IsWithinDistInMap(victim, VISIBILITY_DISTANCE_NORMAL))
|
||||
me->CastSpell(victim, SPELL_SUMMON_PLAYER, true);
|
||||
}
|
||||
|
||||
events.Update(diff);
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
@@ -322,7 +274,7 @@ public:
|
||||
{
|
||||
case EVENT_MARK_CAST:
|
||||
me->CastSpell(me, TABLE_SPELL_MARK[horsemanId], false);
|
||||
events.RepeatEvent((me->GetEntry() == NPC_LADY_BLAUMEUX_40 || me->GetEntry() == NPC_SIR_ZELIEK_40) ? 15000 : 12000);
|
||||
events.RepeatEvent(12000);
|
||||
return;
|
||||
case EVENT_BERSERK:
|
||||
Talk(SAY_SPECIAL);
|
||||
@@ -333,22 +285,22 @@ public:
|
||||
if (horsemanId == HORSEMAN_ZELIEK)
|
||||
{
|
||||
int32 bp0 = 1109; // spell not used in vanilla, reduced damage from ~2.5 to ~1.2k
|
||||
me->CastCustomSpell(me->GetVictim(), SPELL_ZELIEK_HOLY_BOLT_10, &bp0, 0, 0, false);
|
||||
me->CastCustomSpell(me->GetVictim(), SPELL_ZELIEK_HOLY_BOLT, &bp0, 0, 0, false);
|
||||
}
|
||||
else if (horsemanId == HORSEMAN_BLAUMEUX)
|
||||
{
|
||||
int32 bp0 = 1109; // spell not used in vanilla, reduced damage from ~2.5 to ~1.2k
|
||||
me->CastCustomSpell(me->GetVictim(), SPELL_BLAUMEUX_SHADOW_BOLT_10, &bp0, 0, 0, false);
|
||||
me->CastCustomSpell(me->GetVictim(), SPELL_BLAUMEUX_SHADOW_BOLT, &bp0, 0, 0, false);
|
||||
}
|
||||
else if (horsemanId == HORSEMAN_MOGRAINE)
|
||||
{
|
||||
// same dbc as vanilla. Shadow damage instead of fire
|
||||
me->CastSpell(me->GetVictim(), SPELL_RIVENDARE_UNHOLY_SHADOW_10, false);
|
||||
me->CastSpell(me->GetVictim(), SPELL_RIVENDARE_UNHOLY_SHADOW, false);
|
||||
}
|
||||
else // HORSEMAN_KORTHAZZ
|
||||
{
|
||||
int32 bp0 = 12824; // 14.5k to 13.5k
|
||||
me->CastCustomSpell(me->GetVictim(), SPELL_KORTHAZZ_METEOR_10, &bp0, 0, 0, false);
|
||||
me->CastCustomSpell(me->GetVictim(), SPELL_KORTHAZZ_METEOR, &bp0, 0, 0, false);
|
||||
}
|
||||
events.RepeatEvent(15000);
|
||||
return;
|
||||
@@ -359,48 +311,41 @@ public:
|
||||
CustomSpellValues values;
|
||||
values.AddSpellMod(SPELLVALUE_BASE_POINT0, bp0);
|
||||
values.AddSpellMod(SPELLVALUE_MAX_TARGETS, 50); // 30yd
|
||||
me->CastCustomSpell(SPELL_ZELIEK_HOLY_WRATH_10, values, me->GetVictim(), TRIGGERED_NONE, nullptr, nullptr, ObjectGuid::Empty);
|
||||
me->CastCustomSpell(SPELL_ZELIEK_HOLY_WRATH, values, me->GetVictim(), TRIGGERED_NONE, nullptr, nullptr, ObjectGuid::Empty);
|
||||
}
|
||||
else // HORSEMAN_BLAUMEUX
|
||||
{
|
||||
me->CastSpell(me->GetVictim(), SPELL_BLAUMEUX_VOID_ZONE_10, false);
|
||||
me->CastSpell(me->GetVictim(), SPELL_BLAUMEUX_VOID_ZONE, false);
|
||||
}
|
||||
events.RepeatEvent(15000);
|
||||
return;
|
||||
}
|
||||
|
||||
if ((me->GetEntry() == NPC_LADY_BLAUMEUX_40 || me->GetEntry() == NPC_SIR_ZELIEK_40))
|
||||
case EVENT_HEALTH_CHECK:
|
||||
if (!doneFirstShieldWall && me->GetHealthPct() <= 50.0f)
|
||||
{
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::MaxDistance, 0, 45.0f, true))
|
||||
{
|
||||
if (horsemanId == HORSEMAN_ZELIEK)
|
||||
{
|
||||
int32 bp0 = 1109; // spell not used in vanilla, reduced damage from ~2.5 to ~1.2k
|
||||
me->CastCustomSpell(me->GetVictim(), SPELL_ZELIEK_HOLY_BOLT_10, &bp0, 0, 0, false);
|
||||
DoCastSelf(SPELL_SHIELDWALL, true);
|
||||
doneFirstShieldWall = true;
|
||||
events.Repeat(1s);
|
||||
break;
|
||||
}
|
||||
else if (horsemanId == HORSEMAN_BLAUMEUX)
|
||||
if (doneFirstShieldWall && me->GetHealthPct() <= 20.0f)
|
||||
{
|
||||
int32 bp0 = 1109; // spell not used in vanilla, reduced damage from ~2.5 to ~1.2k
|
||||
me->CastCustomSpell(me->GetVictim(), SPELL_BLAUMEUX_SHADOW_BOLT_10, &bp0, 0, 0, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
if (!me->HasAura(SPELL_SHIELDWALL)) // prevent refresh of first shield wall
|
||||
{
|
||||
DoCastSelf(SPELL_SHIELDWALL, true);
|
||||
}
|
||||
break;
|
||||
}
|
||||
events.Repeat(1s);
|
||||
return;
|
||||
}
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
class spell_four_horsemen_mark : public SpellScriptLoader
|
||||
class spell_four_horsemen_mark_aura : public AuraScript
|
||||
{
|
||||
public:
|
||||
spell_four_horsemen_mark() : SpellScriptLoader("spell_four_horsemen_mark") { }
|
||||
|
||||
class spell_four_horsemen_mark_AuraScript : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_four_horsemen_mark_AuraScript);
|
||||
PrepareAuraScript(spell_four_horsemen_mark_aura);
|
||||
|
||||
void OnApply(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
@@ -456,62 +401,12 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
AfterEffectApply += AuraEffectApplyFn(spell_four_horsemen_mark_AuraScript::OnApply, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL_OR_REAPPLY_MASK);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_four_horsemen_mark_AuraScript();
|
||||
}
|
||||
};
|
||||
|
||||
class spell_gen_consumption : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_gen_consumption);
|
||||
|
||||
void CalculateDamage(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Map* map = GetCaster()->GetMap();
|
||||
if (!map)
|
||||
{
|
||||
return;
|
||||
}
|
||||
int32 value = 0;
|
||||
if (map->GetDifficulty() == RAID_DIFFICULTY_25MAN_NORMAL) // NAXX25 N
|
||||
{
|
||||
value = urand(4500, 4700);
|
||||
}
|
||||
else if (map->GetId() == 533) // NAXX10 N
|
||||
{
|
||||
if (map->GetDifficulty() == RAID_DIFFICULTY_10MAN_NORMAL)
|
||||
{
|
||||
value = urand(3000, 3200);
|
||||
}
|
||||
else
|
||||
{
|
||||
value = urand(3960, 4840); // NAXX40
|
||||
}
|
||||
}
|
||||
else if (map->GetId() == 532) // Karazhan
|
||||
{
|
||||
value = urand(1110, 1310);
|
||||
}
|
||||
if (value)
|
||||
{
|
||||
SetEffectValue(value);
|
||||
}
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_gen_consumption::CalculateDamage, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
AfterEffectApply += AuraEffectApplyFn(spell_four_horsemen_mark_aura::OnApply, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL_OR_REAPPLY_MASK);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_four_horsemen_40()
|
||||
{
|
||||
new boss_four_horsemen_40();
|
||||
new spell_four_horsemen_mark();
|
||||
RegisterSpellScript(spell_gen_consumption);
|
||||
RegisterSpellScript(spell_four_horsemen_mark_aura);
|
||||
}
|
||||
|
||||
@@ -179,7 +179,6 @@ public:
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
case EVENT_BERSERK:
|
||||
@@ -251,14 +250,9 @@ public:
|
||||
};
|
||||
};
|
||||
|
||||
class spell_gluth_decimate : public SpellScriptLoader
|
||||
class spell_gluth_decimate : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_gluth_decimate() : SpellScriptLoader("spell_gluth_decimate") { }
|
||||
|
||||
class spell_gluth_decimate_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_gluth_decimate_SpellScript);
|
||||
PrepareSpellScript(spell_gluth_decimate);
|
||||
|
||||
void HandleScriptEffect(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
@@ -282,18 +276,12 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectHitTarget += SpellEffectFn(spell_gluth_decimate_SpellScript::HandleScriptEffect, EFFECT_0, SPELL_EFFECT_SCRIPT_EFFECT);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_gluth_decimate_SpellScript();
|
||||
OnEffectHitTarget += SpellEffectFn(spell_gluth_decimate::HandleScriptEffect, EFFECT_0, SPELL_EFFECT_SCRIPT_EFFECT);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_gluth_40()
|
||||
{
|
||||
new boss_gluth_40();
|
||||
new spell_gluth_decimate();
|
||||
RegisterSpellScript(spell_gluth_decimate);
|
||||
}
|
||||
|
||||
@@ -684,14 +684,9 @@ public:
|
||||
};
|
||||
};
|
||||
|
||||
class spell_gothik_shadow_bolt_volley : public SpellScriptLoader
|
||||
class spell_gothik_shadow_bolt_volley : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_gothik_shadow_bolt_volley() : SpellScriptLoader("spell_gothik_shadow_bolt_volley") { }
|
||||
|
||||
class spell_gothik_shadow_bolt_volley_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_gothik_shadow_bolt_volley_SpellScript);
|
||||
PrepareSpellScript(spell_gothik_shadow_bolt_volley);
|
||||
|
||||
void FilterTargets(std::list<WorldObject*>& targets)
|
||||
{
|
||||
@@ -700,13 +695,7 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_gothik_shadow_bolt_volley_SpellScript::FilterTargets, EFFECT_0, TARGET_UNIT_SRC_AREA_ENEMY);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_gothik_shadow_bolt_volley_SpellScript();
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_gothik_shadow_bolt_volley::FilterTargets, EFFECT_0, TARGET_UNIT_SRC_AREA_ENEMY);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -714,5 +703,5 @@ void AddSC_boss_gothik_40()
|
||||
{
|
||||
new boss_gothik_40();
|
||||
new npc_boss_gothik_minion_40();
|
||||
// new spell_gothik_shadow_bolt_volley();
|
||||
// RegisterSpellScript(spell_gothik_shadow_bolt_volley);
|
||||
}
|
||||
|
||||
@@ -241,14 +241,9 @@ public:
|
||||
};
|
||||
};
|
||||
|
||||
class spell_grobbulus_poison : public SpellScriptLoader
|
||||
class spell_grobbulus_poison : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_grobbulus_poison() : SpellScriptLoader("spell_grobbulus_poison") { }
|
||||
|
||||
class spell_grobbulus_poison_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_grobbulus_poison_SpellScript);
|
||||
PrepareSpellScript(spell_grobbulus_poison);
|
||||
|
||||
void FilterTargets(std::list<WorldObject*>& targets)
|
||||
{
|
||||
@@ -269,26 +264,14 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_grobbulus_poison_SpellScript::FilterTargets, EFFECT_0, TARGET_UNIT_SRC_AREA_ENEMY);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_grobbulus_poison_SpellScript();
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_grobbulus_poison::FilterTargets, EFFECT_0, TARGET_UNIT_SRC_AREA_ENEMY);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// This will overwrite the declared 10 and 25 man mutating injection to handle all versions of the spell script
|
||||
class spell_grobbulus_mutating_injection_40 : public SpellScriptLoader
|
||||
class spell_grobbulus_mutating_injection_aura : public AuraScript
|
||||
{
|
||||
public:
|
||||
spell_grobbulus_mutating_injection_40() : SpellScriptLoader("spell_grobbulus_mutating_injection") { }
|
||||
|
||||
class spell_grobbulus_mutating_injection_40_AuraScript : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_grobbulus_mutating_injection_40_AuraScript);
|
||||
PrepareAuraScript(spell_grobbulus_mutating_injection_aura);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
@@ -321,52 +304,7 @@ class spell_grobbulus_mutating_injection_40 : public SpellScriptLoader
|
||||
|
||||
void Register() override
|
||||
{
|
||||
AfterEffectRemove += AuraEffectRemoveFn(spell_grobbulus_mutating_injection_40_AuraScript::HandleRemove, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_grobbulus_mutating_injection_40_AuraScript();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
class spell_grobbulus_poison_cloud_poison_40 : public SpellScriptLoader
|
||||
{
|
||||
public:
|
||||
spell_grobbulus_poison_cloud_poison_40() : SpellScriptLoader("spell_grobbulus_poison_cloud_poison_40") { }
|
||||
|
||||
class spell_grobbulus_poison_cloud_poison_40_AuraScript : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_grobbulus_poison_cloud_poison_40_AuraScript);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
return ValidateSpellInfo({ SPELL_POISON_CLOUD_POISON_DAMAGE }); // Poison trigger
|
||||
}
|
||||
|
||||
void HandleTriggerSpell(AuraEffect const* /*aurEff*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
PreventDefaultAction();
|
||||
int32 bp0 = 1109;
|
||||
caster->CastCustomSpell(GetTarget(), SPELL_POISON_CLOUD_POISON_DAMAGE, &bp0, 0, 0, true);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_grobbulus_poison_cloud_poison_40_AuraScript::HandleTriggerSpell, EFFECT_0, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_grobbulus_poison_cloud_poison_40_AuraScript();
|
||||
AfterEffectRemove += AuraEffectRemoveFn(spell_grobbulus_mutating_injection_aura::HandleRemove, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -374,7 +312,6 @@ void AddSC_boss_grobbulus_40()
|
||||
{
|
||||
new boss_grobbulus_40();
|
||||
new boss_grobbulus_poison_cloud_40();
|
||||
new spell_grobbulus_mutating_injection_40();
|
||||
// new spell_grobbulus_poison();
|
||||
new spell_grobbulus_poison_cloud_poison_40();
|
||||
// RegisterSpellScript(spell_grobbulus_poison);
|
||||
RegisterSpellScript(spell_grobbulus_mutating_injection_aura);
|
||||
}
|
||||
|
||||
@@ -38,11 +38,12 @@ enum Says
|
||||
|
||||
enum Spells
|
||||
{
|
||||
SPELL_SPELL_DISRUPTION = 29310,
|
||||
SPELL_SUMMON_PLAYER = 25104,
|
||||
SPELL_DISRUPTION = 55010, // 29310->55010: Mana Burn AoE spell similar to vanilla
|
||||
SPELL_DECREPIT_FEVER = 29998,
|
||||
SPELL_PLAGUE_CLOUD = 29350,
|
||||
SPELL_PLAGUE_CLOUD_TRIGGER = 30122,
|
||||
SPELL_TELEPORT_SELF = 30211
|
||||
SPELL_TELEPORT_SELF = 30211,
|
||||
SPELL_TELEPORT_PLAYERS = 29273 // updated target in db
|
||||
};
|
||||
|
||||
enum Events
|
||||
@@ -52,7 +53,8 @@ enum Events
|
||||
EVENT_ERUPT_SECTION = 3,
|
||||
EVENT_SWITCH_PHASE = 4,
|
||||
EVENT_SAFETY_DANCE = 5,
|
||||
EVENT_PLAGUE_CLOUD = 6
|
||||
EVENT_PLAGUE_CLOUD = 6,
|
||||
EVENT_TELEPORT_PLAYER = 7
|
||||
};
|
||||
|
||||
enum Misc
|
||||
@@ -61,14 +63,38 @@ enum Misc
|
||||
PHASE_FAST_DANCE = 1
|
||||
};
|
||||
|
||||
const Position EyeStalkPositions[20] =
|
||||
{
|
||||
{ 2761.28f, -3765.37f, 275.08f, 1.24f },
|
||||
{ 2770.17f, -3782.11f, 275.08f, 1.33f },
|
||||
{ 2798.11f, -3788.94f, 275.08f, 2.35f },
|
||||
{ 2797.91f, -3776.86f, 275.08f, 2.25f },
|
||||
{ 2792.06f, -3762.52f, 275.08f, 2.9f, },
|
||||
{ 2789.87f, -3752.15f, 275.08f, 2.74f },
|
||||
{ 2804.21f, -3757.96f, 275.08f, 3.9f },
|
||||
{ 2821.16f, -3759.75f, 275.08f, 4.47f },
|
||||
{ 2834.64f, -3751.23f, 275.08f, 4.27f },
|
||||
{ 2843.54f, -3768.08f, 275.08f, 3.06f },
|
||||
{ 2862.4f, -3758.3f, 275.08f, 4.8f },
|
||||
{ 2877.8f, -3762.46f, 275.08f, 4.8f },
|
||||
{ 2894.11f, -3757.89f, 275.08f, 4.56f },
|
||||
{ 2895.25f, -3779.5f, 275.08f, 2.4f },
|
||||
{ 2881.59f, -3782.22f, 275.08f, 2.79f },
|
||||
{ 2867.2f, -3778.21f, 275.08f, 3.01f },
|
||||
{ 2851.39f, -3776.54f, 275.08f, 2.69f },
|
||||
{ 2846.16f, -3789.13f, 275.08f, 1.79f },
|
||||
{ 2830.09f, -3776.49f, 275.08f, 0.94f },
|
||||
{ 2813.34f, -3780.97f, 275.08f, 1.84f },
|
||||
};
|
||||
|
||||
class boss_heigan_40 : public CreatureScript
|
||||
{
|
||||
public:
|
||||
boss_heigan_40() : CreatureScript("boss_heigan_40") { }
|
||||
|
||||
CreatureAI* GetAI(Creature* pCreature) const override
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
{
|
||||
return GetNaxxramasAI<boss_heigan_40AI>(pCreature);
|
||||
return GetNaxxramasAI<boss_heigan_40AI>(creature);
|
||||
}
|
||||
|
||||
struct boss_heigan_40AI : public BossAI
|
||||
@@ -83,6 +109,7 @@ public:
|
||||
uint8 currentPhase{};
|
||||
uint8 currentSection{};
|
||||
bool moveRight{};
|
||||
GuidList portedPlayersThisPhase;
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
@@ -90,6 +117,8 @@ public:
|
||||
events.Reset();
|
||||
currentPhase = 0;
|
||||
currentSection = 3;
|
||||
portedPlayersThisPhase.clear();
|
||||
KillPlayersInTheTunnel();
|
||||
moveRight = true;
|
||||
if (pInstance)
|
||||
{
|
||||
@@ -97,6 +126,11 @@ public:
|
||||
{
|
||||
go->SetGoState(GO_STATE_ACTIVE);
|
||||
}
|
||||
// Close tunnel door
|
||||
if (GameObject* go = me->GetMap()->GetGameObject(pInstance->GetGuidData(DATA_HEIGAN_EXIT_GATE)))
|
||||
{
|
||||
go->SetGoState(GO_STATE_READY);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -129,6 +163,16 @@ public:
|
||||
{
|
||||
go->SetGoState(GO_STATE_READY);
|
||||
}
|
||||
// Open tunnel door
|
||||
if (GameObject* go = me->GetMap()->GetGameObject(pInstance->GetGuidData(DATA_HEIGAN_EXIT_GATE)))
|
||||
{
|
||||
go->SetGoState(GO_STATE_ACTIVE);
|
||||
}
|
||||
// Close loatheb door
|
||||
if (GameObject* go = me->GetMap()->GetGameObject(pInstance->GetGuidData(DATA_HEIGAN_EXIT_GATE_OLD)))
|
||||
{
|
||||
go->SetGoState(GO_STATE_READY);
|
||||
}
|
||||
}
|
||||
StartFightPhase(PHASE_SLOW_DANCE);
|
||||
}
|
||||
@@ -147,6 +191,8 @@ public:
|
||||
events.ScheduleEvent(EVENT_DECEPIT_FEVER, 17000);
|
||||
events.ScheduleEvent(EVENT_ERUPT_SECTION, 15000);
|
||||
events.ScheduleEvent(EVENT_SWITCH_PHASE, 90000);
|
||||
events.ScheduleEvent(EVENT_TELEPORT_PLAYER, 40000);
|
||||
portedPlayersThisPhase.clear();
|
||||
}
|
||||
else // if (phase == PHASE_FAST_DANCE)
|
||||
{
|
||||
@@ -176,6 +222,60 @@ public:
|
||||
return true;
|
||||
}
|
||||
|
||||
void KillPlayersInTheTunnel()
|
||||
{
|
||||
// hackfix: kill everyone in the tunnel
|
||||
Map::PlayerList const& PlayerList = me->GetMap()->GetPlayers();
|
||||
for (const auto& itr : PlayerList)
|
||||
{
|
||||
if (Player* player = itr.GetSource())
|
||||
{
|
||||
if (player->IsAlive() && !player->IsGameMaster())
|
||||
{
|
||||
if (player->GetPositionX() <= 2769.0f)
|
||||
{
|
||||
player->KillSelf();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void DoEventTeleportPlayer()
|
||||
{
|
||||
std::list<Unit*> candidates;
|
||||
SelectTargetList(candidates, 3, SelectTargetMethod::Random, 0, [&](Unit* target)
|
||||
{
|
||||
if (!target->IsPlayer()) // never target nonplayers (pets, guardians, etc.)
|
||||
return false;
|
||||
if (!target->IsAlive())
|
||||
return false;
|
||||
if (me->GetVictim() == target) // never target tank
|
||||
return false;
|
||||
// skip players who already have been teleported this phase
|
||||
if (std::find(portedPlayersThisPhase.begin(), portedPlayersThisPhase.end(), target->GetGUID()) != portedPlayersThisPhase.end())
|
||||
return false;
|
||||
return true;
|
||||
});
|
||||
|
||||
if (candidates.empty())
|
||||
return;
|
||||
|
||||
for (int i = 0; i < 3 ; i++)
|
||||
{
|
||||
if (candidates.empty())
|
||||
break;
|
||||
auto itr = candidates.begin();
|
||||
if (candidates.size() > 1)
|
||||
std::advance(itr, urand(0, candidates.size() - 1));
|
||||
Unit *target = *itr;
|
||||
candidates.erase(itr);
|
||||
portedPlayersThisPhase.push_back(target->GetGUID());
|
||||
DoModifyThreatByPercent(target, -99); // prevent heigan chasing and resetting
|
||||
target->CastSpell(target, SPELL_TELEPORT_PLAYERS, true);
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
if (!IsInRoom(me))
|
||||
@@ -184,12 +284,17 @@ public:
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
if (Unit* victim = me->GetVictim())
|
||||
{
|
||||
if (!me->IsWithinDistInMap(victim, VISIBILITY_DISTANCE_NORMAL))
|
||||
me->CastSpell(victim, SPELL_SUMMON_PLAYER, true);
|
||||
}
|
||||
events.Update(diff);
|
||||
|
||||
switch (events.ExecuteEvent())
|
||||
{
|
||||
case EVENT_DISRUPTION:
|
||||
me->CastSpell(me, SPELL_SPELL_DISRUPTION, false);
|
||||
me->CastCustomSpell(SPELL_DISRUPTION, SPELLVALUE_RADIUS_MOD, 2500, me, false); // 25yd
|
||||
events.RepeatEvent(10000);
|
||||
break;
|
||||
case EVENT_DECEPIT_FEVER:
|
||||
@@ -216,6 +321,11 @@ public:
|
||||
case EVENT_ERUPT_SECTION:
|
||||
if (pInstance)
|
||||
{
|
||||
if (currentPhase == PHASE_FAST_DANCE)
|
||||
{
|
||||
if (currentSection >= 1)
|
||||
KillPlayersInTheTunnel();
|
||||
}
|
||||
pInstance->SetData(DATA_HEIGAN_ERUPTION, currentSection);
|
||||
if (currentSection == 3)
|
||||
{
|
||||
@@ -248,85 +358,16 @@ public:
|
||||
events.RepeatEvent(5000);
|
||||
return;
|
||||
}
|
||||
case EVENT_TELEPORT_PLAYER:
|
||||
DoEventTeleportPlayer();
|
||||
break;
|
||||
}
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
class spell_heigan_plague_cloud_40 : public SpellScriptLoader
|
||||
{
|
||||
public:
|
||||
spell_heigan_plague_cloud_40() : SpellScriptLoader("spell_heigan_plague_cloud_40") { }
|
||||
|
||||
class spell_heigan_plague_cloud_40_AuraScript : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_heigan_plague_cloud_40_AuraScript);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
return ValidateSpellInfo({ SPELL_PLAGUE_CLOUD_TRIGGER });
|
||||
}
|
||||
|
||||
void HandleTriggerSpell(AuraEffect const* /*aurEff*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
PreventDefaultAction();
|
||||
int32 bp0 = 4000;
|
||||
caster->CastCustomSpell(caster, SPELL_PLAGUE_CLOUD_TRIGGER, &bp0, 0, 0, true);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_heigan_plague_cloud_40_AuraScript::HandleTriggerSpell, EFFECT_0, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_heigan_plague_cloud_40_AuraScript();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
class spell_heigan_eruption_40 : public SpellScriptLoader
|
||||
{
|
||||
public:
|
||||
spell_heigan_eruption_40() : SpellScriptLoader("spell_heigan_eruption_40") { }
|
||||
|
||||
class spell_heigan_eruption_40_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_heigan_eruption_40_SpellScript);
|
||||
|
||||
void HandleDamageCalc(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
SetEffectValue(urand(3500, 4500));
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_heigan_eruption_40_SpellScript::HandleDamageCalc, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_heigan_eruption_40_SpellScript();
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_heigan_40()
|
||||
{
|
||||
new boss_heigan_40();
|
||||
new spell_heigan_plague_cloud_40();
|
||||
new spell_heigan_eruption_40();
|
||||
}
|
||||
|
||||
@@ -662,14 +662,9 @@ public:
|
||||
};
|
||||
};
|
||||
|
||||
class spell_kelthuzad_frost_blast : public SpellScriptLoader
|
||||
class spell_kelthuzad_frost_blast : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_kelthuzad_frost_blast() : SpellScriptLoader("spell_kelthuzad_frost_blast") { }
|
||||
|
||||
class spell_kelthuzad_frost_blast_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_kelthuzad_frost_blast_SpellScript);
|
||||
PrepareSpellScript(spell_kelthuzad_frost_blast);
|
||||
|
||||
void FilterTargets(std::list<WorldObject*>& targets)
|
||||
{
|
||||
@@ -694,24 +689,13 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_kelthuzad_frost_blast_SpellScript::FilterTargets, EFFECT_ALL, TARGET_UNIT_DEST_AREA_ENEMY);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_kelthuzad_frost_blast_SpellScript();
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_kelthuzad_frost_blast::FilterTargets, EFFECT_ALL, TARGET_UNIT_DEST_AREA_ENEMY);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_kelthuzad_detonate_mana : public SpellScriptLoader
|
||||
class spell_kelthuzad_detonate_mana_aura : public AuraScript
|
||||
{
|
||||
public:
|
||||
spell_kelthuzad_detonate_mana() : SpellScriptLoader("spell_kelthuzad_detonate_mana") { }
|
||||
|
||||
class spell_kelthuzad_detonate_mana_AuraScript : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_kelthuzad_detonate_mana_AuraScript);
|
||||
PrepareAuraScript(spell_kelthuzad_detonate_mana_aura);
|
||||
|
||||
bool Validate(SpellInfo const* /*spell*/) override
|
||||
{
|
||||
@@ -731,34 +715,7 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_kelthuzad_detonate_mana_AuraScript::HandleScript, EFFECT_0, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_kelthuzad_detonate_mana_AuraScript();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
class spell_kelthuzad_dark_blast : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_kelthuzad_dark_blast);
|
||||
|
||||
void CalculateDamage(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
SetEffectValue(urand(1750,2250));
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_kelthuzad_dark_blast::CalculateDamage, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_kelthuzad_detonate_mana_aura::HandleScript, EFFECT_0, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -766,7 +723,6 @@ void AddSC_boss_kelthuzad_40()
|
||||
{
|
||||
new boss_kelthuzad_40();
|
||||
new boss_kelthuzad_minion_40();
|
||||
// new spell_kelthuzad_frost_blast();
|
||||
// new spell_kelthuzad_detonate_mana();
|
||||
RegisterSpellScript(spell_kelthuzad_dark_blast);
|
||||
// RegisterSpellScript(spell_kelthuzad_frost_blast);
|
||||
// RegisterSpellScript(spell_kelthuzad_detonate_mana_aura);
|
||||
}
|
||||
|
||||
@@ -15,20 +15,25 @@
|
||||
* with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "PassiveAI.h"
|
||||
#include "CreatureScript.h"
|
||||
#include "Player.h"
|
||||
#include "ScriptMgr.h"
|
||||
#include "PassiveAI.h"
|
||||
#include "ScriptedCreature.h"
|
||||
#include "SpellAuras.h"
|
||||
#include "SpellAuraEffects.h"
|
||||
#include "SpellScript.h"
|
||||
#include "SpellScriptLoader.h"
|
||||
#include "naxxramas.h"
|
||||
|
||||
enum Spells
|
||||
{
|
||||
SPELL_WEB_WRAP = 28622,
|
||||
SPELL_WEB_SPRAY = 29484,
|
||||
SPELL_POISON_SHOCK = 28741,
|
||||
SPELL_NECROTIC_POISON = 54121,
|
||||
SPELL_FRENZY = 54123,
|
||||
SPELL_WEB_WRAP_STUN = 28622,
|
||||
SPELL_WEB_WRAP_SUMMON = 28627,
|
||||
SPELL_WEB_WRAP_SUMMON_40 = 90007, // custom summon entry: 16486 -> 351075
|
||||
SPELL_WEB_WRAP_PACIFY_5 = 28618
|
||||
};
|
||||
|
||||
enum Events
|
||||
@@ -38,9 +43,9 @@ enum Events
|
||||
EVENT_NECROTIC_POISON = 3,
|
||||
EVENT_WEB_WRAP = 4,
|
||||
EVENT_HEALTH_CHECK = 5,
|
||||
EVENT_SUMMON_SPIDERLINGS = 6
|
||||
EVENT_SUMMON_SPIDERLINGS = 6,
|
||||
EVENT_WEB_WRAP_APPLY_STUN = 7
|
||||
};
|
||||
|
||||
enum Emotes
|
||||
{
|
||||
EMOTE_SPIDERS = 0,
|
||||
@@ -54,11 +59,33 @@ enum Misc
|
||||
NPC_MAEXXNA_SPIDERLING = 351088
|
||||
};
|
||||
|
||||
const Position PosWrap[3] =
|
||||
const Position PosWrap[7] =
|
||||
{
|
||||
{3546.796f, -3869.082f, 296.450f, 0.0f},
|
||||
{3531.271f, -3847.424f, 299.450f, 0.0f},
|
||||
{3497.067f, -3843.384f, 302.384f, 0.0f}
|
||||
{3496.615f, -3834.182f, 320.7863f},
|
||||
{3509.108f, -3833.922f, 320.4750f},
|
||||
{3523.644f, -3838.309f, 320.5775f},
|
||||
{3538.152f, -3846.353f, 320.5188f},
|
||||
{3546.219f, -3856.167f, 320.9324f},
|
||||
{3555.135f, -3869.507f, 320.8307f},
|
||||
{3560.282f, -3886.143f, 321.2827f}
|
||||
};
|
||||
|
||||
struct WebTargetSelector
|
||||
{
|
||||
WebTargetSelector(Unit* maexxna) : _maexxna(maexxna) {}
|
||||
bool operator()(Unit const* target) const
|
||||
{
|
||||
if (!target->IsPlayer()) // never web nonplayers (pets, guardians, etc.)
|
||||
return false;
|
||||
if (_maexxna->GetVictim() == target) // never target tank
|
||||
return false;
|
||||
if (target->HasAura(SPELL_WEB_WRAP_STUN)) // never target targets that are already webbed
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
private:
|
||||
Unit const* _maexxna;
|
||||
};
|
||||
|
||||
class boss_maexxna_40 : public CreatureScript
|
||||
@@ -81,6 +108,7 @@ public:
|
||||
InstanceScript* pInstance;
|
||||
EventMap events;
|
||||
SummonList summons;
|
||||
GuidList wraps;
|
||||
|
||||
bool IsInRoom()
|
||||
{
|
||||
@@ -110,12 +138,12 @@ public:
|
||||
{
|
||||
BossAI::JustEngagedWith(who);
|
||||
me->SetInCombatWithZone();
|
||||
events.ScheduleEvent(EVENT_WEB_WRAP, 20000);
|
||||
events.ScheduleEvent(EVENT_WEB_SPRAY, 40000);
|
||||
events.ScheduleEvent(EVENT_POISON_SHOCK, 10000);
|
||||
events.ScheduleEvent(EVENT_NECROTIC_POISON, 5000);
|
||||
events.ScheduleEvent(EVENT_HEALTH_CHECK, 1000);
|
||||
events.ScheduleEvent(EVENT_SUMMON_SPIDERLINGS, 30000);
|
||||
events.ScheduleEvent(EVENT_WEB_WRAP, 20s);
|
||||
events.ScheduleEvent(EVENT_WEB_SPRAY, 40s);
|
||||
events.ScheduleEvent(EVENT_POISON_SHOCK, 10s);
|
||||
events.ScheduleEvent(EVENT_NECROTIC_POISON, 5s);
|
||||
events.ScheduleEvent(EVENT_HEALTH_CHECK, 1s);
|
||||
events.ScheduleEvent(EVENT_SUMMON_SPIDERLINGS, 30s);
|
||||
if (pInstance)
|
||||
{
|
||||
if (GameObject* go = me->GetMap()->GetGameObject(pInstance->GetGuidData(DATA_MAEXXNA_GATE)))
|
||||
@@ -149,7 +177,55 @@ public:
|
||||
void JustDied(Unit* killer) override
|
||||
{
|
||||
BossAI::JustDied(killer);
|
||||
summons.DespawnAll();
|
||||
}
|
||||
|
||||
void DoCastWebWrap()
|
||||
{
|
||||
std::list<Unit*> candidates;
|
||||
SelectTargetList(candidates, 2, SelectTargetMethod::Random, 0, WebTargetSelector(me));
|
||||
|
||||
std::vector<uint32> positions {0, 1, 2, 3, 4, 5, 6};
|
||||
Acore::Containers::RandomShuffle(positions);
|
||||
|
||||
if (candidates.empty())
|
||||
return;
|
||||
|
||||
for (int i = 0; i < 2 ; i++)
|
||||
{
|
||||
if (candidates.empty())
|
||||
break;
|
||||
const Position &randomPos = PosWrap[positions[i]];
|
||||
|
||||
auto itr = candidates.begin();
|
||||
|
||||
if (candidates.size() > 1)
|
||||
std::advance(itr, urand(0, candidates.size() - 1));
|
||||
|
||||
Unit *target = *itr;
|
||||
candidates.erase(itr);
|
||||
|
||||
float dx = randomPos.GetPositionX() - target->GetPositionX();
|
||||
float dy = randomPos.GetPositionY() - target->GetPositionY();
|
||||
float distXY = std::hypotf(dx, dy);
|
||||
|
||||
// smooth knockback arc that avoids the ceiling
|
||||
float horizontalSpeed = distXY / 1.5f;
|
||||
float verticalSpeed = 28.0f;
|
||||
if (distXY <= 10.0f)
|
||||
verticalSpeed = 12.0f;
|
||||
else if (distXY <= 20.0f)
|
||||
verticalSpeed = 16.0f;
|
||||
else if (distXY <= 30.0f)
|
||||
verticalSpeed = 20.0f;
|
||||
else if (distXY <= 40.0f)
|
||||
verticalSpeed = 24.0f;
|
||||
|
||||
target->KnockbackFrom(randomPos.GetPositionX(), randomPos.GetPositionY(), -horizontalSpeed, verticalSpeed);
|
||||
me->CastSpell(target, SPELL_WEB_WRAP_PACIFY_5, true); // pacify silence for 5 seconds
|
||||
|
||||
wraps.push_back(target->GetGUID());
|
||||
}
|
||||
events.ScheduleEvent(EVENT_WEB_WRAP_APPLY_STUN, 2s);
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
@@ -200,59 +276,48 @@ public:
|
||||
break;
|
||||
case EVENT_WEB_WRAP:
|
||||
Talk(EMOTE_WEB_WRAP);
|
||||
for (uint8 i = 0; i < 2; ++i)
|
||||
{
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 1, 0, true, true, -SPELL_WEB_WRAP))
|
||||
{
|
||||
target->RemoveAura(SPELL_WEB_SPRAY);
|
||||
uint8 pos = urand(0, 2);
|
||||
if (Creature* wrap = me->SummonCreature(NPC_WEB_WRAP, PosWrap[pos].GetPositionX(), PosWrap[pos].GetPositionY(), PosWrap[pos].GetPositionZ(), 0.0f, TEMPSUMMON_TIMED_DESPAWN, 60000))
|
||||
{
|
||||
wrap->AI()->SetGUID(target->GetGUID());
|
||||
target->GetMotionMaster()->MoveJump(PosWrap[pos].GetPositionX(), PosWrap[pos].GetPositionY(), PosWrap[pos].GetPositionZ(), 20, 20);
|
||||
}
|
||||
}
|
||||
}
|
||||
DoCastWebWrap();
|
||||
events.Repeat(40s);
|
||||
break;
|
||||
case EVENT_WEB_WRAP_APPLY_STUN:
|
||||
{
|
||||
for (auto& p : wraps)
|
||||
{
|
||||
if (Player* player = ObjectAccessor::GetPlayer(*me, p))
|
||||
{
|
||||
player->CastSpell(player, SPELL_WEB_WRAP_STUN, true);
|
||||
}
|
||||
}
|
||||
wraps.clear();
|
||||
break;
|
||||
}
|
||||
}
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
class boss_maexxna_webwrap40 : public CreatureScript
|
||||
class boss_maexxna_webwrap_40 : public CreatureScript
|
||||
{
|
||||
public:
|
||||
boss_maexxna_webwrap40() : CreatureScript("boss_maexxna_webwrap40") { }
|
||||
boss_maexxna_webwrap_40() : CreatureScript("boss_maexxna_webwrap40") { }
|
||||
|
||||
CreatureAI* GetAI(Creature* pCreature) const override
|
||||
{
|
||||
return GetNaxxramasAI<boss_maexxna_webwrap40AI>(pCreature);
|
||||
return GetNaxxramasAI<boss_maexxna_webwrap_40AI>(pCreature);
|
||||
}
|
||||
|
||||
struct boss_maexxna_webwrap40AI : public NullCreatureAI
|
||||
struct boss_maexxna_webwrap_40AI : public NullCreatureAI
|
||||
{
|
||||
explicit boss_maexxna_webwrap40AI(Creature* c) : NullCreatureAI(c) {}
|
||||
explicit boss_maexxna_webwrap_40AI(Creature* c) : NullCreatureAI(c) { }
|
||||
|
||||
ObjectGuid victimGUID;
|
||||
|
||||
void SetGUID(ObjectGuid guid, int32 /*param*/) override
|
||||
void IsSummonedBy(WorldObject* summoner) override
|
||||
{
|
||||
victimGUID = guid;
|
||||
|
||||
if (victimGUID)
|
||||
{
|
||||
if (Unit* victim = ObjectAccessor::GetUnit(*me, victimGUID))
|
||||
{
|
||||
if (victim->GetTypeId() == TYPEID_PLAYER && victim->GetEntry() != NPC_WEB_WRAP)
|
||||
{
|
||||
int32 bp1 = 242;
|
||||
victim->CastCustomSpell(victim, SPELL_WEB_WRAP, 0, &bp1, 0, true, nullptr, nullptr, me->GetGUID());
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!summoner)
|
||||
return;
|
||||
victimGUID = summoner->GetGUID();
|
||||
}
|
||||
|
||||
void JustDied(Unit* /*killer*/) override
|
||||
@@ -261,15 +326,55 @@ public:
|
||||
{
|
||||
if (Unit* victim = ObjectAccessor::GetUnit(*me, victimGUID))
|
||||
{
|
||||
victim->RemoveAurasDueToSpell(SPELL_WEB_WRAP, me->GetGUID());
|
||||
victim->RemoveAurasDueToSpell(SPELL_WEB_WRAP_SUMMON);
|
||||
victim->RemoveAurasDueToSpell(SPELL_WEB_WRAP_STUN);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 /*diff*/) override
|
||||
{
|
||||
if (victimGUID)
|
||||
{
|
||||
if (Unit* victim = ObjectAccessor::GetUnit(*me, victimGUID))
|
||||
{
|
||||
if (!victim->IsAlive())
|
||||
{
|
||||
me->KillSelf();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
class spell_web_wrap_damage : public AuraScript
|
||||
{
|
||||
public:
|
||||
PrepareAuraScript(spell_web_wrap_damage);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
return ValidateSpellInfo({ SPELL_WEB_WRAP_SUMMON });
|
||||
}
|
||||
|
||||
void OnPeriodic(AuraEffect const* aurEff)
|
||||
{
|
||||
if (aurEff->GetTickNumber() == 2)
|
||||
{
|
||||
GetTarget()->CastSpell(GetTarget(), SPELL_WEB_WRAP_SUMMON, true);
|
||||
}
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_web_wrap_damage::OnPeriodic, EFFECT_1, SPELL_AURA_PERIODIC_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_maexxna_40()
|
||||
{
|
||||
new boss_maexxna_40();
|
||||
new boss_maexxna_webwrap40();
|
||||
new boss_maexxna_webwrap_40();
|
||||
RegisterSpellScript(spell_web_wrap_damage);
|
||||
}
|
||||
|
||||
@@ -300,51 +300,7 @@ public:
|
||||
};
|
||||
};
|
||||
|
||||
class spell_gothik_curse_of_the_plaguebringer_40 : public SpellScriptLoader
|
||||
{
|
||||
public:
|
||||
spell_gothik_curse_of_the_plaguebringer_40() : SpellScriptLoader("spell_gothik_curse_of_the_plaguebringer_40") { }
|
||||
|
||||
class spell_gothik_curse_of_the_plaguebringer_40_AuraScript : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_gothik_curse_of_the_plaguebringer_40_AuraScript);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
return ValidateSpellInfo({ SPELL_REVENGE_OF_THE_PLAGUEBRINGER }); // Revenge of the Plaguebringer
|
||||
}
|
||||
|
||||
void HandleTriggerSpell(AuraEffect const* /*aurEff*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
PreventDefaultAction();
|
||||
CustomSpellValues values;
|
||||
int32 bp0 = 1757; // instant damage
|
||||
int32 bp1 = 874; // periodic damage
|
||||
values.AddSpellMod(SPELLVALUE_BASE_POINT0, bp0);
|
||||
values.AddSpellMod(SPELLVALUE_BASE_POINT1, bp1);
|
||||
values.AddSpellMod(SPELLVALUE_RADIUS_MOD, 3500); // 35yd
|
||||
GetTarget()->CastCustomSpell(SPELL_REVENGE_OF_THE_PLAGUEBRINGER, values, GetTarget(), TRIGGERED_NONE, nullptr, nullptr, GetCasterGUID());
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_gothik_curse_of_the_plaguebringer_40_AuraScript::HandleTriggerSpell, EFFECT_0, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
AuraScript* GetAuraScript() const override
|
||||
{
|
||||
return new spell_gothik_curse_of_the_plaguebringer_40_AuraScript();
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_noth_40()
|
||||
{
|
||||
new boss_noth_40();
|
||||
new spell_gothik_curse_of_the_plaguebringer_40();
|
||||
}
|
||||
|
||||
@@ -17,6 +17,8 @@
|
||||
|
||||
#include "ScriptMgr.h"
|
||||
#include "ScriptedCreature.h"
|
||||
#include "SpellScript.h"
|
||||
#include "SpellScriptLoader.h"
|
||||
#include "naxxramas.h"
|
||||
|
||||
enum Says
|
||||
@@ -73,14 +75,13 @@ public:
|
||||
|
||||
void SpawnHelpers()
|
||||
{
|
||||
// 10man
|
||||
me->SummonCreature(NPC_DEATH_KNIGHT_UNDERSTUDY, 2762.23f, -3085.07f, 267.685f, 1.95f);
|
||||
me->SummonCreature(NPC_DEATH_KNIGHT_UNDERSTUDY, 2758.24f, -3110.97f, 267.685f, 3.94f);
|
||||
if (Is25ManRaid())
|
||||
{
|
||||
// 25man
|
||||
me->SummonCreature(NPC_DEATH_KNIGHT_UNDERSTUDY, 2782.45f, -3088.03f, 267.685f, 0.75f);
|
||||
me->SummonCreature(NPC_DEATH_KNIGHT_UNDERSTUDY, 2778.56f, -3113.74f, 267.685f, 5.28f);
|
||||
}
|
||||
}
|
||||
|
||||
void JustSummoned(Creature* cr) override
|
||||
{
|
||||
@@ -136,7 +137,8 @@ public:
|
||||
BossAI::JustEngagedWith(who);
|
||||
Talk(SAY_AGGRO);
|
||||
events.ScheduleEvent(EVENT_UNBALANCING_STRIKE, 20000); // TODO: This can be 30 seconds to match vanilla
|
||||
events.ScheduleEvent(EVENT_DISRUPTING_SHOUT, 15000);
|
||||
events.ScheduleEvent(EVENT_DISRUPTING_SHOUT, 5s);
|
||||
// events.ScheduleEvent(EVENT_DISRUPTING_SHOUT, 15s);
|
||||
//events.ScheduleEvent(EVENT_JAGGED_KNIFE, 10000); // New wrath mechanic
|
||||
summons.DoZoneInCombat();
|
||||
}
|
||||
@@ -157,17 +159,9 @@ public:
|
||||
events.RepeatEvent(20000);
|
||||
break;
|
||||
case EVENT_DISRUPTING_SHOUT:
|
||||
{
|
||||
// TODO: Custom patch needed to implement power burn, or remove visual effect
|
||||
// 45yd that ignores line of sight
|
||||
CustomSpellValues values;
|
||||
int32 customDisruptingShoutDamage = 2200; // some value as we ignore LoS without patch
|
||||
values.AddSpellMod(SPELLVALUE_BASE_POINT0, customDisruptingShoutDamage);
|
||||
values.AddSpellMod(SPELLVALUE_RADIUS_MOD, 4500); // 45yd
|
||||
me->CastCustomSpell(SPELL_DISRUPTING_SHOUT, values, me, TRIGGERED_NONE, nullptr, nullptr, ObjectGuid::Empty);
|
||||
events.RepeatEvent(15000);
|
||||
me->CastSpell(me, SPELL_DISRUPTING_SHOUT, false);
|
||||
events.RepeatEvent(10000);
|
||||
break;
|
||||
}
|
||||
case EVENT_JAGGED_KNIFE:
|
||||
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0, 45.0f))
|
||||
{
|
||||
|
||||
@@ -469,14 +469,9 @@ public:
|
||||
};
|
||||
|
||||
// This will overwrite the declared 10 and 25 man frost explosion to handle all versions of the spell script
|
||||
class spell_sapphiron_frost_explosion_40 : public SpellScriptLoader
|
||||
class spell_sapphiron_frost_explosion : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_sapphiron_frost_explosion_40() : SpellScriptLoader("spell_sapphiron_frost_explosion") { }
|
||||
|
||||
class spell_sapphiron_frost_explosion_40_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_sapphiron_frost_explosion_40_SpellScript);
|
||||
PrepareSpellScript(spell_sapphiron_frost_explosion);
|
||||
|
||||
void FilterTargets(std::list<WorldObject*>& targets)
|
||||
{
|
||||
@@ -501,18 +496,12 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_sapphiron_frost_explosion_40_SpellScript::FilterTargets, EFFECT_0, TARGET_UNIT_DEST_AREA_ENEMY);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_sapphiron_frost_explosion_40_SpellScript();
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_sapphiron_frost_explosion::FilterTargets, EFFECT_0, TARGET_UNIT_DEST_AREA_ENEMY);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_sapphiron_40()
|
||||
{
|
||||
new boss_sapphiron_40();
|
||||
new spell_sapphiron_frost_explosion_40();
|
||||
RegisterSpellScript(spell_sapphiron_frost_explosion);
|
||||
}
|
||||
|
||||
@@ -610,14 +610,9 @@ public:
|
||||
};
|
||||
|
||||
// This will overwrite the declared 10 and 25 man pos_neg_charge to handle all versions of the spell script
|
||||
class spell_thaddius_pos_neg_charge_40 : public SpellScriptLoader
|
||||
class spell_thaddius_pos_neg_charge : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_thaddius_pos_neg_charge_40() : SpellScriptLoader("spell_thaddius_pos_neg_charge") { }
|
||||
|
||||
class spell_thaddius_pos_neg_charge_40_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_thaddius_pos_neg_charge_40_SpellScript);
|
||||
PrepareSpellScript(spell_thaddius_pos_neg_charge);
|
||||
|
||||
void HandleTargets(std::list<WorldObject*>& targets)
|
||||
{
|
||||
@@ -669,25 +664,14 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectHitTarget += SpellEffectFn(spell_thaddius_pos_neg_charge_40_SpellScript::HandleDamage, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_thaddius_pos_neg_charge_40_SpellScript::HandleTargets, EFFECT_0, TARGET_UNIT_SRC_AREA_ALLY);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_thaddius_pos_neg_charge_40_SpellScript();
|
||||
OnEffectHitTarget += SpellEffectFn(spell_thaddius_pos_neg_charge::HandleDamage, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_thaddius_pos_neg_charge::HandleTargets, EFFECT_0, TARGET_UNIT_SRC_AREA_ALLY);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_thaddius_polarity_shift : public SpellScriptLoader
|
||||
class spell_thaddius_polarity_shift : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_thaddius_polarity_shift() : SpellScriptLoader("spell_thaddius_polarity_shift") { }
|
||||
|
||||
class spell_thaddius_polarity_shift_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_thaddius_polarity_shift_SpellScript);
|
||||
PrepareSpellScript(spell_thaddius_polarity_shift);
|
||||
|
||||
bool Validate(SpellInfo const* /*spell*/) override
|
||||
{
|
||||
@@ -722,14 +706,8 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectHitTarget += SpellEffectFn(spell_thaddius_polarity_shift_SpellScript::HandleDummy, EFFECT_0, SPELL_EFFECT_DUMMY);
|
||||
AfterCast += SpellCastFn(spell_thaddius_polarity_shift_SpellScript::HandleAfterCast);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_thaddius_polarity_shift_SpellScript();
|
||||
OnEffectHitTarget += SpellEffectFn(spell_thaddius_polarity_shift::HandleDummy, EFFECT_0, SPELL_EFFECT_DUMMY);
|
||||
AfterCast += SpellCastFn(spell_thaddius_polarity_shift::HandleAfterCast);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -775,14 +753,9 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
class spell_feugen_static_field_40 : public SpellScriptLoader
|
||||
class spell_feugen_static_field : public SpellScript
|
||||
{
|
||||
public:
|
||||
spell_feugen_static_field_40() : SpellScriptLoader("spell_feugen_static_field") { }
|
||||
|
||||
class spell_feugen_static_field_40_SpellScript : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_feugen_static_field_40_SpellScript);
|
||||
PrepareSpellScript(spell_feugen_static_field);
|
||||
|
||||
void HandleDamageCalc(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
@@ -801,13 +774,7 @@ public:
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_feugen_static_field_40_SpellScript::HandleDamageCalc, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
SpellScript* GetSpellScript() const override
|
||||
{
|
||||
return new spell_feugen_static_field_40_SpellScript();
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_feugen_static_field::HandleDamageCalc, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -816,8 +783,8 @@ void AddSC_boss_thaddius_40()
|
||||
new boss_thaddius_40();
|
||||
new boss_thaddius_summon_40();
|
||||
// new npc_tesla();
|
||||
new spell_thaddius_pos_neg_charge_40();
|
||||
// new spell_thaddius_polarity_shift();
|
||||
RegisterSpellScript(spell_thaddius_pos_neg_charge);
|
||||
// RegisterSpellScript(spell_thaddius_polarity_shift);
|
||||
// new at_thaddius_entrance();
|
||||
new spell_feugen_static_field_40();
|
||||
RegisterSpellScript(spell_feugen_static_field);
|
||||
}
|
||||
|
||||
175
src/naxx40Scripts/custom_creatures_40.cpp
Normal file
175
src/naxx40Scripts/custom_creatures_40.cpp
Normal file
@@ -0,0 +1,175 @@
|
||||
|
||||
#include "ScriptMgr.h"
|
||||
#include "ScriptedCreature.h"
|
||||
#include "SpellAuraEffects.h"
|
||||
#include "SpellScript.h"
|
||||
#include "Player.h"
|
||||
#include "naxxramas.h"
|
||||
|
||||
class npc_naxx40_area_trigger : public CreatureScript
|
||||
{
|
||||
private:
|
||||
static bool isAttuned(Player* player)
|
||||
{
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_1) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_2) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_3) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
public:
|
||||
npc_naxx40_area_trigger() : CreatureScript("npc_naxx40_area_trigger") {}
|
||||
|
||||
struct npc_naxx40_area_triggerAI: public ScriptedAI
|
||||
{
|
||||
npc_naxx40_area_triggerAI(Creature* creature) : ScriptedAI(creature)
|
||||
{
|
||||
me->SetDisplayId(11686); // Invisible
|
||||
}
|
||||
|
||||
void MoveInLineOfSight(Unit* who) override
|
||||
{
|
||||
if (who && me->GetDistance2d(who) < 5.0f)
|
||||
{
|
||||
if (Player* player = who->ToPlayer())
|
||||
{
|
||||
if (isAttuned(player))
|
||||
{
|
||||
player->SetRaidDifficulty(RAID_DIFFICULTY_10MAN_HEROIC);
|
||||
player->TeleportTo(533, 3005.51f, -3434.64f, 304.195f, 6.2831f);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
else if (who && me->GetDistance2d(who) < 20.0f)
|
||||
{
|
||||
if (Player* player = who->ToPlayer())
|
||||
{
|
||||
if (isAttuned(player))
|
||||
{
|
||||
GameObject* door = me->FindNearestGameObject(NAXX_STRATH_GATE, 100.0f);
|
||||
if (door)
|
||||
{
|
||||
door->SetGoState(GO_STATE_ACTIVE);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
{
|
||||
return new npc_naxx40_area_triggerAI(creature);
|
||||
}
|
||||
};
|
||||
|
||||
class boss_heigan_eye_stalk_40 : public CreatureScript
|
||||
{
|
||||
public:
|
||||
boss_heigan_eye_stalk_40() : CreatureScript("boss_heigan_eye_stalk_40") { }
|
||||
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
{
|
||||
return GetNaxxramasAI<boss_heigan_eye_stalk_40AI>(creature);
|
||||
}
|
||||
|
||||
struct boss_heigan_eye_stalk_40AI : public ScriptedAI
|
||||
{
|
||||
explicit boss_heigan_eye_stalk_40AI(Creature* creature) : ScriptedAI(creature)
|
||||
{
|
||||
timeSinceSpawn = 0;
|
||||
haveSubmerged = false;
|
||||
haveCastSubmerge = false;
|
||||
}
|
||||
|
||||
uint32 timeSinceSpawn;
|
||||
bool haveSubmerged;
|
||||
bool haveCastSubmerge;
|
||||
const uint32 SPELL_MIND_FLAY = 29407;
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
me->SetNoCallAssistance(true);
|
||||
me->SetUnitFlag(UNIT_FLAG_DISABLE_MOVE);
|
||||
}
|
||||
|
||||
void KilledUnit(Unit* who) override
|
||||
{
|
||||
if (who->GetTypeId() == TYPEID_PLAYER && me->GetInstanceScript())
|
||||
{
|
||||
me->GetInstanceScript()->SetData(DATA_IMMORTAL_FAIL, 0);
|
||||
}
|
||||
}
|
||||
|
||||
void MoveInLineOfSight(Unit* who) override
|
||||
{
|
||||
if (timeSinceSpawn < 3000)
|
||||
return;
|
||||
|
||||
if (!who || !(who->GetDistance2d(me) <= 19.0f))
|
||||
return;
|
||||
|
||||
if (me->HasReactState(REACT_AGGRESSIVE) && me->CanStartAttack(who))
|
||||
{
|
||||
if (!me->IsWithinLOSInMap(who))
|
||||
{
|
||||
return;
|
||||
}
|
||||
me->SetNoCallAssistance(true);
|
||||
if (!me->GetVictim())
|
||||
{
|
||||
AttackStart(who);
|
||||
}
|
||||
else if (me->GetMap()->IsDungeon())
|
||||
{
|
||||
who->SetInCombatWith(me);
|
||||
me->AddThreat(who, 0.0f);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
me->SetNoCallAssistance(true);
|
||||
timeSinceSpawn += std::min(diff, std::numeric_limits<uint32>::max() - timeSinceSpawn);
|
||||
|
||||
if (haveSubmerged)
|
||||
{
|
||||
if (!haveCastSubmerge)
|
||||
{
|
||||
haveCastSubmerge = true;
|
||||
me->CastSpell(me, 26234, false);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
if (!me->IsNonMeleeSpellCast(false))
|
||||
{
|
||||
if (me->GetDistance(me->GetVictim()) < 35.0f)
|
||||
{
|
||||
int32 bp0 = 750; // damage
|
||||
int32 bp1 = -20; // movement speed
|
||||
me->CastCustomSpell(me->GetVictim(), SPELL_MIND_FLAY, &bp0, &bp1, 0, false, nullptr, nullptr, ObjectGuid::Empty);
|
||||
}
|
||||
else
|
||||
{
|
||||
DoStopAttack();
|
||||
}
|
||||
}
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
void AddSC_custom_creatures_40()
|
||||
{
|
||||
new npc_naxx40_area_trigger();
|
||||
new boss_heigan_eye_stalk_40();
|
||||
}
|
||||
52
src/naxx40Scripts/custom_gameobjects_40.cpp
Normal file
52
src/naxx40Scripts/custom_gameobjects_40.cpp
Normal file
@@ -0,0 +1,52 @@
|
||||
|
||||
#include "ScriptMgr.h"
|
||||
#include "ScriptedCreature.h"
|
||||
#include "SpellAuraEffects.h"
|
||||
#include "SpellScript.h"
|
||||
#include "naxxramas.h"
|
||||
#include "IndividualProgression.h"
|
||||
|
||||
class gobject_naxx40_tele : public GameObjectScript
|
||||
{
|
||||
private:
|
||||
static bool isAttuned(Player* player)
|
||||
{
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_1) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_2) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_3) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
public:
|
||||
gobject_naxx40_tele() : GameObjectScript("gobject_naxx40_tele") { }
|
||||
|
||||
struct gobject_naxx40_teleAI: GameObjectAI
|
||||
{
|
||||
explicit gobject_naxx40_teleAI(GameObject* object) : GameObjectAI(object) { };
|
||||
|
||||
};
|
||||
|
||||
GameObjectAI* GetAI(GameObject* object) const override
|
||||
{
|
||||
return new gobject_naxx40_teleAI(object);
|
||||
}
|
||||
|
||||
bool OnGossipHello(Player* player, GameObject* /*go*/) override
|
||||
{
|
||||
if ((!sIndividualProgression->requireNaxxStrath || player->GetQuestStatus(NAXX40_ENTRANCE_FLAG) == QUEST_STATUS_REWARDED) && isAttuned(player))
|
||||
{
|
||||
player->SetRaidDifficulty(RAID_DIFFICULTY_10MAN_HEROIC);
|
||||
player->TeleportTo(533, 3005.51f, -3434.64f, 304.195f, 6.2831f);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
void AddSC_custom_gameobjects_40()
|
||||
{
|
||||
new gobject_naxx40_tele();
|
||||
}
|
||||
347
src/naxx40Scripts/custom_spells_40.cpp
Normal file
347
src/naxx40Scripts/custom_spells_40.cpp
Normal file
@@ -0,0 +1,347 @@
|
||||
|
||||
#include "ScriptMgr.h"
|
||||
#include "ScriptedCreature.h"
|
||||
#include "SpellAuraEffects.h"
|
||||
#include "SpellScript.h"
|
||||
#include "naxxramas.h"
|
||||
|
||||
// 28785 - Locust Swarm
|
||||
// Locust Swarm: Reduce damage ~1500 to ~1000, increase radius 25yd to 30yd
|
||||
enum LocustSwarm
|
||||
{
|
||||
SPELL_LOCUST_SWARM = 28785,
|
||||
SPELL_LOCUST_SWARM_TRIGGER = 28786, // periodic effect
|
||||
};
|
||||
|
||||
class spell_anub_locust_swarm_aura_40 : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_anub_locust_swarm_aura_40);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
return ValidateSpellInfo({ SPELL_LOCUST_SWARM_TRIGGER });
|
||||
}
|
||||
|
||||
void HandleTriggerSpell(AuraEffect const* /*aurEff*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
PreventDefaultAction();
|
||||
int32 modifiedLocustSwarmDamage = 812;
|
||||
CustomSpellValues values;
|
||||
values.AddSpellMod(SPELLVALUE_BASE_POINT0, modifiedLocustSwarmDamage);
|
||||
values.AddSpellMod(SPELLVALUE_RADIUS_MOD, 3000); // 30yd
|
||||
caster->CastCustomSpell(SPELL_LOCUST_SWARM_TRIGGER, values, caster, TRIGGERED_FULL_MASK, nullptr, nullptr, GetCasterGUID());
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_anub_locust_swarm_aura_40::HandleTriggerSpell, EFFECT_0, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
// 28865 - Consumption
|
||||
// add Naxx10HC damage
|
||||
class spell_gen_consumption : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_gen_consumption);
|
||||
|
||||
void CalculateDamage(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Map* map = GetCaster()->GetMap();
|
||||
if (!map)
|
||||
{
|
||||
return;
|
||||
}
|
||||
int32 value = 0;
|
||||
if (map->GetDifficulty() == RAID_DIFFICULTY_25MAN_NORMAL) // NAXX25 N
|
||||
{
|
||||
value = urand(4500, 4700);
|
||||
}
|
||||
else if (map->GetId() == 533) // NAXX10 N
|
||||
{
|
||||
if (map->GetDifficulty() == RAID_DIFFICULTY_10MAN_NORMAL)
|
||||
{
|
||||
value = urand(3000, 3200);
|
||||
}
|
||||
else
|
||||
{
|
||||
value = urand(3960, 4840); // NAXX40
|
||||
}
|
||||
}
|
||||
else if (map->GetId() == 532) // Karazhan
|
||||
{
|
||||
value = urand(1110, 1310);
|
||||
}
|
||||
if (value)
|
||||
{
|
||||
SetEffectValue(value);
|
||||
}
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_gen_consumption::CalculateDamage, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
// 28241 - Poison Cloud
|
||||
// poison damage by Poison Cloud ~3k to ~1k
|
||||
class spell_grobbulus_poison_cloud_poison_damage_40 : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_grobbulus_poison_cloud_poison_damage_40);
|
||||
|
||||
void HandleDamageCalc(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
SetEffectValue(urand(1110, 1290));
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_grobbulus_poison_cloud_poison_damage_40::HandleDamageCalc, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
// 29350 - Plague Cloud
|
||||
enum PlagueCloud
|
||||
{
|
||||
SPELL_PLAGUE_CLOUD_TRIGGER = 30122,
|
||||
};
|
||||
|
||||
class spell_heigan_plague_cloud_aura_40 : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_heigan_plague_cloud_aura_40);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
return ValidateSpellInfo({ SPELL_PLAGUE_CLOUD_TRIGGER });
|
||||
}
|
||||
|
||||
void HandleTriggerSpell(AuraEffect const* /*aurEff*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
PreventDefaultAction();
|
||||
int32 bp0 = 4000;
|
||||
caster->CastCustomSpell(caster, SPELL_PLAGUE_CLOUD_TRIGGER, &bp0, 0, 0, true);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_heigan_plague_cloud_aura_40::HandleTriggerSpell, EFFECT_0, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
// 29371 - Eruption
|
||||
class spell_heigan_eruption_40 : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_heigan_eruption_40);
|
||||
|
||||
void HandleDamageCalc(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
SetEffectValue(urand(3500, 4500));
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_heigan_eruption_40::HandleDamageCalc, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
// 28819 - Submerge Visual
|
||||
class spell_submerge_visual_aura : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_submerge_visual_aura);
|
||||
|
||||
void OnApply(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
GetTarget()->SetStandState(UNIT_STAND_STATE_SUBMERGED);
|
||||
}
|
||||
|
||||
void OnRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
|
||||
{
|
||||
GetTarget()->SetStandState(UNIT_STAND_STATE_STAND);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectApply += AuraEffectApplyFn(spell_submerge_visual_aura::OnApply, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
OnEffectRemove += AuraEffectRemoveFn(spell_submerge_visual_aura::OnRemove, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
|
||||
}
|
||||
};
|
||||
|
||||
// 28457 - Dark Blast
|
||||
class spell_kelthuzad_dark_blast_40 : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_kelthuzad_dark_blast_40);
|
||||
|
||||
void CalculateDamage(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
SetEffectValue(urand(1750,2250));
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_kelthuzad_dark_blast_40::CalculateDamage, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
// 29213 - Curse of the Plaguebringer
|
||||
enum CurseOfThePlaguebringer
|
||||
{
|
||||
SPELL_REVENGE_OF_THE_PLAGUEBRINGER = 29214,
|
||||
};
|
||||
|
||||
class spell_noth_curse_of_the_plaguebringer_aura_40 : public AuraScript
|
||||
{
|
||||
PrepareAuraScript(spell_noth_curse_of_the_plaguebringer_aura_40);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
return ValidateSpellInfo({ SPELL_REVENGE_OF_THE_PLAGUEBRINGER }); // Revenge of the Plaguebringer
|
||||
}
|
||||
|
||||
void HandleTriggerSpell(AuraEffect const* /*aurEff*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
PreventDefaultAction();
|
||||
CustomSpellValues values;
|
||||
int32 bp0 = 1757; // instant damage
|
||||
int32 bp1 = 874; // periodic damage
|
||||
values.AddSpellMod(SPELLVALUE_BASE_POINT0, bp0);
|
||||
values.AddSpellMod(SPELLVALUE_BASE_POINT1, bp1);
|
||||
values.AddSpellMod(SPELLVALUE_RADIUS_MOD, 3500); // 35yd
|
||||
GetTarget()->CastCustomSpell(SPELL_REVENGE_OF_THE_PLAGUEBRINGER, values, GetTarget(), TRIGGERED_NONE, nullptr, nullptr, GetCasterGUID());
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectPeriodic += AuraEffectPeriodicFn(spell_noth_curse_of_the_plaguebringer_aura_40::HandleTriggerSpell, EFFECT_0, SPELL_AURA_PERIODIC_TRIGGER_SPELL);
|
||||
}
|
||||
};
|
||||
|
||||
//
|
||||
class spell_razuvious_disrupting_shout_40 : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_razuvious_disrupting_shout_40);
|
||||
|
||||
void PreventLaunchHit(SpellEffIndex effIndex)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (Unit* target = GetHitUnit())
|
||||
{
|
||||
// ignore los -> not ignore los
|
||||
// radius 60yd -> 45yd
|
||||
PreventHitDefaultEffect(effIndex);
|
||||
if (!target->IsWithinLOSInMap(caster) || !target->IsWithinDist2d(caster, 45.0f))
|
||||
{
|
||||
SetEffectValue(0);
|
||||
return;
|
||||
}
|
||||
Powers PowerType = POWER_MANA;
|
||||
// int32 amountToDrain = urand(4050,4950);
|
||||
int32 amountToDrain = urand(500,501);
|
||||
int32 drainedAmount = -target->ModifyPower(PowerType, -amountToDrain);
|
||||
SetEffectValue(drainedAmount);
|
||||
}
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectHitTarget += SpellEffectFn(spell_razuvious_disrupting_shout_40::PreventLaunchHit, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_unholy_staff_arcane_explosion_40 : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_unholy_staff_arcane_explosion_40);
|
||||
|
||||
void PreventLaunchHit(SpellEffIndex effIndex)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (Unit* target = GetHitUnit())
|
||||
{
|
||||
if (target->IsWithinDist2d(caster, 20.0f))
|
||||
{
|
||||
SetEffectValue(urand(1838, 2361));
|
||||
}
|
||||
else
|
||||
{
|
||||
PreventHitDefaultEffect(effIndex);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_unholy_staff_arcane_explosion_40::PreventLaunchHit, EFFECT_1, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_disease_cloud_damage_40 : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_disease_cloud_damage_40);
|
||||
|
||||
void HandleDamageCalc(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
Unit* caster = GetCaster();
|
||||
if (!caster || (caster->GetMap()->GetDifficulty() != RAID_DIFFICULTY_10MAN_HEROIC))
|
||||
{
|
||||
return;
|
||||
}
|
||||
SetEffectValue(urand(278,322));
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_disease_cloud_damage_40::HandleDamageCalc, EFFECT_0, SPELL_EFFECT_SCHOOL_DAMAGE);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_custom_spells_40()
|
||||
{
|
||||
RegisterSpellScript(spell_anub_locust_swarm_aura_40);
|
||||
RegisterSpellScript(spell_gen_consumption);
|
||||
RegisterSpellScript(spell_grobbulus_poison_cloud_poison_damage_40);
|
||||
RegisterSpellScript(spell_heigan_plague_cloud_aura_40);
|
||||
RegisterSpellScript(spell_heigan_eruption_40);
|
||||
RegisterSpellScript(spell_submerge_visual_aura);
|
||||
RegisterSpellScript(spell_kelthuzad_dark_blast_40);
|
||||
RegisterSpellScript(spell_noth_curse_of_the_plaguebringer_aura_40);
|
||||
RegisterSpellScript(spell_razuvious_disrupting_shout_40);
|
||||
RegisterSpellScript(spell_unholy_staff_arcane_explosion_40);
|
||||
RegisterSpellScript(spell_disease_cloud_damage_40);
|
||||
}
|
||||
@@ -25,7 +25,6 @@
|
||||
#include "ObjectMgr.h"
|
||||
#include "GameObjectAI.h"
|
||||
#include "naxxramas.h"
|
||||
#include "IndividualProgression.h"
|
||||
|
||||
const float HeiganPos[2] = {2796, -3707};
|
||||
const float HeiganEruptionSlope[3] =
|
||||
@@ -74,6 +73,7 @@ public:
|
||||
|
||||
// NPCs
|
||||
PatchwerkRoomTrash.clear();
|
||||
HeiganBackRoomAdds.clear();
|
||||
|
||||
// Controls
|
||||
_horsemanKilled = 0;
|
||||
@@ -95,6 +95,7 @@ public:
|
||||
}
|
||||
|
||||
std::set<GameObject*> HeiganEruption[4];
|
||||
std::set<GameObject*> HeiganEruptionTunnel;
|
||||
|
||||
// GOs
|
||||
ObjectGuid _patchwerkGateGUID;
|
||||
@@ -103,6 +104,7 @@ public:
|
||||
ObjectGuid _nothExitGateGUID;
|
||||
ObjectGuid _heiganGateGUID;
|
||||
ObjectGuid _heiganGateExitGUID;
|
||||
ObjectGuid _heiganGateExitOldGUID;
|
||||
ObjectGuid _loathebGateGUID;
|
||||
ObjectGuid _anubGateGUID;
|
||||
ObjectGuid _anubNextGateGUID;
|
||||
@@ -136,6 +138,7 @@ public:
|
||||
|
||||
// NPCs
|
||||
GuidList PatchwerkRoomTrash;
|
||||
GuidList HeiganBackRoomAdds;
|
||||
ObjectGuid _patchwerkGUID;
|
||||
ObjectGuid _thaddiusGUID;
|
||||
ObjectGuid _stalaggGUID;
|
||||
@@ -179,6 +182,17 @@ public:
|
||||
itr->SendCustomAnim(itr->GetGoAnimProgress());
|
||||
itr->CastSpell(nullptr, SPELL_ERUPTION);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
void HeiganEruptSectionsTunnel()
|
||||
{
|
||||
// doesn't work
|
||||
for (auto itr : HeiganEruptionTunnel)
|
||||
{
|
||||
itr->SendCustomAnim(itr->GetGoAnimProgress());
|
||||
itr->CastSpell(nullptr, SPELL_ERUPTION);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -197,6 +211,15 @@ public:
|
||||
|
||||
switch(creature->GetEntry())
|
||||
{
|
||||
case NPC_ROTTING_MAGGOT_40:
|
||||
HeiganBackRoomAdds.push_back(creature->GetGUID());
|
||||
return;
|
||||
case NPC_DISEASED_MAGGOT_40:
|
||||
HeiganBackRoomAdds.push_back(creature->GetGUID());
|
||||
return;
|
||||
case NPC_EYE_STALK_40:
|
||||
HeiganBackRoomAdds.push_back(creature->GetGUID());
|
||||
return;
|
||||
case NPC_PATCHWERK:
|
||||
_patchwerkGUID = creature->GetGUID();
|
||||
return;
|
||||
@@ -314,6 +337,11 @@ public:
|
||||
HeiganEruption[GetEruptionSection(pGo->GetPositionX(), pGo->GetPositionY())].insert(pGo);
|
||||
return;
|
||||
}
|
||||
if (pGo->GetGOInfo()->entry == 361001)
|
||||
{
|
||||
HeiganEruptionTunnel.insert(pGo);
|
||||
return;
|
||||
}
|
||||
|
||||
switch(pGo->GetEntry())
|
||||
{
|
||||
@@ -359,6 +387,13 @@ public:
|
||||
pGo->SetGoState(GO_STATE_ACTIVE);
|
||||
}
|
||||
break;
|
||||
case GO_HEIGAN_EXIT_GATE_OLD:
|
||||
_heiganGateExitOldGUID = pGo->GetGUID();
|
||||
if (GetBossState(BOSS_HEIGAN) == DONE)
|
||||
{
|
||||
pGo->SetGoState(GO_STATE_ACTIVE);
|
||||
}
|
||||
break;
|
||||
case GO_LOATHEB_GATE:
|
||||
_loathebGateGUID = pGo->GetGUID();
|
||||
if (GetBossState(BOSS_LOATHEB) == DONE)
|
||||
@@ -688,6 +723,9 @@ public:
|
||||
case DATA_HEIGAN_ERUPTION:
|
||||
HeiganEruptSections(data);
|
||||
return;
|
||||
case DATA_HEIGAN_ERUPTION_TUNNEL:
|
||||
HeiganEruptSectionsTunnel();
|
||||
return;
|
||||
case DATA_HAD_THADDIUS_GREET:
|
||||
_hadThaddiusGreet = (data == 1);
|
||||
default:
|
||||
@@ -921,6 +959,13 @@ public:
|
||||
}
|
||||
break;
|
||||
case BOSS_HEIGAN:
|
||||
for (auto& mobGUID : HeiganBackRoomAdds)
|
||||
{
|
||||
if (Creature* mob = instance->GetCreature(mobGUID))
|
||||
{
|
||||
mob->DespawnOrUnsummon();
|
||||
}
|
||||
}
|
||||
if (GameObject* go = instance->GetGameObject(_heiganGateGUID))
|
||||
{
|
||||
go->SetGoState(GO_STATE_ACTIVE);
|
||||
@@ -929,6 +974,10 @@ public:
|
||||
{
|
||||
go->SetGoState(GO_STATE_ACTIVE);
|
||||
}
|
||||
if (GameObject* go = instance->GetGameObject(_heiganGateExitOldGUID))
|
||||
{
|
||||
go->SetGoState(GO_STATE_ACTIVE);
|
||||
}
|
||||
break;
|
||||
case BOSS_LOATHEB:
|
||||
if (GameObject* go = instance->GetGameObject(_loathebGateGUID))
|
||||
@@ -1143,6 +1192,10 @@ public:
|
||||
// GameObjects
|
||||
case DATA_HEIGAN_ENTER_GATE:
|
||||
return _heiganGateGUID;
|
||||
case DATA_HEIGAN_EXIT_GATE_OLD:
|
||||
return _heiganGateExitOldGUID;
|
||||
case DATA_HEIGAN_EXIT_GATE:
|
||||
return _heiganGateExitGUID;
|
||||
case DATA_LOATHEB_GATE:
|
||||
return _loathebGateGUID;
|
||||
case DATA_ANUB_GATE:
|
||||
@@ -1203,6 +1256,7 @@ public:
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
class boss_naxxramas_misc : public CreatureScript
|
||||
{
|
||||
public:
|
||||
@@ -1274,112 +1328,11 @@ public:
|
||||
};
|
||||
};
|
||||
|
||||
class npc_naxx40_area_trigger : public CreatureScript
|
||||
{
|
||||
private:
|
||||
static bool isAttuned(Player* player)
|
||||
{
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_1) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_2) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_3) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
public:
|
||||
npc_naxx40_area_trigger() : CreatureScript("npc_naxx40_area_trigger") {}
|
||||
|
||||
struct npc_naxx40_area_triggerAI: public ScriptedAI
|
||||
{
|
||||
npc_naxx40_area_triggerAI(Creature* creature) : ScriptedAI(creature)
|
||||
{
|
||||
me->SetDisplayId(11686); // Invisible
|
||||
}
|
||||
|
||||
void MoveInLineOfSight(Unit* who) override
|
||||
{
|
||||
if (who && me->GetDistance2d(who) < 5.0f)
|
||||
{
|
||||
if (Player* player = who->ToPlayer())
|
||||
{
|
||||
if (isAttuned(player))
|
||||
{
|
||||
player->SetRaidDifficulty(RAID_DIFFICULTY_10MAN_HEROIC);
|
||||
player->TeleportTo(533, 3005.51f, -3434.64f, 304.195f, 6.2831f);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
else if (who && me->GetDistance2d(who) < 20.0f)
|
||||
{
|
||||
if (Player* player = who->ToPlayer())
|
||||
{
|
||||
if (isAttuned(player))
|
||||
{
|
||||
GameObject* door = me->FindNearestGameObject(NAXX_STRATH_GATE, 100.0f);
|
||||
if (door)
|
||||
{
|
||||
door->SetGoState(GO_STATE_ACTIVE);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
CreatureAI* GetAI(Creature* creature) const override
|
||||
{
|
||||
return new npc_naxx40_area_triggerAI(creature);
|
||||
}
|
||||
};
|
||||
|
||||
class gobject_naxx40_tele : public GameObjectScript
|
||||
{
|
||||
private:
|
||||
static bool isAttuned(Player* player)
|
||||
{
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_1) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_2) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
if (player->GetQuestStatus(NAXX40_ATTUNEMENT_3) == QUEST_STATUS_REWARDED)
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
public:
|
||||
gobject_naxx40_tele() : GameObjectScript("gobject_naxx40_tele") { }
|
||||
|
||||
struct gobject_naxx40_teleAI: GameObjectAI
|
||||
{
|
||||
explicit gobject_naxx40_teleAI(GameObject* object) : GameObjectAI(object) { };
|
||||
|
||||
};
|
||||
|
||||
GameObjectAI* GetAI(GameObject* object) const override
|
||||
{
|
||||
return new gobject_naxx40_teleAI(object);
|
||||
}
|
||||
|
||||
bool OnGossipHello(Player* player, GameObject* /*go*/) override
|
||||
{
|
||||
if ((!sIndividualProgression->requireNaxxStrath || player->GetQuestStatus(NAXX40_ENTRANCE_FLAG) == QUEST_STATUS_REWARDED) && isAttuned(player))
|
||||
{
|
||||
player->SetRaidDifficulty(RAID_DIFFICULTY_10MAN_HEROIC);
|
||||
player->TeleportTo(533, 3005.51f, -3434.64f, 304.195f, 6.2831f);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
class NaxxPlayerScript : public PlayerScript
|
||||
{
|
||||
public:
|
||||
NaxxPlayerScript() : PlayerScript("NaxxPlayerScript") { }
|
||||
|
||||
|
||||
void OnBeforeChooseGraveyard(Player* player, TeamId /*teamId*/, bool /*nearCorpse*/, uint32& graveyardOverride) override
|
||||
{
|
||||
if (player->GetMapId() == MAP_NAXX && player->GetMap()->GetSpawnMode() == RAID_DIFFICULTY_10MAN_HEROIC)
|
||||
@@ -1419,7 +1372,8 @@ public:
|
||||
player->TeleportTo(533, 2992.5f, -3434.42f, 293.94f, 3.13f);
|
||||
break;
|
||||
}
|
||||
return true; }
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
class naxx_exit_trigger : public AreaTriggerScript
|
||||
@@ -1454,7 +1408,6 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
const Position sapphironEntryTP = { 3498.300049f, -5349.490234f, 144.968002f, 1.3698910f };
|
||||
|
||||
class at_naxxramas_hub_portal : public AreaTriggerScript
|
||||
@@ -1491,10 +1444,7 @@ public:
|
||||
class NaxxEntryFlag_AllMapScript : public AllMapScript
|
||||
{
|
||||
public:
|
||||
NaxxEntryFlag_AllMapScript()
|
||||
: AllMapScript("NaxxEntryFlag_AllMapScript")
|
||||
{
|
||||
}
|
||||
NaxxEntryFlag_AllMapScript() : AllMapScript("NaxxEntryFlag_AllMapScript") { }
|
||||
|
||||
void OnPlayerEnterAll(Map* map, Player* player) override
|
||||
{
|
||||
@@ -1521,12 +1471,10 @@ public:
|
||||
void AddSC_instance_naxxramas_combined()
|
||||
{
|
||||
new instance_naxxramas_combined();
|
||||
new npc_naxx40_area_trigger();
|
||||
new NaxxPlayerScript();
|
||||
new naxx_exit_trigger();
|
||||
new naxx_northrend_entrance();
|
||||
new at_naxxramas_hub_portal();
|
||||
new NaxxEntryFlag_AllMapScript();
|
||||
new gobject_naxx40_tele();
|
||||
// new boss_naxxramas_misc();
|
||||
}
|
||||
|
||||
@@ -74,7 +74,10 @@ enum NXData
|
||||
DATA_KELTHUZAD_PORTAL_1 = 126,
|
||||
DATA_KELTHUZAD_PORTAL_2 = 127,
|
||||
DATA_KELTHUZAD_PORTAL_3 = 128,
|
||||
DATA_KELTHUZAD_PORTAL_4 = 129
|
||||
DATA_KELTHUZAD_PORTAL_4 = 129,
|
||||
DATA_HEIGAN_EXIT_GATE_OLD = 130,
|
||||
DATA_HEIGAN_EXIT_GATE = 131,
|
||||
DATA_HEIGAN_ERUPTION_TUNNEL = 130
|
||||
};
|
||||
|
||||
enum NXGOs
|
||||
@@ -85,6 +88,7 @@ enum NXGOs
|
||||
GO_NOTH_EXIT_GATE = 181201,
|
||||
GO_HEIGAN_ENTRY_GATE = 181202,
|
||||
GO_HEIGAN_EXIT_GATE = 181203,
|
||||
GO_HEIGAN_EXIT_GATE_OLD = 181496,
|
||||
GO_LOATHEB_GATE = 181241,
|
||||
GO_ANUB_GATE = 181126,
|
||||
GO_ANUB_NEXT_GATE = 181195,
|
||||
@@ -200,6 +204,11 @@ enum NX40NPCs
|
||||
NPC_SURGICAL_ASSIST_40 = 351025,
|
||||
NPC_SLUDGE_BELCHER_40 = 351029,
|
||||
|
||||
// Heigan
|
||||
NPC_ROTTING_MAGGOT_40 = 351034,
|
||||
NPC_DISEASED_MAGGOT_40 = 351033,
|
||||
NPC_EYE_STALK_40 = 351090,
|
||||
|
||||
NPC_ARCHMAGE_TARSIS = 16381,
|
||||
};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user