TrinityCore
Loading...
Searching...
No Matches
boss_kologarn.cpp
Go to the documentation of this file.
1/*
2 * This file is part of the TrinityCore Project. See AUTHORS file for Copyright information
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms of the GNU General Public License as published by the
6 * Free Software Foundation; either version 2 of the License, or (at your
7 * option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12 * more details.
13 *
14 * You should have received a copy of the GNU General Public License along
15 * with this program. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18#include "ScriptMgr.h"
19#include "InstanceScript.h"
20#include "Map.h"
21#include "MotionMaster.h"
22#include "ObjectAccessor.h"
23#include "Player.h"
24#include "ScriptedCreature.h"
25#include "SpellAuraEffects.h"
26#include "SpellScript.h"
27#include "ulduar.h"
28#include "Vehicle.h"
29
30/* ScriptData
31SDName: boss_kologarn
32SD%Complete: 90
33SDComment: @todo Achievements
34SDCategory: Ulduar
35EndScriptData */
36
65
71
86
99
101{
102 public:
103 boss_kologarn() : CreatureScript("boss_kologarn") { }
104
105 struct boss_kologarnAI : public BossAI
106 {
116
117 bool left, right;
119
120 void JustEngagedWith(Unit* who) override
121 {
123
130
131 if (Vehicle* vehicle = me->GetVehicleKit())
132 for (uint8 i = 0; i < 2; ++i)
133 if (Unit* arm = vehicle->GetPassenger(i))
134 DoZoneInCombat(arm->ToCreature());
135
137 }
138
139 void Reset() override
140 {
141 _Reset();
144 }
145
146 void JustDied(Unit* /*killer*/) override
147 {
152 me->SetCorpseDelay(604800); // Prevent corpse from despawning.
153 _JustDied();
154 }
155
156 void KilledUnit(Unit* who) override
157 {
158 if (who->GetTypeId() == TYPEID_PLAYER)
159 Talk(SAY_SLAY);
160 }
161
162 void PassengerBoarded(Unit* who, int8 /*seatId*/, bool apply) override
163 {
164 bool isEncounterInProgress = instance->GetBossState(DATA_KOLOGARN) == IN_PROGRESS;
165 if (who->GetEntry() == NPC_LEFT_ARM)
166 {
167 left = apply;
168 if (!apply && isEncounterInProgress)
169 {
172 }
173 }
174
175 else if (who->GetEntry() == NPC_RIGHT_ARM)
176 {
177 right = apply;
178 if (!apply && isEncounterInProgress)
179 {
182 }
183 }
184
185 if (!isEncounterInProgress)
186 return;
187
188 if (!apply)
189 {
191
192 if (Creature* rubbleStalker = who->FindNearestCreature(NPC_RUBBLE_STALKER, 70.0f))
193 {
194 rubbleStalker->CastSpell(rubbleStalker, SPELL_FALLING_RUBBLE, true);
195 rubbleStalker->CastSpell(rubbleStalker, SPELL_SUMMON_RUBBLE, true);
197 }
198
199 if (!right && !left)
201
203 }
204 else
205 {
208 }
209 }
210
211 void JustSummoned(Creature* summon) override
212 {
213 BossAI::JustSummoned(summon);
214 switch (summon->GetEntry())
215 {
218 break;
221 break;
222 case NPC_RUBBLE:
223 summons.Summon(summon);
224 [[fallthrough]];
225 default:
226 return;
227 }
228
229 summon->CastSpell(summon, SPELL_FOCUSED_EYEBEAM_PERIODIC, true);
230 summon->CastSpell(summon, SPELL_FOCUSED_EYEBEAM_VISUAL, true);
232
233 // Victim gets 67351
234 if (!eyebeamTarget.IsEmpty())
235 {
236 if (Unit* target = ObjectAccessor::GetUnit(*summon, eyebeamTarget))
237 {
238 summon->Attack(target, false);
239 summon->GetMotionMaster()->MoveChase(target);
240 }
241 }
242 }
243
244 void UpdateAI(uint32 diff) override
245 {
246 if (!UpdateVictim())
247 return;
248
249 events.Update(diff);
250
252 return;
253
254 while (uint32 eventId = events.ExecuteEvent())
255 {
256 switch (eventId)
257 {
262 break;
263 case EVENT_SWEEP:
264 if (left)
267 break;
268 case EVENT_SMASH:
269 if (left && right)
271 else if (left || right)
274 break;
278 break;
279 case EVENT_ENRAGE:
282 break;
285 {
286 if (Vehicle* vehicle = me->GetVehicleKit())
287 {
288 int8 seat = eventId == EVENT_RESPAWN_LEFT_ARM ? 0 : 1;
290 vehicle->InstallAccessory(entry, seat, true, TEMPSUMMON_MANUAL_DESPAWN, 0);
291 }
292 break;
293 }
294 case EVENT_STONE_GRIP:
295 {
296 if (right)
297 {
301 }
303 break;
304 }
306 if (Unit* eyebeamTargetUnit = SelectTarget(SelectTargetMethod::MaxDistance, 0, 0, true))
307 {
308 eyebeamTarget = eyebeamTargetUnit->GetGUID();
310 }
312 break;
313 }
314
316 return;
317 }
318
320 }
321 };
322
323 CreatureAI* GetAI(Creature* creature) const override
324 {
325 return GetUlduarAI<boss_kologarnAI>(creature);
326 }
327};
328
329// 63633 - Summon Rubble
331{
332 public:
333 spell_ulduar_rubble_summon() : SpellScriptLoader("spell_ulduar_rubble_summon") { }
334
336 {
338
339 void HandleScript(SpellEffIndex /*effIndex*/)
340 {
341 Unit* caster = GetCaster();
342 if (!caster)
343 return;
344
346 uint32 spellId = GetEffectValue();
347 for (uint8 i = 0; i < 5; ++i)
348 caster->CastSpell(caster, spellId, originalCaster);
349 }
350
355 };
356
357 SpellScript* GetSpellScript() const override
358 {
360 }
361};
362
363// predicate function to select non main tank target
365{
366 public:
367 StoneGripTargetSelector(Creature* me, Unit const* victim) : _me(me), _victim(victim) { }
368
370 {
371 if (target == _victim && _me->GetThreatManager().GetThreatListPlayerCount() > 1)
372 return true;
373
374 if (target->GetTypeId() != TYPEID_PLAYER)
375 return true;
376
377 return false;
378 }
379
381 Unit const* _victim;
382};
383
384// 62166, 63981 - Stone Grip
386{
387 public:
388 spell_ulduar_stone_grip_cast_target() : SpellScriptLoader("spell_ulduar_stone_grip_cast_target") { }
389
391 {
393
394 bool Load() override
395 {
396 if (GetCaster()->GetTypeId() != TYPEID_UNIT)
397 return false;
398 return true;
399 }
400
401 void FilterTargetsInitial(std::list<WorldObject*>& unitList)
402 {
403 // Remove "main tank" and non-player targets
404 unitList.remove_if(StoneGripTargetSelector(GetCaster()->ToCreature(), GetCaster()->GetThreatManager().GetCurrentVictim()));
405 // Maximum affected targets per difficulty mode
406 uint32 maxTargets = 1;
407 if (GetSpellInfo()->Id == 63981)
408 maxTargets = 3;
409
410 // Return a random amount of targets based on maxTargets
411 while (maxTargets < unitList.size())
412 {
413 std::list<WorldObject*>::iterator itr = unitList.begin();
414 advance(itr, urand(0, unitList.size()-1));
415 unitList.erase(itr);
416 }
417
418 // For subsequent effects
419 _unitList = unitList;
420 }
421
422 void FillTargetsSubsequential(std::list<WorldObject*>& unitList)
423 {
424 unitList = _unitList;
425 }
426
433
434 private:
435 // Shared between effects
436 std::list<WorldObject*> _unitList;
437 };
438
439 SpellScript* GetSpellScript() const override
440 {
442 }
443};
444
445// 65594 - Cancel Stone Grip
447{
448 public:
449 spell_ulduar_cancel_stone_grip() : SpellScriptLoader("spell_ulduar_cancel_stone_grip") { }
450
452 {
454
455 void HandleScript(SpellEffIndex /*effIndex*/)
456 {
457 Unit* target = GetHitUnit();
458 if (!target || !target->GetVehicle())
459 return;
460
461 SpellEffIndex effectIndexToCancel = EFFECT_0;
462 if (target->GetMap()->Is25ManRaid())
463 effectIndexToCancel = EFFECT_1;
464
465 target->RemoveAura(GetEffectInfo(effectIndexToCancel).CalcValue());
466 }
467
472 };
473
474 SpellScript* GetSpellScript() const override
475 {
477 }
478};
479
480// 64702 - Squeezed Lifeless
482{
483 public:
484 spell_ulduar_squeezed_lifeless() : SpellScriptLoader("spell_ulduar_squeezed_lifeless") { }
485
487 {
489
491 {
492 if (!GetHitPlayer() || !GetHitPlayer()->GetVehicle())
493 return;
494
497 Position pos;
498 pos.m_positionX = 1756.25f + irand(-3, 3);
499 pos.m_positionY = -8.3f + irand(-3, 3);
500 pos.m_positionZ = 448.8f;
501 pos.SetOrientation(float(M_PI));
503 GetHitPlayer()->ExitVehicle(&pos);
505 }
506
511 };
512
513 SpellScript* GetSpellScript() const override
514 {
516 }
517};
518
519// 64224, 64225 - Stone Grip Absorb
521{
522 public:
523 spell_ulduar_stone_grip_absorb() : SpellScriptLoader("spell_ulduar_stone_grip_absorb") { }
524
526 {
528
531 void OnRemove(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
532 {
533 if (GetTargetApplication()->GetRemoveMode() != AURA_REMOVE_BY_ENEMY_SPELL)
534 return;
535
536 if (!GetOwner()->ToCreature())
537 return;
538
539 uint32 rubbleStalkerEntry = (GetOwner()->GetMap()->GetDifficulty() == DUNGEON_DIFFICULTY_NORMAL ? 33809 : 33942);
540 Creature* rubbleStalker = GetOwner()->FindNearestCreature(rubbleStalkerEntry, 200.0f, true);
541 if (rubbleStalker)
542 rubbleStalker->CastSpell(rubbleStalker, SPELL_STONE_GRIP_CANCEL, true);
543 }
544
549 };
550
551 AuraScript* GetAuraScript() const override
552 {
554 }
555};
556
557// 62056, 63985 - Stone Grip
559{
560 public:
561 spell_ulduar_stone_grip() : SpellScriptLoader("spell_ulduar_stone_grip") { }
562
564 {
566
567 void OnRemoveStun(AuraEffect const* aurEff, AuraEffectHandleModes /*mode*/)
568 {
569 if (Player* owner = GetOwner()->ToPlayer())
570 owner->RemoveAurasDueToSpell(aurEff->GetAmount());
571 }
572
573 void OnRemoveVehicle(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
574 {
576 Unit* caster = GetCaster();
577 if (!caster)
578 return;
579
580 Position exitPosition;
581 exitPosition.m_positionX = 1750.0f;
582 exitPosition.m_positionY = -7.5f + frand(-3.0f, 3.0f);
583 exitPosition.m_positionZ = 457.9322f;
584
585 // Remove pending passengers before exiting vehicle - might cause an Uninstall
587 caster->_ExitVehicle(&exitPosition);
588 caster->RemoveAurasDueToSpell(GetId());
589
590 // Temporarily relocate player to vehicle exit dest serverside to send proper fall movement
591 // beats me why blizzard sends these 2 spline packets one after another instantly
592 Position oldPos = caster->GetPosition();
593 caster->Relocate(exitPosition);
594 caster->GetMotionMaster()->MoveFall();
595 caster->Relocate(oldPos);
596 }
597
603 };
604
605 AuraScript* GetAuraScript() const override
606 {
608 }
609};
610
611// 63720, 64004 - Stone Shout
613{
614 public:
615 spell_kologarn_stone_shout() : SpellScriptLoader("spell_kologarn_stone_shout") { }
616
618 {
620
621 void FilterTargets(std::list<WorldObject*>& targets)
622 {
623 targets.remove_if([](WorldObject* object) -> bool
624 {
625 if (object->GetTypeId() == TYPEID_PLAYER)
626 return false;
627
628 if (Creature* creature = object->ToCreature())
629 return !creature->IsPet();
630
631 return true;
632 });
633 }
634
639 };
640
641 SpellScript* GetSpellScript() const override
642 {
644 }
645};
646
647// 63342 - Focused Eyebeam Summon Trigger
675
#define M_PI
Definition Common.h:72
@ DUNGEON_DIFFICULTY_NORMAL
Definition DBCEnums.h:282
@ ACHIEVEMENT_TIMED_TYPE_EVENT
Definition DBCEnums.h:122
uint8_t uint8
Definition Define.h:135
int8_t int8
Definition Define.h:131
uint32_t uint32
Definition Define.h:133
@ IN_PROGRESS
@ TEMPSUMMON_MANUAL_DESPAWN
@ TYPEID_UNIT
Definition ObjectGuid.h:38
@ TYPEID_PLAYER
Definition ObjectGuid.h:39
Spells
Definition PlayerAI.cpp:32
float frand(float min, float max)
Definition Random.cpp:55
int32 irand(int32 min, int32 max)
Definition Random.cpp:35
uint32 urand(uint32 min, uint32 max)
Definition Random.cpp:42
SpellEffIndex
@ EFFECT_1
@ EFFECT_0
@ EFFECT_2
@ SPELL_EFFECT_SCRIPT_EFFECT
@ SPELL_EFFECT_INSTAKILL
@ SPELL_EFFECT_FORCE_CAST
@ TARGET_UNIT_SRC_AREA_ENEMY
@ AURA_REMOVE_BY_ENEMY_SPELL
AuraEffectHandleModes
@ AURA_EFFECT_HANDLE_REAL
@ SPELL_AURA_CONTROL_VEHICLE
@ SPELL_AURA_SCHOOL_ABSORB
@ SPELL_AURA_MOD_STUN
#define SpellEffectFn(F, I, N)
#define SpellObjectAreaTargetSelectFn(F, I, N)
#define AuraEffectRemoveFn(F, I, N, M)
@ REACT_PASSIVE
@ UNIT_FLAG_UNINTERACTIBLE
@ UNIT_STATE_ROOT
Definition Unit.h:230
@ UNIT_STATE_CASTING
Definition Unit.h:235
@ SAY_DEATH
@ SAY_AGGRO
@ SAY_GRAB_PLAYER
@ SAY_SHOCKWAVE
@ SAY_RIGHT_ARM_GONE
@ SAY_LEFT_ARM_GONE
@ EMOTE_STONE_GRIP
@ SAY_SLAY
@ SAY_BERSERK
@ SPELL_FOCUSED_EYEBEAM_VISUAL
@ SPELL_ARM_SWEEP
@ SPELL_ONE_ARM_SMASH
@ SPELL_PETRIFY_BREATH
@ SPELL_KOLOGARN_UNK_0
@ SPELL_FALLING_RUBBLE
@ SPELL_SUMMON_FOCUSED_EYEBEAM
@ SPELL_ARM_ENTER_VEHICLE
@ SPELL_STONE_GRIP
@ SPELL_STONE_GRIP_CANCEL
@ SPELL_TWO_ARM_SMASH
@ SPELL_ARM_ENTER_VISUAL
@ SPELL_ARM_DEAD_DAMAGE
@ SPELL_STONE_SHOUT
@ SPELL_FOCUSED_EYEBEAM_VISUAL_LEFT
@ SPELL_FOCUSED_EYEBEAM_PERIODIC
@ SPELL_KOLOGARN_REDUCE_PARRY
@ SPELL_BERSERK
@ SPELL_FOCUSED_EYEBEAM_VISUAL_RIGHT
@ SPELL_KOLOGARN_PACIFY
@ SPELL_SUMMON_RUBBLE
@ NPC_ARM_SWEEP_STALKER
@ NPC_RUBBLE_STALKER
void AddSC_boss_kologarn()
@ EVENT_RESPAWN_RIGHT_ARM
@ EVENT_ENRAGE
@ EVENT_INSTALL_ACCESSORIES
@ EVENT_STONE_GRIP
@ EVENT_SMASH
@ EVENT_RESPAWN_LEFT_ARM
@ EVENT_MELEE_CHECK
@ EVENT_NONE
@ EVENT_FOCUSED_EYEBEAM
@ EVENT_SWEEP
@ EVENT_STONE_SHOUT
Yells
int32 GetAmount() const
void PreventDefaultAction()
AuraApplication const * GetTargetApplication() const
HookList< EffectApplyHandler > AfterEffectRemove
WorldObject * GetOwner() const
Unit * GetCaster() const
Unit * GetTarget() const
HookList< EffectApplyHandler > OnEffectRemove
uint32 GetId() const
InstanceScript *const instance
void JustEngagedWith(Unit *who) override
void JustSummoned(Creature *summon) override
SummonList summons
EventMap events
void DoZoneInCombat(Creature *creature=nullptr)
bool UpdateVictim()
Creature *const me
Definition CreatureAI.h:82
void SetReactState(ReactStates st)
Definition Creature.h:119
void DespawnOrUnsummon(Milliseconds timeToDespawn=0s, Seconds forceRespawnTime=0s)
void SetCorpseDelay(uint32 delay, bool ignoreCorpseDecayRatio=false)
Definition Creature.h:89
void Update(uint32 time)
Definition EventMap.h:67
EventId ExecuteEvent()
Definition EventMap.cpp:73
void CancelEvent(EventId eventId)
Definition EventMap.cpp:151
void ScheduleEvent(EventId eventId, Milliseconds time, GroupIndex group=0u, PhaseIndex phase=0u)
Definition EventMap.cpp:36
virtual ObjectGuid GetGuidData(uint32 type) const override
EncounterState GetBossState(uint32 id) const
void DoStartTimedAchievement(AchievementCriteriaTimedTypes type, uint32 entry)
bool Is25ManRaid() const
Definition Map.cpp:4261
Difficulty GetDifficulty() const
Definition Map.h:412
void MoveChase(Unit *target, Optional< ChaseRange > dist={}, Optional< ChaseAngle > angle={})
void MoveTargetedHome()
void MoveFall(uint32 id=0)
static ObjectGuid const Empty
Definition ObjectGuid.h:140
bool IsEmpty() const
Definition ObjectGuid.h:172
void Clear()
Definition ObjectGuid.h:150
static Creature * ToCreature(Object *o)
Definition Object.h:186
TypeID GetTypeId() const
Definition Object.h:93
uint32 GetEntry() const
Definition Object.h:81
void UpdateObjectVisibility(bool forced=true) override
Definition Player.cpp:22297
Player * GetHitPlayer() const
Unit * GetCaster() const
void PreventHitDefaultEffect(SpellEffIndex effIndex)
Unit * GetHitUnit() const
int32 GetEffectValue() const
SpellEffectInfo const & GetEffectInfo() const
HookList< EffectHandler > OnEffectHitTarget
SpellInfo const * GetSpellInfo() const
HookList< ObjectAreaTargetSelectHandler > OnObjectAreaTargetSelect
StoneGripTargetSelector(Creature *me, Unit const *victim)
bool operator()(WorldObject *target)
void Summon(Creature const *summon)
uint32 GetThreatListPlayerCount(bool includeOffline=false) const
void DoMeleeAttackIfReady()
Definition UnitAI.cpp:54
SpellCastResult DoCastVictim(uint32 spellId, CastSpellExtraArgs const &args={})
Definition UnitAI.cpp:166
Unit * SelectTarget(SelectTargetMethod targetType, uint32 offset=0, float dist=0.0f, bool playerOnly=false, bool withTank=true, int32 aura=0)
Definition UnitAI.cpp:96
SpellCastResult DoCast(uint32 spellId)
Definition UnitAI.cpp:106
Definition Unit.h:769
bool IsWithinMeleeRange(Unit const *obj) const
Definition Unit.h:844
Vehicle * GetVehicle() const
Definition Unit.h:1737
void RemoveAura(AuraApplicationMap::iterator &i, AuraRemoveMode mode=AURA_REMOVE_BY_DEFAULT)
Definition Unit.cpp:3638
ThreatManager & GetThreatManager()
Definition Unit.h:1155
void SetControlled(bool apply, UnitState state)
Definition Unit.cpp:11256
MotionMaster * GetMotionMaster()
Definition Unit.h:1667
void _ExitVehicle(Position const *exitPosition=nullptr)
Definition Unit.cpp:12680
bool Attack(Unit *victim, bool meleeAttack)
Definition Unit.cpp:5535
void RemoveAurasDueToSpell(uint32 spellId, ObjectGuid casterGUID=ObjectGuid::Empty, uint8 reqEffMask=0, AuraRemoveMode removeMode=AURA_REMOVE_BY_DEFAULT)
Definition Unit.cpp:3784
Unit * GetVictim() const
Definition Unit.h:859
bool HasUnitState(const uint32 f) const
Definition Unit.h:876
void SetUnitFlag(UnitFlags flags)
Definition Unit.h:954
Vehicle * GetVehicleKit() const
Definition Unit.h:1735
void RemoveUnitFlag(UnitFlags flags)
Definition Unit.h:955
virtual void ExitVehicle(Position const *exitPosition=nullptr)
Definition Unit.cpp:12661
void RemovePendingEventsForPassenger(Unit *passenger)
Definition Vehicle.cpp:761
Map * GetMap() const
Definition Object.h:449
InstanceScript * GetInstanceScript() const
Definition Object.cpp:1087
SpellCastResult CastSpell(CastSpellTargetArg const &targets, uint32 spellId, CastSpellExtraArgs const &args={ })
Definition Object.cpp:2832
void DestroyForNearbyPlayers()
Definition Object.cpp:3449
Creature * FindNearestCreature(uint32 entry, float range, bool alive=true) const
Definition Object.cpp:2099
CreatureAI * GetAI(Creature *creature) const override
PrepareSpellScript(spell_kologarn_stone_shout_SpellScript)
SpellScript * GetSpellScript() const override
SpellScript * GetSpellScript() const override
SpellScript * GetSpellScript() const override
PrepareSpellScript(spell_ulduar_rubble_summonSpellScript)
SpellScript * GetSpellScript() const override
SpellScript * GetSpellScript() const override
PrepareAuraScript(spell_ulduar_stone_grip_AuraScript)
void OnRemoveStun(AuraEffect const *aurEff, AuraEffectHandleModes)
void OnRemoveVehicle(AuraEffect const *, AuraEffectHandleModes)
AuraScript * GetAuraScript() const override
SpellScript * GetSpellScript() const override
AuraScript * GetAuraScript() const override
TC_GAME_API Unit * GetUnit(WorldObject const &, ObjectGuid const &guid)
float m_positionZ
Definition Position.h:58
float m_positionX
Definition Position.h:56
float m_positionY
Definition Position.h:57
void SetOrientation(float orientation)
Definition Position.h:74
void GetPosition(float &x, float &y) const
Definition Position.h:84
void Relocate(float x, float y)
Definition Position.h:66
void SetCombatMovement(bool allowMovement)
void JustSummoned(Creature *summon) override
void KilledUnit(Unit *who) override
void PassengerBoarded(Unit *who, int8, bool apply) override
== Fields =======================================
void JustDied(Unit *) override
boss_kologarnAI(Creature *creature)
void UpdateAI(uint32 diff) override
void JustEngagedWith(Unit *who) override
@ DATA_KOLOGARN
Definition ulduar.h:41
@ NPC_RIGHT_ARM
Definition ulduar.h:74
@ NPC_FOCUSED_EYEBEAM_RIGHT
Definition ulduar.h:72
@ NPC_LEFT_ARM
Definition ulduar.h:73
@ NPC_FOCUSED_EYEBEAM
Definition ulduar.h:71
@ NPC_RUBBLE
Definition ulduar.h:75
@ CRITERIA_DISARMED
Definition ulduar.h:356