510 lines
23 KiB
C#
510 lines
23 KiB
C#
// Copyright (c) CypherCore <http://github.com/CypherCore> All rights reserved.
|
|
// Licensed under the GNU GENERAL PUBLIC LICENSE. See LICENSE file in the project root for full license information.
|
|
|
|
using Framework.Constants;
|
|
using Game.AI;
|
|
using Game.Entities;
|
|
using Game.Scripting;
|
|
using System;
|
|
|
|
namespace Scripts.EasternKingdoms.BlackrockMountain.BlackrockSpire.RendBlackhand
|
|
{
|
|
struct SpellIds
|
|
{
|
|
public const uint Whirlwind = 13736; // sniffed
|
|
public const uint Cleave = 15284;
|
|
public const uint MortalStrike = 16856;
|
|
public const uint Frenzy = 8269;
|
|
public const uint Knockdown = 13360; // On spawn during Gyth fight
|
|
}
|
|
|
|
struct TextIds
|
|
{
|
|
// Rend Blackhand
|
|
public const uint SayBlackhand1 = 0;
|
|
public const uint SayBlackhand2 = 1;
|
|
public const uint EmoteBlackhandDismount = 2;
|
|
// Victor Nefarius
|
|
public const uint SayNefarius0 = 0;
|
|
public const uint SayNefarius1 = 1;
|
|
public const uint SayNefarius2 = 2;
|
|
public const uint SayNefarius3 = 3;
|
|
public const uint SayNefarius4 = 4;
|
|
public const uint SayNefarius5 = 5;
|
|
public const uint SayNefarius6 = 6;
|
|
public const uint SayNefarius7 = 7;
|
|
public const uint SayNefarius8 = 8;
|
|
public const uint SayNefarius9 = 9;
|
|
}
|
|
|
|
struct AddIds
|
|
{
|
|
public const uint ChromaticWhelp = 10442;
|
|
public const uint ChromaticDragonspawn = 10447;
|
|
public const uint BlackhandDragonHandler = 10742;
|
|
}
|
|
|
|
struct MiscConst
|
|
{
|
|
public const uint NefariusPath1 = 11037360;
|
|
public const uint NefariusPath2 = 11037368;
|
|
public const uint NefariusPath3 = 11037376;
|
|
public const uint RendPath1 = 11037440;
|
|
public const uint RendPath2 = 11037448;
|
|
|
|
public static Wave[] Wave2 = // 22 sec
|
|
{
|
|
new Wave(10447, 209.8637f, -428.2729f, 110.9877f, 0.6632251f),
|
|
new Wave(10442, 209.3122f, -430.8724f, 110.9814f, 2.9147f),
|
|
new Wave(10442, 211.3309f, -425.9111f, 111.0006f, 1.727876f)
|
|
};
|
|
|
|
public static Wave[] Wave3 = // 60 sec
|
|
{
|
|
new Wave(10742, 208.6493f, -424.5787f, 110.9872f, 5.8294f),
|
|
new Wave(10447, 203.9482f, -428.9446f, 110.982f, 4.677482f),
|
|
new Wave(10442, 203.3441f, -426.8668f, 110.9772f, 4.712389f),
|
|
new Wave(10442, 206.3079f, -424.7509f, 110.9943f, 4.08407f)
|
|
};
|
|
|
|
public static Wave[] Wave4 = // 49 sec
|
|
{
|
|
new Wave(10742, 212.3541f, -412.6826f, 111.0352f, 5.88176f),
|
|
new Wave(10447, 212.5754f, -410.2841f, 111.0296f, 2.740167f),
|
|
new Wave(10442, 212.3449f, -414.8659f, 111.0348f, 2.356194f),
|
|
new Wave(10442, 210.6568f, -412.1552f, 111.0124f, 0.9773844f)
|
|
};
|
|
|
|
public static Wave[] Wave5 = // 60 sec
|
|
{
|
|
new Wave(10742, 210.2188f, -410.6686f, 111.0211f, 5.8294f),
|
|
new Wave(10447, 209.4078f, -414.13f, 111.0264f, 4.677482f),
|
|
new Wave(10442, 208.0858f, -409.3145f, 111.0118f, 4.642576f),
|
|
new Wave(10442, 207.9811f, -413.0728f, 111.0098f, 5.288348f),
|
|
new Wave(10442, 208.0854f, -412.1505f, 111.0057f, 4.08407f)
|
|
};
|
|
|
|
public static Wave[] Wave6 = // 27 sec
|
|
{
|
|
new Wave(10742, 213.9138f, -426.512f, 111.0013f, 3.316126f),
|
|
new Wave(10447, 213.7121f, -429.8102f, 110.9888f, 1.413717f),
|
|
new Wave(10447, 213.7157f, -424.4268f, 111.009f, 3.001966f),
|
|
new Wave(10442, 210.8935f, -423.913f, 111.0125f, 5.969026f),
|
|
new Wave(10442, 212.2642f, -430.7648f, 110.9807f, 5.934119f)
|
|
};
|
|
|
|
public static Position GythLoc = new Position(211.762f, -397.5885f, 111.1817f, 4.747295f);
|
|
public static Position Teleport1Loc = new Position(194.2993f, -474.0814f, 121.4505f, -0.01225555f);
|
|
public static Position Teleport2Loc = new Position(216.485f, -434.93f, 110.888f, -0.01225555f);
|
|
}
|
|
|
|
class Wave
|
|
{
|
|
public uint entry;
|
|
public float x_pos;
|
|
public float y_pos;
|
|
public float z_pos;
|
|
public float o_pos;
|
|
|
|
public Wave(uint _entry, float x, float y, float z, float o)
|
|
{
|
|
entry = _entry;
|
|
x_pos = x;
|
|
y_pos = y;
|
|
z_pos = z;
|
|
o_pos = o;
|
|
}
|
|
}
|
|
|
|
struct EventIds
|
|
{
|
|
public const uint Start1 = 1;
|
|
public const uint Start2 = 2;
|
|
public const uint Start3 = 3;
|
|
public const uint Start4 = 4;
|
|
public const uint TurnToRend = 5;
|
|
public const uint TurnToPlayer = 6;
|
|
public const uint TurnToFacing1 = 7;
|
|
public const uint TurnToFacing2 = 8;
|
|
public const uint TurnToFacing3 = 9;
|
|
public const uint Wave1 = 10;
|
|
public const uint Wave2 = 11;
|
|
public const uint Wave3 = 12;
|
|
public const uint Wave4 = 13;
|
|
public const uint Wave5 = 14;
|
|
public const uint Wave6 = 15;
|
|
public const uint WavesText1 = 16;
|
|
public const uint WavesText2 = 17;
|
|
public const uint WavesText3 = 18;
|
|
public const uint WavesText4 = 19;
|
|
public const uint WavesText5 = 20;
|
|
public const uint WavesCompleteText1 = 21;
|
|
public const uint WavesCompleteText2 = 22;
|
|
public const uint WavesCompleteText3 = 23;
|
|
public const uint WavesEmote1 = 24;
|
|
public const uint WavesEmote2 = 25;
|
|
public const uint PathRend = 26;
|
|
public const uint PathNefarius = 27;
|
|
public const uint Teleport1 = 28;
|
|
public const uint Teleport2 = 29;
|
|
public const uint Whirlwind = 30;
|
|
public const uint Cleave = 31;
|
|
public const uint MortalStrike = 32;
|
|
}
|
|
|
|
[Script]
|
|
class boss_rend_blackhand : BossAI
|
|
{
|
|
bool gythEvent;
|
|
ObjectGuid victorGUID;
|
|
ObjectGuid portcullisGUID;
|
|
|
|
public boss_rend_blackhand(Creature creature) : base(creature, DataTypes.WarchiefRendBlackhand) { }
|
|
|
|
public override void Reset()
|
|
{
|
|
_Reset();
|
|
gythEvent = false;
|
|
victorGUID.Clear();
|
|
portcullisGUID.Clear();
|
|
}
|
|
|
|
public override void JustEngagedWith(Unit who)
|
|
{
|
|
base.JustEngagedWith(who);
|
|
_events.ScheduleEvent(EventIds.Whirlwind, TimeSpan.FromSeconds(13), TimeSpan.FromSeconds(15));
|
|
_events.ScheduleEvent(EventIds.Cleave, TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(17));
|
|
_events.ScheduleEvent(EventIds.MortalStrike, TimeSpan.FromSeconds(17), TimeSpan.FromSeconds(19));
|
|
}
|
|
|
|
public override void IsSummonedBy(WorldObject summoner)
|
|
{
|
|
me.SetImmuneToPC(false);
|
|
DoZoneInCombat();
|
|
}
|
|
|
|
public override void JustDied(Unit killer)
|
|
{
|
|
_JustDied();
|
|
Creature victor = me.FindNearestCreature(CreaturesIds.LordVictorNefarius, 75.0f, true);
|
|
if (victor != null)
|
|
victor.GetAI().SetData(1, 2);
|
|
}
|
|
|
|
public override void SetData(uint type, uint data)
|
|
{
|
|
if (type == BRSMiscConst.Areatrigger && data == BRSMiscConst.AreatriggerBlackrockStadium)
|
|
{
|
|
if (!gythEvent)
|
|
{
|
|
gythEvent = true;
|
|
|
|
Creature victor = me.FindNearestCreature(CreaturesIds.LordVictorNefarius, 5.0f, true);
|
|
if (victor != null)
|
|
victorGUID = victor.GetGUID();
|
|
|
|
GameObject portcullis = me.FindNearestGameObject(GameObjectsIds.DrPortcullis, 50.0f);
|
|
if (portcullis != null)
|
|
portcullisGUID = portcullis.GetGUID();
|
|
|
|
_events.ScheduleEvent(EventIds.TurnToPlayer, TimeSpan.FromSeconds(0));
|
|
_events.ScheduleEvent(EventIds.Start1, TimeSpan.FromSeconds(1));
|
|
}
|
|
}
|
|
}
|
|
|
|
public override void MovementInform(MovementGeneratorType type, uint id)
|
|
{
|
|
if (type == MovementGeneratorType.Waypoint)
|
|
{
|
|
switch (id)
|
|
{
|
|
case 5:
|
|
_events.ScheduleEvent(EventIds.Teleport1, TimeSpan.FromSeconds(2));
|
|
break;
|
|
case 11:
|
|
Creature gyth = me.FindNearestCreature(CreaturesIds.Gyth, 10.0f, true);
|
|
if (gyth != null)
|
|
gyth.GetAI().SetData(1, 1);
|
|
me.DespawnOrUnsummon(TimeSpan.FromSeconds(1), TimeSpan.FromDays(7));
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
public override void UpdateAI(uint diff)
|
|
{
|
|
if (gythEvent)
|
|
{
|
|
_events.Update(diff);
|
|
|
|
_events.ExecuteEvents(eventId =>
|
|
{
|
|
switch (eventId)
|
|
{
|
|
case EventIds.Start1:
|
|
{
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetAI().Talk(TextIds.SayNefarius0);
|
|
_events.ScheduleEvent(EventIds.Start2, TimeSpan.FromSeconds(4));
|
|
break;
|
|
}
|
|
case EventIds.Start2:
|
|
{
|
|
_events.ScheduleEvent(EventIds.TurnToPlayer, TimeSpan.FromSeconds(0));
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.HandleEmoteCommand(Emote.OneshotPoint);
|
|
_events.ScheduleEvent(EventIds.Start3, TimeSpan.FromSeconds(4));
|
|
break;
|
|
}
|
|
case EventIds.Start3:
|
|
{
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetAI().Talk(TextIds.SayNefarius1);
|
|
_events.ScheduleEvent(EventIds.Wave1, TimeSpan.FromSeconds(2));
|
|
_events.ScheduleEvent(EventIds.TurnToRend, TimeSpan.FromSeconds(4));
|
|
_events.ScheduleEvent(EventIds.WavesText1, TimeSpan.FromSeconds(20));
|
|
break;
|
|
}
|
|
case EventIds.TurnToRend:
|
|
{
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
{
|
|
victor.SetFacingToObject(me);
|
|
victor.HandleEmoteCommand(Emote.OneshotTalk);
|
|
}
|
|
break;
|
|
}
|
|
case EventIds.TurnToPlayer:
|
|
{
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
{
|
|
Unit player = victor.SelectNearestPlayer(60.0f);
|
|
if (player != null)
|
|
victor.SetFacingToObject(player);
|
|
}
|
|
break;
|
|
}
|
|
case EventIds.TurnToFacing1:
|
|
{
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.SetFacingTo(1.518436f);
|
|
break;
|
|
}
|
|
case EventIds.TurnToFacing2:
|
|
me.SetFacingTo(1.658063f);
|
|
break;
|
|
case EventIds.TurnToFacing3:
|
|
me.SetFacingTo(1.500983f);
|
|
break;
|
|
case EventIds.WavesEmote1:
|
|
{
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.HandleEmoteCommand(Emote.OneshotQuestion);
|
|
break;
|
|
}
|
|
case EventIds.WavesEmote2:
|
|
me.HandleEmoteCommand(Emote.OneshotRoar);
|
|
break;
|
|
case EventIds.WavesText1:
|
|
{
|
|
_events.ScheduleEvent(EventIds.TurnToPlayer, TimeSpan.FromSeconds(0));
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetAI().Talk(TextIds.SayNefarius2);
|
|
me.HandleEmoteCommand(Emote.OneshotTalk);
|
|
_events.ScheduleEvent(EventIds.TurnToFacing1, TimeSpan.FromSeconds(4));
|
|
_events.ScheduleEvent(EventIds.WavesEmote1, TimeSpan.FromSeconds(5));
|
|
_events.ScheduleEvent(EventIds.Wave2, TimeSpan.FromSeconds(2));
|
|
_events.ScheduleEvent(EventIds.WavesText2, TimeSpan.FromSeconds(20));
|
|
break;
|
|
}
|
|
case EventIds.WavesText2:
|
|
{
|
|
_events.ScheduleEvent(EventIds.TurnToPlayer, TimeSpan.FromSeconds(0));
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetAI().Talk(TextIds.SayNefarius3);
|
|
_events.ScheduleEvent(EventIds.TurnToFacing1, TimeSpan.FromSeconds(4));
|
|
_events.ScheduleEvent(EventIds.Wave3, TimeSpan.FromSeconds(2));
|
|
_events.ScheduleEvent(EventIds.WavesText3, TimeSpan.FromSeconds(20));
|
|
break;
|
|
}
|
|
case EventIds.WavesText3:
|
|
{
|
|
_events.ScheduleEvent(EventIds.TurnToPlayer, TimeSpan.FromSeconds(0));
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetAI().Talk(TextIds.SayNefarius4);
|
|
_events.ScheduleEvent(EventIds.TurnToFacing1, TimeSpan.FromSeconds(4));
|
|
_events.ScheduleEvent(EventIds.Wave4, TimeSpan.FromSeconds(2));
|
|
_events.ScheduleEvent(EventIds.WavesText4, TimeSpan.FromSeconds(20));
|
|
break;
|
|
}
|
|
case EventIds.WavesText4:
|
|
Talk(TextIds.SayBlackhand1);
|
|
_events.ScheduleEvent(EventIds.WavesEmote2, TimeSpan.FromSeconds(4));
|
|
_events.ScheduleEvent(EventIds.TurnToFacing3, TimeSpan.FromSeconds(8));
|
|
_events.ScheduleEvent(EventIds.Wave5, TimeSpan.FromSeconds(2));
|
|
_events.ScheduleEvent(EventIds.WavesText5, TimeSpan.FromSeconds(20));
|
|
break;
|
|
case EventIds.WavesText5:
|
|
{
|
|
_events.ScheduleEvent(EventIds.TurnToPlayer, TimeSpan.FromSeconds(0));
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetAI().Talk(TextIds.SayNefarius5);
|
|
_events.ScheduleEvent(EventIds.TurnToFacing1, TimeSpan.FromSeconds(4));
|
|
_events.ScheduleEvent(EventIds.Wave6, TimeSpan.FromSeconds(2));
|
|
_events.ScheduleEvent(EventIds.WavesCompleteText1, TimeSpan.FromSeconds(20));
|
|
break;
|
|
}
|
|
case EventIds.WavesCompleteText1:
|
|
{
|
|
_events.ScheduleEvent(EventIds.TurnToPlayer, TimeSpan.FromSeconds(0));
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetAI().Talk(TextIds.SayNefarius6);
|
|
_events.ScheduleEvent(EventIds.TurnToFacing1, TimeSpan.FromSeconds(4));
|
|
_events.ScheduleEvent(EventIds.WavesCompleteText2, TimeSpan.FromSeconds(13));
|
|
break;
|
|
}
|
|
case EventIds.WavesCompleteText2:
|
|
{
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetAI().Talk(TextIds.SayNefarius7);
|
|
Talk(TextIds.SayBlackhand2);
|
|
_events.ScheduleEvent(EventIds.PathRend, TimeSpan.FromSeconds(1));
|
|
_events.ScheduleEvent(EventIds.WavesCompleteText3, TimeSpan.FromSeconds(4));
|
|
break;
|
|
}
|
|
case EventIds.WavesCompleteText3:
|
|
{
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetAI().Talk(TextIds.SayNefarius8);
|
|
_events.ScheduleEvent(EventIds.PathNefarius, TimeSpan.FromSeconds(1));
|
|
_events.ScheduleEvent(EventIds.PathRend, TimeSpan.FromSeconds(1));
|
|
break;
|
|
}
|
|
case EventIds.PathNefarius:
|
|
{
|
|
Creature victor = ObjectAccessor.GetCreature(me, victorGUID);
|
|
if (victor != null)
|
|
victor.GetMotionMaster().MovePath(MiscConst.NefariusPath1, true);
|
|
break;
|
|
}
|
|
case EventIds.PathRend:
|
|
me.GetMotionMaster().MovePath(MiscConst.RendPath1, false);
|
|
break;
|
|
case EventIds.Teleport1:
|
|
me.NearTeleportTo(194.2993f, -474.0814f, 121.4505f, -0.01225555f);
|
|
_events.ScheduleEvent(EventIds.Teleport2, TimeSpan.FromSeconds(50));
|
|
break;
|
|
case EventIds.Teleport2:
|
|
me.NearTeleportTo(216.485f, -434.93f, 110.888f, -0.01225555f);
|
|
me.SummonCreature(CreaturesIds.Gyth, 211.762f, -397.5885f, 111.1817f, 4.747295f);
|
|
break;
|
|
case EventIds.Wave1:
|
|
{
|
|
GameObject portcullis = ObjectAccessor.GetGameObject(me, portcullisGUID);
|
|
if (portcullis != null)
|
|
portcullis.UseDoorOrButton();
|
|
|
|
// move wave
|
|
break;
|
|
}
|
|
case EventIds.Wave2:
|
|
{
|
|
// spawn wave
|
|
GameObject portcullis = ObjectAccessor.GetGameObject(me, portcullisGUID);
|
|
if (portcullis != null)
|
|
portcullis.UseDoorOrButton();
|
|
// move wave
|
|
break;
|
|
}
|
|
case EventIds.Wave3:
|
|
{
|
|
// spawn wave
|
|
GameObject portcullis = ObjectAccessor.GetGameObject(me, portcullisGUID);
|
|
if (portcullis != null)
|
|
portcullis.UseDoorOrButton();
|
|
// move wave
|
|
break;
|
|
}
|
|
case EventIds.Wave4:
|
|
{
|
|
// spawn wave
|
|
GameObject portcullis = ObjectAccessor.GetGameObject(me, portcullisGUID);
|
|
if (portcullis != null)
|
|
portcullis.UseDoorOrButton();
|
|
// move wave
|
|
break;
|
|
}
|
|
case EventIds.Wave5:
|
|
{
|
|
// spawn wave
|
|
GameObject portcullis = ObjectAccessor.GetGameObject(me, portcullisGUID);
|
|
if (portcullis != null)
|
|
portcullis.UseDoorOrButton();
|
|
// move wave
|
|
break;
|
|
}
|
|
case EventIds.Wave6:
|
|
{
|
|
// spawn wave
|
|
GameObject portcullis = ObjectAccessor.GetGameObject(me, portcullisGUID);
|
|
if (portcullis != null)
|
|
portcullis.UseDoorOrButton();
|
|
// move wave
|
|
break;
|
|
}
|
|
default:
|
|
break;
|
|
}
|
|
});
|
|
}
|
|
|
|
if (!UpdateVictim())
|
|
return;
|
|
|
|
_events.Update(diff);
|
|
|
|
if (me.HasUnitState(UnitState.Casting))
|
|
return;
|
|
|
|
_events.ExecuteEvents(eventId =>
|
|
{
|
|
switch (eventId)
|
|
{
|
|
case EventIds.Whirlwind:
|
|
DoCast(SpellIds.Whirlwind);
|
|
_events.ScheduleEvent(EventIds.Whirlwind, TimeSpan.FromSeconds(13), TimeSpan.FromSeconds(18));
|
|
break;
|
|
case EventIds.Cleave:
|
|
DoCastVictim(SpellIds.Cleave);
|
|
_events.ScheduleEvent(EventIds.Cleave, TimeSpan.FromSeconds(10), TimeSpan.FromSeconds(14));
|
|
break;
|
|
case EventIds.MortalStrike:
|
|
DoCastVictim(SpellIds.MortalStrike);
|
|
_events.ScheduleEvent(EventIds.MortalStrike, TimeSpan.FromSeconds(14), TimeSpan.FromSeconds(16));
|
|
break;
|
|
}
|
|
|
|
if (me.HasUnitState(UnitState.Casting))
|
|
return;
|
|
});
|
|
DoMeleeAttackIfReady();
|
|
}
|
|
}
|
|
}
|
|
|