From 7acf0b568ffd4a077b8ccb21f5ec65624b0990db Mon Sep 17 00:00:00 2001 From: offl <11556157+offl@users.noreply.github.com> Date: Sat, 11 Apr 2026 12:13:44 +0300 Subject: [PATCH] Scripts/Serpentshrine Cavern: Rewrite Morogrim (#31733) (cherry picked from commit 355e2ef0dcece565f717bce09580826162db8b64) --- ...026_06_30_18_world_2026_04_11_00_world.sql | 53 ++ .../boss_morogrim_tidewalker.cpp | 499 ++++++++++-------- 2 files changed, 318 insertions(+), 234 deletions(-) create mode 100644 sql/updates/world/master/2026_06_30_18_world_2026_04_11_00_world.sql diff --git a/sql/updates/world/master/2026_06_30_18_world_2026_04_11_00_world.sql b/sql/updates/world/master/2026_06_30_18_world_2026_04_11_00_world.sql new file mode 100644 index 0000000000..f336f69ace --- /dev/null +++ b/sql/updates/world/master/2026_06_30_18_world_2026_04_11_00_world.sql @@ -0,0 +1,53 @@ +-- Morogrim +UPDATE `creature_template` SET `speed_run` = 2.14286, `BaseAttackTime` = 1600 WHERE `entry` = 21213; +UPDATE `creature_model_info` SET `BoundingRadius` = 6.315, `CombatReach` = 6 WHERE `DisplayID` = 20739; + +UPDATE `creature_text` SET `Type` = 41 WHERE `CreatureID` = 21213 AND `GroupID` IN (5,7); + +UPDATE `creature` SET `position_x` = 370.829, `position_y` = -723.939, `position_z` = -14.005, `orientation` = 2.93215 WHERE `id` = 21213; + +-- Murlocs +DELETE FROM `spell_target_position` WHERE `ID` IN (37766,37923,37925,37926,37927,39813,39814,39815,39816,39817,37772,37928,37929,37931,37932,39818,39819,39820,39821,39822); +INSERT INTO `spell_target_position` (`ID`, `EffectIndex`, `MapID`, `PositionX`, `PositionY`, `PositionZ`, `Orientation`, `VerifiedBuild`) VALUES +(37766,0,548,266,-707,-2.91667,5.34071,0), +(37925,0,548,260,-712,-2.91667,5.34071,0), +(37927,0,548,254,-719,-2.91667,5.34071,0), +(39814,0,548,260,-704,-2.91667,5.11381,0), +(39816,0,548,253,-707,-2.91667,5.2709,0), +(39817,0,548,250,-708,-2.91667,5.14872,0), + +(37928,0,548,528,-699,-6.91667,3.9968,0), +(37931,0,548,534,-706,-6.91667,3.9968,0), +(39818,0,548,540,-700,-6.91667,4.32842,0), +(39820,0,548,535,-695,-6.91667,4.01426,0), +(39821,0,548,533,-691,-6.91667,4.31096,0), +(39822,0,548,529,-691,-6.91667,4.31096,0); + +UPDATE `creature_template` SET `speed_walk` = 1.6, `speed_run` = 1.42857 WHERE `entry` = 21920; + +DELETE FROM `smart_scripts` WHERE `entryorguid` = 21920 AND `source_type` = 0; +INSERT INTO `smart_scripts` (`entryorguid`,`source_type`,`id`,`link`,`event_type`,`event_phase_mask`,`event_chance`,`event_flags`,`event_param1`,`event_param2`,`event_param3`,`event_param4`,`event_param5`,`action_type`,`action_param1`,`action_param2`,`action_param3`,`action_param4`,`action_param5`,`action_param6`,`target_type`,`target_param1`,`target_param2`,`target_param3`,`target_param4`,`target_x`,`target_y`,`target_z`,`target_o`,`comment`) VALUES +(21920,0,0,0,37,0,100,0,0,0,0,0,0,116,2,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Tidewalker Lurker - On AI Initialize - Set Corpse Delay"), +(21920,0,1,0,0,0,100,0,5000,10000,5000,10000,0,11,41932,0,0,0,0,0,2,0,0,0,0,0,0,0,0,"Tidewalker Lurker - In Combat - Cast 'Carnivorous Bite'"); + +-- Watery Grave (first is sniffed, other copied from Water Globule spells) +UPDATE `spell_target_position` SET `PositionX` = 334, `PositionY` = -728, `PositionZ` = -14, `Orientation` = 0, `VerifiedBuild` = 26365 WHERE `ID` = 37850; +UPDATE `spell_target_position` SET `PositionX` = 366, `PositionY` = -736, `PositionZ` = -14, `Orientation` = 2.513274 WHERE `ID` = 38023; +UPDATE `spell_target_position` SET `PositionX` = 366, `PositionY` = -709, `PositionZ` = -14, `Orientation` = 2.513274 WHERE `ID` = 38024; +UPDATE `spell_target_position` SET `PositionX` = 372, `PositionY` = -690, `PositionZ` = -14, `Orientation` = 4.258604 WHERE `ID` = 38025; + +-- Water Globule +UPDATE `spell_target_position` SET `PositionX` = 334, `PositionY` = -728, `PositionZ` = -14, `Orientation` = 0, `VerifiedBuild` = 26365 WHERE `ID` = 37854; +UPDATE `spell_target_position` SET `PositionX` = 366, `PositionY` = -736, `PositionZ` = -14, `Orientation` = 2.513274, `VerifiedBuild` = 26365 WHERE `ID` = 37858; +UPDATE `spell_target_position` SET `PositionX` = 366, `PositionY` = -709, `PositionZ` = -14, `Orientation` = 2.513274, `VerifiedBuild` = 26365 WHERE `ID` = 37860; +UPDATE `spell_target_position` SET `PositionX` = 372, `PositionY` = -690, `PositionZ` = -14, `Orientation` = 4.258604, `VerifiedBuild` = 26365 WHERE `ID` = 37861; + +UPDATE `creature_template` SET `speed_walk` = 0.4, `speed_run` = 0.285714 WHERE `entry` = 21913; + +-- Spell scripts +DELETE FROM `spell_script_names` WHERE `ScriptName` IN ( +'spell_morogrim_tidewalker_watery_grave', +'spell_morogrim_tidewalker_summon_water_globules'); +INSERT INTO `spell_script_names` (`spell_id`, `ScriptName`) VALUES +(38028, 'spell_morogrim_tidewalker_watery_grave'), +(37866, 'spell_morogrim_tidewalker_summon_water_globules'); diff --git a/src/server/scripts/Outland/CoilfangReservoir/SerpentShrine/boss_morogrim_tidewalker.cpp b/src/server/scripts/Outland/CoilfangReservoir/SerpentShrine/boss_morogrim_tidewalker.cpp index c9736fcacb..95cce958f0 100644 --- a/src/server/scripts/Outland/CoilfangReservoir/SerpentShrine/boss_morogrim_tidewalker.cpp +++ b/src/server/scripts/Outland/CoilfangReservoir/SerpentShrine/boss_morogrim_tidewalker.cpp @@ -15,117 +15,189 @@ * with this program. If not, see . */ -/* ScriptData -SDName: Boss_Morogrim_Tidewalker -SD%Complete: 90 -SDComment: Water globules don't explode properly, remove hacks -SDCategory: Coilfang Resevoir, Serpent Shrine Cavern -EndScriptData */ +/* + * Combat timers requires to be revisited + * Everything requires sniff verification, especially Water Globule + */ #include "ScriptMgr.h" -#include "InstanceScript.h" -#include "Map.h" +#include "Containers.h" #include "ScriptedCreature.h" #include "serpent_shrine.h" -#include "TemporarySummon.h" +#include "SpellInfo.h" +#include "SpellScript.h" -enum Yells +enum MorogrimTexts { - // Yell SAY_AGGRO = 0, SAY_SUMMON = 1, SAY_SUMMON_BUBL = 2, SAY_SLAY = 3, SAY_DEATH = 4, - // Emotes EMOTE_WATERY_GRAVE = 5, EMOTE_EARTHQUAKE = 6, - EMOTE_WATERY_GLOBULES = 7 + EMOTE_WATER_GLOBULES = 7 }; -enum Spells +enum MorogrimSpells { - SPELL_TIDAL_WAVE = 37730, - SPELL_WATERY_GRAVE = 38049, - SPELL_EARTHQUAKE = 37764, - SPELL_WATERY_GRAVE_EXPLOSION = 37852, + // Passive + SPELL_DOUBLE_ATTACK = 18943, - SPELL_WATERY_GRAVE_1 = 38023, - SPELL_WATERY_GRAVE_2 = 38024, - SPELL_WATERY_GRAVE_3 = 38025, - SPELL_WATERY_GRAVE_4 = 37850, + // Combat + SPELL_TIDAL_WAVE = 37730, + SPELL_EARTHQUAKE = 37764, + SPELL_WATERY_GRAVE = 38028, + SPELL_SUMMON_WATER_GLOBULES = 37866, + + SPELL_SUMMON_MURLOC_A1 = 37766, + SPELL_SUMMON_MURLOC_A2 = 37923, + SPELL_SUMMON_MURLOC_A3 = 37925, + SPELL_SUMMON_MURLOC_A4 = 37926, + SPELL_SUMMON_MURLOC_A5 = 37927, + SPELL_SUMMON_MURLOC_A6 = 39813, + SPELL_SUMMON_MURLOC_A7 = 39814, + SPELL_SUMMON_MURLOC_A8 = 39815, + SPELL_SUMMON_MURLOC_A9 = 39816, + SPELL_SUMMON_MURLOC_A10 = 39817, + + SPELL_SUMMON_MURLOC_B1 = 37772, + SPELL_SUMMON_MURLOC_B2 = 37928, + SPELL_SUMMON_MURLOC_B3 = 37929, + SPELL_SUMMON_MURLOC_B4 = 37931, + SPELL_SUMMON_MURLOC_B5 = 37932, + SPELL_SUMMON_MURLOC_B6 = 39818, + SPELL_SUMMON_MURLOC_B7 = 39819, + SPELL_SUMMON_MURLOC_B8 = 39820, + SPELL_SUMMON_MURLOC_B9 = 39821, + SPELL_SUMMON_MURLOC_B10 = 39822, + + // Water Globule + SPELL_WATER_GLOBULE_EXPLODE = 37871, + SPELL_WATER_GLOBULE_NEW_TARGET = 39848, + + // Scripts + SPELL_WATERY_GRAVE_TELEPORT_1 = 37850, + SPELL_WATERY_GRAVE_TELEPORT_2 = 38023, + SPELL_WATERY_GRAVE_TELEPORT_3 = 38024, + SPELL_WATERY_GRAVE_TELEPORT_4 = 38025, SPELL_SUMMON_WATER_GLOBULE_1 = 37854, SPELL_SUMMON_WATER_GLOBULE_2 = 37858, SPELL_SUMMON_WATER_GLOBULE_3 = 37860, - SPELL_SUMMON_WATER_GLOBULE_4 = 37861, - - // Water Globule - SPELL_GLOBULE_EXPLOSION = 37871 + SPELL_SUMMON_WATER_GLOBULE_4 = 37861 }; -enum Creatures +enum MorogrimEvents { - // Creatures - NPC_WATER_GLOBULE = 21913, - NPC_TIDEWALKER_LURKER = 21920 + EVENT_TIDAL_WAVE = 1, + EVENT_EARTHQUAKE, + EVENT_WATERY_GRAVE, + EVENT_SUMMON_WATER_GLOBULES }; -float MurlocCords[10][4] = +static constexpr std::array SummonMurlocsNorthSpells = { - {424.36f, -715.4f, -7.14f, 0.124f}, - {425.13f, -719.3f, -7.14f, 0.124f}, - {425.05f, -724.23f, -7.14f, 0.124f}, - {424.91f, -728.68f, -7.14f, 0.124f}, - {424.84f, -732.18f, -7.14f, 0.124f}, - {321.05f, -734.2f, -13.15f, 0.124f}, - {321.05f, -729.4f, -13.15f, 0.124f}, - {321.05f, -724.03f, -13.15f, 0.124f}, - {321.05f, -718.73f, -13.15f, 0.124f}, - {321.05f, -714.24f, -13.15f, 0.124f} + SPELL_SUMMON_MURLOC_A1, + SPELL_SUMMON_MURLOC_A3, + SPELL_SUMMON_MURLOC_A5, + SPELL_SUMMON_MURLOC_A7, + SPELL_SUMMON_MURLOC_A9, + SPELL_SUMMON_MURLOC_A10 }; -//Morogrim Tidewalker AI +static constexpr std::array SummonMurlocsSouthSpells = +{ + SPELL_SUMMON_MURLOC_B2, + SPELL_SUMMON_MURLOC_B4, + SPELL_SUMMON_MURLOC_B6, + SPELL_SUMMON_MURLOC_B8, + SPELL_SUMMON_MURLOC_B9, + SPELL_SUMMON_MURLOC_B10 +}; + +static constexpr std::array WateryGraveTeleportSpells = +{ + SPELL_WATERY_GRAVE_TELEPORT_1, + SPELL_WATERY_GRAVE_TELEPORT_2, + SPELL_WATERY_GRAVE_TELEPORT_3, + SPELL_WATERY_GRAVE_TELEPORT_4 +}; + +static constexpr std::array SummonWaterGlobulesSpells = +{ + SPELL_SUMMON_WATER_GLOBULE_1, + SPELL_SUMMON_WATER_GLOBULE_2, + SPELL_SUMMON_WATER_GLOBULE_3, + SPELL_SUMMON_WATER_GLOBULE_4 +}; + +// 21213 - Morogrim Tidewalker struct boss_morogrim_tidewalker : public BossAI { - boss_morogrim_tidewalker(Creature* creature) : BossAI(creature, BOSS_MOROGRIM_TIDEWALKER) - { - Initialize(); - Playercount = 0; - counter = 0; - } - - void Initialize() - { - TidalWave_Timer = 10000; - WateryGrave_Timer = 30000; - Earthquake_Timer = 40000; - WateryGlobules_Timer = 0; - globulespell[0] = SPELL_SUMMON_WATER_GLOBULE_1; - globulespell[1] = SPELL_SUMMON_WATER_GLOBULE_2; - globulespell[2] = SPELL_SUMMON_WATER_GLOBULE_3; - globulespell[3] = SPELL_SUMMON_WATER_GLOBULE_4; - - Earthquake = false; - Phase2 = false; - } - - uint32 TidalWave_Timer; - uint32 WateryGrave_Timer; - uint32 Earthquake_Timer; - uint32 WateryGlobules_Timer; - uint32 globulespell[4]; - int8 Playercount; - int8 counter; - - bool Earthquake; - bool Phase2; + boss_morogrim_tidewalker(Creature* creature) : BossAI(creature, BOSS_MOROGRIM_TIDEWALKER), _isSecondPhaseStarted(false) { } void Reset() override { - Initialize(); - _Reset(); + + _isSecondPhaseStarted = false; + + DoCastSelf(SPELL_DOUBLE_ATTACK); + } + + void JustEngagedWith(Unit* who) override + { + BossAI::JustEngagedWith(who); + + Talk(SAY_AGGRO); + + events.ScheduleEvent(EVENT_TIDAL_WAVE, 10s, 15s); + events.ScheduleEvent(EVENT_EARTHQUAKE, 35s, 45s); + events.ScheduleEvent(EVENT_WATERY_GRAVE, 20s, 25s); + } + + void OnSpellCast(SpellInfo const* spellInfo) override + { + switch (spellInfo->Id) + { + case SPELL_EARTHQUAKE: + Talk(EMOTE_EARTHQUAKE); + Talk(SAY_SUMMON); + + for (uint32 spell : SummonMurlocsNorthSpells) + DoCastSelf(spell, true); + + for (uint32 spell : SummonMurlocsSouthSpells) + DoCastSelf(spell, true); + + break; + case SPELL_WATERY_GRAVE: + Talk(EMOTE_WATERY_GRAVE); + break; + case SPELL_SUMMON_WATER_GLOBULES: + Talk(EMOTE_WATER_GLOBULES); + Talk(SAY_SUMMON_BUBL); + break; + default: + break; + } + } + + void DamageTaken(Unit* /*attacker*/, uint32& damage, DamageEffectType /*damageType*/, SpellInfo const* /*spellInfo = nullptr*/) override + { + if (!_isSecondPhaseStarted && me->HealthBelowPctDamaged(25, damage)) + { + _isSecondPhaseStarted = true; + events.ScheduleEvent(EVENT_SUMMON_WATER_GLOBULES, 0s); + events.CancelEvent(EVENT_WATERY_GRAVE); + } + } + + void JustReachedHome() override + { + _JustReachedHome(); + DoCastSelf(SPELL_DOUBLE_ATTACK); } void KilledUnit(Unit* /*victim*/) override @@ -135,197 +207,154 @@ struct boss_morogrim_tidewalker : public BossAI void JustDied(Unit* /*killer*/) override { - Talk(SAY_DEATH); - _JustDied(); - } - - void JustEngagedWith(Unit* who) override - { - Playercount = me->GetMap()->GetPlayers().size(); - Talk(SAY_AGGRO); - _JustEngagedWith(who); - } - - void ApplyWateryGrave(Unit* player, uint8 i) - { - switch (i) - { - case 0: player->CastSpell(player, SPELL_WATERY_GRAVE_1, true); break; - case 1: player->CastSpell(player, SPELL_WATERY_GRAVE_2, true); break; - case 2: player->CastSpell(player, SPELL_WATERY_GRAVE_3, true); break; - case 3: player->CastSpell(player, SPELL_WATERY_GRAVE_4, true); break; - } + Talk(SAY_DEATH); } void UpdateAI(uint32 diff) override { - //Return since we have no target if (!UpdateVictim()) return; - //Earthquake_Timer - if (Earthquake_Timer <= diff) + events.Update(diff); + + if (me->HasUnitState(UNIT_STATE_CASTING)) + return; + + while (uint32 eventId = events.ExecuteEvent()) { - if (!Earthquake) + switch (eventId) { - DoCastVictim(SPELL_EARTHQUAKE); - Earthquake = true; - Earthquake_Timer = 10000; + case EVENT_TIDAL_WAVE: + DoCastSelf(SPELL_TIDAL_WAVE, TRIGGERED_IGNORE_SPELL_AND_CATEGORY_CD); + events.Repeat(20s, 25s); + break; + case EVENT_EARTHQUAKE: + DoCastSelf(SPELL_EARTHQUAKE, TRIGGERED_IGNORE_SPELL_AND_CATEGORY_CD); + events.Repeat(50s, 60s); + break; + case EVENT_WATERY_GRAVE: + DoCastSelf(SPELL_WATERY_GRAVE, TRIGGERED_IGNORE_SPELL_AND_CATEGORY_CD); + events.Repeat(30s, 35s); + break; + case EVENT_SUMMON_WATER_GLOBULES: + DoCastSelf(SPELL_SUMMON_WATER_GLOBULES); + events.Repeat(40s, 50s); + break; + default: + break; } - else - { - Talk(SAY_SUMMON); - for (uint8 i = 0; i < 10; ++i) - { - if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0)) - if (Creature* Murloc = me->SummonCreature(NPC_TIDEWALKER_LURKER, MurlocCords[i][0], MurlocCords[i][1], MurlocCords[i][2], MurlocCords[i][3], TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 10s)) - Murloc->AI()->AttackStart(target); - } - Talk(EMOTE_EARTHQUAKE); - Earthquake = false; - Earthquake_Timer = 40000 + rand32() % 5000; - } - } else Earthquake_Timer -= diff; - - //TidalWave_Timer - if (TidalWave_Timer <= diff) - { - DoCastVictim(SPELL_TIDAL_WAVE); - TidalWave_Timer = 20000; - } else TidalWave_Timer -= diff; - - if (!Phase2) - { - //WateryGrave_Timer - if (WateryGrave_Timer <= diff) - { - //Teleport 4 players under the waterfalls - GuidSet targets; - GuidSet::const_iterator itr = targets.begin(); - for (uint8 i = 0; i < 4; ++i) - { - counter = 0; - Unit* target; - do - { - target = SelectTarget(SelectTargetMethod::Random, 1, 50, true); //target players only - if (counter < Playercount) - break; - if (target) - itr = targets.find(target->GetGUID()); - ++counter; - } while (itr != targets.end()); - - if (target) - { - targets.insert(target->GetGUID()); - ApplyWateryGrave(target, i); - } - } - - Talk(SAY_SUMMON_BUBL); - - Talk(EMOTE_WATERY_GRAVE); - WateryGrave_Timer = 30000; - } else WateryGrave_Timer -= diff; - - //Start Phase2 - if (HealthBelowPct(25)) - Phase2 = true; - } - else - { - //WateryGlobules_Timer - if (WateryGlobules_Timer <= diff) - { - GuidSet globules; - GuidSet::const_iterator itr = globules.begin(); - for (uint8 g = 0; g < 4; g++) //one unit can't cast more than one spell per update, so some players have to cast for us XD - { - counter = 0; - Unit* pGlobuleTarget; - do - { - pGlobuleTarget = SelectTarget(SelectTargetMethod::Random, 0, 50, true); - if (pGlobuleTarget) - itr = globules.find(pGlobuleTarget->GetGUID()); - if (counter > Playercount) - break; - ++counter; - } while (itr != globules.end()); - - if (pGlobuleTarget) - { - globules.insert(pGlobuleTarget->GetGUID()); - pGlobuleTarget->CastSpell(pGlobuleTarget, globulespell[g], true); - } - } - Talk(EMOTE_WATERY_GLOBULES); - WateryGlobules_Timer = 25000; - } else WateryGlobules_Timer -= diff; + if (me->HasUnitState(UNIT_STATE_CASTING)) + return; } } + +private: + bool _isSecondPhaseStarted; }; +// 21913 - Water Globule struct npc_water_globule : public ScriptedAI { - npc_water_globule(Creature* creature) : ScriptedAI(creature) + using ScriptedAI::ScriptedAI; + + void JustAppeared() override { - Initialize(); + DoZoneInCombat(); + + _scheduler + .Schedule(0s, [this](TaskContext& task) + { + ResetThreatList(); + DoCastSelf(SPELL_WATER_GLOBULE_NEW_TARGET, { SPELLVALUE_MAX_TARGETS, 1 }); + task.Repeat(7s, 10s); + }) + .Schedule(0s, [this](TaskContext& task) + { + if (me->IsWithinDistInMap(me->GetVictim(), 5.0f)) + DoCastVictim(SPELL_WATER_GLOBULE_EXPLODE); + task.Repeat(1200ms); + }); } - void Initialize() + void SpellHitTarget(WorldObject* target, SpellInfo const* spellInfo) override { - Check_Timer = 1000; - } - - uint32 Check_Timer; - - void Reset() override - { - Initialize(); - - me->SetFaction(FACTION_MONSTER); - } - - void JustEngagedWith(Unit* /*who*/) override { } - - void MoveInLineOfSight(Unit* who) override - - { - if (!who || me->GetVictim()) - return; - - if (me->CanCreatureAttack(who)) + switch (spellInfo->Id) { - //no attack radius check - it attacks the first target that moves in his los - //who->RemoveSpellsCausingAura(SPELL_AURA_MOD_STEALTH); - AttackStart(who); + case SPELL_WATER_GLOBULE_NEW_TARGET: + if (Unit* unit = target->ToUnit()) + AddThreat(unit, 3000000.0f); + break; + case SPELL_WATER_GLOBULE_EXPLODE: + me->DespawnOrUnsummon(); + break; + default: + break; } } void UpdateAI(uint32 diff) override { - //Return since we have no target if (!UpdateVictim()) return; - if (Check_Timer <= diff) - { - if (me->IsWithinDistInMap(me->GetVictim(), 5)) - { - DoCastVictim(SPELL_GLOBULE_EXPLOSION); + _scheduler.Update(diff); + } - //despawn - me->DespawnOrUnsummon(); - return; - } - Check_Timer = 500; - } else Check_Timer -= diff; +private: + TaskScheduler _scheduler; +}; - //do NOT deal any melee damage to the target. +// 38028 - Watery Grave +class spell_morogrim_tidewalker_watery_grave : public SpellScript +{ +public: + bool Validate(SpellInfo const* /*spellInfo*/) override + { + return ValidateSpellInfo(WateryGraveTeleportSpells); + } + + void FilterTargets(std::list& targets) + { + targets.remove(GetCaster()->GetVictim()); + Trinity::Containers::RandomResize(targets, 4); + } + + void HandleDummy(SpellEffIndex /*effIndex*/) + { + GetCaster()->CastSpell(GetHitUnit(), WateryGraveTeleportSpells[std::min(_targetCount, WateryGraveTeleportSpells.size() - 1)], true); + _targetCount++; + } + + void Register() override + { + OnObjectAreaTargetSelect += SpellObjectAreaTargetSelectFn(spell_morogrim_tidewalker_watery_grave::FilterTargets, EFFECT_0, TARGET_UNIT_SRC_AREA_ENEMY); + OnEffectHitTarget += SpellEffectFn(spell_morogrim_tidewalker_watery_grave::HandleDummy, EFFECT_0, SPELL_EFFECT_DUMMY); + } + +private: + std::size_t _targetCount = 0; +}; + +// 37866 - Summon Water Globules +class spell_morogrim_tidewalker_summon_water_globules : public SpellScript +{ + bool Validate(SpellInfo const* /*spellInfo*/) override + { + return ValidateSpellInfo(SummonWaterGlobulesSpells); + } + + void HandleDummy(SpellEffIndex /*effIndex*/) + { + Unit* caster = GetCaster(); + for (uint32 spell : SummonWaterGlobulesSpells) + caster->CastSpell(caster, spell, true); + } + + void Register() override + { + OnEffectHit += SpellEffectFn(spell_morogrim_tidewalker_summon_water_globules::HandleDummy, EFFECT_0, SPELL_EFFECT_DUMMY); } }; @@ -333,4 +362,6 @@ void AddSC_boss_morogrim_tidewalker() { RegisterSerpentshrineCavernCreatureAI(boss_morogrim_tidewalker); RegisterSerpentshrineCavernCreatureAI(npc_water_globule); + RegisterSpellScript(spell_morogrim_tidewalker_watery_grave); + RegisterSpellScript(spell_morogrim_tidewalker_summon_water_globules); }