TrinityCore
Loading...
Searching...
No Matches
instance_culling_of_stratholme.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
19#include "Creature.h"
20#include "CreatureAI.h"
21#include "CreatureTextMgr.h"
22#include "EventMap.h"
23#include "GameObject.h"
24#include "GameTime.h"
25#include "InstanceScript.h"
26#include "Map.h"
27#include "MotionMaster.h"
28#include "Log.h"
29#include "Player.h"
30#include "ScriptMgr.h"
31#include "SpellInfo.h"
32#include "TemporarySummon.h"
33#include "WorldStatePackets.h"
34#include <array>
35#include <unordered_map>
36#include <unordered_set>
37#include <vector>
38
39/*
40 * Culling of Stratholme encounters:
41 * 0 - Meathook
42 * 1 - Salramm the Fleshcrafter
43 * 2 - Chrono-Lord Epoch
44 * 3 - Mal'Ganis
45 * 4 - Infinite Corruptor (Heroic only)
46 */
47
56
58{
61 NPC_CHROMIE = 26527, // first chromie - we don't need the other two for anything
70 NPC_ACOLYTE = 27731,
73 NPC_MEATHOOK = 26529,
74 NPC_SALRAMM = 26530,
75
77 GO_EXIT_GATE = 191788,
78
80};
81
95
109
117
126
133
135{
136 switch (state)
137 {
138 case JUST_STARTED:
139 default:
140 return JUST_STARTED;
142 return CRATES_IN_PROGRESS;
143 case CRATES_DONE:
144 return CRATES_DONE;
145 case UTHER_TALK:
146 case PURGE_PENDING:
147 case PURGE_STARTING:
149 return PURGE_PENDING;
150 case WAVES_DONE:
152 case TOWN_HALL:
153 return TOWN_HALL_PENDING;
156 case GAUNTLET_PENDING:
158 return GAUNTLET_PENDING;
161 return GAUNTLET_COMPLETE;
162 case COMPLETE:
163 return COMPLETE;
164 }
165}
166
167static Position const CorruptorPos = { 2331.642f, 1273.273f, 132.9524f, 3.717551f };
168static Position const GuardianPos = { 2321.489f, 1268.383f, 132.8507f, 0.418879f };
169static Position const CorruptorRiftPos = { 2443.626f, 1280.450f, 133.0066f, 1.727876f };
170
171static std::array<std::array<uint32, MAX_SPAWNS_PER_WAVE>, NUM_SCOURGE_WAVES> const HeroicWaves =
172{
173 {
178 { { 0 } }, // wave 5, meathook (special)
183 { { 0 } } // wave 10, salramm (special)
184 }
185};
186
188{
190 std::array<Position, MAX_SPAWNS_PER_WAVE> SpawnPoints;
191};
192
193static const std::array<WaveLocation, WAVE_LOC_MAX - WAVE_LOC_MIN + 1> WaveLocations =
194{
195 {
196 { // King's Square
198 {
199 {
200 { 2131.474f, 1352.615f, 131.372f, 6.10960f },
201 { 2131.463f, 1357.127f, 131.587f, 5.95173f },
202 { 2129.795f, 1345.093f, 131.194f, 0.17905f },
203 { 2136.235f, 1347.894f, 131.628f, 0.20262f },
204 { 2138.219f, 1356.240f, 132.169f, 5.95173f },
205 { 2140.584f, 1351.624f, 132.142f, 6.08525f }
206 }
207 }
208 },
209 { // Market Row
211 {
212 {
213 { 2226.364f, 1331.808f, 127.0193f, 3.298672f },
214 { 2229.934f, 1329.146f, 127.057f, 3.24605f },
215 { 2225.028f, 1327.269f, 127.791f, 3.03792f },
216 { 2223.844f, 1335.282f, 127.749f, 3.47774f },
217 { 2222.192f, 1330.859f, 127.526f, 3.18793f },
218 { 2225.865f, 1331.029f, 127.007f, 3.18793f }
219 }
220 }
221 },
222 { // Festival Lane
224 {
225 {
226 { 2183.596f, 1238.823f, 136.551f, 2.16377f },
227 { 2181.420f, 1237.357f, 136.565f, 2.16377f },
228 { 2178.692f, 1237.446f, 136.694f, 1.99098f },
229 { 2184.980f, 1242.458f, 136.772f, 2.59181f },
230 { 2176.873f, 1240.463f, 136.420f, 2.10094f },
231 { 2181.523f, 1244.298f, 136.338f, 2.38997f }
232 }
233 }
234 },
235 { // Elders' Square
237 {
238 {
239 { 2267.003f, 1168.055f, 137.821f, 2.79050f },
240 { 2264.392f, 1162.145f, 137.910f, 2.39937f },
241 { 2262.785f, 1166.648f, 138.053f, 2.71353f },
242 { 2265.214f, 1170.771f, 137.972f, 2.80385f },
243 { 2259.745f, 1159.360f, 138.198f, 2.34047f },
244 { 2264.222f, 1171.708f, 138.047f, 2.82742f }
245 }
246 }
247 },
248 { // Town Hall
250 {
251 {
252 { 2351.656f, 1218.682f, 130.062f, 4.63383f },
253 { 2354.921f, 1218.425f, 130.280f, 4.63383f },
254 { 2347.516f, 1216.976f, 130.491f, 5.02496f },
255 { 2356.508f, 1216.656f, 130.445f, 4.29061f },
256 { 2346.674f, 1216.739f, 130.576f, 5.32341f },
257 { 2351.728f, 1214.561f, 130.255f, 4.61891f }
258 }
259 }
260 }
261 }
262};
263
265{
266 public:
267 instance_culling_of_stratholme() : InstanceMapScript("instance_culling_of_stratholme", 595) { }
268
270 {
281
283 {
284 for (WorldStateMap::const_iterator itr = _sentWorldStates.begin(); itr != _sentWorldStates.end(); ++itr)
285 packet.Worldstates.emplace_back(itr->first, itr->second);
286 }
287
288 void WriteSaveDataMore(std::ostringstream& data) override
289 {
290 data << _currentState << ' ' << _infiniteGuardianTimeout;
291 }
292
293 void ReadSaveDataMore(std::istringstream& data) override
294 {
295 // read current instance progress from save data, then regress to the previous stable state
296 uint32 state = JUST_STARTED;
297 time_t infiniteGuardianTime = 0;
298 data >> state;
299 data >> infiniteGuardianTime; // UNIX timestamp
300
302 SetInstanceProgress(loadState, true);
303
304 if (infiniteGuardianTime)
305 {
306 _infiniteGuardianTimeout = infiniteGuardianTime;
308 }
309
310 time_t timediff = (infiniteGuardianTime - GameTime::GetGameTime());
311 if (!infiniteGuardianTime)
312 timediff = -1;
313
314 TC_LOG_DEBUG("scripts.cos", "instance_culling_of_stratholme::ReadSaveDataMore: Loaded with state {} and guardian timeout at {} minutes {} seconds from now", (uint32)loadState, timediff / MINUTE, timediff % MINUTE);
315 }
316
317 void SetData(uint32 type, uint32 data) override
318 {
319 switch (type)
320 {
321 case DATA_GM_OVERRIDE:
323 break;
324 case DATA_ARTHAS_DIED:
325 // Respawn everything, then regress to last stable state
328 break;
332 break;
334 if (uint32 missingCrates = MissingPlagueCrates())
336 else
338 break;
342 break;
346 break;
347 case DATA_START_WAVES:
350 break;
354 break;
358 break;
362 break;
366 break;
370 break;
371 default:
372 break;
373 }
374 }
375
376 void OnUnitDeath(Unit* unit) override
377 {
379 return;
380
381 // if this is a wave spawn...
382 auto it = _waveSpawns.find(unit->GetGUID());
383 if (it == _waveSpawns.end())
384 return;
385
386 // ... then erase it from our list, then check if there are no more spawns alive...
387 _waveSpawns.erase(it);
388 if (!_waveSpawns.empty())
389 return;
390
391 // ... and if there are none, the wave is done and we progress
392
393 // clear existing world markers
394 for (uint32 marker = WAVE_MARKER_MIN; marker <= WAVE_MARKER_MAX; ++marker)
395 SetWorldState(COSWorldStates(marker), 0, false);
397
398 // schedule next wave if applicable
401 else
403 }
404
405 void SetGuidData(uint32 type, ObjectGuid guid) override
406 {
407 switch (type)
408 {
409 case DATA_GM_RECALL:
410 {
412 Position const& target = arthas ? arthas->GetPosition() : GetArthasSnapbackFor(_currentState);
413
414 for (auto itr = instance->GetPlayers().begin(); itr != instance->GetPlayers().end(); ++itr)
415 {
416 if (Player* player = itr->GetSource())
417 if (player->GetGUID() == guid || !player->IsGameMaster())
418 {
419 player->CombatStop(true);
420 const float offsetDist = 10;
421 float myAngle = rand_norm() * 2.0 * M_PI;
422 Position myTarget(target.GetPositionX() + std::sin(myAngle) * offsetDist, target.GetPositionY() + std::sin(myAngle) * offsetDist, target.GetPositionZ(), myAngle + M_PI);
423 player->NearTeleportTo(myTarget);
424 }
425 }
426 break;
427 }
428 case DATA_UTHER_START:
431 break;
432 case DATA_START_PURGE:
434 break;
437 break;
438 case DATA_TO_GAUNTLET:
440 break;
443 break;
446 break;
447 default:
448 break;
449 }
450 }
451
452 uint32 GetData(uint32 type) const override
453 {
454 if (type == DATA_INSTANCE_PROGRESS)
455 return _currentState;
456 return 0;
457 }
458
459 bool SetBossState(uint32 type, EncounterState state) override
460 {
461 if (type == DATA_INFINITE_CORRUPTOR && state == DONE)
462 {
466 }
467
468 if (!InstanceScript::SetBossState(type, state))
469 return false;
470
471 return true;
472 }
473
474 void Update(uint32 diff) override
475 {
476 events.Update(diff);
477 while (uint32 eventId = events.ExecuteEvent())
478 {
479 switch (eventId)
480 {
481 case EVENT_GUARDIAN_TICK: // regular ticks at :00 seconds on the timer, and then at 04:30 remaining for the chromie whisper
482 { // we do the whisper as a guardian tick because i don't want to duplicate the real-time code
484 return;
485
486 time_t secondsToGuardianDeath = _infiniteGuardianTimeout - GameTime::GetGameTime();
487 if (secondsToGuardianDeath <= 0)
488 {
492
493 if (Creature* corruptor = instance->GetCreature(_corruptorGUID))
494 {
495 corruptor->AI()->DoAction(-ACTION_CORRUPTOR_LEAVE);
496 if (Creature* guardian = instance->GetCreature(_guardianGUID))
497 Unit::Kill(corruptor, guardian); // @todo is there some spell for this?
498 }
500 }
501 else
502 {
503 time_t minutes = (secondsToGuardianDeath - 1) / MINUTE;
504 time_t seconds = ((secondsToGuardianDeath - 1) % MINUTE) + 1;
505
506 // chromie whispers - we only ever tick at :00 and :30, but give some leeway in case of slow tick rate
507 if (minutes == 24 && seconds >= 45)
508 if (Creature* chromie = instance->GetCreature(_chromieGUID))
509 chromie->AI()->Talk(CHROMIE_WHISPER_GUARDIAN_1);
510 if (minutes == 4 && seconds < 45)
511 if (Creature* chromie = instance->GetCreature(_chromieGUID))
512 chromie->AI()->Talk(CHROMIE_WHISPER_GUARDIAN_2);
513 if (minutes == 0)
514 if (Creature* chromie = instance->GetCreature(_chromieGUID))
515 chromie->AI()->Talk(CHROMIE_WHISPER_GUARDIAN_3);
516
517 // update the timer state
520 if (minutes == 4 && seconds > 30)
521 events.Repeat(Seconds(seconds - 30));
522 else
523 events.Repeat(Seconds(seconds));
524 }
525 break;
526 }
528 TC_LOG_DEBUG("scripts.cos", "instance_culling_of_stratholme::Update: Spawning new Arthas for instance...");
530 events.CancelEvent(EVENT_RESPAWN_ARTHAS); // make sure we don't have two scheduled
531 break;
535 crier->AI()->Talk(CRIER_SAY_CALL_TO_GATES);
536 break;
538 {
540 break;
541
542 ++_waveCount;
544
546 while (spawnLoc == _currentSpawnLoc) // don't allow repeats
547 spawnLoc = urand(WAVE_LOC_MIN, WAVE_LOC_MAX);
548 WaveLocation const& spawnLocation = WaveLocations[spawnLoc - WAVE_LOC_MIN];
549
550 switch (_waveCount)
551 {
552 case WAVE_MEATHOOK:
553 if (Creature* spawn = instance->SummonCreature(NPC_MEATHOOK, spawnLocation.SpawnPoints[0]))
554 _waveSpawns.insert(spawn->GetGUID());
555 break;
556 case WAVE_SALRAMM:
557 if (Creature* spawn = instance->SummonCreature(NPC_SALRAMM, spawnLocation.SpawnPoints[0]))
558 _waveSpawns.insert(spawn->GetGUID());
559 break;
560 default:
562 {
563 for (uint32 i = 0; i < MAX_SPAWNS_PER_WAVE; ++i)
564 if (uint32 entry = HeroicWaves[_waveCount - 1][i])
565 if (Creature* spawn = instance->SummonCreature(entry, spawnLocation.SpawnPoints[i]))
566 _waveSpawns.insert(spawn->GetGUID());
567 }
568 else
569 {
570 for (uint32 i = 0; i <= 1; ++i)
571 if (Creature* spawn = instance->SummonCreature(NPC_DEVOURING_GHOUL, spawnLocation.SpawnPoints[i]))
572 _waveSpawns.insert(spawn->GetGUID());
573 }
574 break;
575 }
576
577 for (uint32 marker = WAVE_MARKER_MIN; marker <= WAVE_MARKER_MAX; ++marker)
578 SetWorldState(COSWorldStates(marker), 0, false);
579 SetWorldState(spawnLocation.WorldState, 1);
580
582 _currentSpawnLoc = spawnLoc;
583 break;
584 }
588 crier->AI()->Talk(_currentSpawnLoc);
589 break;
590 default:
591 break;
592 }
593 }
594 }
595
596 void OnCreatureCreate(Creature* creature) override
597 {
598 switch (creature->GetEntry())
599 {
600 case NPC_CHROMIE:
601 _chromieGUID = creature->GetGUID();
602 creature->setActive(true);
603 break;
605 _corruptorGUID = creature->GetGUID();
606 creature->setActive(true);
607 break;
609 _guardianGUID = creature->GetGUID();
610 creature->setActive(true);
611 break;
613 _genericBunnyGUID = creature->GetGUID();
614 creature->setActive(true);
615 break;
616 case NPC_CRATE_HELPER:
617 _plagueCrates.push_back(creature->GetGUID());
618 break;
619 case NPC_ARTHAS:
620 TC_LOG_DEBUG("scripts.cos", "instance_culling_of_stratholme::OnCreatureCreate: Arthas spawned at {}", creature->GetPosition().ToString());
621 _arthasGUID = creature->GetGUID();
622 creature->setActive(true);
623 break;
625 _crierGUID = creature->GetGUID();
626 creature->setActive(true);
627 break;
628 default:
629 break;
630 }
631 }
632
633 void OnGameObjectCreate(GameObject* object) override
634 {
635 switch (object->GetEntry())
636 {
638 _passageGUID = object->GetGUID();
639 object->setActive(true);
641 break;
642 default:
643 break;
644 }
645 }
646
648 {
649 if (_currentState != fromState)
650 return;
651 SetInstanceProgress(toState, false);
653 arthas->AI()->SetGUID(starterGUID, -startAction);
654 }
655
657 {
658 TC_LOG_DEBUG("scripts.cos", "instance_culling_of_stratholme::SetInstanceProgress: Instance progress is now 0x{:X}", (uint32)state);
659 _currentState = state;
660
661 /* Spawn group management */
667
668 /* Arthas management */
669 if (state > CRATES_DONE)
670 { // there might be an Arthas instance in the dungeon somewhere
671 // notify him of the change so he can adjust
673 if (arthas)
674 {
675 if (force)
676 {
677 arthas->DespawnOrUnsummon();
678 arthas = nullptr;
679 }
680 else
682 }
683
684 if (!arthas) // if there is currently no arthas, then we need to spawn one
686 }
687 else if (Creature* arthas = instance->GetCreature(_arthasGUID)) // there shouldn't be any Arthas around
688 arthas->DespawnOrUnsummon();
689
690 /* World state management */
691 // Plague crates
692 if (state == CRATES_IN_PROGRESS)
693 {
696 }
697 else if (state == CRATES_DONE)
698 {
701 }
702 else
703 {
706 }
707 // Scourge wave counter
708 if (state == WAVES_DONE)
710 else
712
714
715 // Hidden Passage status handling
717 passage->SetGoState(state <= GAUNTLET_TRANSITION ? GO_STATE_READY : GO_STATE_ACTIVE);
718
719 switch (state)
720 {
721 case CRATES_DONE:
723 bunny->CastSpell(nullptr, SPELL_CRATES_KILL_CREDIT, TRIGGERED_FULL_MASK);
725 break;
727 _waveCount = 0;
729 _waveSpawns.clear();
732 break;
733 default:
734 break;
735 }
736
737 if (force)
738 {
739 // Forced transitions are regressions (event failures) or GM overrides; respawn all dead creatures, and despawn any temporary summons
740 events.Reset();
742
743 // Reset respawn time on all permanent spawns, despawn all temporary spawns
744 // @todo dynspawn, this won't work
745 std::vector<Creature*> toDespawn;
746 std::unordered_map<ObjectGuid, Creature*> const& objects = instance->GetObjectsStore().GetElements()._elements._element;
747 for (std::unordered_map<ObjectGuid, Creature*>::const_iterator itr = objects.cbegin(); itr != objects.cend(); ++itr)
748 {
749 if (itr->second && (itr->second->isDead() || !itr->second->GetSpawnId() || itr->second->GetOriginalEntry() != itr->second->GetEntry()))
750 {
751 if (itr->second->getDeathState() == DEAD) // despawned, not corpse
752 itr->second->SetRespawnTime(1);
753 else
754 toDespawn.push_back(itr->second);
755 }
756 }
757
758 for (Creature* creature : toDespawn)
759 {
760 if (creature->GetSpawnId())
761 creature->SetRespawnTime(1);
762 creature->DespawnOrUnsummon(0s, 1s);
763 }
764
767 }
768
769 SaveToDB();
770 }
771
772 private:
773 typedef std::unordered_map<uint32, uint32> WorldStateMap;
774
776 {
777 uint32 returnValue = 0;
778 for (ObjectGuid const& crateHelperGUID : _plagueCrates)
779 if (Creature* crateHelper = instance->GetCreature(crateHelperGUID))
780 if (crateHelper->IsAlive() && !crateHelper->AI()->GetData(DATA_CRATE_REVEALED))
781 ++returnValue;
782 return returnValue;
783 }
784
796
797 void SetWorldState(COSWorldStates state, uint32 value, bool immediate = true)
798 {
799 TC_LOG_DEBUG("scripts.cos", "instance_culling_of_stratholme::SetWorldState: {} {}", uint32(state), value);
800 _currentWorldStates[state] = value;
801 if (immediate)
803 }
804
806 {
807 TC_LOG_DEBUG("scripts.cos", "instance_culling_of_stratholme::PropagateWorldStateUpdate: Propagate world states");
808 for (WorldStateMap::const_iterator it = _currentWorldStates.begin(); it != _currentWorldStates.end(); ++it)
809 {
810 uint32& sent = _sentWorldStates[it->first];
811 if (sent != it->second)
812 {
813 TC_LOG_DEBUG("scripts.cos", "instance_culling_of_stratholme::PropagateWorldStateUpdate: Sending world state {} ({})", it->first, it->second);
814 DoUpdateWorldState(it->first, it->second);
815 sent = it->second;
816 }
817 }
818 }
819
820 void SetSpawnGroupState(COSInstanceEntries group, bool state, bool force)
821 {
822 if (state)
823 instance->SpawnGroupSpawn(group, true);
824 else if (force)
825 instance->SpawnGroupDespawn(group, true);
826 else
828 }
829
835
836 // Generic
841 std::vector<ObjectGuid> _plagueCrates;
842
845
846 // Scourge Waves
849 std::unordered_set<ObjectGuid> _waveSpawns;
850
851 // Gauntlet
853 };
854
859};
860
@ MINUTE
Definition Common.h:29
#define M_PI
Definition Common.h:72
@ DUNGEON_DIFFICULTY_HEROIC
Definition DBCEnums.h:283
uint8_t uint8
Definition Define.h:135
uint32_t uint32
Definition Define.h:133
std::chrono::seconds Seconds
Seconds shorthand typedef.
Definition Duration.h:27
EncounterState
@ FAIL
@ DONE
@ DOOR_TYPE_ROOM
@ DOOR_TYPE_PASSAGE
#define TC_LOG_DEBUG(filterType__,...)
Definition Log.h:156
uint32 urand(uint32 min, uint32 max)
Definition Random.cpp:42
double rand_norm()
Definition Random.cpp:75
@ GO_STATE_READY
@ GO_STATE_ACTIVE
@ TRIGGERED_FULL_MASK
Will return SPELL_FAILED_DONT_REPORT in CheckCast functions.
@ DEAD
Definition Unit.h:214
#define DataHeader
uint32 const EncounterCount
void DespawnOrUnsummon(Milliseconds timeToDespawn=0s, Seconds forceRespawnTime=0s)
CreatureAI * AI() const
Definition Creature.h:154
void Update(uint32 time)
Definition EventMap.h:67
void Repeat(Milliseconds time)
Definition EventMap.cpp:63
EventId ExecuteEvent()
Definition EventMap.cpp:73
void RescheduleEvent(EventId eventId, Milliseconds time, GroupIndex group=0u, PhaseIndex phase=0u)
Definition EventMap.cpp:52
void CancelEvent(EventId eventId)
Definition EventMap.cpp:151
void ScheduleEvent(EventId eventId, Milliseconds time, GroupIndex group=0u, PhaseIndex phase=0u)
Definition EventMap.cpp:36
void Reset()
Definition EventMap.cpp:21
void SetBossNumber(uint32 number)
virtual bool SetBossState(uint32 id, EncounterState state)
InstanceMap * instance
EncounterState GetBossState(uint32 id) const
void LoadDoorData(DoorData const *data)
void DoUpdateWorldState(uint32 worldstateId, uint32 worldstateValue)
void SetHeaders(std::string const &dataHeaders)
iterator end()
iterator begin()
void SetSpawnGroupInactive(uint32 groupId)
Definition Map.h:779
MapStoredObjectTypesContainer & GetObjectsStore()
Definition Map.h:489
bool SpawnGroupSpawn(uint32 groupId, bool ignoreRespawn=false, bool force=false, std::vector< WorldObject * > *spawnedObjects=nullptr)
Definition Map.cpp:3382
void DeleteRespawnTimes()
Definition Map.h:562
uint8 GetSpawnMode() const
Definition Map.h:388
GameObject * GetGameObject(ObjectGuid const &guid)
Definition Map.cpp:4430
bool SpawnGroupDespawn(uint32 groupId, bool deleteRespawnTimes=false, size_t *count=nullptr)
Definition Map.cpp:3458
TempSummon * SummonCreature(uint32 entry, Position const &pos, SummonPropertiesEntry const *properties=nullptr, uint32 duration=0, WorldObject *summoner=nullptr, uint32 spellId=0, uint32 vehId=0, ObjectGuid privateObjectOwner=ObjectGuid::Empty)
Definition Object.cpp:1852
PlayerList const & GetPlayers() const
Definition Map.h:448
Creature * GetCreature(ObjectGuid const &guid)
Definition Map.cpp:4397
static ObjectGuid const Empty
Definition ObjectGuid.h:140
uint32 GetEntry() const
Definition Object.h:81
static ObjectGuid GetGUID(Object const *o)
Definition Object.h:78
ContainerUnorderedMap< OBJECT_TYPES, KEY_TYPE > & GetElements()
virtual void DoAction(int32)
Definition UnitAI.h:154
Definition Unit.h:769
static void Kill(Unit *attacker, Unit *victim, bool durabilityLoss=true)
Definition Unit.cpp:10930
void setActive(bool isActiveObject)
Definition Object.cpp:991
std::vector< WorldStateInfo > Worldstates
InstanceScript * GetInstanceScript(InstanceMap *map) const override
Position const & GetArthasSnapbackFor(COSProgressStates state)
@ DATA_START_MALGANIS
@ DATA_SKIP_TO_PURGE
@ DATA_INSTANCE_PROGRESS
@ DATA_ARTHAS_DIED
@ DATA_GAUNTLET_DONE
@ DATA_MALGANIS_DONE
@ DATA_TO_GAUNTLET
@ DATA_START_GAUNTLET
@ DATA_START_WAVES
@ DATA_GM_OVERRIDE
@ DATA_UTHER_START
@ DATA_CRATES_START
@ DATA_TOWN_HALL_DONE
@ DATA_REACH_TOWN_HALL
@ DATA_START_TOWN_HALL
@ DATA_GAUNTLET_REACHED
@ DATA_START_PURGE
@ DATA_INFINITE_CORRUPTOR
@ DATA_CRATE_REVEALED
@ DATA_UTHER_FINISHED
@ ACTION_START_RP_EVENT2
@ ACTION_CORRUPTOR_LEAVE
@ ACTION_PROGRESS_UPDATE
@ ACTION_START_RP_EVENT3
@ ACTION_START_RP_EVENT4_2
@ ACTION_START_RP_EVENT4_1
@ ACTION_START_RP_EVENT5
@ TOWN_HALL_COMPLETE
@ CRATES_IN_PROGRESS
@ GAUNTLET_IN_PROGRESS
@ TOWN_HALL_PENDING
@ GAUNTLET_PENDING
@ MALGANIS_IN_PROGRESS
@ WAVES_IN_PROGRESS
@ GAUNTLET_TRANSITION
@ PURGE_PENDING
@ PURGE_STARTING
@ GAUNTLET_COMPLETE
@ SPAWNGRP_UNDEAD_TRASH
@ GO_HIDDEN_PASSAGE
@ SPAWNGRP_RESIDENTS
@ SPAWNGRP_GAUNTLET_TRASH
@ SPAWNGRP_CHROMIE_MID
@ SPAWNGRP_CRATE_HELPERS
static Position const GuardianPos
static std::array< std::array< uint32, MAX_SPAWNS_PER_WAVE >, NUM_SCOURGE_WAVES > const HeroicWaves
DoorData const doorData[]
static const std::array< WaveLocation, WAVE_LOC_MAX - WAVE_LOC_MIN+1 > WaveLocations
static Position const CorruptorPos
COSProgressStates GetStableStateFor(COSProgressStates const state)
void AddSC_instance_culling_of_stratholme()
static Position const CorruptorRiftPos
time_t GetGameTime()
Definition GameTime.cpp:42
std::unordered_map< KEY_TYPE, OBJECT * > _element
float GetPositionZ() const
Definition Position.h:81
float GetPositionX() const
Definition Position.h:79
void GetPosition(float &x, float &y) const
Definition Position.h:84
float GetPositionY() const
Definition Position.h:80
COSWorldStates const WorldState
std::array< Position, MAX_SPAWNS_PER_WAVE > SpawnPoints
void InitiateArthasEvent(COSProgressStates fromState, COSProgressStates toState, COSInstanceActions startAction, ObjectGuid starterGUID)
void FillInitialWorldStates(WorldPackets::WorldState::InitWorldStates &packet) override