diff --git a/data/sql/updates/db_world/0000_00_00_00.sql b/data/sql/updates/db_world/0000_00_00_00.sql index c9b3646492..4f6fce5c8a 100644 --- a/data/sql/updates/db_world/0000_00_00_00.sql +++ b/data/sql/updates/db_world/0000_00_00_00.sql @@ -83,3 +83,8 @@ DELETE FROM `spell_script_names` WHERE `ScriptName`='spell_vael_burning_adrenali INSERT INTO `spell_script_names` (`spell_id`, `ScriptName`) VALUES ('18173', 'spell_vael_burning_adrenaline'); +-- Suppression Room +SET @GO_TURRET = 179784; +UPDATE `gameobject_template` SET `ScriptName`='go_suppression_device' WHERE `entry`=@GO_TURRET; +UPDATE `gameobject_template_addon` SET `faction`=14 WHERE `entry`=@GO_TURRET; + diff --git a/src/server/scripts/EasternKingdoms/BlackrockMountain/BlackwingLair/blackwing_lair.h b/src/server/scripts/EasternKingdoms/BlackrockMountain/BlackwingLair/blackwing_lair.h index 8aaffc2f0d..1b5831b2c8 100644 --- a/src/server/scripts/EasternKingdoms/BlackrockMountain/BlackwingLair/blackwing_lair.h +++ b/src/server/scripts/EasternKingdoms/BlackrockMountain/BlackwingLair/blackwing_lair.h @@ -68,4 +68,9 @@ enum BWLMisc TALK_EGG_BROKEN_RAND = 3, }; +enum Gameobjects +{ + GO_SUPPRESSION_DEVICE = 179784 +}; + #endif diff --git a/src/server/scripts/EasternKingdoms/BlackrockMountain/BlackwingLair/boss_broodlord_lashlayer.cpp b/src/server/scripts/EasternKingdoms/BlackrockMountain/BlackwingLair/boss_broodlord_lashlayer.cpp index 177821f37e..5a0f1d4943 100644 --- a/src/server/scripts/EasternKingdoms/BlackrockMountain/BlackwingLair/boss_broodlord_lashlayer.cpp +++ b/src/server/scripts/EasternKingdoms/BlackrockMountain/BlackwingLair/boss_broodlord_lashlayer.cpp @@ -7,6 +7,9 @@ #include "ScriptMgr.h" #include "ScriptedCreature.h" #include "blackwing_lair.h" +#include "GameObject.h" +#include "GameObjectAI.h" +#include "InstanceScript.h" enum Say { @@ -19,7 +22,8 @@ enum Spells SPELL_CLEAVE = 26350, SPELL_BLASTWAVE = 23331, SPELL_MORTALSTRIKE = 24573, - SPELL_KNOCKBACK = 25778 + SPELL_KNOCKBACK = 25778, + SPELL_SUPPRESSION_AURA = 22247 // Suppression Device Spell }; enum Events @@ -28,7 +32,15 @@ enum Events EVENT_BLASTWAVE = 2, EVENT_MORTALSTRIKE = 3, EVENT_KNOCKBACK = 4, - EVENT_CHECK = 5 + EVENT_CHECK = 5, + // Suppression Device Events + EVENT_SUPPRESSION_CAST = 6, + EVENT_SUPPRESSION_RESET = 7 +}; + +enum Actions +{ + ACTION_DEACTIVATE = 0 }; class boss_broodlord : public CreatureScript @@ -58,6 +70,16 @@ public: events.ScheduleEvent(EVENT_CHECK, 1000); } + void JustDied(Unit* /*killer*/) override + { + _JustDied(); + + std::list _goList; + GetGameObjectListWithEntryInGrid(_goList, me, GO_SUPPRESSION_DEVICE, 200.0f); + for (std::list::const_iterator itr = _goList.begin(); itr != _goList.end(); itr++) + ((*itr)->AI()->DoAction(ACTION_DEACTIVATE)); + } + void UpdateAI(uint32 diff) { if (!UpdateVictim()) @@ -75,17 +97,17 @@ public: break; case EVENT_BLASTWAVE: DoCastVictim(SPELL_BLASTWAVE); - events.ScheduleEvent(EVENT_BLASTWAVE, urand(8000, 16000)); + events.ScheduleEvent(EVENT_BLASTWAVE, 8000, 16000); break; case EVENT_MORTALSTRIKE: DoCastVictim(SPELL_MORTALSTRIKE); - events.ScheduleEvent(EVENT_MORTALSTRIKE, urand(25000, 35000)); + events.ScheduleEvent(EVENT_MORTALSTRIKE, 25000, 35000); break; case EVENT_KNOCKBACK: DoCastVictim(SPELL_KNOCKBACK); - if (DoGetThreat(me->GetVictim())) - DoModifyThreatPercent(me->GetVictim(), -50); - events.ScheduleEvent(EVENT_KNOCKBACK, urand(15000, 30000)); + if (me->getThreatManager().getThreat(me->GetVictim())) + me->getThreatManager().modifyThreatPercent(me->GetVictim(), -50); + events.ScheduleEvent(EVENT_KNOCKBACK, 15000, 30000); break; case EVENT_CHECK: if (me->GetDistance(me->GetHomePosition()) > 150.0f) @@ -108,7 +130,109 @@ public: } }; +class go_suppression_device : public GameObjectScript +{ + public: + go_suppression_device() : GameObjectScript("go_suppression_device") { } + + struct go_suppression_deviceAI : public GameObjectAI + { + go_suppression_deviceAI(GameObject* go) : GameObjectAI(go), _instance(go->GetInstanceScript()), _active(true) { } + + void InitializeAI() override + { + if (_instance->GetBossState(DATA_BROODLORD_LASHLAYER) == DONE) + { + Deactivate(); + return; + } + + _events.ScheduleEvent(EVENT_SUPPRESSION_CAST, 1000, 5000); + } + + void UpdateAI(uint32 diff) override + { + _events.Update(diff); + + while (uint32 eventId = _events.ExecuteEvent()) + { + switch (eventId) + { + case EVENT_SUPPRESSION_CAST: + if (go->GetGoState() == GO_STATE_READY) + { + go->CastSpell(nullptr, SPELL_SUPPRESSION_AURA); + go->SendCustomAnim(0); + } + _events.ScheduleEvent(EVENT_SUPPRESSION_CAST, 5000); + break; + case EVENT_SUPPRESSION_RESET: + Activate(); + break; + } + } + } + + void OnLootStateChanged(uint32 state, Unit* /*unit*/) + { + switch (state) + { + case GO_ACTIVATED: + Deactivate(); + _events.CancelEvent(EVENT_SUPPRESSION_CAST); + _events.ScheduleEvent(EVENT_SUPPRESSION_RESET, 30000, 120000); + break; + case GO_JUST_DEACTIVATED: // This case prevents the Gameobject despawn by Disarm Trap + go->SetLootState(GO_READY); + break; + } + } + + void DoAction(int32 action) override + { + if (action == ACTION_DEACTIVATE) + { + Deactivate(); + _events.CancelEvent(EVENT_SUPPRESSION_RESET); + } + } + + void Activate() + { + if (_active) + return; + _active = true; + if (go->GetGoState() == GO_STATE_ACTIVE) + go->SetGoState(GO_STATE_READY); + go->SetLootState(GO_READY); + go->RemoveFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); + _events.ScheduleEvent(EVENT_SUPPRESSION_CAST, 1000); + } + + void Deactivate() + { + if (!_active) + return; + _active = false; + go->SetGoState(GO_STATE_ACTIVE); + go->SetFlag(GAMEOBJECT_FLAGS, GO_FLAG_NOT_SELECTABLE); + _events.CancelEvent(EVENT_SUPPRESSION_CAST); + } + + private: + InstanceScript* _instance; + EventMap _events; + bool _active; + }; + + GameObjectAI* GetAI(GameObject* go) const + { + return new go_suppression_deviceAI(go); + } +}; + void AddSC_boss_broodlord() { new boss_broodlord(); + new go_suppression_device(); }