From 092b9c85e1c9a32d9ea05093e613dc0d0d12fd7c Mon Sep 17 00:00:00 2001 From: Yehonal Date: Fri, 6 Jan 2017 01:47:57 +0100 Subject: [PATCH] Revert "Prince rework and Nightbane code clean up" This reverts commit 25a3b5fb0e1c48577500f9ac1397f6656d67d2a4. --- .../Karazhan/boss_nightbane.cpp | 44 +- .../Karazhan/boss_prince_malchezaar.cpp | 550 ++++++++++-------- .../EasternKingdoms/Karazhan/bosses_opera.cpp | 51 +- .../Karazhan/instance_karazhan.cpp | 10 +- .../EasternKingdoms/Karazhan/karazhan.h | 8 +- 5 files changed, 350 insertions(+), 313 deletions(-) diff --git a/src/scripts/EasternKingdoms/Karazhan/boss_nightbane.cpp b/src/scripts/EasternKingdoms/Karazhan/boss_nightbane.cpp index 633108a32..0ac3660e3 100644 --- a/src/scripts/EasternKingdoms/Karazhan/boss_nightbane.cpp +++ b/src/scripts/EasternKingdoms/Karazhan/boss_nightbane.cpp @@ -135,7 +135,6 @@ public: { me->SetHomePosition(IntroWay[7][0], IntroWay[7][1], IntroWay[7][2], 0); me->GetMotionMaster()->MoveTargetedHome(); - } } @@ -296,26 +295,20 @@ public: { DoCastVictim(SPELL_BELLOWING_ROAR); BellowingRoarTimer = urand(30000, 40000); - } - else - BellowingRoarTimer -= diff; + } else BellowingRoarTimer -= diff; if (SmolderingBreathTimer <= diff) { DoCastVictim(SPELL_SMOLDERING_BREATH); SmolderingBreathTimer = 20000; - } - else - SmolderingBreathTimer -= diff; + } else SmolderingBreathTimer -= diff; if (CharredEarthTimer <= diff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(target, SPELL_CHARRED_EARTH); CharredEarthTimer = 20000; - } - else - CharredEarthTimer -= diff; + } else CharredEarthTimer -= diff; if (TailSweepTimer <= diff) { @@ -323,18 +316,14 @@ public: if (!me->HasInArc(M_PI, target)) DoCast(target, SPELL_TAIL_SWEEP); TailSweepTimer = 15000; - } - else - TailSweepTimer -= diff; + } else TailSweepTimer -= diff; if (SearingCindersTimer <= diff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(target, SPELL_SEARING_CINDERS); SearingCindersTimer = 10000; - } - else - SearingCindersTimer -= diff; + } else SearingCindersTimer -= diff; uint32 Prozent = uint32(me->GetHealthPct()); @@ -369,18 +358,14 @@ public: DoCastVictim(SPELL_RAIN_OF_BONES); RainBones = true; SmokingBlastTimer = 20000; - } - else - RainofBonesTimer -= diff; + } else RainofBonesTimer -= diff; if (DistractingAshTimer <= diff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(target, SPELL_DISTRACTING_ASH); DistractingAshTimer = 2000; //timer wrong - } - else - DistractingAshTimer -= diff; + } else DistractingAshTimer -= diff; } if (RainBones) @@ -389,9 +374,7 @@ public: { DoCastVictim(SPELL_SMOKING_BLAST); SmokingBlastTimer = 1500; //timer wrong - } - else - SmokingBlastTimer -= diff; + } else SmokingBlastTimer -= diff; } if (FireballBarrageTimer <= diff) @@ -399,8 +382,7 @@ public: if (Unit* target = SelectTarget(SELECT_TARGET_FARTHEST, 0)) DoCast(target, SPELL_FIREBALL_BARRAGE); FireballBarrageTimer = 20000; - } else - FireballBarrageTimer -= diff; + } else FireballBarrageTimer -= diff; if (FlyTimer <= diff) //landing { @@ -410,9 +392,7 @@ public: me->GetMotionMaster()->MovePoint(3, IntroWay[3][0], IntroWay[3][1], IntroWay[3][2]); Flying = true; - } - else - FlyTimer -= diff; + } else FlyTimer -= diff; } } }; @@ -429,12 +409,8 @@ public: if (InstanceScript* pInstance = pGo->GetInstanceScript()) { if (pInstance->GetData(DATA_NIGHTBANE) != DONE && !pGo->FindNearestCreature(NPC_NIGHTBANE, 40.0f)) - { if (Creature *cr = ObjectAccessor::GetCreature(*pPlayer, pInstance->GetData64(DATA_NIGHTBANE))) - { cr->GetMotionMaster()->MovePoint(0, IntroWay[0][0], IntroWay[0][1], IntroWay[0][2]); - } - } } return false; } diff --git a/src/scripts/EasternKingdoms/Karazhan/boss_prince_malchezaar.cpp b/src/scripts/EasternKingdoms/Karazhan/boss_prince_malchezaar.cpp index e30e3d452..5302c3be1 100644 --- a/src/scripts/EasternKingdoms/Karazhan/boss_prince_malchezaar.cpp +++ b/src/scripts/EasternKingdoms/Karazhan/boss_prince_malchezaar.cpp @@ -2,55 +2,27 @@ * Copyright (C) 2016+ AzerothCore , released under GNU GPL v2 license: http://github.com/azerothcore/azerothcore-wotlk/LICENSE-GPL2 * Copyright (C) 2008-2016 TrinityCore * Copyright (C) 2005-2009 MaNGOS -* Rescripted By Lee (Talamortis) */ +/* ScriptData +SDName: Boss_Prince_Malchezzar +SD%Complete: 100 +SDComment: +SDCategory: Karazhan +EndScriptData */ + #include "ScriptMgr.h" #include "ScriptedCreature.h" #include "karazhan.h" #include "SpellInfo.h" - -enum PrinceSay -{ - SAY_AGGRO = 0, - SAY_AXE_TOSS1 = 1, - SAY_AXE_TOSS2 = 2, - SAY_SLAY = 6, - SAY_SUMMON = 7, - SAY_DEATH = 8, -}; - -enum Spells -{ - SPELL_ENFEEBLE = 30843, //Enfeeble during phase 1 and 2 - SPELL_ENFEEBLE_EFFECT = 41624, - SPELL_SHADOWNOVA = 30852, //Shadownova used during all phases - SPELL_SW_PAIN = 30854, //Shadow word pain during phase 1 and 3 (different targeting rules though) - SPELL_THRASH_PASSIVE = 12787, //Extra attack chance during phase 2 - SPELL_SUNDER_ARMOR = 30901, //Sunder armor during phase 2 - SPELL_THRASH_AURA = 12787, //Passive proc chance for thrash - SPELL_EQUIP_AXES = 30857, //Visual for axe equiping - SPELL_AMPLIFY_DAMAGE = 39095, //Amplifiy during phase 3 - SPELL_CLEAVE = 30131, //Same as Nightbane. - SPELL_HELLFIRE = 30859, //Infenals' hellfire aura -}; - -enum creatures -{ - NETHERSPITE_INFERNAL = 17646, - MALCHEZARS_AXE = 17650, - INFERNAL_MODEL_INVISIBLE = 11686, - SPELL_INFERNAL_RELAY = 30834, - EQUIP_ID_AXE = 33542 -}; - +// 18 Coordinates for Infernal spawns struct InfernalPoint { float x, y; }; -#define INFERNAL_Z 275.5f +#define INFERNAL_Z 275.5f static InfernalPoint InfernalPoints[] = { @@ -74,6 +46,43 @@ static InfernalPoint InfernalPoints[] = { -10935.7f, -1996.0f } }; +//Enfeeble is supposed to reduce hp to 1 and then heal player back to full when it ends +//Along with reducing healing and regen while enfeebled to 0% +//This spell effect will only reduce healing +enum PrinceMalchezaar +{ + SAY_AGGRO = 0, + SAY_AXE_TOSS1 = 1, + SAY_AXE_TOSS2 = 2, + // SAY_SPECIAL1 = 3, Not used, needs to be implemented, but I don't know where it should be used. + // SAY_SPECIAL2 = 4, Not used, needs to be implemented, but I don't know where it should be used. + // SAY_SPECIAL3 = 5, Not used, needs to be implemented, but I don't know where it should be used. + SAY_SLAY = 6, + SAY_SUMMON = 7, + SAY_DEATH = 8, + + TOTAL_INFERNAL_POINTS = 18, + + SPELL_ENFEEBLE = 30843, //Enfeeble during phase 1 and 2 + SPELL_ENFEEBLE_EFFECT = 41624, + + SPELL_SHADOWNOVA = 30852, //Shadownova used during all phases + SPELL_SW_PAIN = 30854, //Shadow word pain during phase 1 and 3 (different targeting rules though) + SPELL_THRASH_PASSIVE = 12787, //Extra attack chance during phase 2 + SPELL_SUNDER_ARMOR = 30901, //Sunder armor during phase 2 + SPELL_THRASH_AURA = 12787, //Passive proc chance for thrash + SPELL_EQUIP_AXES = 30857, //Visual for axe equiping + SPELL_AMPLIFY_DAMAGE = 39095, //Amplifiy during phase 3 + SPELL_CLEAVE = 30131, //Same as Nightbane. + SPELL_HELLFIRE = 30859, //Infenals' hellfire aura + NETHERSPITE_INFERNAL = 17646, //The netherspite infernal creature + MALCHEZARS_AXE = 17650, //Malchezar's axes (creatures), summoned during phase 3 + + INFERNAL_MODEL_INVISIBLE = 11686, //Infernal Effects + SPELL_INFERNAL_RELAY = 30834, + + EQUIP_ID_AXE = 33542 //Axes info +}; //---------Infernal code first class netherspite_infernal : public CreatureScript @@ -110,18 +119,17 @@ public: DoCast(me, SPELL_HELLFIRE); HellfireTimer = 0; } - else - HellfireTimer -= diff; + else HellfireTimer -= diff; } if (CleanupTimer) { if (CleanupTimer <= diff) { + Cleanup(); CleanupTimer = 0; } - else - CleanupTimer -= diff; + else CleanupTimer -= diff; } } @@ -148,16 +156,17 @@ public: if (!done_by || done_by->GetGUID() != malchezaar) damage = 0; } + + void Cleanup(); }; }; - class boss_malchezaar : public CreatureScript { public: boss_malchezaar() : CreatureScript("boss_malchezaar") { } - CreatureAI* GetAI(Creature* creature) const override + CreatureAI* GetAI(Creature* creature) const { return GetInstanceAI(creature); } @@ -167,9 +176,9 @@ public: boss_malchezaarAI(Creature* creature) : ScriptedAI(creature) { instance = creature->GetInstanceScript(); + memset(axes, 0, sizeof(axes)); } - InstanceScript* instance; uint32 EnfeebleTimer; uint32 EnfeebleResetTimer; @@ -179,60 +188,105 @@ public: uint32 AmplifyDamageTimer; uint32 Cleave_Timer; uint32 InfernalTimer; + uint32 AxesTargetSwitchTimer; uint32 InfernalCleanupTimer; - uint32 phase; - uint32 enfeeble_health[5]; - uint64 enfeeble_targets[5]; std::vector infernals; std::vector positions; - void Initialize() + uint64 axes[2]; + uint64 enfeeble_targets[5]; + uint32 enfeeble_health[5]; + + uint32 phase; + + void Reset() { + AxesCleanup(); + ClearWeapons(); + InfernalCleanup(); + positions.clear(); + + for (uint8 i = 0; i < 5; ++i) + { + enfeeble_targets[i] = 0; + enfeeble_health[i] = 0; + } + + for (uint8 i = 0; i < TOTAL_INFERNAL_POINTS; ++i) + positions.push_back(&InfernalPoints[i]); + EnfeebleTimer = 30000; EnfeebleResetTimer = 38000; ShadowNovaTimer = 35500; SWPainTimer = 20000; - Cleave_Timer = 8000; - InfernalCleanupTimer = 47000; AmplifyDamageTimer = 5000; - SunderArmorTimer = urand(5000, 10000); + Cleave_Timer = 8000; InfernalTimer = 40000; + InfernalCleanupTimer = 47000; + AxesTargetSwitchTimer = urand(7500, 20000); + SunderArmorTimer = urand(5000, 10000); phase = 1; - clearweapons(); - positions.clear(); + instance->HandleGameObject(instance->GetData64(DATA_GO_NETHER_DOOR), true); } - void clearweapons() - { - SetEquipmentSlots(false, EQUIP_UNEQUIP, EQUIP_UNEQUIP, EQUIP_NO_CHANGE); - me->SetCanDualWield(false); - } - - void Reset() override - { - Initialize(); - } - - void KilledUnit(Unit* /*victim*/) override + void KilledUnit(Unit* /*victim*/) { Talk(SAY_SLAY); } - void JustDied(Unit* /*killer*/) override + void JustDied(Unit* /*killer*/) { Talk(SAY_DEATH); + + AxesCleanup(); + ClearWeapons(); + InfernalCleanup(); + positions.clear(); + + for (uint8 i = 0; i < TOTAL_INFERNAL_POINTS; ++i) + positions.push_back(&InfernalPoints[i]); + + instance->HandleGameObject(instance->GetData64(DATA_GO_NETHER_DOOR), true); } - void EnterCombat(Unit* /*who*/) override + void EnterCombat(Unit* /*who*/) { Talk(SAY_AGGRO); + + instance->HandleGameObject(instance->GetData64(DATA_GO_NETHER_DOOR), false); // Open the door leading further in } - void SummonAxes() + void InfernalCleanup() { - Creature* axe = me->SummonCreature(MALCHEZARS_AXE, me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 10000); + //Infernal Cleanup + for (std::vector::const_iterator itr = infernals.begin(); itr != infernals.end(); ++itr) + if (Unit* pInfernal = ObjectAccessor::GetUnit(*me, *itr)) + if (pInfernal->IsAlive()) + { + pInfernal->SetVisible(false); + pInfernal->setDeathState(JUST_DIED); + } + + infernals.clear(); + } + + void AxesCleanup() + { + for (uint8 i = 0; i < 2; ++i) + { + Unit* axe = ObjectAccessor::GetUnit(*me, axes[i]); + if (axe && axe->IsAlive()) + Unit::Kill(axe, axe); + axes[i] = 0; + } + } + + void ClearWeapons() + { + SetEquipmentSlots(false, EQUIP_UNEQUIP, EQUIP_UNEQUIP, EQUIP_NO_CHANGE); + me->SetCanDualWield(false); } void EnfeebleHealthEffect() @@ -283,78 +337,176 @@ public: } } - void SummonInfernal() + void SummonInfernal(const uint32 /*diff*/) { - InfernalPoint *point = 0; - Position pos; + InfernalPoint *point = NULL; + Position pos; + + if ((me->GetMapId() != 532) || positions.empty()) + me->GetRandomNearPosition(pos, 60); + else + { + point = Trinity::Containers::SelectRandomContainerElement(positions); + pos.Relocate(point->x, point->y, INFERNAL_Z, frand(0.0f, float(M_PI * 2))); + } - if ((me->GetMapId() != 532) || positions.empty()) - me->GetRandomNearPosition(pos, 40); - else - { - point = Trinity::Containers::SelectRandomContainerElement(positions); - pos.Relocate(point->x, point->y, INFERNAL_Z, frand(0.0f, float(M_PI * 2))); - } + Creature* infernal = me->SummonCreature(NETHERSPITE_INFERNAL, pos, TEMPSUMMON_TIMED_DESPAWN, 180000); - if (Creature* RELAY = me->FindNearestCreature(NPC_RELAY, 100.0f)) - { - Creature* infernal = RELAY->SummonCreature(NETHERSPITE_INFERNAL, pos, TEMPSUMMON_TIMED_DESPAWN, 180000); + if (infernal) + { + + infernal->SetDisplayId(INFERNAL_MODEL_INVISIBLE); + infernal->setFaction(me->getFaction()); + if (point) + CAST_AI(netherspite_infernal::netherspite_infernalAI, infernal->AI())->point = point; + CAST_AI(netherspite_infernal::netherspite_infernalAI, infernal->AI())->malchezaar = me->GetGUID(); - if (infernal) - { - infernal->SetDisplayId(INFERNAL_MODEL_INVISIBLE); - infernal->setFaction(me->getFaction()); - if (point) - CAST_AI(netherspite_infernal::netherspite_infernalAI, infernal->AI())->point = point; - CAST_AI(netherspite_infernal::netherspite_infernalAI, infernal->AI())->malchezaar = me->GetGUID(); - infernals.push_back(infernal->GetGUID()); - //Creature* PRINCE = me->FindNearestCreature(NPC_PRINCE, 100.0f); - RELAY->AI()->DoCast(infernal ,SPELL_INFERNAL_RELAY); - } - } - Talk(SAY_SUMMON); + infernals.push_back(infernal->GetGUID()); + DoCast(infernal, SPELL_INFERNAL_RELAY); + } + + Talk(SAY_SUMMON); } - void Phase2() - { - me->InterruptNonMeleeSpells(false); - phase = 2; - DoCast(me, SPELL_EQUIP_AXES); - Talk(SAY_AXE_TOSS1); - DoCast(me, SPELL_THRASH_AURA, true); - SetEquipmentSlots(false, EQUIP_ID_AXE, EQUIP_ID_AXE, EQUIP_NO_CHANGE); - me->SetCanDualWield(true); - me->SetAttackTime(OFF_ATTACK, (me->GetAttackTime(BASE_ATTACK) * 150) / 100); - } - - void Phase3() - { - me->RemoveAurasDueToSpell(SPELL_THRASH_AURA); - Talk(SAY_AXE_TOSS2); - phase = 3; - clearweapons(); - SummonAxes(); - } - - void UpdateAI(uint32 diff) override + void UpdateAI(uint32 diff) { if (!UpdateVictim()) return; + if (EnfeebleResetTimer && EnfeebleResetTimer <= diff) // Let's not forget to reset that + { + EnfeebleResetHealth(); + EnfeebleResetTimer = 0; + } + else EnfeebleResetTimer -= diff; + + if (me->HasUnitState(UNIT_STATE_STUNNED)) // While shifting to phase 2 malchezaar stuns himself + return; + + if (me->GetUInt64Value(UNIT_FIELD_TARGET) != me->GetVictim()->GetGUID()) + me->SetTarget(me->GetVictim()->GetGUID()); + + if (phase == 1) + { + if (HealthBelowPct(60)) + { + me->InterruptNonMeleeSpells(false); + + phase = 2; + + //animation + DoCast(me, SPELL_EQUIP_AXES); + + //text + Talk(SAY_AXE_TOSS1); + + //passive thrash aura + DoCast(me, SPELL_THRASH_AURA, true); + + //models + SetEquipmentSlots(false, EQUIP_ID_AXE, EQUIP_ID_AXE, EQUIP_NO_CHANGE); + + me->SetAttackTime(OFF_ATTACK, (me->GetAttackTime(BASE_ATTACK) * 150) / 100); + me->SetCanDualWield(true); + } + } + else if (phase == 2) + { + if (HealthBelowPct(30)) + { + InfernalTimer = 15000; + + phase = 3; + + ClearWeapons(); + + //remove thrash + me->RemoveAurasDueToSpell(SPELL_THRASH_AURA); + + Talk(SAY_AXE_TOSS2); + + Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true); + { + Creature* axe = me->SummonCreature(MALCHEZARS_AXE, me->GetPositionX(), me->GetPositionY(), me->GetPositionZ(), 0, TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT, 1000); + if (axe) + { + axe->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); + axe->setFaction(me->getFaction()); + axe->GetGUID(); + if (target) + { + axe->AI()->AttackStart(target); + //axe->getThreatManager().tauntApply(target); //Taunt Apply and fade out does not work properly + // So we'll use a hack to add a lot of threat to our target + axe->AddThreat(target, 10000000.0f); + } + } + } + + if (ShadowNovaTimer > 35000) + ShadowNovaTimer = EnfeebleTimer + 5000; + + return; + } + + if (SunderArmorTimer <= diff) + { + DoCastVictim(SPELL_SUNDER_ARMOR); + SunderArmorTimer = urand(10000, 18000); + } + else SunderArmorTimer -= diff; + + if (Cleave_Timer <= diff) + { + DoCastVictim(SPELL_CLEAVE); + Cleave_Timer = urand(6000, 12000); + } + else Cleave_Timer -= diff; + } + else + { + if (AxesTargetSwitchTimer <= diff) + { + AxesTargetSwitchTimer = urand(7500, 20000); + + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) + { + if (Unit* axe = ObjectAccessor::GetUnit(*me, axes[0])) + { + if (axe->GetVictim()) + DoModifyThreatPercent(axe->GetVictim(), -100); + if (target) + axe->AddThreat(target, 1000000.0f); + //axe->getThreatManager().tauntFadeOut(axe->GetVictim()); + //axe->getThreatManager().tauntApply(target); + } + } + } + else AxesTargetSwitchTimer -= diff; + + if (AmplifyDamageTimer <= diff) + { + if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) + DoCast(target, SPELL_AMPLIFY_DAMAGE); + AmplifyDamageTimer = urand(20000, 30000); + } + else AmplifyDamageTimer -= diff; + } + + //Time for global and double timers if (InfernalTimer <= diff) { - SummonInfernal(); + SummonInfernal(diff); InfernalTimer = phase == 3 ? 14500 : 44500; // 15 secs in phase 3, 45 otherwise } else InfernalTimer -= diff; - if (Cleave_Timer <= diff) + if (ShadowNovaTimer <= diff) { - DoCast(SPELL_CLEAVE); - Cleave_Timer = 8000; + DoCastVictim(SPELL_SHADOWNOVA); + ShadowNovaTimer = phase == 3 ? 31000 : uint32(-1); } - else - Cleave_Timer -= diff; + else ShadowNovaTimer -= diff; if (phase != 2) { @@ -362,7 +514,7 @@ public: { Unit* target = NULL; if (phase == 1) - target = me->GetVictim(); // Target the Tank + target = me->GetVictim(); // the tank else // anyone but the tank target = SelectTarget(SELECT_TARGET_RANDOM, 1, 100, true); @@ -371,41 +523,7 @@ public: SWPainTimer = 20000; } - else - SWPainTimer -= diff; - } - - if (ShadowNovaTimer <= diff) - { - DoCast(SPELL_SHADOWNOVA); - ShadowNovaTimer = 35500; - } - else - ShadowNovaTimer -= diff; - - if (phase == 1) - { - if (HealthBelowPct(60)) - { - Phase2(); - } - } - if (phase == 2) - { - if (HealthBelowPct(30)) - { - Phase3(); - - if (AmplifyDamageTimer <= diff) - { - Unit* target = NULL; - target = SelectTarget(SELECT_TARGET_RANDOM, 1, 100, true); - DoCast(target, SPELL_AMPLIFY_DAMAGE); - AmplifyDamageTimer = urand(20000, 30000); - } - else - AmplifyDamageTimer -= diff; - } + else SWPainTimer -= diff; } if (phase != 3) @@ -420,84 +538,56 @@ public: else EnfeebleTimer -= diff; } - - DoMeleeAttackIfReady(); - } - - }; -}; - -class prince_axes : public CreatureScript -{ -public: - prince_axes() : CreatureScript("prince_axes") { } - - CreatureAI* GetAI(Creature* creature) const override - { - return GetInstanceAI(creature); - } - - struct prince_axesAI : public ScriptedAI - { - - prince_axesAI(Creature* creature) : ScriptedAI(creature) - { - Initialize(); - instance = creature->GetInstanceScript(); - } - - uint32 AxesTargetSwitchTimer; - InstanceScript* instance; - - - void Initialize() - { - AxesTargetSwitchTimer = 7500; - me->SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NOT_SELECTABLE); - me->SetCanDualWield(true); - } - - void Reset() - { - } - - void EnterCombat(Unit* /*who*/) override - { - DoZoneInCombat(); - } - - void changetarget() - { - if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) - { - if (me->GetVictim()) - DoModifyThreatPercent(me->GetVictim(), -100); - if (target) - me->AddThreat(target, 1000000.0f); - } - } - - void UpdateAI(uint32 diff) override - { - if (!UpdateVictim()) - return; - - if (AxesTargetSwitchTimer <= diff) - { - AxesTargetSwitchTimer = urand(7500, 20000); - changetarget(); - } + if (phase == 2) + DoMeleeAttacksIfReady(); else - AxesTargetSwitchTimer -= diff; + DoMeleeAttackIfReady(); + } - DoMeleeAttackIfReady(); + void DoMeleeAttacksIfReady() + { + if (me->IsWithinMeleeRange(me->GetVictim()) && !me->IsNonMeleeSpellCast(false)) + { + //Check for base attack + if (me->isAttackReady() && me->GetVictim()) + { + me->AttackerStateUpdate(me->GetVictim()); + me->resetAttackTimer(); + } + //Check for offhand attack + if (me->isAttackReady(OFF_ATTACK) && me->GetVictim()) + { + me->AttackerStateUpdate(me->GetVictim(), OFF_ATTACK); + me->resetAttackTimer(OFF_ATTACK); + } + } + } + + void Cleanup(Creature* infernal, InfernalPoint *point) + { + for (std::vector::iterator itr = infernals.begin(); itr != infernals.end(); ++itr) + if (*itr == infernal->GetGUID()) + { + infernals.erase(itr); + break; + } + + positions.push_back(point); } }; }; +void netherspite_infernal::netherspite_infernalAI::Cleanup() +{ + Creature* pMalchezaar = ObjectAccessor::GetCreature(*me, malchezaar); + + if (pMalchezaar && pMalchezaar->IsAlive()) + CAST_AI(boss_malchezaar::boss_malchezaarAI, pMalchezaar->AI())->Cleanup(me, point); + +} + void AddSC_boss_malchezaar() { new boss_malchezaar(); - new prince_axes(); new netherspite_infernal(); -} \ No newline at end of file +} diff --git a/src/scripts/EasternKingdoms/Karazhan/bosses_opera.cpp b/src/scripts/EasternKingdoms/Karazhan/bosses_opera.cpp index 560208f19..531eb424a 100644 --- a/src/scripts/EasternKingdoms/Karazhan/bosses_opera.cpp +++ b/src/scripts/EasternKingdoms/Karazhan/bosses_opera.cpp @@ -193,8 +193,7 @@ public: { me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE); AggroTimer = 0; - } else - AggroTimer -= diff; + } else AggroTimer -= diff; } if (!UpdateVictim()) @@ -204,22 +203,19 @@ public: { DoCast(SelectTarget(SELECT_TARGET_RANDOM, 0), SPELL_WATERBOLT); WaterBoltTimer = TitoDied ? 1500 : 5000; - } else - WaterBoltTimer -= diff; + } else WaterBoltTimer -= diff; if (FearTimer <= diff) { DoCastVictim(SPELL_SCREAM); FearTimer = 30000; - } else - FearTimer -= diff; + } else FearTimer -= diff; if (!SummonedTito) { if (SummonTitoTimer <= diff) SummonTito(); - else - SummonTitoTimer -= diff; + else SummonTitoTimer -= diff; } DoMeleeAttackIfReady(); @@ -277,8 +273,7 @@ public: { DoCastVictim(SPELL_YIPPING); YipTimer = 10000; - } else - YipTimer -= diff; + } else YipTimer -= diff; DoMeleeAttackIfReady(); } @@ -388,8 +383,7 @@ public: { me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE); AggroTimer = 0; - } else - AggroTimer -= diff; + } else AggroTimer -= diff; } if (!UpdateVictim()) @@ -399,16 +393,14 @@ public: { DoCastVictim(SPELL_BRAIN_BASH); BrainBashTimer = 15000; - } else - BrainBashTimer -= diff; + } else BrainBashTimer -= diff; if (BrainWipeTimer <= diff) { if (Unit* target = SelectTarget(SELECT_TARGET_RANDOM, 0, 100, true)) DoCast(target, SPELL_BRAIN_WIPE); BrainWipeTimer = 20000; - } else - BrainWipeTimer -= diff; + } else BrainWipeTimer -= diff; DoMeleeAttackIfReady(); } @@ -497,8 +489,7 @@ public: { me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE); AggroTimer = 0; - } else - AggroTimer -= diff; + } else AggroTimer -= diff; } if (!UpdateVictim()) @@ -508,8 +499,7 @@ public: { DoCastVictim(SPELL_CLEAVE); CleaveTimer = 5000; - } else - CleaveTimer -= diff; + } else CleaveTimer -= diff; if (RustCount < 8) { @@ -519,8 +509,7 @@ public: Talk(EMOTE_RUST); DoCast(me, SPELL_RUST); RustTimer = 6000; - } else - RustTimer -= diff; + } else RustTimer -= diff; } DoMeleeAttackIfReady(); @@ -608,8 +597,7 @@ public: { me->RemoveFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_NON_ATTACKABLE); AggroTimer = 0; - } else - AggroTimer -= diff; + } else AggroTimer -= diff; } if (!UpdateVictim()) @@ -619,22 +607,19 @@ public: { DoCastVictim(SPELL_MANGLE); MangleTimer = urand(5000, 8000); - } else - MangleTimer -= diff; + } else MangleTimer -= diff; if (ShredTimer <= diff) { DoCastVictim(SPELL_SHRED); ShredTimer = urand(10000, 15000); - } else - ShredTimer -= diff; + } else ShredTimer -= diff; if (ScreamTimer <= diff) { DoCastVictim(SPELL_FRIGHTENED_SCREAM); ScreamTimer = urand(20000, 30000); - } else - ScreamTimer -= diff; + } else ScreamTimer -= diff; DoMeleeAttackIfReady(); } @@ -710,15 +695,13 @@ public: if (Creature* Cyclone = DoSpawnCreature(CREATURE_CYCLONE, float(urand(0, 9)), float(urand(0, 9)), 0, 0, TEMPSUMMON_TIMED_DESPAWN, 15000)) Cyclone->CastSpell(Cyclone, SPELL_CYCLONE_VISUAL, true); CycloneTimer = 22000; - } else - CycloneTimer -= diff; + } else CycloneTimer -= diff; if (ChainLightningTimer <= diff) { DoCastVictim(SPELL_CHAIN_LIGHTNING); ChainLightningTimer = 8000; - } else - ChainLightningTimer -= diff; + } else ChainLightningTimer -= diff; DoMeleeAttackIfReady(); } diff --git a/src/scripts/EasternKingdoms/Karazhan/instance_karazhan.cpp b/src/scripts/EasternKingdoms/Karazhan/instance_karazhan.cpp index 4e336a2b6..f7a687a85 100644 --- a/src/scripts/EasternKingdoms/Karazhan/instance_karazhan.cpp +++ b/src/scripts/EasternKingdoms/Karazhan/instance_karazhan.cpp @@ -47,10 +47,6 @@ public: break; case NPC_NIGHTBANE: m_uiNightBaneGUID = creature->GetGUID(); - case NPC_RELAY: - m_uiInfernalRelay = creature->GetGUID(); - case NPC_INFERNAL_TARGET: - m_uiInfernaltargetGUID = creature->GetGUID(); } } @@ -219,6 +215,7 @@ public: return OperaEvent; case DATA_OPERA_OZ_DEATHCOUNT: return OzDeathCount; + case DATA_KILREK: return m_uiKilrekGUID; case DATA_TERESTIAN: @@ -276,14 +273,12 @@ public: case DATA_MASTERS_TERRACE_DOOR_2: return MastersTerraceDoor[1]; case DATA_IMAGE_OF_MEDIVH: return ImageGUID; case DATA_NIGHTBANE: return m_uiNightBaneGUID; - case DATA_PRINCE_INFERNAL_RELAY: return m_uiInfernalRelay; } return 0; } private: - uint64 InfernalTargetsGuidList; uint32 OperaEvent; uint32 OzDeathCount; uint32 OptionalBossCount; @@ -307,9 +302,6 @@ public: uint64 MastersTerraceDoor[2]; uint64 ImageGUID; uint64 DustCoveredChest; - uint64 m_uiInfernalRelay; // Summoning Infernals From sky. - uint64 m_uiInfernaltargetGUID; - }; }; diff --git a/src/scripts/EasternKingdoms/Karazhan/karazhan.h b/src/scripts/EasternKingdoms/Karazhan/karazhan.h index c1ee95b6c..910390163 100644 --- a/src/scripts/EasternKingdoms/Karazhan/karazhan.h +++ b/src/scripts/EasternKingdoms/Karazhan/karazhan.h @@ -57,8 +57,7 @@ enum KZDataTypes DATA_MASTERS_TERRACE_DOOR_1 = 27, DATA_MASTERS_TERRACE_DOOR_2 = 28, DATA_GO_SIDE_ENTRANCE_DOOR = 29, - DATA_PRINCE = 30, - DATA_PRINCE_INFERNAL_RELAY = 31 + DATA_PRINCE = 30 }; enum KZOperaEvents @@ -78,8 +77,6 @@ enum KZMiscCreatures NPC_ATTUMEN_THE_HUNTSMAN = 15550, NPC_ATTUMEN_THE_HUNTSMAN_MOUNTED = 16152, NPC_NIGHTBANE = 17225, - NPC_RELAY = 17645, - NPC_PRINCE = 15690, // Trash NPC_COLDMIST_WIDOW = 16171, @@ -90,8 +87,7 @@ enum KZMiscCreatures NPC_PHASE_HOUND = 16178, NPC_DREADBEAST = 16177, NPC_SHADOWBEAST = 16176, - NPC_KILREK = 17229, - NPC_INFERNAL_TARGET = 17644 + NPC_KILREK = 17229 }; enum KZGameObjectIds