fix(Scripts/Ulduar): Yogg-Saron reset recovery sequence (#26781)

This commit is contained in:
sogladev
2026-07-28 18:27:47 +02:00
committed by GitHub
parent dbd8610c32
commit 0398c6baf8
2 changed files with 84 additions and 15 deletions

View File

@@ -174,6 +174,9 @@ enum YoggEvents
EVENT_YS_DEAFENING_ROAR = 31,
EVENT_YS_SUMMON_GUARDIAN = 32,
EVENT_YS_SHADOW_BEACON = 33,
EVENT_SARA_WIPE_OPEN_DOOR = 40,
EVENT_SARA_WIPE_RESPAWN = 41,
};
enum NPCsGOs
@@ -257,6 +260,7 @@ enum Misc
EVENT_PHASE_ONE = 1,
EVENT_PHASE_TWO = 2,
EVENT_PHASE_THREE = 3,
EVENT_PHASE_WIPE_RECOVERY = 4,
CRITERIA_NOT_GETTING_OLDER = 21001,
@@ -388,6 +392,7 @@ struct boss_yoggsaron_sara : public ScriptedAI
float _summonSpeed;
uint8 _currentIllusion;
bool _isIllusionReversed;
bool _isWipeRecovering = false;
void AttackStart(Unit*) override { }
void MoveInLineOfSight(Unit*) override { }
@@ -414,11 +419,10 @@ struct boss_yoggsaron_sara : public ScriptedAI
if (!_EnterEvadeMode(why))
return;
Position pos;
pos = me->GetHomePosition();
Position pos = me->GetHomePosition();
me->NearTeleportTo(pos.GetPositionX(), pos.GetPositionY(), pos.GetPositionZ(), pos.GetOrientation());
Reset();
me->setActive(false);
HandleWipeRecovery();
}
void EnableSara(bool apply)
@@ -437,6 +441,18 @@ struct boss_yoggsaron_sara : public ScriptedAI
}
}
void HandleWipeRecovery()
{
_isWipeRecovering = true;
Reset();
me->SetVisible(false);
events.SetPhase(EVENT_PHASE_WIPE_RECOVERY);
events.ScheduleEvent(EVENT_SARA_WIPE_OPEN_DOOR, 20s, 0, EVENT_PHASE_WIPE_RECOVERY);
events.ScheduleEvent(EVENT_SARA_WIPE_RESPAWN, 30s, 0, EVENT_PHASE_WIPE_RECOVERY);
me->setActive(true);
}
void Reset() override
{
// Whisper only on a real phase 1 wipe, not on the initial reset
@@ -455,17 +471,20 @@ struct boss_yoggsaron_sara : public ScriptedAI
events.Reset();
summons.DespawnAll();
me->SetVisible(true);
if (!_isWipeRecovering)
{
me->SetVisible(true);
SpawnClouds();
UpdateKeeperSpawns();
}
me->SetDisplayId(me->GetNativeDisplayId());
me->SetDisableGravity(true);
me->SetFaction(FACTION_FRIENDLY);
me->ClearUnitState(UNIT_STATE_EVADE);
EnableSara(false);
SpawnClouds();
_initFight = 1;
UpdateKeeperSpawns();
_summonedGuardiansCount = 0;
_p2TalkTimer = 0;
_secondPhase = false;
@@ -479,9 +498,12 @@ struct boss_yoggsaron_sara : public ScriptedAI
_instance->DoRemoveAurasDueToSpellOnPlayers(SPELL_SANITY);
if (Creature* voice = _instance->GetCreature(DATA_VOICE_OF_YOGG_SARON))
voice->AI()->DoAction(ACTION_VOICE_STOP);
_instance->SetBossState(BOSS_YOGGSARON, NOT_STARTED);
if (GameObject* go = _instance->GetGameObject(DATA_YOGG_SARON_DOORS))
go->SetGoState(GO_STATE_ACTIVE);
if (!_isWipeRecovering)
{
_instance->SetBossState(BOSS_YOGGSARON, NOT_STARTED);
if (GameObject* go = _instance->GetGameObject(DATA_YOGG_SARON_DOORS))
go->SetGoState(GO_STATE_ACTIVE);
}
}
}
@@ -490,9 +512,6 @@ struct boss_yoggsaron_sara : public ScriptedAI
if (!_instance)
return;
if (_instance->GetBossState(BOSS_VEZAX) != DONE)
return;
_instance->DoStartTimedAchievement(ACHIEVEMENT_TIMED_TYPE_EVENT, CRITERIA_NOT_GETTING_OLDER);
_instance->SetBossState(BOSS_YOGGSARON, IN_PROGRESS);
me->SetInCombatWithZone();
@@ -724,7 +743,6 @@ struct boss_yoggsaron_sara : public ScriptedAI
void DamageTaken(Unit* attacker, uint32& damage, DamageEffectType /*damagetype*/, SpellSchoolMask /*damageSchoolMask*/) override
{
// Guardians can be spawned by walking into Ominous Clouds even when InitFight
// never ran (e.g. Vezax not defeated); their novas must not start phase 2 then.
if (!_instance || _instance->GetBossState(BOSS_YOGGSARON) != IN_PROGRESS || !attacker || attacker->GetEntry() != NPC_GUARDIAN_OF_YS || _secondPhase)
{
damage = 0;
@@ -769,6 +787,39 @@ struct boss_yoggsaron_sara : public ScriptedAI
void UpdateAI(uint32 diff) override
{
if (_isWipeRecovering)
{
events.Update(diff);
while (uint32 eventId = events.ExecuteEvent())
{
switch (eventId)
{
case EVENT_SARA_WIPE_OPEN_DOOR:
if (_instance)
if (GameObject* go = _instance->GetGameObject(DATA_YOGG_SARON_DOORS))
go->SetGoState(GO_STATE_ACTIVE);
break;
case EVENT_SARA_WIPE_RESPAWN:
if (_instance)
{
if (GameObject* go = _instance->GetGameObject(DATA_YOGG_SARON_DOORS))
go->SetGoState(GO_STATE_ACTIVE);
_instance->SetBossState(BOSS_YOGGSARON, NOT_STARTED);
}
me->SetVisible(true);
SpawnClouds();
UpdateKeeperSpawns();
events.Reset();
_isWipeRecovering = false;
me->setActive(false);
break;
}
}
return;
}
if (_initFight)
{
_initFight += diff;

View File

@@ -997,6 +997,24 @@ public:
}
return false;
}
bool CheckRequiredBosses(uint32 bossId, Player const* player) const override
{
if (_SkipCheckRequiredBosses(player))
return true;
switch (bossId)
{
case BOSS_YOGGSARON:
if (GetBossState(BOSS_VEZAX) != DONE)
return false;
break;
default:
break;
}
return true;
}
};
};