Scripts/BWD: initial work on Maloriak encounter
This commit is contained in:
1 parent
d849ae131d
commit
c1627e6a3e
4 files changed
+406
-8
No files matched your search
+12
-5
@@ -36,7 +36,6 @@ enum BWDDataTypes
|
||||
DATA_NEFARIANS_END = 5,
|
||||
|
||||
/*Events*/
|
||||
|
||||
DATA_DEAD_DWARF_SPIRITS,
|
||||
DATA_ANCIENT_BELL,
|
||||
DATA_COLUMN_OF_LIGHT,
|
||||
@@ -62,7 +61,11 @@ enum BWDDataTypes
|
||||
/*Chimaeron*/
|
||||
DATA_BILE_O_TRON_800,
|
||||
DATA_FINKLE_EINHORN,
|
||||
DATA_LORD_VICTOR_NEFARIUS_CHIMAERON
|
||||
DATA_LORD_VICTOR_NEFARIUS_CHIMAERON,
|
||||
|
||||
/*Maloriak*/
|
||||
DATA_CAULDRON_TRIGGER,
|
||||
DATA_CAULDRON
|
||||
};
|
||||
|
||||
enum BWDCreatureIds
|
||||
@@ -115,6 +118,9 @@ enum BWDCreatureIds
|
||||
NPC_BILE_O_TRON_800 = 44418,
|
||||
NPC_LORD_VICTOR_NEFARIUS_CHIMAERON = 48964,
|
||||
|
||||
/*Maloriak*/
|
||||
NPC_CAULDRON_TRIGGER = 41505,
|
||||
|
||||
/*Events*/
|
||||
NPC_SPIRIT_OF_MOLTENFIST = 43125,
|
||||
NPC_SPIRIT_OF_ANVILRAGE = 43128,
|
||||
@@ -129,9 +135,10 @@ enum BWDCreatureIds
|
||||
|
||||
enum BWDGameObjectIds
|
||||
{
|
||||
GO_INNER_CHAMBER_DOOR = 205830,
|
||||
GO_ANCIENT_BELL = 204276,
|
||||
GO_ATHENAEUM_DOOR = 208291,
|
||||
GO_INNER_CHAMBER_DOOR = 205830,
|
||||
GO_ANCIENT_BELL = 204276,
|
||||
GO_ATHENAEUM_DOOR = 208291,
|
||||
GO_DOODAD_BLACKROCKV2_LABROOM_CAULDRON_01 = 203306
|
||||
};
|
||||
|
||||
enum BWDMisc
|
||||
|
||||
+386
@@ -0,0 +1,386 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2019 TrinityCore <https://www.trinitycore.org/>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License as published by the
|
||||
* Free Software Foundation; either version 2 of the License, or (at your
|
||||
* option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||
* more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License along
|
||||
* with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "ObjectMgr.h"
|
||||
#include "ScriptMgr.h"
|
||||
#include "CommonPredicates.h"
|
||||
#include "GridNotifiers.h"
|
||||
#include "PassiveAI.h"
|
||||
#include "ScriptedCreature.h"
|
||||
#include "SpellScript.h"
|
||||
#include "SpellAuraEffects.h"
|
||||
#include "SpellMgr.h"
|
||||
#include "blackwing_descent.h"
|
||||
|
||||
enum Spells
|
||||
{
|
||||
// Maloriak
|
||||
SPELL_ARCANE_STORM = 77896,
|
||||
SPELL_REMEDY = 77912,
|
||||
|
||||
SPELL_THROW_RED_BOTTLE = 77925,
|
||||
SPELL_THROW_BLUE_BOTTLE = 77932,
|
||||
SPELL_THROW_GREEN_BOTTLE = 77937,
|
||||
SPELL_DRINK_RED_BOTTLE = 88699,
|
||||
SPELL_DRINK_BLUE_BOTTLE = 88700,
|
||||
SPELL_DRINK_BLACK_BOTTLE = 92828,
|
||||
SPELL_FIRE_IMBUED = 78896,
|
||||
SPELL_FROST_IMBUED = 78895,
|
||||
SPELL_SHADOW_IMBUED = 92716,
|
||||
SPELL_SLIME_IMBUED = 92917,
|
||||
SPELL_THROW_RED_BOTTLE_TRIGGERED = 77928,
|
||||
SPELL_THROW_BLUE_BOTTLE_TRIGGERED = 77934,
|
||||
SPELL_THROW_GREEN_BOTTLE_TRIGGERED = 77938,
|
||||
SPELL_THROW_BLACK_BOTTLE_TRIGGERED = 92837,
|
||||
SPELL_RELEASE_ABERRATIONS = 77569,
|
||||
|
||||
// Cauldron Trigger
|
||||
SPELL_DEBILITATING_SLIME_CAST = 77602,
|
||||
SPELL_DEBILITATING_SLIME_KNOCKBACK = 77948,
|
||||
SPELL_DEBILITATING_SLIME_DEBUFF = 77615,
|
||||
|
||||
};
|
||||
|
||||
enum Events
|
||||
{
|
||||
// Maloriak
|
||||
EVENT_ARCANE_STORM = 1,
|
||||
EVENT_REMEDY,
|
||||
EVENT_RELEASE_ABERRATIONS,
|
||||
EVENT_FACE_TO_CAULDRON,
|
||||
EVENT_THROW_VIAL,
|
||||
EVENT_MOVE_TO_CAULDRON,
|
||||
EVENT_DRINK_BOTTLE,
|
||||
EVENT_IMBUED_BUFF,
|
||||
EVENT_EXPLODE_CAULDRON,
|
||||
EVENT_ATTACK_PLAYERS,
|
||||
};
|
||||
|
||||
enum Actions
|
||||
{
|
||||
ACTION_SCHEDULE_EVENTS_FOR_PHASE = 1
|
||||
};
|
||||
|
||||
enum MovePoints
|
||||
{
|
||||
POINT_CAULDRON = 1
|
||||
};
|
||||
|
||||
enum Texts
|
||||
{
|
||||
// Maloriak
|
||||
SAY_AGGRO = 0,
|
||||
SAY_RED_VIAL = 1,
|
||||
SAY_ANNOUNCE_RED_VIAL = 2,
|
||||
SAY_BLUE_VIAL = 3,
|
||||
SAY_ANNOUNCE_BLUE_VIAL = 4,
|
||||
SAY_GREEN_VIAL = 5,
|
||||
SAY_ANNOUNCE_GREEN_VIAL = 6,
|
||||
SAY_RELEASE_ABERRATIONS = 7,
|
||||
};
|
||||
|
||||
enum Vials
|
||||
{
|
||||
VIAL_RED = 0,
|
||||
VIAL_BLUE = 1,
|
||||
VIAL_GREEN = 2
|
||||
};
|
||||
|
||||
enum GameObjectCustomAnim
|
||||
{
|
||||
CUSTOM_ANIM_RED_CAULDRON = 0,
|
||||
CUSTOM_ANIM_BLUE_CAULDRON = 1,
|
||||
CUSTOM_ANIM_GREEN_CAULDRON = 2,
|
||||
CUSTOM_ANIM_BLACK_CAULDRON = 3
|
||||
};
|
||||
|
||||
Position const CauldronMovePosition = { -106.6782f, -475.4438f, 73.45684f };
|
||||
|
||||
struct VialData
|
||||
{
|
||||
uint8 SayTextId;
|
||||
uint8 AnnounceTextId;
|
||||
uint32 ThrowSpellId;
|
||||
uint32 DrinkSpellId;
|
||||
uint32 ImbuedSpellId;
|
||||
};
|
||||
|
||||
std::unordered_map<uint8, VialData> vialData =
|
||||
{
|
||||
{ VIAL_RED, { SAY_RED_VIAL, SAY_ANNOUNCE_RED_VIAL, SPELL_THROW_RED_BOTTLE, SPELL_DRINK_RED_BOTTLE, SPELL_FIRE_IMBUED }},
|
||||
{ VIAL_BLUE, { SAY_BLUE_VIAL, SAY_ANNOUNCE_BLUE_VIAL, SPELL_THROW_BLUE_BOTTLE, SPELL_DRINK_BLUE_BOTTLE, SPELL_FROST_IMBUED }},
|
||||
{ VIAL_GREEN, { SAY_GREEN_VIAL, SAY_ANNOUNCE_GREEN_VIAL, SPELL_THROW_GREEN_BOTTLE, 0, SPELL_SLIME_IMBUED }},
|
||||
};
|
||||
|
||||
struct boss_maloriak : public BossAI
|
||||
{
|
||||
boss_maloriak(Creature* creature) : BossAI(creature, DATA_MALORIAK),
|
||||
_currentVial(urand(VIAL_RED, VIAL_BLUE)), _usedVialsCount(0) { }
|
||||
|
||||
void Reset() override
|
||||
{
|
||||
_Reset();
|
||||
me->MakeInterruptable(false);
|
||||
}
|
||||
|
||||
void JustEngagedWith(Unit* /*who*/) override
|
||||
{
|
||||
_JustEngagedWith();
|
||||
Talk(SAY_AGGRO);
|
||||
instance->SendEncounterUnit(ENCOUNTER_FRAME_ENGAGE, me);
|
||||
events.ScheduleEvent(EVENT_FACE_TO_CAULDRON, 15s + 500ms);
|
||||
}
|
||||
|
||||
void EnterEvadeMode(EvadeReason /*why*/) override
|
||||
{
|
||||
_EnterEvadeMode();
|
||||
instance->SendEncounterUnit(ENCOUNTER_FRAME_DISENGAGE, me);
|
||||
summons.DespawnAll();
|
||||
_DespawnAtEvade();
|
||||
}
|
||||
|
||||
void OnSpellCastInterrupt(SpellInfo const* spell) override
|
||||
{
|
||||
switch (spell->Id)
|
||||
{
|
||||
case SPELL_ARCANE_STORM:
|
||||
me->MakeInterruptable(false);
|
||||
me->m_Events.KillAllEvents(true);
|
||||
break;
|
||||
case SPELL_RELEASE_ABERRATIONS:
|
||||
me->MakeInterruptable(false);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void OnSuccessfulSpellCast(SpellInfo const* spell) override
|
||||
{
|
||||
switch (spell->Id)
|
||||
{
|
||||
case SPELL_RELEASE_ABERRATIONS:
|
||||
Talk(SAY_RELEASE_ABERRATIONS);
|
||||
me->MakeInterruptable(false);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void MovementInform(uint32 motionType, uint32 pointId) override
|
||||
{
|
||||
if (motionType != POINT_MOTION_TYPE && motionType != EFFECT_MOTION_TYPE)
|
||||
return;
|
||||
|
||||
switch (pointId)
|
||||
{
|
||||
case POINT_CAULDRON:
|
||||
events.ScheduleEvent(EVENT_DRINK_BOTTLE, 1s + 500ms);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void DoAction(int32 action) override
|
||||
{
|
||||
switch (action)
|
||||
{
|
||||
case ACTION_SCHEDULE_EVENTS_FOR_PHASE:
|
||||
events.ScheduleEvent(EVENT_ATTACK_PLAYERS, _currentVial != VIAL_GREEN ? 1ms : 4s);
|
||||
|
||||
if (_currentVial == VIAL_RED || _currentVial == VIAL_BLUE)
|
||||
{
|
||||
events.ScheduleEvent(EVENT_ARCANE_STORM, 14s + 500ms);
|
||||
events.ScheduleEvent(EVENT_REMEDY, 21s + 500ms);
|
||||
events.ScheduleEvent(EVENT_RELEASE_ABERRATIONS, 11s);
|
||||
}
|
||||
else if (_currentVial == VIAL_GREEN)
|
||||
{
|
||||
if (Creature* cauldron = instance->GetCreature(DATA_CAULDRON_TRIGGER))
|
||||
cauldron->CastSpell(cauldron, SPELL_DEBILITATING_SLIME_DEBUFF);
|
||||
|
||||
events.ScheduleEvent(EVENT_ARCANE_STORM, 8s);
|
||||
events.ScheduleEvent(EVENT_REMEDY, 33s + 500ms);
|
||||
events.ScheduleEvent(EVENT_RELEASE_ABERRATIONS, 15s);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateAI(uint32 diff) override
|
||||
{
|
||||
if (!UpdateVictim())
|
||||
return;
|
||||
|
||||
events.Update(diff);
|
||||
|
||||
if (me->HasUnitState(UNIT_STATE_CASTING))
|
||||
return;
|
||||
|
||||
while (uint32 eventId = events.ExecuteEvent())
|
||||
{
|
||||
switch (eventId)
|
||||
{
|
||||
case EVENT_ARCANE_STORM:
|
||||
{
|
||||
me->MakeInterruptable(true);
|
||||
DoCastSelf(SPELL_ARCANE_STORM);
|
||||
Creature* maloriak = me;
|
||||
me->m_Events.AddEventAtOffset([maloriak]() { maloriak->MakeInterruptable(false); }, 6s + 500ms);
|
||||
events.Repeat(13s + 500ms);
|
||||
break;
|
||||
}
|
||||
case EVENT_REMEDY:
|
||||
DoCastSelf(SPELL_REMEDY);
|
||||
break;
|
||||
case EVENT_RELEASE_ABERRATIONS:
|
||||
me->MakeInterruptable(true);
|
||||
DoCastAOE(SPELL_RELEASE_ABERRATIONS);
|
||||
events.Repeat(24s + 500ms);
|
||||
break;
|
||||
case EVENT_FACE_TO_CAULDRON:
|
||||
events.Reset();
|
||||
if (Creature* cauldron = instance->GetCreature(DATA_CAULDRON_TRIGGER))
|
||||
{
|
||||
me->AttackStop();
|
||||
me->SetReactState(REACT_PASSIVE);
|
||||
me->SetFacingToObject(cauldron);
|
||||
|
||||
_currentVial = _usedVialsCount < 2 ? _currentVial == VIAL_BLUE ? VIAL_RED : VIAL_BLUE : VIAL_GREEN;
|
||||
Talk(vialData[_currentVial].SayTextId);
|
||||
_usedVialsCount = _usedVialsCount < 2 ? _usedVialsCount + 1 : 0;
|
||||
|
||||
events.Repeat(50s);
|
||||
events.ScheduleEvent(EVENT_THROW_VIAL, 1s + 300ms);
|
||||
}
|
||||
break;
|
||||
case EVENT_THROW_VIAL:
|
||||
DoCastSelf(vialData[_currentVial].ThrowSpellId);
|
||||
Talk(vialData[_currentVial].AnnounceTextId);
|
||||
events.ScheduleEvent(EVENT_MOVE_TO_CAULDRON, 1s);
|
||||
break;
|
||||
case EVENT_MOVE_TO_CAULDRON:
|
||||
me->GetMotionMaster()->MovePoint(POINT_CAULDRON, CauldronMovePosition);
|
||||
break;
|
||||
case EVENT_DRINK_BOTTLE:
|
||||
DoCastSelf(vialData[_currentVial].DrinkSpellId);
|
||||
events.ScheduleEvent(EVENT_IMBUED_BUFF, 2s + 500ms);
|
||||
|
||||
if (_currentVial == VIAL_GREEN)
|
||||
events.ScheduleEvent(EVENT_EXPLODE_CAULDRON, 1s);
|
||||
break;
|
||||
case EVENT_IMBUED_BUFF:
|
||||
DoCastSelf(vialData[_currentVial].ImbuedSpellId);
|
||||
DoAction(ACTION_SCHEDULE_EVENTS_FOR_PHASE);
|
||||
break;
|
||||
case EVENT_EXPLODE_CAULDRON:
|
||||
if (Creature* cauldron = instance->GetCreature(DATA_CAULDRON_TRIGGER))
|
||||
{
|
||||
cauldron->CastSpell(cauldron, SPELL_DEBILITATING_SLIME_CAST);
|
||||
cauldron->CastSpell(cauldron, SPELL_DEBILITATING_SLIME_KNOCKBACK);
|
||||
}
|
||||
break;
|
||||
case EVENT_ATTACK_PLAYERS:
|
||||
me->SetReactState(REACT_AGGRESSIVE);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
DoMeleeAttackIfReady();
|
||||
}
|
||||
private:
|
||||
uint8 _currentVial;
|
||||
uint8 _usedVialsCount;
|
||||
};
|
||||
|
||||
class spell_maloriak_throw_bottle : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_maloriak_throw_bottle);
|
||||
|
||||
void HandleDummyEffect(SpellEffIndex effIndex)
|
||||
{
|
||||
if (Unit* caster = GetCaster())
|
||||
caster->CastSpell(GetHitUnit(), GetSpellInfo()->Effects[effIndex].BasePoints, true);
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectLaunchTarget += SpellEffectFn(spell_maloriak_throw_bottle::HandleDummyEffect, EFFECT_0, SPELL_EFFECT_DUMMY);
|
||||
}
|
||||
};
|
||||
|
||||
class spell_maloriak_throw_bottle_triggered : public SpellScript
|
||||
{
|
||||
PrepareSpellScript(spell_maloriak_throw_bottle_triggered);
|
||||
|
||||
bool Validate(SpellInfo const* /*spellInfo*/) override
|
||||
{
|
||||
return ValidateSpellInfo(
|
||||
{
|
||||
SPELL_THROW_RED_BOTTLE_TRIGGERED,
|
||||
SPELL_THROW_BLUE_BOTTLE_TRIGGERED,
|
||||
SPELL_THROW_GREEN_BOTTLE_TRIGGERED,
|
||||
SPELL_THROW_BLACK_BOTTLE_TRIGGERED
|
||||
});
|
||||
}
|
||||
|
||||
void HandleDummyEffect(SpellEffIndex /*effIndex*/)
|
||||
{
|
||||
InstanceScript* instance = GetHitUnit()->GetInstanceScript();
|
||||
if (!instance)
|
||||
return;
|
||||
|
||||
if (GameObject* cauldron = instance->GetGameObject(DATA_CAULDRON))
|
||||
{
|
||||
switch (GetSpellInfo()->Id)
|
||||
{
|
||||
case SPELL_THROW_RED_BOTTLE_TRIGGERED:
|
||||
cauldron->SendCustomAnim(CUSTOM_ANIM_RED_CAULDRON);
|
||||
break;
|
||||
case SPELL_THROW_BLUE_BOTTLE_TRIGGERED:
|
||||
cauldron->SendCustomAnim(CUSTOM_ANIM_BLUE_CAULDRON);
|
||||
break;
|
||||
case SPELL_THROW_GREEN_BOTTLE_TRIGGERED:
|
||||
cauldron->SendCustomAnim(CUSTOM_ANIM_GREEN_CAULDRON);
|
||||
break;
|
||||
case SPELL_THROW_BLACK_BOTTLE_TRIGGERED:
|
||||
cauldron->SendCustomAnim(CUSTOM_ANIM_BLACK_CAULDRON);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Register() override
|
||||
{
|
||||
OnEffectHitTarget += SpellEffectFn(spell_maloriak_throw_bottle_triggered::HandleDummyEffect, EFFECT_0, SPELL_EFFECT_DUMMY);
|
||||
}
|
||||
};
|
||||
|
||||
void AddSC_boss_maloriak()
|
||||
{
|
||||
RegisterBlackwingDescentCreatureAI(boss_maloriak);
|
||||
RegisterSpellScript(spell_maloriak_throw_bottle);
|
||||
RegisterSpellScript(spell_maloriak_throw_bottle_triggered);
|
||||
}
|
||||
+6
-3
@@ -28,6 +28,7 @@ ObjectData const creatureData[] =
|
||||
{ BOSS_OMNOTRON, DATA_OMNOTRON_DEFENSE_SYSTEM },
|
||||
{ BOSS_ATRAMEDES, DATA_ATRAMEDES },
|
||||
{ BOSS_CHIMAERON, DATA_CHIMAERON },
|
||||
{ BOSS_MALORIAK, DATA_MALORIAK },
|
||||
{ NPC_ELECTRON, DATA_ELECTRON },
|
||||
{ NPC_MAGMATRON, DATA_MAGMATRON },
|
||||
{ NPC_TOXITRON, DATA_TOXITRON },
|
||||
@@ -39,14 +40,16 @@ ObjectData const creatureData[] =
|
||||
{ NPC_BILE_O_TRON_800, DATA_BILE_O_TRON_800 },
|
||||
{ NPC_FINKLE_EINHORN, DATA_FINKLE_EINHORN },
|
||||
{ NPC_LORD_VICTOR_NEFARIUS_CHIMAERON, DATA_LORD_VICTOR_NEFARIUS_CHIMAERON },
|
||||
{ NPC_CAULDRON_TRIGGER, DATA_CAULDRON_TRIGGER },
|
||||
{ 0, 0 } // END
|
||||
};
|
||||
|
||||
ObjectData const gameobjectData[] =
|
||||
{
|
||||
{ GO_ANCIENT_BELL, DATA_ANCIENT_BELL },
|
||||
{ GO_ATHENAEUM_DOOR, DATA_ATHENAEUM_DOOR },
|
||||
{ 0, 0 } // END
|
||||
{ GO_ANCIENT_BELL, DATA_ANCIENT_BELL },
|
||||
{ GO_ATHENAEUM_DOOR, DATA_ATHENAEUM_DOOR },
|
||||
{ GO_DOODAD_BLACKROCKV2_LABROOM_CAULDRON_01, DATA_CAULDRON },
|
||||
{ 0, 0 } // END
|
||||
};
|
||||
|
||||
DoorData const doorData[] =
|
||||
|
||||
@@ -78,6 +78,7 @@ void AddSC_boss_magmaw();
|
||||
void AddSC_boss_omnotron_defense_system();
|
||||
void AddSC_boss_atramedes();
|
||||
void AddSC_boss_chimaeron();
|
||||
void AddSC_boss_maloriak();
|
||||
void AddSC_blackwing_descent();
|
||||
void AddSC_instance_deadmines(); //Deadmines
|
||||
void AddSC_boss_glubtok();
|
||||
@@ -307,6 +308,7 @@ void AddEasternKingdomsScripts()
|
||||
AddSC_boss_omnotron_defense_system();
|
||||
AddSC_boss_atramedes();
|
||||
AddSC_boss_chimaeron();
|
||||
AddSC_boss_maloriak();
|
||||
AddSC_blackwing_descent();
|
||||
AddSC_instance_deadmines(); //Deadmines
|
||||
AddSC_boss_glubtok();
|
||||
|
||||
Reference in new issue
Block a user