aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/server/game/Entities/Creature/Creature.h5
-rw-r--r--src/server/game/Entities/GameObject/GameObject.h6
-rw-r--r--src/server/game/Globals/ObjectMgr.cpp66
-rw-r--r--src/server/game/Globals/ObjectMgr.h22
-rw-r--r--src/server/game/Handlers/QueryHandler.cpp17
-rw-r--r--src/server/game/World/World.cpp6
6 files changed, 105 insertions, 17 deletions
diff --git a/src/server/game/Entities/Creature/Creature.h b/src/server/game/Entities/Creature/Creature.h
index 3fd06e41458..5d18e1e079d 100644
--- a/src/server/game/Entities/Creature/Creature.h
+++ b/src/server/game/Entities/Creature/Creature.h
@@ -69,7 +69,6 @@ enum CreatureFlagsExtra
#define MAX_KILL_CREDIT 2
#define MAX_CREATURE_MODELS 4
-#define MAX_CREATURE_QUEST_ITEMS 6
#define MAX_CREATURE_NAMES 4
#define CREATURE_MAX_SPELLS 8
#define MAX_CREATURE_DIFFICULTIES 3
@@ -136,7 +135,6 @@ struct CreatureTemplate
float ModDamage;
float ModExperience;
bool RacialLeader;
- uint32 questItems[MAX_CREATURE_QUEST_ITEMS];
uint32 movementId;
bool RegenHealth;
uint32 MechanicImmuneMask;
@@ -205,6 +203,9 @@ struct CreatureTemplate
}
};
+typedef std::vector<uint32> CreatureQuestItemList;
+typedef std::unordered_map<uint32, CreatureQuestItemList> CreatureQuestItemMap;
+
// Benchmarked: Faster than std::map (insert/find)
typedef std::unordered_map<uint32, CreatureTemplate> CreatureTemplateContainer;
diff --git a/src/server/game/Entities/GameObject/GameObject.h b/src/server/game/Entities/GameObject/GameObject.h
index b4492cd77c7..50bd1ebd9f5 100644
--- a/src/server/game/Entities/GameObject/GameObject.h
+++ b/src/server/game/Entities/GameObject/GameObject.h
@@ -30,8 +30,6 @@ class GameObjectAI;
class Group;
class Transport;
-#define MAX_GAMEOBJECT_QUEST_ITEMS 6
-
// from `gameobject_template`
struct GameObjectTemplate
{
@@ -45,7 +43,6 @@ struct GameObjectTemplate
uint32 faction;
uint32 flags;
float size;
- uint32 questItems[MAX_GAMEOBJECT_QUEST_ITEMS];
int32 unkInt32;
union
{
@@ -847,6 +844,9 @@ struct GameObjectData
bool dbData;
};
+typedef std::vector<uint32> GameObjectQuestItemList;
+typedef std::unordered_map<uint32, GameObjectQuestItemList> GameObjectQuestItemMap;
+
// For containers: [GO_NOT_READY]->GO_READY (close)->GO_ACTIVATED (open) ->GO_JUST_DEACTIVATED->GO_READY -> ...
// For bobber: GO_NOT_READY ->GO_READY (close)->GO_ACTIVATED (open) ->GO_JUST_DEACTIVATED-><deleted>
// For door(closed):[GO_NOT_READY]->GO_READY (close)->GO_ACTIVATED (open) ->GO_JUST_DEACTIVATED->GO_READY(close) -> ...
diff --git a/src/server/game/Globals/ObjectMgr.cpp b/src/server/game/Globals/ObjectMgr.cpp
index 51063666470..0316c31794c 100644
--- a/src/server/game/Globals/ObjectMgr.cpp
+++ b/src/server/game/Globals/ObjectMgr.cpp
@@ -539,9 +539,6 @@ void ObjectMgr::LoadCreatureTemplate(Field* fields)
creatureTemplate.ModExperience = fields[72].GetFloat();
creatureTemplate.RacialLeader = fields[73].GetBool();
- for (uint8 i = 0; i < MAX_CREATURE_QUEST_ITEMS; ++i)
- creatureTemplate.questItems[i] = fields[74 + i].GetUInt32();
-
creatureTemplate.movementId = fields[80].GetUInt32();
creatureTemplate.RegenHealth = fields[81].GetBool();
creatureTemplate.MechanicImmuneMask = fields[82].GetUInt32();
@@ -6231,9 +6228,6 @@ void ObjectMgr::LoadGameObjectTemplate()
got.flags = fields[8].GetUInt32();
got.size = fields[9].GetFloat();
- for (uint8 i = 0; i < MAX_GAMEOBJECT_QUEST_ITEMS; ++i)
- got.questItems[i] = fields[10 + i].GetUInt32();
-
for (uint8 i = 0; i < MAX_GAMEOBJECT_DATA; ++i)
got.raw.data[i] = fields[16 + i].GetUInt32();
@@ -8920,3 +8914,63 @@ std::string ObjectMgr::GetRealmName(uint32 realm) const
RealmNameContainer::const_iterator iter = _realmNameStore.find(realm);
return iter != _realmNameStore.end() ? iter->second : "";
}
+
+void ObjectMgr::LoadGameObjectQuestItems()
+{
+ uint32 oldMSTime = getMSTime();
+
+ // 0 1
+ QueryResult result = WorldDatabase.Query("SELECT GameObjectEntry, ItemId FROM gameobject_questitem ORDER BY Idx ASC");
+
+ if (!result)
+ {
+ TC_LOG_INFO("server.loading", ">> Loaded 0 gameobject quest items. DB table `gameobject_questitem` is empty.");
+ return;
+ }
+
+ uint32 count = 0;
+ do
+ {
+ Field* fields = result->Fetch();
+
+ uint32 entry = fields[0].GetUInt32();
+ uint32 item = fields[1].GetUInt32();
+
+ _gameObjectQuestItemStore[entry].push_back(item);
+
+ ++count;
+ }
+ while (result->NextRow());
+
+ TC_LOG_INFO("server.loading", ">> Loaded %u gameobject quest items in %u ms", count, GetMSTimeDiffToNow(oldMSTime));
+}
+
+void ObjectMgr::LoadCreatureQuestItems()
+{
+ uint32 oldMSTime = getMSTime();
+
+ // 0 1
+ QueryResult result = WorldDatabase.Query("SELECT CreatureEntry, ItemId FROM creature_questitem ORDER BY Idx ASC");
+
+ if (!result)
+ {
+ TC_LOG_INFO("server.loading", ">> Loaded 0 creature quest items. DB table `creature_questitem` is empty.");
+ return;
+ }
+
+ uint32 count = 0;
+ do
+ {
+ Field* fields = result->Fetch();
+
+ uint32 entry = fields[0].GetUInt32();
+ uint32 item = fields[1].GetUInt32();
+
+ _creatureQuestItemStore[entry].push_back(item);
+
+ ++count;
+ }
+ while (result->NextRow());
+
+ TC_LOG_INFO("server.loading", ">> Loaded %u creature quest items in %u ms", count, GetMSTimeDiffToNow(oldMSTime));
+} \ No newline at end of file
diff --git a/src/server/game/Globals/ObjectMgr.h b/src/server/game/Globals/ObjectMgr.h
index 49d7b024b19..b49b46cb555 100644
--- a/src/server/game/Globals/ObjectMgr.h
+++ b/src/server/game/Globals/ObjectMgr.h
@@ -725,6 +725,24 @@ class ObjectMgr
static ObjectGuid GetPlayerGUIDByName(std::string const& name);
+ GameObjectQuestItemList* GetGameObjectQuestItemList(uint32 id)
+ {
+ GameObjectQuestItemMap::iterator itr = _gameObjectQuestItemStore.find(id);
+ if (itr != _gameObjectQuestItemStore.end())
+ return &itr->second;
+ return NULL;
+ }
+ GameObjectQuestItemMap const* GetGameObjectQuestItemMap() const { return &_gameObjectQuestItemStore; }
+
+ CreatureQuestItemList* GetCreatureQuestItemList(uint32 id)
+ {
+ CreatureQuestItemMap::iterator itr = _creatureQuestItemStore.find(id);
+ if (itr != _creatureQuestItemStore.end())
+ return &itr->second;
+ return NULL;
+ }
+ CreatureQuestItemMap const* GetCreatureQuestItemMap() const { return &_creatureQuestItemStore; }
+
/**
* Retrieves the player name by guid.
*
@@ -930,6 +948,8 @@ class ObjectMgr
void LoadCreatureTemplateAddons();
void LoadCreatureTemplate(Field* fields);
void CheckCreatureTemplate(CreatureTemplate const* cInfo);
+ void LoadGameObjectQuestItems();
+ void LoadCreatureQuestItems();
void LoadTempSummons();
void LoadCreatures();
void LoadLinkedRespawn();
@@ -1401,6 +1421,8 @@ class ObjectMgr
CreatureModelContainer _creatureModelStore;
CreatureAddonContainer _creatureAddonStore;
GameObjectAddonContainer _gameObjectAddonStore;
+ GameObjectQuestItemMap _gameObjectQuestItemStore;
+ CreatureQuestItemMap _creatureQuestItemStore;
CreatureTemplateAddonContainer _creatureTemplateAddonStore;
EquipmentInfoContainer _equipmentInfoStore;
LinkedRespawnContainer _linkedRespawnStore;
diff --git a/src/server/game/Handlers/QueryHandler.cpp b/src/server/game/Handlers/QueryHandler.cpp
index 93ae3873857..a5288b274a4 100644
--- a/src/server/game/Handlers/QueryHandler.cpp
+++ b/src/server/game/Handlers/QueryHandler.cpp
@@ -89,9 +89,12 @@ void WorldSession::HandleCreatureQuery(WorldPackets::Query::QueryCreature& packe
stats.HpMulti = creatureInfo->ModHealth;
stats.EnergyMulti = creatureInfo->ModMana;
stats.Leader = creatureInfo->RacialLeader;
- for (uint8 i = 0; i < MAX_CREATURE_QUEST_ITEMS; ++i)
- if (creatureInfo->questItems[i])
- stats.QuestItems.push_back(creatureInfo->questItems[i]);
+
+ CreatureQuestItemList* items = sObjectMgr->GetCreatureQuestItemList(packet.CreatureID);
+ if (items)
+ for (uint32 item : *items)
+ stats.QuestItems.push_back(item);
+
stats.CreatureMovementInfoID = creatureInfo->movementId;
stats.RequiredExpansion = creatureInfo->expansionUnknown;
stats.Flags[0] = creatureInfo->type_flags;
@@ -128,9 +131,11 @@ void WorldSession::HandleGameObjectQueryOpcode(WorldPackets::Query::QueryGameObj
stats.IconName = gameObjectInfo->IconName;
stats.Name[0] = gameObjectInfo->name;
- for (uint8 i = 0; i < MAX_GAMEOBJECT_QUEST_ITEMS; i++)
- if (gameObjectInfo->questItems[i])
- stats.QuestItems.push_back(gameObjectInfo->questItems[i]);
+ GameObjectQuestItemList* items = sObjectMgr->GetGameObjectQuestItemList(packet.GameObjectID);
+ if (items)
+ for (uint32 item : *items)
+ stats.QuestItems.push_back(item);
+
for (uint32 i = 0; i < MAX_GAMEOBJECT_DATA; i++)
stats.Data[i] = gameObjectInfo->raw.data[i];
diff --git a/src/server/game/World/World.cpp b/src/server/game/World/World.cpp
index dc40e5f3c2b..3a38acae452 100644
--- a/src/server/game/World/World.cpp
+++ b/src/server/game/World/World.cpp
@@ -1622,6 +1622,12 @@ void World::SetInitialWorldSettings()
TC_LOG_INFO("server.loading", "Loading GameObject Addon Data...");
sObjectMgr->LoadGameObjectAddons(); // must be after LoadGameObjectTemplate() and LoadGameobjects()
+
+ TC_LOG_INFO("server.loading", "Loading GameObject Quest Items...");
+ sObjectMgr->LoadGameObjectQuestItems();
+
+ TC_LOG_INFO("server.loading", "Loading Creature Quest Items...");
+ sObjectMgr->LoadCreatureQuestItems();
TC_LOG_INFO("server.loading", "Loading Creature Linked Respawn...");
sObjectMgr->LoadLinkedRespawn(); // must be after LoadCreatures(), LoadGameObjects()