Scripts/Nexus: Rework Telestra (#28104)

Closes #27792 Closes #27941
This commit is contained in:
offl
2022-07-11 00:08:21 +03:00
committed by GitHub
parent b484b7e927
commit 93db014cb9
2 changed files with 352 additions and 240 deletions

View File

@@ -0,0 +1,80 @@
--
DELETE FROM `spell_script_names` WHERE `ScriptName` IN (
'spell_magus_telestra_summon_clones',
'spell_magus_telestra_clone_dies');
INSERT INTO `spell_script_names` (`spell_id`,`ScriptName`) VALUES
(47710,'spell_magus_telestra_summon_clones'),
(47711,'spell_magus_telestra_clone_dies'),
(47712,'spell_magus_telestra_clone_dies'),
(47713,'spell_magus_telestra_clone_dies');
DELETE FROM `spell_target_position` WHERE `ID` = 47754;
INSERT INTO `spell_target_position` (`ID`,`EffectIndex`,`MapID`,`PositionX`,`PositionY`,`PositionZ`,`Orientation`,`VerifiedBuild`) VALUES
(47754,0,576,504.742,88.9122,-16.1245,0,11159);
UPDATE `creature_template` SET `minlevel` = 72, `maxlevel` = 72 WHERE `entry` = 26731;
-- Should be 15214 but it has 2 models.
UPDATE `spell_dbc` SET `ProcChance` = 101, `Effect1` = 6, `EffectImplicitTargetA1` = 1, `EffectApplyAuraName1` = 56, `EffectMiscValue1` = 2334, `DmgMultiplier1` = 1 WHERE `Id` = 41577;
UPDATE `creature_template` SET `BaseAttackTime` = 2000 WHERE `entry` IN (26928,26929,26930);
DELETE FROM `smart_scripts` WHERE `entryorguid` IN (26928,26929,26930) AND `source_type` = 0;
DELETE FROM `smart_scripts` WHERE `entryorguid` IN (2692800,2692900,2693000) AND `source_type` = 9;
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
(26928,0,0,0,37,0,100,0,0,0,0,0,0,42,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On AI Initialize - Set Invincibility HP 1"),
(26928,0,1,0,11,0,100,0,0,0,0,0,0,11,47705,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Spawn - Cast 'Grand Magus Telestra (Fire) Visual'"),
(26928,0,2,0,2,0,100,1,0,1,0,0,0,80,2692800,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - Between 0-1% Health - Run Script (No Repeat)"),
(26928,0,3,0,0,0,100,2,0,0,1600,2400,0,11,47723,64,0,0,0,0,2,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat CMC - Cast 'Scorch'"),
(26928,0,4,0,0,0,100,4,0,0,1600,2400,0,11,56938,64,0,0,0,0,2,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat CMC - Cast 'Scorch'"),
(26928,0,5,0,0,0,100,2,6000,12000,6000,12000,0,11,47721,0,0,0,0,0,2,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat - Cast 'Fire Blast'"),
(26928,0,6,0,0,0,100,4,6000,12000,6000,12000,0,11,56939,0,0,0,0,0,2,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat - Cast 'Fire Blast'"),
(2692800,9,0,0,0,0,100,0,0,0,0,0,0,45,0,1,0,0,0,0,23,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Set Data 0 1 (Summoner)"),
(2692800,9,1,0,0,0,100,0,0,0,0,0,0,28,47705,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Remove Aura 'Grand Magus Telestra (Fire) Visual'"),
(2692800,9,2,0,0,0,100,0,0,0,0,0,0,11,41577,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Cast 'Transform: Invisible Stalker'"),
(2692800,9,3,0,0,0,100,0,0,0,0,0,0,11,47711,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Cast 'Telestra Clone Dies (Fire)'"),
(2692800,9,4,0,0,0,100,0,0,0,0,0,0,8,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Set Reactstate Passive"),
(2692800,9,5,0,0,0,100,0,0,0,0,0,0,146,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Set Uninteractible"),
-- Actually despawn after 3 sec, but aura can't be applied if caster is already destroyed
-- (if clone is just 20 yards away from boss, aura will not be applied, breaking whole encounter)
-- Great, now, as creature can continue cast COMBAT spells while being passive AND THAT IS ACTUALLY PROBABLY CORRECT,
-- but we increased despawn time to 30 sec, hackily silence it, what else we can do
(2692800,9,6,0,0,0,100,0,0,0,0,0,0,11,42201,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Cast 'Eternal Silence'"),
(2692800,9,7,0,0,0,100,0,30000,30000,0,0,0,41,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Despawn"),
(26929,0,0,0,37,0,100,0,0,0,0,0,0,42,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On AI Initialize - Set Invincibility HP 1"),
(26929,0,1,0,11,0,100,0,0,0,0,0,0,11,47704,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Spawn - Cast 'Grand Magus Telestra (Arcane) Visual'"),
(26929,0,2,0,2,0,100,1,0,1,0,0,0,80,2692900,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - Between 0-1% Health - Run Script (No Repeat)"),
(26929,0,3,0,0,0,100,0,6000,8000,12000,12000,0,11,47731,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat - Cast 'Critter'"),
(26929,0,4,0,0,0,100,0,10000,15000,15000,15000,0,11,47736,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat - Cast 'Time Stop'"),
(2692900,9,0,0,0,0,100,0,0,0,0,0,0,45,0,1,0,0,0,0,23,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Set Data 0 1 (Summoner)"),
(2692900,9,1,0,0,0,100,0,0,0,0,0,0,28,47704,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Remove Aura 'Grand Magus Telestra (Arcane) Visual'"),
(2692900,9,2,0,0,0,100,0,0,0,0,0,0,11,41577,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Cast 'Transform: Invisible Stalker'"),
(2692900,9,3,0,0,0,100,0,0,0,0,0,0,11,47713,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Cast 'Telestra Clone Dies (Arcane)'"),
(2692900,9,4,0,0,0,100,0,0,0,0,0,0,8,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Set Reactstate Passive"),
(2692900,9,5,0,0,0,100,0,0,0,0,0,0,146,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Set Uninteractible"),
(2692900,9,6,0,0,0,100,0,0,0,0,0,0,11,42201,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Cast 'Eternal Silence'"),
(2692900,9,7,0,0,0,100,0,30000,30000,0,0,0,41,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Despawn"),
(26930,0,0,0,37,0,100,0,0,0,0,0,0,42,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On AI Initialize - Set Invincibility HP 1"),
(26930,0,1,0,11,0,100,0,0,0,0,0,0,11,47706,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Spawn - Cast 'Grand Magus Telestra (Frost) Visual'"),
(26930,0,2,0,2,0,100,1,0,1,0,0,0,80,2693000,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - Between 0-1% Health - Run Script (No Repeat)"),
(26930,0,3,0,0,0,100,2,0,0,1200,1200,0,11,47729,64,0,0,0,0,2,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat CMC - Cast 'Ice Barb'"),
(26930,0,4,0,0,0,100,4,0,0,1200,1200,0,11,56937,64,0,0,0,0,2,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat CMC - Cast 'Ice Barb'"),
(26930,0,5,0,0,0,100,2,8000,12000,10000,15000,0,11,47727,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat - Cast 'Blizzard'"),
(26930,0,6,0,0,0,100,4,8000,12000,10000,15000,0,11,56936,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - In Combat - Cast 'Blizzard'"),
(2693000,9,0,0,0,0,100,0,0,0,0,0,0,45,0,1,0,0,0,0,23,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Set Data 0 1 (Summoner)"),
(2693000,9,1,0,0,0,100,0,0,0,0,0,0,28,47706,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Remove Aura 'Grand Magus Telestra (Frost) Visual'"),
(2693000,9,2,0,0,0,100,0,0,0,0,0,0,11,41577,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Cast 'Transform: Invisible Stalker'"),
(2693000,9,3,0,0,0,100,0,0,0,0,0,0,11,47712,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Cast 'Telestra Clone Dies (Frost)'"),
(2693000,9,4,0,0,0,100,0,0,0,0,0,0,8,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Set Reactstate Passive"),
(2693000,9,5,0,0,0,100,0,0,0,0,0,0,146,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Set Uninteractible"),
(2693000,9,6,0,0,0,100,0,0,0,0,0,0,11,42201,2,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Cast 'Eternal Silence'"),
(2693000,9,7,0,0,0,100,0,30000,30000,0,0,0,41,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,"Grand Magus Telestra - On Script - Despawn");

View File

@@ -15,135 +15,134 @@
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "ScriptMgr.h"
/*
Achievement implementation requires additional research.
Telestra's clones are unkillable and only executes set of actions when damaged to full health. Those actions includes cast of
'Telestra Clone Dies' aura which lands on boss(3 auras for 3 clones). Comments claims 'frost' clone can fail achievement due to
her Blizzard spell. Thing is action sets on retail cannot be started when creature casts spell(general mechanic or supported by flag or by
special action-check which can be used directly in action set as first action, preventing execution of next events until current cast is
finished. You can notice that everywhere - bosses don't enter in another phase while casting spells, for example).
But while actions clones executes surely has something related to achievement, Telestra Clone Dies auras probably aren't. The problem is those
auras are missiles and it may take seconds to hit boss, leaving a small chance to complete achievement. Speed of missiles is just 5 and unique
missile motion makes it slower. On top of that when clone dies, it can be not close enough to the boss.
That achievement is more trickier, some people claim it can be enough to kill clones only once, or it requires to kill clones twice. Or that
it is possible to get achievement even if she didn't summoned clones.
At least we can be sure auras are scripted to inform AI that all 3 clones are dead because once 3 auras are applied on boss, she casts a spell
which we can use later in SpellHit hook to perform merge sequence.
Currently we force clones to use SetData (in DB) to inform boss that clone is dead. And auras are used only to inform boss that
all clones are dead.
World Trigger spawned in front of boss may be related to something.
*/
#include "GameEventMgr.h"
#include "GameTime.h"
#include "InstanceScript.h"
#include "MotionMaster.h"
#include "nexus.h"
#include "ScriptedCreature.h"
#include "TemporarySummon.h"
#include "ScriptMgr.h"
#include "SpellInfo.h"
#include "SpellScript.h"
#include "nexus.h"
enum Texts
{
SAY_AGGRO = 0,
SAY_KILL = 1,
SAY_DEATH = 2,
SAY_MERGE = 3,
SAY_SPLIT = 4
};
enum Spells
{
SPELL_ICE_NOVA = 47772,
H_SPELL_ICE_NOVA = 56935,
SPELL_FIREBOMB = 47773,
H_SPELL_FIREBOMB = 56934,
SPELL_GRAVITY_WELL = 47756,
SPELL_TELESTRA_BACK = 47714,
SPELL_ICE_NOVA = 47772,
SPELL_FIREBOMB = 47773,
SPELL_GRAVITY_WELL = 47756,
SPELL_FIRE_MAGUS_VISUAL = 47705,
SPELL_FROST_MAGUS_VISUAL = 47706,
SPELL_ARCANE_MAGUS_VISUAL = 47704,
SPELL_SUMMON_CLONE_FIRE = 47707,
SPELL_SUMMON_CLONE_ARCANE = 47708,
SPELL_SUMMON_CLONE_FROST = 47709,
SPELL_SUMMON_CLONES = 47710,
SPELL_WEAR_CHRISTMAS_HAT = 61400
SPELL_CLONE_DIES_FIRE = 47711,
SPELL_CLONE_DIES_FROST = 47712,
SPELL_CLONE_DIES_ARCANE = 47713,
SPELL_TRIGGER_000 = 36294,
SPELL_TELEPORT = 47754,
SPELL_SPAWN_BACK_IN = 47714,
SPELL_WEAR_CHRISTMAS_HAT = 61400
};
enum Creatures
enum Events
{
NPC_FIRE_MAGUS = 26928,
NPC_FROST_MAGUS = 26930,
NPC_ARCANE_MAGUS = 26929
};
EVENT_ICE_NOVA = 1,
EVENT_FIREBOMB,
EVENT_GRAVITY_WELL,
enum Yells
{
SAY_AGGRO = 0,
SAY_KILL = 1,
SAY_DEATH = 2,
SAY_MERGE = 3,
SAY_SPLIT = 4
EVENT_SPLIT,
EVENT_SPLIT_2,
EVENT_SPLIT_3,
EVENT_MERGE,
EVENT_MERGE_2
};
enum Misc
{
ACTION_MAGUS_DEAD = 1,
DATA_SPLIT_PERSONALITY = 2,
ACTION_MAGUS_DEAD = 1,
DATA_SPLIT_PERSONALITY = 2,
GAME_EVENT_WINTER_VEIL = 2,
GAME_EVENT_WINTER_VEIL = 2
};
const Position CenterOfRoom = {504.80f, 89.07f, -16.12f, 6.27f};
struct boss_magus_telestra : public ScriptedAI
struct boss_magus_telestra : public BossAI
{
boss_magus_telestra(Creature* creature) : ScriptedAI(creature)
boss_magus_telestra(Creature* creature) : BossAI(creature, DATA_MAGUS_TELESTRA),
_split1(false), _split2(false), _unkillable(false), _splitted(false)
{
Initialize();
instance = creature->GetInstanceScript();
bFireMagusDead = false;
bFrostMagusDead = false;
bArcaneMagusDead = false;
uiIsWaitingToAppearTimer = 0;
}
void Initialize()
{
Phase = 0;
//These times are probably wrong
uiIceNovaTimer = 7 * IN_MILLISECONDS;
uiFireBombTimer = 0;
uiGravityWellTimer = 15 * IN_MILLISECONDS;
uiCooldown = 0;
uiFireMagusGUID.Clear();
uiFrostMagusGUID.Clear();
uiArcaneMagusGUID.Clear();
for (uint8 n = 0; n < 3; ++n)
time[n] = 0;
splitPersonality = 0;
bIsWaitingToAppear = false;
}
InstanceScript* instance;
ObjectGuid uiFireMagusGUID;
ObjectGuid uiFrostMagusGUID;
ObjectGuid uiArcaneMagusGUID;
bool bFireMagusDead;
bool bFrostMagusDead;
bool bArcaneMagusDead;
bool bIsWaitingToAppear;
uint32 uiIsWaitingToAppearTimer;
uint32 uiIceNovaTimer;
uint32 uiFireBombTimer;
uint32 uiGravityWellTimer;
uint32 uiCooldown;
uint8 Phase;
uint8 splitPersonality;
time_t time[3];
void Reset() override
{
_Reset();
_split1 = false;
_split2 = false;
_unkillable = false;
_splitted = false;
Initialize();
me->SetReactState(REACT_AGGRESSIVE);
me->RemoveUnitFlag(UNIT_FLAG_UNINTERACTIBLE);
me->SetVisible(true);
instance->SetBossState(DATA_MAGUS_TELESTRA, NOT_STARTED);
if (IsHeroic() && sGameEventMgr->IsActiveEvent(GAME_EVENT_WINTER_VEIL) && !me->HasAura(SPELL_WEAR_CHRISTMAS_HAT))
me->AddAura(SPELL_WEAR_CHRISTMAS_HAT, me);
}
void JustEngagedWith(Unit* /*who*/) override
void JustEngagedWith(Unit* who) override
{
Talk(SAY_AGGRO);
BossAI::JustEngagedWith(who);
instance->SetBossState(DATA_MAGUS_TELESTRA, IN_PROGRESS);
events.ScheduleEvent(EVENT_ICE_NOVA, 20s, 25s);
events.ScheduleEvent(EVENT_FIREBOMB, 0s);
events.ScheduleEvent(EVENT_GRAVITY_WELL, 10s, 15s);
}
void JustDied(Unit* /*killer*/) override
void AttackStart(Unit* who) override
{
Talk(SAY_DEATH);
me->SetVisible(true);
instance->SetBossState(DATA_MAGUS_TELESTRA, DONE);
ScriptedAI::AttackStartCaster(who, 40.0f);
}
void KilledUnit(Unit* who) override
@@ -152,6 +151,60 @@ struct boss_magus_telestra : public ScriptedAI
Talk(SAY_KILL);
}
void DamageTaken(Unit* /*killer*/, uint32& damage, DamageEffectType /*damageType*/, SpellInfo const* /*spellInfo = nullptr*/) override
{
if (damage >= me->GetHealth() && _unkillable)
damage = me->GetHealth() - 1;
// Boss can receive damage while being already splitted, prevent performing second split if already splitted
if (_splitted)
return;
// Once in normal
if (!_split1 && me->HealthBelowPctDamaged(50, damage) && !IsHeroic())
{
_split1 = true;
events.ScheduleEvent(EVENT_SPLIT, 0s);
}
// Twice in heroic
if (!_split1 && me->HealthBelowPctDamaged(65, damage) && IsHeroic())
{
_split1 = true;
events.ScheduleEvent(EVENT_SPLIT, 0s);
}
if (!_split2 && me->HealthBelowPctDamaged(35, damage) && IsHeroic())
{
_split2 = true;
events.ScheduleEvent(EVENT_SPLIT, 0s);
}
}
void OnSpellCast(SpellInfo const* spell) override
{
if (spell->Id == SPELL_SUMMON_CLONES)
events.ScheduleEvent(EVENT_SPLIT_2, 0s);
}
void SpellHit(WorldObject* /*caster*/, SpellInfo const* spellInfo) override
{
if (spellInfo->Id == SPELL_TRIGGER_000)
events.ScheduleEvent(EVENT_MERGE, 5s);
}
void JustDied(Unit* /*killer*/) override
{
_JustDied();
Talk(SAY_DEATH);
}
void SetData(uint32 type, uint32 data) override
{
if (type == 0 && data == 1)
DoAction(ACTION_MAGUS_DEAD);
}
void DoAction(int32 action) override
{
if (action == ACTION_MAGUS_DEAD)
@@ -161,8 +214,15 @@ struct boss_magus_telestra : public ScriptedAI
++i;
time[i] = GameTime::GetGameTime();
if (i == 2 && (time[2] - time[1] < 5) && (time[1] - time[0] < 5))
++splitPersonality;
if (i == 2)
{
if ((time[2] - time[1] < 5) && (time[1] - time[0] < 5))
++splitPersonality;
// Reset time
for (uint8 n = 0; n < 3; ++n)
time[n] = 0;
}
}
}
@@ -174,177 +234,147 @@ struct boss_magus_telestra : public ScriptedAI
return 0;
}
ObjectGuid SplitPersonality(uint32 entry)
{
if (Creature* Summoned = me->SummonCreature(entry, me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(), me->GetOrientation(), TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 1s))
{
switch (entry)
{
case NPC_FIRE_MAGUS:
{
Summoned->CastSpell(Summoned, SPELL_FIRE_MAGUS_VISUAL, false);
break;
}
case NPC_FROST_MAGUS:
{
Summoned->CastSpell(Summoned, SPELL_FROST_MAGUS_VISUAL, false);
break;
}
case NPC_ARCANE_MAGUS:
{
Summoned->CastSpell(Summoned, SPELL_ARCANE_MAGUS_VISUAL, false);
break;
}
}
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0))
Summoned->AI()->AttackStart(target);
return Summoned->GetGUID();
}
return ObjectGuid::Empty;
}
void SummonedCreatureDespawn(Creature* summon) override
{
if (summon->IsAlive())
return;
if (summon->GetGUID() == uiFireMagusGUID)
{
DoAction(ACTION_MAGUS_DEAD);
bFireMagusDead = true;
}
else if (summon->GetGUID() == uiFrostMagusGUID)
{
DoAction(ACTION_MAGUS_DEAD);
bFrostMagusDead = true;
}
else if (summon->GetGUID() == uiArcaneMagusGUID)
{
DoAction(ACTION_MAGUS_DEAD);
bArcaneMagusDead = true;
}
}
void UpdateAI(uint32 diff) override
{
//Return since we have no target
if (!UpdateVictim())
return;
if (bIsWaitingToAppear)
{
me->StopMoving();
me->AttackStop();
if (uiIsWaitingToAppearTimer <= diff)
{
me->RemoveUnitFlag(UNIT_FLAG_UNINTERACTIBLE);
bIsWaitingToAppear = false;
} else uiIsWaitingToAppearTimer -= diff;
return;
}
events.Update(diff);
if ((Phase == 1) ||(Phase == 3))
if (me->HasUnitState(UNIT_STATE_CASTING))
return;
while (uint32 eventId = events.ExecuteEvent())
{
if (bFireMagusDead && bFrostMagusDead && bArcaneMagusDead)
switch (eventId)
{
for (uint8 n = 0; n < 3; ++n)
time[n] = 0;
me->GetMotionMaster()->Clear();
me->UpdatePosition(CenterOfRoom.GetPositionX(), CenterOfRoom.GetPositionY(), CenterOfRoom.GetPositionZ(), CenterOfRoom.GetOrientation());
DoCast(me, SPELL_TELESTRA_BACK);
me->SetVisible(true);
if (Phase == 1)
Phase = 2;
if (Phase == 3)
Phase = 4;
uiFireMagusGUID.Clear();
uiFrostMagusGUID.Clear();
uiArcaneMagusGUID.Clear();
bIsWaitingToAppear = true;
uiIsWaitingToAppearTimer = 4*IN_MILLISECONDS;
Talk(SAY_MERGE);
// Combat spells
case EVENT_ICE_NOVA:
DoCastSelf(SPELL_ICE_NOVA);
events.Repeat(20s, 25s);
break;
case EVENT_FIREBOMB:
DoCastVictim(SPELL_FIREBOMB);
events.Repeat(1600ms, 2400ms);
break;
case EVENT_GRAVITY_WELL:
DoCastSelf(SPELL_GRAVITY_WELL);
events.Repeat(20s, 25s);
break;
// Split sequence, continues in OnSpellCast
case EVENT_SPLIT:
_splitted = true;
// Cancel combat spells
events.Reset();
Talk(SAY_SPLIT);
me->SetReactState(REACT_PASSIVE);
DoCastSelf(SPELL_SUMMON_CLONES);
break;
case EVENT_SPLIT_2:
_unkillable = true;
// Hack, transform creature (from aura) has visible and invisible models and probability is NYI
me->SetDisplayId(15435);
me->SetUnitFlag(UNIT_FLAG_UNINTERACTIBLE);
// Not restored later, maybe after wipe
SetEquipmentSlots(false, EQUIP_UNEQUIP);
events.ScheduleEvent(EVENT_SPLIT_3, 4s);
break;
case EVENT_SPLIT_3:
DoCastSelf(SPELL_TELEPORT);
break;
// Merge sequence
case EVENT_MERGE:
DoCastSelf(SPELL_SPAWN_BACK_IN);
me->RemoveAurasDueToSpell(SPELL_CLONE_DIES_FIRE);
me->RemoveAurasDueToSpell(SPELL_CLONE_DIES_FROST);
me->RemoveAurasDueToSpell(SPELL_CLONE_DIES_ARCANE);
me->RemoveAurasDueToSpell(SPELL_SUMMON_CLONES);
Talk(SAY_MERGE);
me->RemoveUnitFlag(UNIT_FLAG_UNINTERACTIBLE);
_unkillable = false;
events.ScheduleEvent(EVENT_MERGE_2, 3s);
break;
case EVENT_MERGE_2:
me->SetReactState(REACT_AGGRESSIVE);
events.ScheduleEvent(EVENT_GRAVITY_WELL, 0s);
events.ScheduleEvent(EVENT_ICE_NOVA, 6s);
events.ScheduleEvent(EVENT_FIREBOMB, 8s);
_splitted = false;
break;
default:
break;
}
else
if (me->HasUnitState(UNIT_STATE_CASTING))
return;
}
if ((Phase == 0) && HealthBelowPct(50))
{
Phase = 1;
me->CastStop();
me->RemoveAllAuras();
me->SetVisible(false);
me->SetUnitFlag(UNIT_FLAG_UNINTERACTIBLE);
uiFireMagusGUID = SplitPersonality(NPC_FIRE_MAGUS);
uiFrostMagusGUID = SplitPersonality(NPC_FROST_MAGUS);
uiArcaneMagusGUID = SplitPersonality(NPC_ARCANE_MAGUS);
bFireMagusDead = false;
bFrostMagusDead = false;
bArcaneMagusDead = false;
Talk(SAY_SPLIT);
return;
}
if (IsHeroic() && (Phase == 2) && HealthBelowPct(10))
{
Phase = 3;
me->CastStop();
me->RemoveAllAuras();
me->SetVisible(false);
me->SetUnitFlag(UNIT_FLAG_UNINTERACTIBLE);
uiFireMagusGUID = SplitPersonality(NPC_FIRE_MAGUS);
uiFrostMagusGUID = SplitPersonality(NPC_FROST_MAGUS);
uiArcaneMagusGUID = SplitPersonality(NPC_ARCANE_MAGUS);
bFireMagusDead = false;
bFrostMagusDead = false;
bArcaneMagusDead = false;
Talk(SAY_SPLIT);
return;
}
if (uiCooldown)
{
if (uiCooldown <= diff)
uiCooldown = 0;
else
{
uiCooldown -= diff;
return;
}
}
if (uiIceNovaTimer <= diff)
{
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0))
{
DoCast(target, SPELL_ICE_NOVA, false);
uiCooldown = 1500;
}
uiIceNovaTimer = 15*IN_MILLISECONDS;
} else uiIceNovaTimer -= diff;
if (uiGravityWellTimer <= diff)
{
if (Unit* target = me->GetVictim())
{
DoCast(target, SPELL_GRAVITY_WELL);
uiCooldown = 6*IN_MILLISECONDS;
}
uiGravityWellTimer = 15*IN_MILLISECONDS;
} else uiGravityWellTimer -= diff;
if (uiFireBombTimer <= diff)
{
if (Unit* target = SelectTarget(SelectTargetMethod::Random, 0))
{
DoCast(target, SPELL_FIREBOMB, false);
uiCooldown = 2*IN_MILLISECONDS;
}
uiFireBombTimer = 2*IN_MILLISECONDS;
} else uiFireBombTimer -=diff;
DoMeleeAttackIfReady();
}
private:
bool _split1;
bool _split2;
bool _unkillable;
bool _splitted;
time_t time[3];
uint8 splitPersonality;
};
// 47710 - Summon Telestra Clones
class spell_magus_telestra_summon_clones : public SpellScript
{
PrepareSpellScript(spell_magus_telestra_summon_clones);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo(
{
SPELL_SUMMON_CLONE_FIRE,
SPELL_SUMMON_CLONE_ARCANE,
SPELL_SUMMON_CLONE_FROST
});
}
void HandleScript(SpellEffIndex /*effIndex*/)
{
Unit* caster = GetCaster();
caster->CastSpell(caster, SPELL_SUMMON_CLONE_FIRE);
caster->CastSpell(caster, SPELL_SUMMON_CLONE_ARCANE);
caster->CastSpell(caster, SPELL_SUMMON_CLONE_FROST);
}
void Register() override
{
OnEffectHit += SpellEffectFn(spell_magus_telestra_summon_clones::HandleScript, EFFECT_0, SPELL_EFFECT_SCRIPT_EFFECT);
}
};
// 47711 - Telestra Clone Dies (Fire)
// 47712 - Telestra Clone Dies (Frost)
// 47713 - Telestra Clone Dies (Arcane)
class spell_magus_telestra_clone_dies : public AuraScript
{
PrepareAuraScript(spell_magus_telestra_clone_dies);
bool Validate(SpellInfo const* /*spellInfo*/) override
{
return ValidateSpellInfo({ SPELL_TRIGGER_000 });
}
void AfterApply(AuraEffect const* /*aurEff*/, AuraEffectHandleModes /*mode*/)
{
Unit* target = GetTarget();
if (target->HasAura(SPELL_CLONE_DIES_FIRE) && target->HasAura(SPELL_CLONE_DIES_FROST) && target->HasAura(SPELL_CLONE_DIES_ARCANE))
target->CastSpell(target, SPELL_TRIGGER_000);
}
void Register() override
{
AfterEffectApply += AuraEffectApplyFn(spell_magus_telestra_clone_dies::AfterApply, EFFECT_0, SPELL_AURA_DUMMY, AURA_EFFECT_HANDLE_REAL);
}
};
class achievement_split_personality : public AchievementCriteriaScript
@@ -370,5 +400,7 @@ class achievement_split_personality : public AchievementCriteriaScript
void AddSC_boss_magus_telestra()
{
RegisterNexusCreatureAI(boss_magus_telestra);
RegisterSpellScript(spell_magus_telestra_summon_clones);
RegisterSpellScript(spell_magus_telestra_clone_dies);
new achievement_split_personality();
}