From cdceb775a03ecfec8117d922108b21817aff1394 Mon Sep 17 00:00:00 2001 From: Benjamin Jackson <38561765+heyitsbench@users.noreply.github.com> Date: Wed, 27 Aug 2025 05:28:18 -0400 Subject: [PATCH] fix(Scripts/Karazhan): Implement Tenris Mirkblood. (#22551) Co-authored-by: amed80 <8395873+amed80@users.noreply.github.com> --- .../pending_db_world/tenris-mirkblood.sql | 82 ++++ .../Karazhan/boss_tenris_mirkblood.cpp | 375 ++++++++++++++++++ .../Karazhan/instance_karazhan.cpp | 1 + .../EasternKingdoms/Karazhan/karazhan.h | 8 +- .../eastern_kingdoms_script_loader.cpp | 2 + 5 files changed, 466 insertions(+), 2 deletions(-) create mode 100644 data/sql/updates/pending_db_world/tenris-mirkblood.sql create mode 100644 src/server/scripts/EasternKingdoms/Karazhan/boss_tenris_mirkblood.cpp diff --git a/data/sql/updates/pending_db_world/tenris-mirkblood.sql b/data/sql/updates/pending_db_world/tenris-mirkblood.sql new file mode 100644 index 000000000..67a76c31a --- /dev/null +++ b/data/sql/updates/pending_db_world/tenris-mirkblood.sql @@ -0,0 +1,82 @@ +SET @SAY_APPROACH = 0, +@SAY_AGGRO = 1, +@SAY_SUMMON = 2, +@GUID = 12748; + +DELETE FROM `areatrigger_scripts` WHERE `entry` IN (5014, 5015); +INSERT INTO `areatrigger_scripts` (`entry`, `ScriptName`) VALUES +(5014, 'at_karazhan_mirkblood_approach'), +(5015, 'at_karazhan_mirkblood_entrance'); + +UPDATE `creature_template` SET `minlevel` = 73, `maxlevel` = 73, `speed_run` = 1.85714285714, `ScriptName` = 'boss_tenris_mirkblood' WHERE `entry` = 28194; +UPDATE `creature_template` SET `speed_walk` = 0.4, `speed_run` = 0.14285714285, `ScriptName` = 'npc_sanguine_spirit' WHERE `entry` = 28232; +UPDATE `creature_template` SET `unit_flags` = 33554432, `AIName` = 'SmartAI' WHERE `entry` = 28485; +UPDATE `creature_template` SET `unit_flags` = 33555200 WHERE `entry` = 28493; + +UPDATE `creature_model_info` SET `BoundingRadius` = 0.200000002980232238, `CombatReach` = 0.400000005960464477 WHERE `DisplayID` = 25296; +UPDATE `creature_model_info` SET `BoundingRadius` = 0.465000003576278686, `CombatReach` = 1.5 WHERE `DisplayID` = 25541; + +DELETE FROM `creature_text` WHERE `CreatureID` = 28194; +INSERT INTO `creature_text` (`CreatureID`, `GroupID`, `ID`, `Text`, `Type`, `Language`, `Probability`, `Emote`, `Duration`, `Sound`, `BroadcastTextId`, `TextRange`, `comment`) VALUES +(28194, @SAY_APPROACH, 0, 'I smell... $r. Delicious!', 14, 0, 100, 0, 0, 0, 27780, 0, 'Prince Tenris Mirkblood - SAY_APPROACH'), +(28194, @SAY_AGGRO, 0, 'I shall consume you!', 14, 0, 100, 0, 0, 0, 27781, 0, 'Prince Tenris Mirkblood - SAY_AGGRO'), +(28194, @SAY_SUMMON, 0, 'Drink, mortals! Taste my blood! Taste your death!', 12, 0, 100, 0, 0, 0, 27712, 0, 'Prince Tenris Mirkblood - SAY_SUMMON'); + +UPDATE `gameobject_template` SET `ScriptName` = 'go_blood_drenched_door' WHERE `entry` = 181032; + +DELETE FROM `spell_script_names` WHERE `spell_id` IN (50883, 50925, 51013); +INSERT INTO `spell_script_names` (`spell_id`, `ScriptName`) VALUES +(50883, 'spell_mirkblood_blood_mirror_target_picker'), +(50925, 'spell_mirkblood_dash_gash_return_to_tank_pre_spell'), +(51013, 'spell_mirkblood_exsanguinate'); + +DELETE FROM `spell_linked_spell` WHERE `spell_trigger` = -50845 AND `spell_effect` = -50844; +INSERT INTO `spell_linked_spell` (`spell_trigger`, `spell_effect`, `type`, `comment`) VALUES +(-50845, -50844, 0, 'Tenris Mirkblood Blood Mirror'); + +DELETE FROM `creature_template_addon` WHERE `entry` IN (28232, 28485, 28493); +INSERT INTO `creature_template_addon` (`entry`, `path_id`, `mount`, `bytes1`, `bytes2`, `emote`, `visibilityDistanceType`, `auras`) VALUES +(28232, 0, 0, 0, 0, 0, 0, '51282'), +(28485, 0, 0, 0, 0, 0, 0, '30987'), +(28493, 0, 0, 0, 0, 383, 0, ''); + +DELETE FROM `creature_template_movement` WHERE `CreatureId` IN (28485, 28493); +INSERT INTO `creature_template_movement` (`CreatureId`, `Ground`, `Swim`, `Flight`, `Rooted`, `Chase`, `Random`, `InteractionPauseTimer`) VALUES +(28485, 0, 0, 1, 0, 0, 0, NULL), +(28493, 0, 0, 1, 0, 0, 0, NULL); + +DELETE FROM `creature` WHERE `guid` BETWEEN @GUID+0 AND @GUID+9 AND `id1` IN (28485, 28493); +INSERT INTO `creature` (`guid`, `id1`, `id2`, `id3`, `map`, `zoneId`, `areaId`, `spawnMask`, `phaseMask`, `equipment_id`, `position_x`, `position_y`, `position_z`, `orientation`, `spawntimesecs`, `wander_distance`, `currentwaypoint`, `curhealth`, `curmana`, `MovementType`, `npcflag`, `unit_flags`, `dynamicflags`, `ScriptName`, `VerifiedBuild`, `CreateObject`, `Comment`) VALUES +(@GUID+0, 28485, 0, 0, 532, 0, 0, 1, 1, 0, -11087.619, -1996.4193, 82.59072, 0.453785598278045654, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL), +(@GUID+1, 28485, 0, 0, 532, 0, 0, 1, 1, 0, -11104.703, -1973.5052, 82.73294, 0.05235987901687622, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL), +(@GUID+2, 28485, 0, 0, 532, 0, 0, 1, 1, 0, -11084.556, -1981.4388, 82.4658, 0.575958669185638427, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL), +(@GUID+3, 28485, 0, 0, 532, 0, 0, 1, 1, 0, -11091.643, -1961.8134, 82.77006, 0.104719758033752441, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL), +(@GUID+4, 28485, 0, 0, 532, 0, 0, 1, 1, 0, -11097.971, -1982.734, 82.39082, 0.418879032135009765, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL), +(@GUID+5, 28493, 0, 0, 532, 0, 0, 1, 1, 0, -11097.721, -1982.62, 77.43985, 5.113814830780029296, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL), +(@GUID+6, 28493, 0, 0, 532, 0, 0, 1, 1, 0, -11104.523, -1973.4592, 78.07421, 1.396263360977172851, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL), +(@GUID+7, 28493, 0, 0, 532, 0, 0, 1, 1, 0, -11084.696, -1981.4202, 77.87848, 4.904375076293945312, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL), +(@GUID+8, 28493, 0, 0, 532, 0, 0, 1, 1, 0, -11091.594, -1962.1276, 78.054115, 2.146754980087280273, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL), +(@GUID+9, 28493, 0, 0, 532, 0, 0, 1, 1, 0, -11087.617, -1996.2291, 77.72322, 0.436332315206527709, 300, 0, 0, 4050, 0, 0, 0, 0, 0, '', 49345, 2, NULL); + +DELETE FROM `game_event_creature` WHERE `eventEntry` = 120 AND `guid` BETWEEN @GUID+0 AND @GUID+9; +INSERT INTO `game_event_creature` (`eventEntry`, `guid`) VALUES +(120, @GUID+0), +(120, @GUID+1), +(120, @GUID+2), +(120, @GUID+3), +(120, @GUID+4), +(120, @GUID+5), +(120, @GUID+6), +(120, @GUID+7), +(120, @GUID+8), +(120, @GUID+9); + +DELETE FROM `smart_scripts` WHERE (`entryorguid` = 28485) AND (`source_type` = 0) AND (`id` IN (0)); +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 +(28485, 0, 0, 0, 37, 0, 100, 0, 0, 0, 0, 0, 0, 11, 51773, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 'Blood Vat Bunny - On Initialize - Cast \'Scourge Invasion Blood Vat Bunny\''); + +DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId` = 13 AND `SourceEntry` = 51773 AND `ConditionTypeOrReference` = 31 AND `ConditionValue2` = 28485; +INSERT INTO `conditions` (`SourceTypeOrReferenceId`, `SourceGroup`, `SourceEntry`, `SourceId`, `ElseGroup`, `ConditionTypeOrReference`, `ConditionTarget`, `ConditionValue1`, `ConditionValue2`, `ConditionValue3`, `NegativeCondition`, `ErrorType`, `ErrorTextId`, `ScriptName`, `Comment`) VALUES +(13, 1, 51773, 0, 0, 31, 0, 3, 28485, 0, 0, 0, 0, '', 'Target must be unit Blood Vat Bunny'); + +UPDATE `spell_dbc` SET `Effect_1` = 28, `EffectMiscValue_1` = 28232, `EffectMiscValueB_1` = 64 WHERE `ID` = 50996; diff --git a/src/server/scripts/EasternKingdoms/Karazhan/boss_tenris_mirkblood.cpp b/src/server/scripts/EasternKingdoms/Karazhan/boss_tenris_mirkblood.cpp new file mode 100644 index 000000000..518a46055 --- /dev/null +++ b/src/server/scripts/EasternKingdoms/Karazhan/boss_tenris_mirkblood.cpp @@ -0,0 +1,375 @@ +/* + * This file is part of the AzerothCore Project. See AUTHORS file for Copyright information + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Affero General Public License as published by the + * Free Software Foundation; either version 3 of the License, or (at your + * option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see . + */ + +#include "karazhan.h" +#include "AreaTriggerScript.h" +#include "CreatureScript.h" +#include "GameObjectAI.h" +#include "GameObjectScript.h" +#include "Player.h" +#include "ScriptedCreature.h" +#include "SpellInfo.h" +#include "SpellScript.h" +#include "SpellScriptLoader.h" +#include "UnitAI.h" + +enum Text +{ + SAY_APPROACH = 0, + SAY_AGGRO = 1, + SAY_SUMMON = 2 +}; + +enum Spells +{ + SPELL_BLOOD_MIRROR0 = 50844, + SPELL_BLOOD_MIRROR1 = 50845, + SPELL_BLOOD_MIRROR_TARGET_PICKER = 50883, + SPELL_BLOOD_MIRROR_TRANSITION_VISUAL = 50910, + SPELL_BLOOD_MIRROR_DAMAGE = 50846, + + SPELL_BLOOD_TAP = 51135, + + SPELL_BLOOD_SWOOP = 50922, + SPELL_DASH_GASH_PRE_SPELL = 50923, + SPELL_DASH_GASH_RETURN_TO_TANK = 50924, + // SPELL_DASH_GASH_RETURN_TO_TANK_PRE_SPELL = 50925, + // SPELL_DASH_GASH_RETURN_TO_TANK_PRE_SPELL_ROOT = 50932, + + SPELL_DESPAWN_SANGUINE_SPIRIT_VISUAL = 51214, + SPELL_DESPAWN_SANGUINE_SPIRITS = 51212, + SPELL_SANGUINE_SPIRIT_AURA = 50993, + SPELL_SANGUINE_SPIRIT_PRE_AURA = 51282, + SPELL_SANGUINE_SPIRIT_PRE_AURA2 = 51283, + SPELL_SUMMON_SANGUINE_SPIRIT0 = 50996, + SPELL_SUMMON_SANGUINE_SPIRIT1 = 50998, + // SPELL_SUMMON_SANGUINE_SPIRIT2 = 51204, + SPELL_SUMMON_SANGUINE_SPIRIT_MISSILE_BURST = 51208, + SPELL_SUMMON_SANGUINE_SPIRIT_SHORT_MISSILE_BURST = 51280, + SPELL_SUMMON_SANGUINE_SPIRIT_ON_KILL = 51205, + SPELL_EXSANGUINATE = 51013, + SPELL_DUMMY_NUKE_RANGE_SELF = 51106, +}; + +enum Events +{ + EVENT_SAY = 1, + EVENT_FLAG = 2 +}; + +struct boss_tenris_mirkblood : public BossAI +{ + boss_tenris_mirkblood(Creature* creature) : BossAI(creature, DATA_MIRKBLOOD) + { + scheduler.SetValidator([this] + { + return !me->HasUnitState(UNIT_STATE_CASTING); + }); + } + + void Reset() override + { + _Reset(); + + me->SetImmuneToPC(true); + + ScheduleHealthCheckEvent(50, [&] { + Talk(SAY_SUMMON); + DoCast(SPELL_SUMMON_SANGUINE_SPIRIT_MISSILE_BURST); + }); + + ScheduleHealthCheckEvent(45, [&] { + ScheduleTimedEvent(10s, 15s, [&] { + DoCast(SPELL_BLOOD_TAP); + }, 15s, 40s); + }); + } + + void JustEngagedWith(Unit* /*who*/) override + { + DoZoneInCombat(); + + ScheduleTimedEvent(1s, 5s, [&] { + // Blood Mirror + DoCast(SPELL_BLOOD_MIRROR_TARGET_PICKER); + }, 20s, 50s); + ScheduleTimedEvent(30s, [&] { + // Blood Swoop + DoCast(SPELL_DASH_GASH_PRE_SPELL); + }, 15s, 40s); + ScheduleTimedEvent(6s, 15s, [&] { + // Sanguine Spirit + DoCast(SPELL_SUMMON_SANGUINE_SPIRIT_SHORT_MISSILE_BURST); + }, 6s, 15s); + } + + void KilledUnit(Unit* victim) override + { + if (!victim) + return; + + DoCast(victim, SPELL_SUMMON_SANGUINE_SPIRIT_ON_KILL); + } + + void DamageTaken(Unit* attacker, uint32& damage, DamageEffectType damageType, SpellSchoolMask damageSchoolMask) override + { + BossAI::DamageTaken(attacker, damage, damageType, damageSchoolMask); + + if (!me->HasAura(SPELL_BLOOD_MIRROR0)) + return; + + if (!_mirrorTarget) + return; + + int32 damageTaken = damage; + + me->CastCustomSpell(_mirrorTarget, SPELL_BLOOD_MIRROR_DAMAGE, &damageTaken, &damageTaken, &damageTaken, true, nullptr, nullptr, me->GetGUID()); + } + + void SpellHit(Unit* caster, SpellInfo const* spell) override + { + if (spell->Id == SPELL_BLOOD_MIRROR0 && caster != me) + _mirrorTarget = caster; + } + + void EnterEvadeMode(EvadeReason why) override + { + _EnterEvadeMode(why); + me->SetImmuneToPC(false); + } + +private: + Unit* _mirrorTarget = nullptr; +}; + +struct npc_sanguine_spirit : public ScriptedAI +{ + npc_sanguine_spirit(Creature* creature) : ScriptedAI(creature) {} + + void Reset() override + { + scheduler.CancelAll(); + me->ApplySpellImmune(0, IMMUNITY_SCHOOL, SPELL_SCHOOL_MASK_ALL, true); + + me->SetReactState(REACT_PASSIVE); + + DoCastSelf(SPELL_SANGUINE_SPIRIT_PRE_AURA); + + scheduler.Schedule(5s, [this](TaskContext /*context*/) + { + DoCastSelf(SPELL_SANGUINE_SPIRIT_PRE_AURA2); + }).Schedule(3s, [this](TaskContext /*context*/) + { + me->SetReactState(REACT_AGGRESSIVE); + me->SetInCombatWithZone(); + DoCastSelf(SPELL_SANGUINE_SPIRIT_AURA); + }); + } + + void UpdateAI(uint32 diff) override + { + scheduler.Update(diff); + UpdateVictim(); + } +}; + +class spell_mirkblood_blood_mirror_target_picker : public SpellScript +{ + PrepareSpellScript(spell_mirkblood_blood_mirror_target_picker) + + bool Validate(SpellInfo const* /*spell*/) override + { + return ValidateSpellInfo({ SPELL_BLOOD_MIRROR0, SPELL_BLOOD_MIRROR1, SPELL_BLOOD_MIRROR_TRANSITION_VISUAL }); + } + + void HandleHit() + { + Unit* caster = GetCaster(); + + if (!caster->ToCreature()) + return; + + Unit* target = caster->GetAI()->SelectTarget(SelectTargetMethod::Random, 0, 0.0f, true, false); + + if (!target) // Only Blood Mirror the tank if they're the only one around + target = caster->GetVictim(); + + if (!target) + return; + + caster->CastSpell(caster, SPELL_BLOOD_MIRROR_TRANSITION_VISUAL, TRIGGERED_FULL_MASK); + caster->CastSpell(target, SPELL_BLOOD_MIRROR_TRANSITION_VISUAL, TRIGGERED_FULL_MASK); + + caster->AddAura(SPELL_BLOOD_MIRROR1, caster); // Should be a cast, but channeled spell results in either Mirkblood or player being unactionable + caster->AddAura(SPELL_BLOOD_MIRROR1, target); // Adding aura manually causes visual to not appear properly, but better than breaking gameplay + + target->CastSpell(caster, SPELL_BLOOD_MIRROR0); // Clone player + } + + void Register() override + { + OnCast += SpellCastFn(spell_mirkblood_blood_mirror_target_picker::HandleHit); + } +}; + +class spell_mirkblood_dash_gash_return_to_tank_pre_spell : public SpellScript +{ + PrepareSpellScript(spell_mirkblood_dash_gash_return_to_tank_pre_spell) + + bool Validate(SpellInfo const* /*spell*/) override + { + return ValidateSpellInfo({ SPELL_DASH_GASH_RETURN_TO_TANK }); + } + + void HandleCast() + { + if (!GetCaster() || !GetCaster()->GetThreatMgr().GetCurrentVictim()) + return; + // Probably wrong, maybe don't charge if would charge the same target? + if (GetCaster()->GetDistance2d(GetCaster()->GetThreatMgr().GetCurrentVictim()) < 5.0f) + return; + + GetCaster()->CastSpell(GetCaster()->GetVictim(), SPELL_DASH_GASH_RETURN_TO_TANK); + } + + void Register() override + { + OnCast += SpellCastFn(spell_mirkblood_dash_gash_return_to_tank_pre_spell::HandleCast); + } +}; + +class spell_mirkblood_exsanguinate : public SpellScript +{ + PrepareSpellScript(spell_mirkblood_exsanguinate) + + void CalculateDamage() + { + if (!GetHitUnit()) + return; + + SetHitDamage(std::max((GetHitUnit()->GetHealth() * 0.66f), 2000.0f)); + } + + void Register() override + { + OnHit += SpellHitFn(spell_mirkblood_exsanguinate::CalculateDamage); + } +}; + +class at_karazhan_mirkblood_approach : public AreaTriggerScript +{ +public: + at_karazhan_mirkblood_approach() : AreaTriggerScript("at_karazhan_mirkblood_approach") {} + + bool OnTrigger(Player* player, AreaTrigger const* /*trigger*/) override + { + if (InstanceScript* instance = player->GetInstanceScript()) + if (instance->GetBossState(DATA_MIRKBLOOD) != DONE) + if (Creature* mirkblood = instance->GetCreature(DATA_MIRKBLOOD)) + mirkblood->AI()->Talk(SAY_APPROACH, player); + + return false; + } +}; + +class at_karazhan_mirkblood_entrance : public AreaTriggerScript +{ +public: + at_karazhan_mirkblood_entrance() : AreaTriggerScript("at_karazhan_mirkblood_entrance") {} + + bool OnTrigger(Player* player, AreaTrigger const* /*trigger*/) override + { + if (InstanceScript* instance = player->GetInstanceScript()) + if (instance->GetBossState(DATA_MIRKBLOOD) != DONE) + if (Creature* mirkblood = instance->GetCreature(DATA_MIRKBLOOD)) + mirkblood->SetImmuneToPC(false); + + return false; + } +}; + +class go_blood_drenched_door : public GameObjectScript +{ +public: + go_blood_drenched_door() : GameObjectScript("go_blood_drenched_door") {} + + struct go_blood_drenched_doorAI : public GameObjectAI + { + go_blood_drenched_doorAI(GameObject* go) : GameObjectAI(go) {} + + EventMap events; + Creature* mirkblood; + Player* opener; + + bool GossipHello(Player* player, bool /*reportUse*/) override + { + events.Reset(); + + if (InstanceScript* instance = player->GetInstanceScript()) + if (instance->GetBossState(DATA_MIRKBLOOD) != DONE) + { + opener = player; + mirkblood = instance->GetCreature(DATA_MIRKBLOOD); + + events.ScheduleEvent(EVENT_SAY, 1s); + events.ScheduleEvent(EVENT_FLAG, 5s); + me->SetGameObjectFlag(GO_FLAG_NOT_SELECTABLE); + } + + return true; + } + + void UpdateAI(uint32 diff) override + { + if (events.Empty()) + return; + + events.Update(diff); + switch (events.ExecuteEvent()) + { + case EVENT_SAY: + if (!mirkblood) + return; + mirkblood->AI()->Talk(SAY_AGGRO, opener); + break; + case EVENT_FLAG: + if (!mirkblood) + return; + mirkblood->SetImmuneToPC(false); + me->Delete(); + break; + } + } + }; + + GameObjectAI* GetAI(GameObject* go) const override + { + return new go_blood_drenched_doorAI(go); + } +}; + +void AddSC_boss_tenris_mirkblood() +{ + RegisterKarazhanCreatureAI(boss_tenris_mirkblood); + RegisterKarazhanCreatureAI(npc_sanguine_spirit); + RegisterSpellScript(spell_mirkblood_blood_mirror_target_picker); + RegisterSpellScript(spell_mirkblood_dash_gash_return_to_tank_pre_spell); + RegisterSpellScript(spell_mirkblood_exsanguinate); + new at_karazhan_mirkblood_approach(); + new at_karazhan_mirkblood_entrance(); + new go_blood_drenched_door(); +} diff --git a/src/server/scripts/EasternKingdoms/Karazhan/instance_karazhan.cpp b/src/server/scripts/EasternKingdoms/Karazhan/instance_karazhan.cpp index 2f4f27dae..a283e65cc 100644 --- a/src/server/scripts/EasternKingdoms/Karazhan/instance_karazhan.cpp +++ b/src/server/scripts/EasternKingdoms/Karazhan/instance_karazhan.cpp @@ -47,6 +47,7 @@ ObjectData const creatureData[] = { NPC_JULIANNE, DATA_JULIANNE }, { NPC_NIGHTBANE, DATA_NIGHTBANE }, { NPC_TERESTIAN_ILLHOOF, DATA_TERESTIAN }, + { NPC_TENRIS_MIRKBLOOD, DATA_MIRKBLOOD }, { 0, 0 } }; diff --git a/src/server/scripts/EasternKingdoms/Karazhan/karazhan.h b/src/server/scripts/EasternKingdoms/Karazhan/karazhan.h index 4e0d57f4b..890fdcf2d 100644 --- a/src/server/scripts/EasternKingdoms/Karazhan/karazhan.h +++ b/src/server/scripts/EasternKingdoms/Karazhan/karazhan.h @@ -73,7 +73,9 @@ enum KZDataTypes DATA_ROAR = 41, DATA_STRAWMAN = 42, DATA_TINHEAD = 43, - DATA_TITO = 44 + DATA_TITO = 44, + + DATA_MIRKBLOOD = 45 }; enum KZOperaEvents @@ -135,7 +137,9 @@ enum KZCreatures // Malchezaar Helpers NPC_INFERNAL_TARGET = 17644, - NPC_INFERNAL_RELAY = 17645 + NPC_INFERNAL_RELAY = 17645, + + NPC_TENRIS_MIRKBLOOD = 28194 }; diff --git a/src/server/scripts/EasternKingdoms/eastern_kingdoms_script_loader.cpp b/src/server/scripts/EasternKingdoms/eastern_kingdoms_script_loader.cpp index 67360281a..b92b35215 100644 --- a/src/server/scripts/EasternKingdoms/eastern_kingdoms_script_loader.cpp +++ b/src/server/scripts/EasternKingdoms/eastern_kingdoms_script_loader.cpp @@ -78,6 +78,7 @@ void AddSC_bosses_opera(); void AddSC_boss_netherspite(); void AddSC_karazhan(); void AddSC_boss_nightbane(); +void AddSC_boss_tenris_mirkblood(); void AddSC_boss_felblood_kaelthas(); // Magister's Terrace void AddSC_boss_selin_fireheart(); void AddSC_boss_vexallus(); @@ -229,6 +230,7 @@ void AddEasternKingdomsScripts() AddSC_boss_netherspite(); AddSC_karazhan(); AddSC_boss_nightbane(); + AddSC_boss_tenris_mirkblood(); AddSC_boss_felblood_kaelthas(); // Magister's Terrace AddSC_boss_selin_fireheart(); AddSC_boss_vexallus();