diff --git a/data/sql/updates/pending_db_world/rev_1644762673519914900.sql b/data/sql/updates/pending_db_world/rev_1644762673519914900.sql new file mode 100644 index 000000000..f16945b76 --- /dev/null +++ b/data/sql/updates/pending_db_world/rev_1644762673519914900.sql @@ -0,0 +1,29 @@ +INSERT INTO `version_db_world` (`sql_rev`) VALUES ('1644762673519914900'); + +UPDATE `creature_template` SET `npcflag`=`npcflag`|128, `ScriptName` = "" WHERE `entry`=12919; + +DELETE FROM `gossip_menu` WHERE `MenuID`=6445 AND `TextID` IN (7639,7640); +DELETE FROM `gossip_menu` WHERE `MenuID` IN (57023,57024); +INSERT INTO `gossip_menu` (`MenuID`,`TextID`) VALUES +(6445,7639), +(57023,7640), +(57024,7645); + +DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId`=14 AND `SourceGroup`=6445; +INSERT INTO `conditions` (`SourceTypeOrReferenceId`,`SourceGroup`,`SourceEntry`,`SourceId`,`ElseGroup`,`ConditionTypeOrReference`,`ConditionTarget`,`ConditionValue1`,`ConditionValue2`,`ConditionValue3`,`NegativeCondition`,`ErrorType`,`ErrorTextId`,`ScriptName`,`Comment`) VALUES +(14,6445,7638,0,0,8,0,8227,0,0,1,0,0,"","Group 0: Show gossip text 7638 if quest 'Nat's Measuring Tape' is not rewarded"), +(14,6445,7639,0,0,8,0,8227,0,0,0,0,0,"","Group 0: Show gossip text 7639 if quest 'Nat's Measuring Tape' is rewarded"); + +DELETE FROM `gossip_menu_option` WHERE `MenuID` IN (6445,57023); +INSERT INTO `gossip_menu_option` (`MenuID`,`OptionID`,`OptionIcon`,`OptionText`,`OptionBroadcastTextID`,`OptionType`,`OptionNpcFlag`,`ActionMenuID`,`ActionPoiID`,`BoxCoded`,`BoxMoney`,`BoxText`,`BoxBroadcastTextID`,`VerifiedBuild`) VALUES +(6445,0,0,"I want to catch Gahz'ranka! Tell me how!",10490,1,1,57023,0,0,0,"",0,0), +(57023,0,1,"Nat, I want to buy your mudskunk lures!",10492,3,128,0,0,0,0,"",0,0), +(57023,1,0,"How do I catch the mudskunks for your lure?",10500,1,1,57024,0,0,0,"",0,0); + +DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId`=15 AND `SourceGroup`=6445; +INSERT INTO `conditions` (`SourceTypeOrReferenceId`,`SourceGroup`,`SourceEntry`,`SourceId`,`ElseGroup`,`ConditionTypeOrReference`,`ConditionTarget`,`ConditionValue1`,`ConditionValue2`,`ConditionValue3`,`NegativeCondition`,`ErrorType`,`ErrorTextId`,`ScriptName`,`Comment`) VALUES +(15,6445,0,0,0,8,0,8227,0,0,0,0,0,"","Group 0: Show Gossip Option 0 if quest 'Nat's Measuring Tape' is rewarded"); + +DELETE FROM `conditions` WHERE `SourceTypeOrReferenceId`=23 AND `SourceGroup`=12919; +INSERT INTO `conditions` (`SourceTypeOrReferenceId`,`SourceGroup`,`SourceEntry`,`SourceId`,`ElseGroup`,`ConditionTypeOrReference`,`ConditionTarget`,`ConditionValue1`,`ConditionValue2`,`ConditionValue3`,`NegativeCondition`,`ErrorType`,`ErrorTextId`,`ScriptName`,`Comment`) VALUES +(23,12919,0,0,0,8,0,8227,0,0,0,0,0,"","Show vendor npc flag if quest 'Nat's Measuring Tape' is rewarded"); diff --git a/src/server/game/Conditions/ConditionMgr.cpp b/src/server/game/Conditions/ConditionMgr.cpp index 34c1bc6d5..4fb805da1 100644 --- a/src/server/game/Conditions/ConditionMgr.cpp +++ b/src/server/game/Conditions/ConditionMgr.cpp @@ -885,7 +885,14 @@ ConditionList ConditionMgr::GetConditionsForNpcVendorEvent(uint32 creatureId, ui if (i != (*itr).second.end()) { cond = (*i).second; - LOG_DEBUG("condition", "GetConditionsForNpcVendorEvent: found conditions for creature entry {} item {}", creatureId, itemId); + if (itemId) + { + LOG_DEBUG("condition", "GetConditionsForNpcVendorEvent: found conditions for creature entry {} item {}", creatureId, itemId); + } + else + { + LOG_DEBUG("condition", "GetConditionsForNpcVendorEvent: found conditions for creature entry {}", creatureId); + } } } return cond; @@ -1650,11 +1657,14 @@ bool ConditionMgr::isSourceTypeValid(Condition* cond) LOG_ERROR("condition", "SourceEntry {} in `condition` table, does not exist in `creature_template`, ignoring.", cond->SourceGroup); return false; } - ItemTemplate const* itemTemplate = sObjectMgr->GetItemTemplate(cond->SourceEntry); - if (!itemTemplate) + if (cond->SourceEntry) { - LOG_ERROR("condition", "SourceEntry {} in `condition` table, does not exist in `item_template`, ignoring.", cond->SourceEntry); - return false; + ItemTemplate const* itemTemplate = sObjectMgr->GetItemTemplate(cond->SourceEntry); + if (!itemTemplate) + { + LOG_ERROR("condition", "SourceEntry {} in `condition` table, does not exist in `item_template`, ignoring.", cond->SourceEntry); + return false; + } } break; } diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp index f3cce991e..f42f62380 100644 --- a/src/server/game/Entities/Player/Player.cpp +++ b/src/server/game/Entities/Player/Player.cpp @@ -13806,6 +13806,20 @@ bool Player::CanSeeSpellClickOn(Creature const* c) const return false; } +bool Player::CanSeeVendor(Creature const* creature) const +{ + if (!creature->HasFlag(UNIT_NPC_FLAGS, UNIT_NPC_FLAG_VENDOR)) + return true; + + ConditionList conditions = sConditionMgr->GetConditionsForNpcVendorEvent(creature->GetEntry(), 0); + if (!sConditionMgr->IsObjectMeetToConditions(const_cast(this), const_cast(creature), conditions)) + { + return false; + } + + return true; +} + void Player::BuildPlayerTalentsInfoData(WorldPacket* data) { *data << uint32(GetFreeTalentPoints()); // unspentTalentPoints diff --git a/src/server/game/Entities/Player/Player.h b/src/server/game/Entities/Player/Player.h index 04d33b183..cbb1af85d 100644 --- a/src/server/game/Entities/Player/Player.h +++ b/src/server/game/Entities/Player/Player.h @@ -2490,6 +2490,7 @@ public: //bool isActiveObject() const { return true; } bool CanSeeSpellClickOn(Creature const* creature) const; + [[nodiscard]] bool CanSeeVendor(Creature const* creature) const; [[nodiscard]] uint32 GetChampioningFaction() const { return m_ChampioningFaction; } void SetChampioningFaction(uint32 faction) { m_ChampioningFaction = faction; } diff --git a/src/server/game/Entities/Unit/Unit.cpp b/src/server/game/Entities/Unit/Unit.cpp index 0888aea9e..e241e1e1c 100644 --- a/src/server/game/Entities/Unit/Unit.cpp +++ b/src/server/game/Entities/Unit/Unit.cpp @@ -20099,6 +20099,11 @@ void Unit::BuildValuesUpdate(uint8 updateType, ByteBuffer* data, Player* target) appendValue &= ~UNIT_NPC_FLAG_SPELLCLICK; } + if (!target->CanSeeVendor(creature)) + { + appendValue &= ~UNIT_NPC_FLAG_VENDOR_MASK; + } + if (!creature->IsValidTrainerForPlayer(target, &appendValue)) { appendValue &= ~UNIT_NPC_FLAG_TRAINER; diff --git a/src/server/game/Entities/Unit/Unit.h b/src/server/game/Entities/Unit/Unit.h index 69235c055..ed8f32d0f 100644 --- a/src/server/game/Entities/Unit/Unit.h +++ b/src/server/game/Entities/Unit/Unit.h @@ -527,7 +527,9 @@ enum NPCFlags : uint32 UNIT_NPC_FLAG_GUILD_BANKER = 0x00800000, // TITLE is guild banker DESCRIPTION cause client to send 997 opcode UNIT_NPC_FLAG_SPELLCLICK = 0x01000000, // TITLE has spell click enabled DESCRIPTION cause client to send 1015 opcode (spell click) UNIT_NPC_FLAG_PLAYER_VEHICLE = 0x02000000, // TITLE is player vehicle DESCRIPTION players with mounts that have vehicle data should have it set - UNIT_NPC_FLAG_MAILBOX = 0x04000000 // TITLE is mailbox + UNIT_NPC_FLAG_MAILBOX = 0x04000000, // TITLE is mailbox + + UNIT_NPC_FLAG_VENDOR_MASK = UNIT_NPC_FLAG_VENDOR | UNIT_NPC_FLAG_VENDOR_AMMO | UNIT_NPC_FLAG_VENDOR_POISON | UNIT_NPC_FLAG_VENDOR_REAGENT }; enum MovementFlags diff --git a/src/server/scripts/Kalimdor/zone_dustwallow_marsh.cpp b/src/server/scripts/Kalimdor/zone_dustwallow_marsh.cpp index e253e8c4c..ade26f798 100644 --- a/src/server/scripts/Kalimdor/zone_dustwallow_marsh.cpp +++ b/src/server/scripts/Kalimdor/zone_dustwallow_marsh.cpp @@ -18,12 +18,11 @@ /* ScriptData SDName: Dustwallow_Marsh SD%Complete: 95 -SDComment: Quest support: 11180, 11126, 11174, Vendor Nat Pagle +SDComment: Quest support: 11180, 11126, 11174 SDCategory: Dustwallow Marsh EndScriptData */ /* ContentData -npc_nat_pagle npc_cassa_crimsonwing - handled by npc_taxi EndContentData */ @@ -34,46 +33,6 @@ EndContentData */ #include "SpellScript.h" #include "WorldSession.h" -/*###### -## npc_nat_pagle -######*/ - -enum NatPagle -{ - QUEST_NATS_MEASURING_TAPE = 8227 -}; - -class npc_nat_pagle : public CreatureScript -{ -public: - npc_nat_pagle() : CreatureScript("npc_nat_pagle") { } - - bool OnGossipSelect(Player* player, Creature* creature, uint32 /*sender*/, uint32 action) override - { - ClearGossipMenuFor(player); - if (action == GOSSIP_ACTION_TRADE) - player->GetSession()->SendListInventory(creature->GetGUID()); - - return true; - } - - bool OnGossipHello(Player* player, Creature* creature) override - { - if (creature->IsQuestGiver()) - player->PrepareQuestMenu(creature->GetGUID()); - - if (creature->IsVendor() && player->GetQuestRewardStatus(QUEST_NATS_MEASURING_TAPE)) - { - AddGossipItemFor(player, GOSSIP_ICON_VENDOR, GOSSIP_TEXT_BROWSE_GOODS, GOSSIP_SENDER_MAIN, GOSSIP_ACTION_TRADE); - SendGossipMenuFor(player, 7640, creature->GetGUID()); - } - else - SendGossipMenuFor(player, 7638, creature->GetGUID()); - - return true; - } -}; - /*###### ## npc_zelfrax ######*/ @@ -285,7 +244,6 @@ public: void AddSC_dustwallow_marsh() { - new npc_nat_pagle(); new npc_zelfrax(); new spell_ooze_zap(); new spell_ooze_zap_channel_end();