refactor(Core/Scripts): move Northrend gossip handlers to database (#25275)

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Andrew
2026-03-28 19:14:31 -03:00
committed by GitHub
parent c10e19e2c6
commit 0803e77488
5 changed files with 96 additions and 225 deletions

View File

@@ -0,0 +1,96 @@
-- Move Northrend gossip handlers from C++ to database
-- NPCs: Iruk (26219), Razael & Lyana (23998, 23778), Roxi Ramrocket (31247), Avatar of Freya (27801)
-- =====================================================
-- 1. npc_iruk (26219) - zone_borean_tundra
-- Show gossip option if quest 11961 is incomplete
-- On select: player self-casts spell 46816 (Create Totem of Issliruk)
-- =====================================================
-- Condition on gossip_menu_option: show option if quest 11961 is in progress
DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId`=15 AND `SourceGroup`=9280 AND `SourceEntry`=0;
INSERT INTO `conditions` (`SourceTypeOrReferenceId`, `SourceGroup`, `SourceEntry`, `SourceId`, `ElseGroup`, `ConditionTypeOrReference`, `ConditionTarget`, `ConditionValue1`, `ConditionValue2`, `ConditionValue3`, `NegativeCondition`, `ErrorType`, `ErrorTextId`, `ScriptName`, `Comment`) VALUES
(15, 9280, 0, 0, 0, 47, 0, 11961, 8, 0, 0, 0, 0, '', 'Iruk - Show option if quest 11961 is in progress');
-- SAI: on gossip select (menu 9280, option 0) -> close gossip + invoker self-cast spell 46816
DELETE FROM `smart_scripts` WHERE `entryorguid`=26219 AND `source_type`=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`, `event_param6`, `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
(26219, 0, 0, 1, 62, 0, 100, 512, 9280, 0, 0, 0, 0, 0, 72, 0, 0, 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 'Iruk - On Gossip Select - Close Gossip'),
(26219, 0, 1, 0, 61, 0, 100, 512, 0, 0, 0, 0, 0, 0, 134, 46816, 2, 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 'Iruk - Linked - Invoker Cast Create Totem of Issliruk');
-- Update creature_template
UPDATE `creature_template` SET `ScriptName`='', `AIName`='SmartAI' WHERE `entry`=26219;
-- =====================================================
-- 2. npc_razael_and_lyana - zone_howling_fjord
-- Razael (23998), menu 8870 -> ActionMenuID 8869 (already wired)
-- Lyana (23778), menu 8879 -> ActionMenuID 8878 (already wired)
-- Both require quest 11221 incomplete, give TalkedToCreature credit on select
-- =====================================================
-- Condition on menu 8870 option 0: quest 11221 in progress
DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId`=15 AND `SourceGroup`=8870 AND `SourceEntry`=0;
INSERT INTO `conditions` (`SourceTypeOrReferenceId`, `SourceGroup`, `SourceEntry`, `SourceId`, `ElseGroup`, `ConditionTypeOrReference`, `ConditionTarget`, `ConditionValue1`, `ConditionValue2`, `ConditionValue3`, `NegativeCondition`, `ErrorType`, `ErrorTextId`, `ScriptName`, `Comment`) VALUES
(15, 8870, 0, 0, 0, 47, 0, 11221, 8, 0, 0, 0, 0, '', 'Razael - Show gossip option if quest 11221 is in progress');
-- Condition on menu 8879 option 0: quest 11221 in progress
DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId`=15 AND `SourceGroup`=8879 AND `SourceEntry`=0;
INSERT INTO `conditions` (`SourceTypeOrReferenceId`, `SourceGroup`, `SourceEntry`, `SourceId`, `ElseGroup`, `ConditionTypeOrReference`, `ConditionTarget`, `ConditionValue1`, `ConditionValue2`, `ConditionValue3`, `NegativeCondition`, `ErrorType`, `ErrorTextId`, `ScriptName`, `Comment`) VALUES
(15, 8879, 0, 0, 0, 47, 0, 11221, 8, 0, 0, 0, 0, '', 'Lyana - Show gossip option if quest 11221 is in progress');
-- SAI for Razael (23998): on gossip select (menu 8870, option 0) -> quest credit 23998
DELETE FROM `smart_scripts` WHERE `entryorguid`=23998 AND `source_type`=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`, `event_param6`, `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
(23998, 0, 0, 0, 62, 0, 100, 512, 8870, 0, 0, 0, 0, 0, 33, 23998, 0, 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 'Razael - On Gossip Select - Quest Credit 23998');
-- Update Razael creature_template
UPDATE `creature_template` SET `ScriptName`='', `AIName`='SmartAI' WHERE `entry`=23998;
-- SAI for Lyana (23778): append gossip handler to existing SAI (id 0 = OOC say already exists)
DELETE FROM `smart_scripts` WHERE `entryorguid`=23778 AND `source_type`=0 AND `id`=1;
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`, `event_param6`, `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
(23778, 0, 1, 0, 62, 0, 100, 512, 8879, 0, 0, 0, 0, 0, 33, 23778, 0, 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 'Lyana - On Gossip Select - Quest Credit 23778');
-- Update Lyana creature_template (already has SmartAI)
UPDATE `creature_template` SET `ScriptName`='' WHERE `entry`=23778;
-- =====================================================
-- 3. npc_roxi_ramrocket (31247) - zone_storm_peaks
-- Trainer option already in DB (menu 10210, OptionID 0, type 5)
-- Add vendor option gated by HasSpell (60866 Mechano-Hog OR 60867 Mekgineer's Chopper)
-- =====================================================
-- Add vendor gossip_menu_option
DELETE FROM `gossip_menu_option` WHERE `MenuID`=10210 AND `OptionID`=1;
INSERT INTO `gossip_menu_option` (`MenuID`, `OptionID`, `OptionIcon`, `OptionText`, `OptionBroadcastTextID`, `OptionType`, `OptionNpcFlag`, `ActionMenuID`, `ActionPoiID`, `BoxCoded`, `BoxMoney`, `BoxText`, `BoxBroadcastTextID`, `VerifiedBuild`) VALUES
(10210, 1, 1, 'I want to browse your goods.', 3370, 3, 128, 0, 0, 0, 0, '', 0, 0);
-- Condition on vendor option: HasSpell 60866 (Mechano-Hog) OR HasSpell 60867 (Mekgineer's Chopper)
DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId`=15 AND `SourceGroup`=10210 AND `SourceEntry`=1;
INSERT INTO `conditions` (`SourceTypeOrReferenceId`, `SourceGroup`, `SourceEntry`, `SourceId`, `ElseGroup`, `ConditionTypeOrReference`, `ConditionTarget`, `ConditionValue1`, `ConditionValue2`, `ConditionValue3`, `NegativeCondition`, `ErrorType`, `ErrorTextId`, `ScriptName`, `Comment`) VALUES
(15, 10210, 1, 0, 0, 25, 0, 60866, 0, 0, 0, 0, 0, '', 'Roxi Ramrocket - Show vendor option if player has Mechano-Hog'),
(15, 10210, 1, 0, 1, 25, 0, 60867, 0, 0, 0, 0, 0, '', 'Roxi Ramrocket - Show vendor option if player has Mekgineer''s Chopper');
-- Remove ScriptName
UPDATE `creature_template` SET `ScriptName`='' WHERE `entry`=31247;
-- =====================================================
-- 4. npc_avatar_of_freya (27801) - zone_sholazar_basin
-- 3-step gossip chain already wired: 9720 -> 9721 -> 9722 -> close
-- Condition on first option: quest 12621 incomplete
-- SAI on final select: invoker self-cast spell 52045
-- =====================================================
-- Condition on menu 9720 option 0: quest 12621 in progress
DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId`=15 AND `SourceGroup`=9720 AND `SourceEntry`=0;
INSERT INTO `conditions` (`SourceTypeOrReferenceId`, `SourceGroup`, `SourceEntry`, `SourceId`, `ElseGroup`, `ConditionTypeOrReference`, `ConditionTarget`, `ConditionValue1`, `ConditionValue2`, `ConditionValue3`, `NegativeCondition`, `ErrorType`, `ErrorTextId`, `ScriptName`, `Comment`) VALUES
(15, 9720, 0, 0, 0, 47, 0, 12621, 8, 0, 0, 0, 0, '', 'Avatar of Freya - Show gossip option if quest 12621 is in progress');
-- SAI: on gossip select (menu 9722, option 0) -> close gossip + invoker self-cast spell 52045
DELETE FROM `smart_scripts` WHERE `entryorguid`=27801 AND `source_type`=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`, `event_param6`, `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
(27801, 0, 0, 1, 62, 0, 100, 512, 9722, 0, 0, 0, 0, 0, 72, 0, 0, 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 'Avatar of Freya - On Gossip Select - Close Gossip'),
(27801, 0, 1, 0, 61, 0, 100, 512, 0, 0, 0, 0, 0, 0, 134, 52045, 2, 0, 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 'Avatar of Freya - Linked - Invoker Cast Freya Conversation');
-- Update creature_template
UPDATE `creature_template` SET `ScriptName`='', `AIName`='SmartAI' WHERE `entry`=27801;

View File

@@ -239,50 +239,6 @@ public:
}
};
/*######
## npc_iruk
######*/
enum Iruk
{
GOSSIP_MENU_ID_NPC_IRUK = 9280,
GOSSIP_OPTION_SEARCH_CORPSE = 0,
NPC_TEXT_THIS_YOUNG_TUSKARR = 12585,
QUEST_SPIRITS_WATCH_OVER_US = 11961,
SPELL_CREATE_TOTEM_OF_ISSLIRUK = 46816
};
class npc_iruk : public CreatureScript
{
public:
npc_iruk() : CreatureScript("npc_iruk") { }
bool OnGossipHello(Player* player, Creature* creature) override
{
if (player->GetQuestStatus(QUEST_SPIRITS_WATCH_OVER_US) == QUEST_STATUS_INCOMPLETE)
AddGossipItemFor(player, GOSSIP_MENU_ID_NPC_IRUK, GOSSIP_OPTION_SEARCH_CORPSE, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
SendGossipMenuFor(player, NPC_TEXT_THIS_YOUNG_TUSKARR, creature->GetGUID());
return true;
}
bool OnGossipSelect(Player* player, Creature* /*creature*/, uint32 /*sender*/, uint32 action) override
{
ClearGossipMenuFor(player);
if (action == GOSSIP_ACTION_INFO_DEF + 1)
{
player->CastSpell(player, SPELL_CREATE_TOTEM_OF_ISSLIRUK, true);
CloseGossipMenuFor(player);
}
return true;
}
};
/*######
## npc_nerubar_victim
######*/
@@ -1379,7 +1335,6 @@ void AddSC_borean_tundra()
RegisterSpellScript(spell_q11919_q11940_drake_hunt_aura);
new npc_sinkhole_kill_credit();
new npc_khunok_the_behemoth();
new npc_iruk();
new npc_nerubar_victim();
new npc_lurgglbr();
RegisterSpellScript(spell_arcane_chains_character_force_cast);

View File

@@ -20,7 +20,6 @@
#include "Player.h"
#include "ScriptedCreature.h"
#include "ScriptedEscortAI.h"
#include "ScriptedGossip.h"
#include "SpellInfo.h"
#include "SpellScript.h"
@@ -227,73 +226,6 @@ public:
}
};
/*######
## npc_razael_and_lyana
######*/
enum Razael
{
QUEST_REPORTS_FROM_THE_FIELD = 11221,
NPC_RAZAEL = 23998,
NPC_LYANA = 23778,
GOSSIP_TEXTID_RAZAEL1 = 11562,
GOSSIP_TEXTID_RAZAEL2 = 11564,
GOSSIP_TEXTID_LYANA1 = 11586,
GOSSIP_TEXTID_LYANA2 = 11588
};
class npc_razael_and_lyana : public CreatureScript
{
public:
npc_razael_and_lyana() : CreatureScript("npc_razael_and_lyana") { }
bool OnGossipHello(Player* player, Creature* creature) override
{
if (creature->IsQuestGiver())
player->PrepareQuestMenu(creature->GetGUID());
if (player->GetQuestStatus(QUEST_REPORTS_FROM_THE_FIELD) == QUEST_STATUS_INCOMPLETE)
switch (creature->GetEntry())
{
case NPC_RAZAEL:
if (!player->GetReqKillOrCastCurrentCount(QUEST_REPORTS_FROM_THE_FIELD, NPC_RAZAEL))
{
AddGossipItemFor(player, 8870, 0, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
SendGossipMenuFor(player, GOSSIP_TEXTID_RAZAEL1, creature->GetGUID());
return true;
}
break;
case NPC_LYANA:
if (!player->GetReqKillOrCastCurrentCount(QUEST_REPORTS_FROM_THE_FIELD, NPC_LYANA))
{
AddGossipItemFor(player, 8879, 0, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
SendGossipMenuFor(player, GOSSIP_TEXTID_LYANA1, creature->GetGUID());
return true;
}
break;
}
SendGossipMenuFor(player, player->GetGossipTextId(creature), creature->GetGUID());
return true;
}
bool OnGossipSelect(Player* player, Creature* creature, uint32 /*sender*/, uint32 action) override
{
ClearGossipMenuFor(player);
switch (action)
{
case GOSSIP_ACTION_INFO_DEF + 1:
SendGossipMenuFor(player, GOSSIP_TEXTID_RAZAEL2, creature->GetGUID());
player->TalkedToCreature(NPC_RAZAEL, creature->GetGUID());
break;
case GOSSIP_ACTION_INFO_DEF + 2:
SendGossipMenuFor(player, GOSSIP_TEXTID_LYANA2, creature->GetGUID());
player->TalkedToCreature(NPC_LYANA, creature->GetGUID());
break;
}
return true;
}
};
enum RodinLightningSpells
{
SPELL_RODIN_LIGHTNING_START = 44787,
@@ -490,7 +422,6 @@ void AddSC_howling_fjord()
new npc_attracted_reef_bull();
new npc_apothecary_hanes();
new npc_plaguehound_tracker();
new npc_razael_and_lyana();
RegisterCreatureAI(npc_rodin_lightning_enabler);
RegisterSpellScript(spell_hawk_hunting);
RegisterSpellScript(spell_the_cleansing_shrine_cast);

View File

@@ -387,64 +387,6 @@ public:
}
};
/*######
## avatar_of_freya
######*/
enum Freya
{
QUEST_FREYA_PACT = 12621,
SPELL_FREYA_CONVERSATION = 52045,
GOSSIP_AVATAR_MENU_1 = 9720,
GOSSIP_AVATAR_MENU_2 = 9721,
GOSSIP_AVATAR_MENU_3 = 9722,
GOSSIP_TEXTID_AVATAR_1 = 13303,
GOSSIP_TEXTID_AVATAR_2 = 13304,
GOSSIP_TEXTID_AVATAR_3 = 13305,
};
class npc_avatar_of_freya : public CreatureScript
{
public:
npc_avatar_of_freya() : CreatureScript("npc_avatar_of_freya") { }
bool OnGossipHello(Player* player, Creature* creature) override
{
if (creature->IsQuestGiver())
player->PrepareQuestMenu(creature->GetGUID());
if (player->GetQuestStatus(QUEST_FREYA_PACT) == QUEST_STATUS_INCOMPLETE)
AddGossipItemFor(player, GOSSIP_AVATAR_MENU_1, 0, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 1);
SendGossipMenuFor(player, GOSSIP_TEXTID_AVATAR_1, creature);
return true;
}
bool OnGossipSelect(Player* player, Creature* creature, uint32 /*sender*/, uint32 action) override
{
ClearGossipMenuFor(player);
switch (action)
{
case GOSSIP_ACTION_INFO_DEF+1:
AddGossipItemFor(player, GOSSIP_AVATAR_MENU_2, 0, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 2);
SendGossipMenuFor(player, GOSSIP_TEXTID_AVATAR_2, creature);
break;
case GOSSIP_ACTION_INFO_DEF+2:
AddGossipItemFor(player, GOSSIP_AVATAR_MENU_3, 0, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_INFO_DEF + 3);
SendGossipMenuFor(player, GOSSIP_TEXTID_AVATAR_3, creature);
break;
case GOSSIP_ACTION_INFO_DEF+3:
player->CastSpell(player, SPELL_FREYA_CONVERSATION, true);
CloseGossipMenuFor(player);
break;
}
return true;
}
};
/*######
## npc_bushwhacker
######*/
@@ -1187,7 +1129,6 @@ void AddSC_sholazar_basin()
new go_pressure_valve();
new go_brazier();
new npc_vekjik();
new npc_avatar_of_freya();
new npc_bushwhacker();
new npc_engineer_helice();
new npc_adventurous_dwarf();

View File

@@ -22,7 +22,6 @@
#include "ScriptedCreature.h"
#include "SpellMgr.h"
#include "ScriptedEscortAI.h"
#include "ScriptedGossip.h"
#include "SpellAuraEffects.h"
#include "SpellScript.h"
#include "SpellScriptLoader.h"
@@ -339,56 +338,6 @@ class spell_q13007_iron_colossus : public SpellScript
}
};
/*######
## npc_roxi_ramrocket
######*/
enum RoxiRamrocket
{
SPELL_MECHANO_HOG = 60866,
SPELL_MEKGINEERS_CHOPPER = 60867
};
class npc_roxi_ramrocket : public CreatureScript
{
public:
npc_roxi_ramrocket() : CreatureScript("npc_roxi_ramrocket") { }
bool OnGossipHello(Player* player, Creature* creature) override
{
//Quest Menu
if (creature->IsQuestGiver())
player->PrepareQuestMenu(creature->GetGUID());
//Trainer Menu
if (creature->IsTrainer())
AddGossipItemFor(player, GOSSIP_ICON_TRAINER, GOSSIP_TEXT_TRAIN, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_TRAIN);
//Vendor Menu
if (creature->IsVendor())
if (player->HasSpell(SPELL_MECHANO_HOG) || player->HasSpell(SPELL_MEKGINEERS_CHOPPER))
AddGossipItemFor(player, GOSSIP_ICON_VENDOR, GOSSIP_TEXT_BROWSE_GOODS, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_TRADE);
SendGossipMenuFor(player, player->GetGossipTextId(creature), creature->GetGUID());
return true;
}
bool OnGossipSelect(Player* player, Creature* creature, uint32 /*sender*/, uint32 action) override
{
ClearGossipMenuFor(player);
switch (action)
{
case GOSSIP_ACTION_TRAIN:
player->GetSession()->SendTrainerList(creature);
break;
case GOSSIP_ACTION_TRADE:
player->GetSession()->SendListInventory(creature->GetGUID());
break;
}
return true;
}
};
/*######
## npc_brunnhildar_prisoner
######*/
@@ -1386,7 +1335,6 @@ void AddSC_storm_peaks()
new npc_iron_watcher();
new npc_time_lost_proto_drake();
RegisterSpellScript(spell_q13007_iron_colossus);
new npc_roxi_ramrocket();
new npc_brunnhildar_prisoner();
new npc_freed_protodrake();
new npc_icefang();