AzerothCore 3.3.5a
OpenSource WoW Emulator
Loading...
Searching...
No Matches
ObjectMgr Class Reference

#include "ObjectMgr.h"

Classes

struct  GameobjectInstanceSavedState
 

Public Types

typedef std::unordered_map< uint32, Item * > ItemMap
 
typedef std::unordered_map< uint32, Quest * > QuestMap
 
typedef std::unordered_map< uint32, AreaTriggerAreaTriggerContainer
 
typedef std::unordered_map< uint32, AreaTriggerTeleportAreaTriggerTeleportContainer
 
typedef std::unordered_map< uint32, uint32AreaTriggerScriptContainer
 
typedef std::unordered_map< uint32, std::unordered_map< uint8, DungeonProgressionRequirements * > > DungeonProgressionRequirementsContainer
 
typedef std::unordered_map< uint32, RepRewardRateRepRewardRateContainer
 
typedef std::unordered_map< uint32, ReputationOnKillEntryRepOnKillContainer
 
typedef std::unordered_map< uint32, RepSpilloverTemplateRepSpilloverTemplateContainer
 
typedef std::unordered_map< uint32, PointOfInterestPointOfInterestContainer
 
typedef std::vector< std::string > ScriptNameContainer
 
typedef std::map< uint32, uint32CharacterConversionMap
 
typedef std::unordered_map< ObjectGuid::LowType, std::vector< float > > CreatureSparringContainer
 
typedef std::multimap< int32, uint32ExclusiveQuestGroups
 
typedef std::pair< ExclusiveQuestGroups::const_iterator, ExclusiveQuestGroups::const_iterator > ExclusiveQuestGroupsBounds
 
typedef std::unordered_map< uint32, std::vector< uint32 > > BreadcrumbQuestMap
 

Public Member Functions

GameObjectTemplate const * GetGameObjectTemplate (uint32 entry)
 
bool IsGameObjectStaticTransport (uint32 entry)
 
GameObjectTemplateContainer const * GetGameObjectTemplates () const
 
int LoadReferenceVendor (int32 vendor, int32 item_id, std::set< uint32 > *skip_vendors)
 
void LoadGameObjectTemplate ()
 
void LoadGameObjectTemplateAddons ()
 
void AddGameobjectInfo (GameObjectTemplate *goinfo)
 
CreatureTemplate const * GetCreatureTemplate (uint32 entry)
 
CreatureTemplateContainer const * GetCreatureTemplates () const
 
CreatureModelInfo const * GetCreatureModelInfo (uint32 modelId) const
 
CreatureModelInfo const * GetCreatureModelRandomGender (CreatureModel *model, CreatureTemplate const *creatureTemplate) const
 
EquipmentInfo const * GetEquipmentInfo (uint32 entry, int8 &id)
 
CreatureAddon const * GetCreatureAddon (ObjectGuid::LowType lowguid)
 
GameObjectAddon const * GetGameObjectAddon (ObjectGuid::LowType lowguid)
 
GameObjectTemplateAddon const * GetGameObjectTemplateAddon (uint32 entry) const
 
CreatureAddon const * GetCreatureTemplateAddon (uint32 entry)
 
CreatureMovementData const * GetCreatureMovementOverride (ObjectGuid::LowType spawnId) const
 
ItemTemplate const * GetItemTemplate (uint32 entry)
 
ItemTemplateContainer const * GetItemTemplateStore () const
 
std::vector< ItemTemplate * > const * GetItemTemplateStoreFast () const
 
uint32 GetModelForTotem (SummonSlot totemSlot, Races race) const
 
uint32 GetModelForShapeshift (ShapeshiftForm form, Player *player) const
 
ItemSetNameEntry const * GetItemSetNameEntry (uint32 itemId)
 
InstanceTemplate const * GetInstanceTemplate (uint32 mapId)
 
PetLevelInfo const * GetPetLevelInfo (uint32 creature_id, uint8 level) const
 
PlayerClassInfo const * GetPlayerClassInfo (uint32 class_) const
 
void GetPlayerClassLevelInfo (uint32 class_, uint8 level, PlayerClassLevelInfo *info) const
 
PlayerInfo const * GetPlayerInfo (uint32 race, uint32 class_) const
 
void GetPlayerLevelInfo (uint32 race, uint32 class_, uint8 level, PlayerLevelInfo *info) const
 
uint32 GetNearestTaxiNode (float x, float y, float z, uint32 mapid, uint32 teamId)
 
uint32 GetNearestTaxiNode (WorldLocation const &loc, uint32 teamId)
 
void GetTaxiPath (uint32 source, uint32 destination, uint32 &path, uint32 &cost)
 
uint32 GetTaxiMountDisplayId (uint32 id, TeamId teamId, bool allowed_alt_team=false)
 
GameObjectQuestItemList const * GetGameObjectQuestItemList (uint32 id) const
 
GameObjectQuestItemMap const * GetGameObjectQuestItemMap () const
 
CreatureQuestItemList const * GetCreatureQuestItemList (uint32 id) const
 
CreatureQuestItemMap const * GetCreatureQuestItemMap () const
 
Quest const * GetQuestTemplate (uint32 quest_id) const
 
QuestMap const & GetQuestTemplates () const
 
uint32 GetQuestForAreaTrigger (uint32 Trigger_ID) const
 
bool IsTavernAreaTrigger (uint32 triggerID, uint32 faction) const
 
GossipText const * GetGossipText (uint32 Text_ID) const
 
AreaTrigger const * GetAreaTrigger (uint32 trigger) const
 
AreaTriggerTeleport const * GetAreaTriggerTeleport (uint32 trigger) const
 
DungeonProgressionRequirements const * GetAccessRequirement (uint32 mapid, Difficulty difficulty) const
 
AreaTriggerTeleport const * GetGoBackTrigger (uint32 Map) const
 
AreaTriggerTeleport const * GetMapEntranceTrigger (uint32 Map) const
 
AreaTriggerScriptContainer const & GetAllAreaTriggerScriptData () const
 
uint32 GetAreaTriggerScriptId (uint32 trigger_id)
 
SpellScriptsBounds GetSpellScriptsBounds (uint32 spell_id)
 
RepRewardRate const * GetRepRewardRate (uint32 factionId) const
 
ReputationOnKillEntry const * GetReputationOnKilEntry (uint32 id) const
 
int32 GetBaseReputationOf (FactionEntry const *factionEntry, uint8 race, uint8 playerClass)
 
RepSpilloverTemplate const * GetRepSpilloverTemplate (uint32 factionId) const
 
PointOfInterest const * GetPointOfInterest (uint32 id) const
 
QuestPOIVector const * GetQuestPOIVector (uint32 questId)
 
VehicleAccessoryList const * GetVehicleAccessoryList (Vehicle *veh) const
 
DungeonEncounterList const * GetDungeonEncounterList (uint32 mapId, Difficulty difficulty)
 
void LoadQuests ()
 
void LoadQuestMoneyRewards ()
 
void LoadQuestStartersAndEnders ()
 
void LoadGameobjectQuestStarters ()
 
void LoadGameobjectQuestEnders ()
 
void LoadCreatureQuestStarters ()
 
void LoadCreatureQuestEnders ()
 
QuestRelationsGetGOQuestRelationMap ()
 
QuestRelationsGetGOQuestInvolvedRelationMap ()
 
QuestRelationBounds GetGOQuestRelationBounds (uint32 go_entry)
 
QuestRelationBounds GetGOQuestInvolvedRelationBounds (uint32 go_entry)
 
QuestRelationsGetCreatureQuestRelationMap ()
 
QuestRelationsGetCreatureQuestInvolvedRelationMap ()
 
QuestRelationBounds GetCreatureQuestRelationBounds (uint32 creature_entry)
 
QuestRelationBounds GetCreatureQuestInvolvedRelationBounds (uint32 creature_entry)
 
void LoadEventScripts ()
 
void LoadSpellScripts ()
 
void LoadWaypointScripts ()
 
void LoadSpellScriptNames ()
 
void ValidateSpellScripts ()
 
void InitializeSpellInfoPrecomputedData ()
 
bool LoadModuleStrings ()
 
bool LoadModuleStringsLocale ()
 
bool LoadAcoreStrings ()
 
void LoadBroadcastTexts ()
 
void LoadBroadcastTextLocales ()
 
void LoadCreatureClassLevelStats ()
 
void LoadCreatureLocales ()
 
void LoadCreatureTemplates ()
 
void LoadCreatureTemplate (Field *fields, bool triggerHook=false)
 Loads a creature template from a database result.
 
void LoadCreatureTemplateModels ()
 
void LoadCreatureTemplateAddons ()
 
void LoadCreatureTemplateResistances ()
 
void LoadCreatureTemplateSpells ()
 
void LoadCreatureCustomIDs ()
 Load config option Creatures.CustomIDs into Store.
 
void CheckCreatureTemplate (CreatureTemplate const *cInfo)
 
void CheckCreatureMovement (char const *table, uint64 id, CreatureMovementData &creatureMovement)
 
void LoadGameObjectQuestItems ()
 
void LoadCreatureQuestItems ()
 
void LoadTempSummons ()
 
void LoadGameObjectSummons ()
 
void LoadCreatures ()
 
void LoadCreatureSparring ()
 
void LoadLinkedRespawn ()
 
bool SetCreatureLinkedRespawn (ObjectGuid::LowType guid, ObjectGuid::LowType linkedGuid)
 
void LoadCreatureAddons ()
 
void LoadGameObjectAddons ()
 
void LoadCreatureModelInfo ()
 
void LoadPlayerTotemModels ()
 
void LoadPlayerShapeshiftModels ()
 
void LoadEquipmentTemplates ()
 
void LoadCreatureMovementOverrides ()
 
void LoadGameObjectLocales ()
 
void LoadGameobjects ()
 
void LoadItemTemplates ()
 
void LoadItemLocales ()
 
void LoadItemSetNames ()
 
void LoadItemSetNameLocales ()
 
void LoadQuestLocales ()
 
void LoadNpcTextLocales ()
 
void LoadQuestOfferRewardLocale ()
 
void LoadQuestRequestItemsLocale ()
 
void LoadPageTextLocales ()
 
void LoadGossipMenuItemsLocales ()
 
void LoadPointOfInterestLocales ()
 
void LoadQuestGreetingsLocales ()
 
void LoadInstanceTemplate ()
 
void LoadInstanceEncounters ()
 
void LoadMailLevelRewards ()
 
void LoadVehicleTemplateAccessories ()
 
void LoadVehicleAccessories ()
 
void LoadVehicleSeatAddon ()
 
void LoadGossipText ()
 
void LoadAreaTriggers ()
 
void LoadAreaTriggerTeleports ()
 
void LoadAccessRequirements ()
 
void LoadQuestAreaTriggers ()
 
void LoadQuestGreetings ()
 
void LoadAreaTriggerScripts ()
 
void LoadTavernAreaTriggers ()
 
void LoadGameObjectForQuests ()
 
void LoadPageTexts ()
 
PageText const * GetPageText (uint32 pageEntry)
 
void LoadPlayerInfo ()
 
void LoadPetLevelInfo ()
 
void LoadExplorationBaseXP ()
 
void LoadPetNames ()
 
void LoadPetNamesLocales ()
 
void LoadPetNumber ()
 
void LoadFishingBaseSkillLevel ()
 
void ChangeFishingBaseSkillLevel (uint32 entry, int32 skill)
 
void LoadReputationRewardRate ()
 
void LoadReputationOnKill ()
 
void LoadReputationSpilloverTemplate ()
 
void LoadPointsOfInterest ()
 
void LoadQuestPOI ()
 
void LoadNPCSpellClickSpells ()
 
void LoadGameTele ()
 
void LoadGossipMenu ()
 
void LoadGossipMenuItems ()
 
void LoadVendors ()
 
void LoadTrainers ()
 
void LoadCreatureDefaultTrainers ()
 
std::string GeneratePetName (uint32 entry)
 
std::string GeneratePetNameLocale (uint32 entry, LocaleConstant locale)
 
uint32 GetBaseXP (uint8 level)
 
uint32 GetXPForLevel (uint8 level) const
 
int32 GetFishingBaseSkillLevel (uint32 entry) const
 
void ReturnOrDeleteOldMails (bool serverUp)
 
CreatureBaseStats const * GetCreatureBaseStats (uint8 level, uint8 unitClass)
 
void SetHighestGuids ()
 
template<HighGuid type>
ObjectGuidGeneratorBaseGetGenerator ()
 
uint32 GenerateAuctionID ()
 
uint64 GenerateEquipmentSetGuid ()
 
uint32 GenerateMailID ()
 
uint32 GeneratePetNumber ()
 
ObjectGuid::LowType GenerateCreatureSpawnId ()
 
ObjectGuid::LowType GenerateGameObjectSpawnId ()
 
std::vector< uint32 > const * GetBreadcrumbsForQuest (uint32 questId) const
 
MailLevelReward const * GetMailLevelReward (uint32 level, uint32 raceMask)
 
CellObjectGuids const & GetGridObjectGuids (uint16 mapid, uint8 spawnMode, uint32 gridId)
 
CellObjectGuidsMap const & GetMapObjectGuids (uint16 mapid, uint8 spawnMode)
 
std::vector< TempSummonData > const * GetSummonGroup (uint32 summonerId, SummonerType summonerType, uint8 group) const
 
std::vector< GameObjectSummonData > const * GetGameObjectSummonGroup (uint32 summonerId, SummonerType summonerType, uint8 group) const
 
BroadcastText const * GetBroadcastText (uint32 id) const
 
CreatureDataContainer const & GetAllCreatureData () const
 
CreatureData const * GetCreatureData (ObjectGuid::LowType spawnId) const
 
CreatureSparringContainer const & GetSparringData () const
 
CreatureDataNewOrExistCreatureData (ObjectGuid::LowType spawnId)
 
CreatureData const * LoadCreatureDataFromDB (ObjectGuid::LowType spawnId)
 Loads a single creature spawn entry from the database into the data store cache.
 
void DeleteCreatureData (ObjectGuid::LowType spawnId)
 
ObjectGuid GetLinkedRespawnGuid (ObjectGuid guid) const
 
GameObjectDataContainer const & GetAllGOData () const
 
GameObjectData const * GetGameObjectData (ObjectGuid::LowType spawnId) const
 
SpawnData const * GetSpawnData (SpawnObjectType type, ObjectGuid::LowType spawnId) const
 
SpawnGroupTemplateData const * GetSpawnGroupData (uint32 groupId) const
 
CreatureLocale const * GetCreatureLocale (uint32 entry) const
 
GameObjectLocale const * GetGameObjectLocale (uint32 entry) const
 
ItemLocale const * GetItemLocale (uint32 entry) const
 
ItemSetNameLocale const * GetItemSetNameLocale (uint32 entry) const
 
PageTextLocale const * GetPageTextLocale (uint32 entry) const
 
QuestLocale const * GetQuestLocale (uint32 entry) const
 
GossipMenuItemsLocale const * GetGossipMenuItemsLocale (uint32 entry) const
 
PointOfInterestLocale const * GetPointOfInterestLocale (uint32 poi_id) const
 
QuestOfferRewardLocale const * GetQuestOfferRewardLocale (uint32 entry) const
 
QuestRequestItemsLocale const * GetQuestRequestItemsLocale (uint32 entry) const
 
NpcTextLocale const * GetNpcTextLocale (uint32 entry) const
 
QuestGreeting const * GetQuestGreeting (TypeID type, uint32 id) const
 
GameObjectDataNewGOData (ObjectGuid::LowType guid)
 
GameObjectData const * LoadGameObjectDataFromDB (ObjectGuid::LowType spawnId)
 Loads a single gameobject spawn entry from the database into the data store cache.
 
void DeleteGOData (ObjectGuid::LowType guid)
 
ModuleString const * GetModuleString (std::string module, uint32 id) const
 
std::string const * GetModuleString (std::string module, uint32 id, LocaleConstant locale) const
 
AcoreString const * GetAcoreString (uint32 entry) const
 
std::string GetAcoreString (uint32 entry, LocaleConstant locale) const
 
std::string GetAcoreStringForDBCLocale (uint32 entry) const
 
LocaleConstant GetDBCLocaleIndex () const
 
void SetDBCLocaleIndex (LocaleConstant locale)
 
void AddCreatureToGrid (ObjectGuid::LowType guid, CreatureData const *data)
 
void RemoveCreatureFromGrid (ObjectGuid::LowType guid, CreatureData const *data)
 
void AddGameobjectToGrid (ObjectGuid::LowType guid, GameObjectData const *data)
 
void RemoveGameobjectFromGrid (ObjectGuid::LowType guid, GameObjectData const *data)
 
ObjectGuid::LowType AddGOData (uint32 entry, uint32 map, float x, float y, float z, float o, uint32 spawntimedelay=0, float rotation0=0, float rotation1=0, float rotation2=0, float rotation3=0)
 
ObjectGuid::LowType AddCreData (uint32 entry, uint32 map, float x, float y, float z, float o, uint32 spawntimedelay=0)
 
void LoadReservedPlayerNamesDB ()
 
void LoadReservedPlayerNamesDBC ()
 
bool IsReservedName (std::string_view name) const
 
void AddReservedPlayerName (std::string const &name)
 
void LoadProfanityNamesFromDB ()
 
void LoadProfanityNamesFromDBC ()
 
bool IsProfanityName (std::string_view name) const
 
void AddProfanityPlayerName (std::string const &name)
 
GameTele const * GetGameTele (uint32 id) const
 
GameTele const * GetGameTele (std::string_view name, bool exactSearch=false) const
 
GameTeleContainer const & GetGameTeleMap () const
 
bool AddGameTele (GameTele &data)
 
bool DeleteGameTele (std::string_view name)
 
Trainer::TrainerGetTrainer (uint32 creatureId)
 
std::vector< Trainer::Trainer const * > const & GetClassTrainers (uint8 classId) const
 
VendorItemData const * GetNpcVendorItemList (uint32 entry) const
 
void AddVendorItem (uint32 entry, uint32 item, uint32 maxcount, uint32 incrtime, uint32 extendedCost, bool persist=true)
 
bool RemoveVendorItem (uint32 entry, uint32 item, bool persist=true)
 
bool IsVendorItemValid (uint32 vendor_entry, uint32 item, uint32 maxcount, uint32 ptime, uint32 ExtendedCost, Player *player=nullptr, std::set< uint32 > *skip_vendors=nullptr, uint32 ORnpcflag=0) const
 
void LoadScriptNames ()
 
ScriptNameContainerGetScriptNames ()
 
std::string const & GetScriptName (uint32 id) const
 
uint32 GetScriptId (std::string const &name)
 
SpellClickInfoMapBounds GetSpellClickInfoMapBounds (uint32 creature_id) const
 
GossipMenusMapBounds GetGossipMenusMapBounds (uint32 uiMenuId) const
 
GossipMenusMapBoundsNonConst GetGossipMenusMapBoundsNonConst (uint32 uiMenuId)
 
GossipMenuItemsMapBounds GetGossipMenuItemsMapBounds (uint32 uiMenuId) const
 
GossipMenuItemsMapBoundsNonConst GetGossipMenuItemsMapBoundsNonConst (uint32 uiMenuId)
 
void LoadFactionChangeAchievements ()
 
void LoadFactionChangeItems ()
 
void LoadFactionChangeQuests ()
 
void LoadFactionChangeReputations ()
 
void LoadFactionChangeSpells ()
 
void LoadFactionChangeTitles ()
 
bool IsTransportMap (uint32 mapId) const
 
VehicleSeatAddon const * GetVehicleSeatAddon (uint32 seatId) const
 
uint32 GetQuestMoneyReward (uint8 level, uint32 questMoneyDifficulty) const
 

Static Public Member Functions

static ObjectMgrinstance ()
 
static CreatureModel const * ChooseDisplayId (CreatureTemplate const *cinfo, CreatureData const *data=nullptr)
 
static void ChooseCreatureFlags (CreatureTemplate const *cinfo, uint32 &npcflag, uint32 &unit_flags, uint32 &dynamicflags, CreatureData const *data=nullptr)
 
static uint8 CheckPlayerName (std::string_view name, bool create=false)
 
static PetNameInvalidReason CheckPetName (std::string_view name)
 
static bool IsValidCharterName (std::string_view name)
 
static bool IsValidChannelName (std::string const &name)
 
static bool CheckDeclinedNames (std::wstring w_ownname, DeclinedName const &names)
 
static void AddLocaleString (std::string &&s, LocaleConstant locale, std::vector< std::string > &data)
 
static std::string_view GetLocaleString (std::vector< std::string > const &data, std::size_t locale)
 
static void GetLocaleString (const std::vector< std::string > &data, int loc_idx, std::string &value)
 

Public Attributes

ExclusiveQuestGroups mExclusiveQuestGroups
 
BreadcrumbQuestMap _breadcrumbsForQuest
 
CharacterConversionMap FactionChangeAchievements
 
CharacterConversionMap FactionChangeItems
 
CharacterConversionMap FactionChangeQuests
 
CharacterConversionMap FactionChangeReputation
 
CharacterConversionMap FactionChangeSpells
 
CharacterConversionMap FactionChangeTitles
 

Private Types

enum  CreatureLinkedRespawnType {
  CREATURE_TO_CREATURE ,
  CREATURE_TO_GO ,
  GO_TO_GO ,
  GO_TO_CREATURE
}
 
typedef std::unordered_map< uint32, GossipTextGossipTextContainer
 
typedef std::unordered_map< uint32, uint32QuestAreaTriggerContainer
 
typedef std::unordered_map< uint32, uint32TavernAreaTriggerContainer
 
typedef std::set< std::wstring > ReservedNamesContainer
 
typedef std::set< std::wstring > ProfanityNamesContainer
 
typedef std::map< uint32, PetLevelInfo * > PetLevelInfoContainer
 
typedef std::vector< uint32PlayerXPperLevel
 
typedef std::map< uint32, uint32BaseXPContainer
 
typedef std::map< uint32, int32FishingBaseSkillContainer
 
typedef std::map< uint32, std::vector< std::string > > HalfNameContainer
 
typedef std::map< std::pair< uint32, LocaleConstant >, std::vector< std::string > > HalfNameContainerLocale
 
typedef std::unordered_map< uint32, ItemSetNameEntryItemSetNameContainer
 

Private Member Functions

 ObjectMgr ()
 
 ~ObjectMgr ()
 
template<HighGuid high>
ObjectGuidGeneratorBaseGetGuidSequenceGenerator ()
 
void LoadScripts (ScriptsType type)
 
void LoadQuestRelationsHelper (QuestRelations &map, std::string const &table, bool starter, bool go)
 
void PlayerCreateInfoAddItemHelper (uint32 race_, uint32 class_, uint32 itemId, int32 count)
 
void BuildPlayerLevelInfo (uint8 race, uint8 class_, uint8 level, PlayerLevelInfo *plinfo) const
 

Private Attributes

uint32 _auctionId
 
uint64 _equipmentSetGuid
 
uint32 _mailId
 
std::mutex _mailIdMutex
 
uint32 _hiPetNumber
 
std::mutex _hiPetNumberMutex
 
ObjectGuid::LowType _creatureSpawnId
 
ObjectGuid::LowType _gameObjectSpawnId
 
std::map< HighGuid, std::unique_ptr< ObjectGuidGeneratorBase > > _guidGenerators
 
QuestMap _questTemplates
 
std::vector< Quest * > _questTemplatesFast
 
QuestAreaTriggerContainer _questAreaTriggerStore
 
TavernAreaTriggerContainer _tavernAreaTriggerStore
 
GossipTextContainer _gossipTextStore
 
QuestGreetingContainer _questGreetingStore
 
AreaTriggerContainer _areaTriggerStore
 
AreaTriggerTeleportContainer _areaTriggerTeleportStore
 
AreaTriggerScriptContainer _areaTriggerScriptStore
 
DungeonProgressionRequirementsContainer _accessRequirementStore
 
DungeonEncounterContainer _dungeonEncounterStore
 
RepRewardRateContainer _repRewardRateStore
 
RepOnKillContainer _repOnKillStore
 
RepSpilloverTemplateContainer _repSpilloverTemplateStore
 
GossipMenusContainer _gossipMenusStore
 
GossipMenuItemsContainer _gossipMenuItemsStore
 
PointOfInterestContainer _pointsOfInterestStore
 
QuestPOIContainer _questPOIStore
 
QuestRelations _goQuestRelations
 
QuestRelations _goQuestInvolvedRelations
 
QuestRelations _creatureQuestRelations
 
QuestRelations _creatureQuestInvolvedRelations
 
ReservedNamesContainer _reservedNamesStore
 
ProfanityNamesContainer _profanityNamesStore
 
GameTeleContainer _gameTeleStore
 
ScriptNameContainer _scriptNamesStore
 
SpellClickInfoContainer _spellClickInfoStore
 
SpellScriptsContainer _spellScriptsStore
 
VehicleAccessoryContainer _vehicleTemplateAccessoryStore
 
VehicleAccessoryContainer _vehicleAccessoryStore
 
VehicleSeatAddonContainer _vehicleSeatAddonStore
 
LocaleConstant DBCLocaleIndex
 
PageTextContainer _pageTextStore
 
InstanceTemplateContainer _instanceTemplateStore
 
CreatureSparringContainer _creatureSparringStore
 
MailLevelRewardContainer _mailLevelRewardStore
 
CreatureBaseStatsContainer _creatureBaseStatsStore
 
PetLevelInfoContainer _petInfoStore
 
PlayerClassInfo_playerClassInfo [MAX_CLASSES]
 
std::vector< std::vector< PlayerInfo * > > _playerInfo
 
PlayerXPperLevel _playerXPperLevel
 
BaseXPContainer _baseXPTable
 
FishingBaseSkillContainer _fishingBaseForAreaStore
 
HalfNameContainer _petHalfName0
 
HalfNameContainer _petHalfName1
 
HalfNameContainerLocale _petHalfLocaleName0
 
HalfNameContainerLocale _petHalfLocaleName1
 
ItemSetNameContainer _itemSetNameStore
 
MapObjectGuids _mapObjectGuidsStore
 
CellObjectGuidsMap _emptyCellObjectGuidsMap
 
CellObjectGuids _emptyCellObjectGuids
 
CreatureDataContainer _creatureDataStore
 
CreatureTemplateContainer _creatureTemplateStore
 
CreatureCustomIDsContainer _creatureCustomIDsStore
 
std::vector< CreatureTemplate * > _creatureTemplateStoreFast
 
CreatureModelContainer _creatureModelStore
 
CreatureAddonContainer _creatureAddonStore
 
CreatureAddonContainer _creatureTemplateAddonStore
 
std::unordered_map< ObjectGuid::LowType, CreatureMovementData_creatureMovementOverrides
 
GameObjectAddonContainer _gameObjectAddonStore
 
GameObjectQuestItemMap _gameObjectQuestItemStore
 
CreatureQuestItemMap _creatureQuestItemStore
 
EquipmentInfoContainer _equipmentInfoStore
 
LinkedRespawnContainer _linkedRespawnStore
 
CreatureLocaleContainer _creatureLocaleStore
 
GameObjectDataContainer _gameObjectDataStore
 
SpawnGroupDataContainer _spawnGroupDataStore
 
GameObjectLocaleContainer _gameObjectLocaleStore
 
GameObjectTemplateContainer _gameObjectTemplateStore
 
GameObjectTemplateAddonContainer _gameObjectTemplateAddonStore
 
TempSummonDataContainer _tempSummonDataStore
 Stores temp summon data grouped by summoner's entry, summoner's type and group id.
 
GameObjectSummonDataContainer _goSummonDataStore
 Stores gameobject summon data grouped by summoner's entry, summoner's type and group id.
 
BroadcastTextContainer _broadcastTextStore
 
ItemTemplateContainer _itemTemplateStore
 
std::vector< ItemTemplate * > _itemTemplateStoreFast
 
ItemLocaleContainer _itemLocaleStore
 
ItemSetNameLocaleContainer _itemSetNameLocaleStore
 
QuestLocaleContainer _questLocaleStore
 
QuestOfferRewardLocaleContainer _questOfferRewardLocaleStore
 
QuestRequestItemsLocaleContainer _questRequestItemsLocaleStore
 
NpcTextLocaleContainer _npcTextLocaleStore
 
PageTextLocaleContainer _pageTextLocaleStore
 
ModuleStringContainer _moduleStringStore
 
AcoreStringContainer _acoreStringStore
 
GossipMenuItemsLocaleContainer _gossipMenuItemsLocaleStore
 
PointOfInterestLocaleContainer _pointOfInterestLocaleStore
 
CacheVendorItemContainer _cacheVendorItemStore
 
std::unordered_map< uint32, Trainer::Trainer_trainers
 
std::unordered_map< uint8, std::vector< Trainer::Trainer const * > > _classTrainers
 
std::unordered_map< uint32, uint32_creatureDefaultTrainers
 
std::set< uint32_difficultyEntries [MAX_DIFFICULTY - 1]
 
std::set< uint32_hasDifficultyEntries [MAX_DIFFICULTY - 1]
 
std::set< uint32_transportMaps
 
PlayerTotemModelMap _playerTotemModel
 
PlayerShapeshiftModelMap _playerShapeshiftModel
 
QuestMoneyRewardStore _questMoneyRewards
 
std::vector< GameobjectInstanceSavedStateGameobjectInstanceSavedStateList
 

Friends

class PlayerDumpReader
 

Detailed Description

Member Typedef Documentation

◆ AreaTriggerContainer

typedef std::unordered_map<uint32, AreaTrigger> ObjectMgr::AreaTriggerContainer

◆ AreaTriggerScriptContainer

typedef std::unordered_map<uint32, uint32> ObjectMgr::AreaTriggerScriptContainer

◆ AreaTriggerTeleportContainer

◆ BaseXPContainer

typedef std::map<uint32, uint32> ObjectMgr::BaseXPContainer
private

◆ BreadcrumbQuestMap

typedef std::unordered_map<uint32, std::vector<uint32> > ObjectMgr::BreadcrumbQuestMap

◆ CharacterConversionMap

◆ CreatureSparringContainer

typedef std::unordered_map<ObjectGuid::LowType, std::vector<float> > ObjectMgr::CreatureSparringContainer

◆ DungeonProgressionRequirementsContainer

◆ ExclusiveQuestGroups

typedef std::multimap<int32, uint32> ObjectMgr::ExclusiveQuestGroups

◆ ExclusiveQuestGroupsBounds

typedef std::pair<ExclusiveQuestGroups::const_iterator, ExclusiveQuestGroups::const_iterator> ObjectMgr::ExclusiveQuestGroupsBounds

◆ FishingBaseSkillContainer

◆ GossipTextContainer

typedef std::unordered_map<uint32, GossipText> ObjectMgr::GossipTextContainer
private

◆ HalfNameContainer

typedef std::map<uint32, std::vector<std::string> > ObjectMgr::HalfNameContainer
private

◆ HalfNameContainerLocale

typedef std::map<std::pair<uint32, LocaleConstant>, std::vector<std::string> > ObjectMgr::HalfNameContainerLocale
private

◆ ItemMap

typedef std::unordered_map<uint32, Item*> ObjectMgr::ItemMap

◆ ItemSetNameContainer

typedef std::unordered_map<uint32, ItemSetNameEntry> ObjectMgr::ItemSetNameContainer
private

◆ PetLevelInfoContainer

◆ PlayerXPperLevel

typedef std::vector<uint32> ObjectMgr::PlayerXPperLevel
private

◆ PointOfInterestContainer

◆ ProfanityNamesContainer

typedef std::set<std::wstring> ObjectMgr::ProfanityNamesContainer
private

◆ QuestAreaTriggerContainer

typedef std::unordered_map<uint32, uint32> ObjectMgr::QuestAreaTriggerContainer
private

◆ QuestMap

typedef std::unordered_map<uint32, Quest*> ObjectMgr::QuestMap

◆ RepOnKillContainer

◆ RepRewardRateContainer

◆ RepSpilloverTemplateContainer

◆ ReservedNamesContainer

typedef std::set<std::wstring> ObjectMgr::ReservedNamesContainer
private

◆ ScriptNameContainer

typedef std::vector<std::string> ObjectMgr::ScriptNameContainer

◆ TavernAreaTriggerContainer

typedef std::unordered_map<uint32, uint32> ObjectMgr::TavernAreaTriggerContainer
private

Member Enumeration Documentation

◆ CreatureLinkedRespawnType

Enumerator
CREATURE_TO_CREATURE 
CREATURE_TO_GO 
GO_TO_GO 
GO_TO_CREATURE 
1688 {
1690 CREATURE_TO_GO, // Creature is dependant on GO
1691 GO_TO_GO,
1692 GO_TO_CREATURE, // GO is dependant on creature
1693 };
@ CREATURE_TO_GO
Definition ObjectMgr.h:1690
@ CREATURE_TO_CREATURE
Definition ObjectMgr.h:1689
@ GO_TO_GO
Definition ObjectMgr.h:1691
@ GO_TO_CREATURE
Definition ObjectMgr.h:1692

Constructor & Destructor Documentation

◆ ObjectMgr()

ObjectMgr::ObjectMgr ( )
private
300 :
301 _auctionId(1),
303 _mailId(1),
304 _hiPetNumber(1),
308{
309 for (uint8 i = 0; i < MAX_CLASSES; ++i)
310 {
311 _playerClassInfo[i] = nullptr;
312 }
313
314 // Initialize default spawn group
315 _spawnGroupDataStore[0] = {0, "Default Group", 0, SpawnGroupFlags(SPAWNGROUP_FLAG_SYSTEM)};
316}
@ LOCALE_enUS
Definition Common.h:118
std::uint8_t uint8
Definition Define.h:109
#define MAX_CLASSES
Definition SharedDefines.h:140
SpawnGroupFlags
Definition SpawnData.h:41
@ SPAWNGROUP_FLAG_SYSTEM
Definition SpawnData.h:43
SpawnGroupDataContainer _spawnGroupDataStore
Definition ObjectMgr.h:1655
ObjectGuid::LowType _gameObjectSpawnId
Definition ObjectMgr.h:1525
uint32 _mailId
Definition ObjectMgr.h:1519
ObjectGuid::LowType _creatureSpawnId
Definition ObjectMgr.h:1524
LocaleConstant DBCLocaleIndex
Definition ObjectMgr.h:1592
PlayerClassInfo * _playerClassInfo[MAX_CLASSES]
Definition ObjectMgr.h:1612
uint64 _equipmentSetGuid
Definition ObjectMgr.h:1518
uint32 _auctionId
Definition ObjectMgr.h:1517
uint32 _hiPetNumber
Definition ObjectMgr.h:1521

References _playerClassInfo, _spawnGroupDataStore, MAX_CLASSES, and SPAWNGROUP_FLAG_SYSTEM.

◆ ~ObjectMgr()

ObjectMgr::~ObjectMgr ( )
private
319{
320 for (QuestMap::iterator i = _questTemplates.begin(); i != _questTemplates.end(); ++i)
321 delete i->second;
322
323 for (PetLevelInfoContainer::iterator i = _petInfoStore.begin(); i != _petInfoStore.end(); ++i)
324 delete[] i->second;
325
326 // free only if loaded
327 for (int class_ = 0; class_ < MAX_CLASSES; ++class_)
328 {
329 if (_playerClassInfo[class_])
330 delete[] _playerClassInfo[class_]->levelInfo;
331 delete _playerClassInfo[class_];
332 }
333
334 for (int race = 0; race < sRaceMgr->GetMaxRaces(); ++race)
335 {
336 for (int class_ = 0; class_ < MAX_CLASSES; ++class_)
337 {
338 if (_playerInfo[race][class_])
339 delete[] _playerInfo[race][class_]->levelInfo;
340 delete _playerInfo[race][class_];
341 }
342 }
343
344 for (CacheVendorItemContainer::iterator itr = _cacheVendorItemStore.begin(); itr != _cacheVendorItemStore.end(); ++itr)
345 itr->second.Clear();
346
347 for (DungeonEncounterContainer::iterator itr = _dungeonEncounterStore.begin(); itr != _dungeonEncounterStore.end(); ++itr)
348 for (DungeonEncounterList::iterator encounterItr = itr->second.begin(); encounterItr != itr->second.end(); ++encounterItr)
349 delete *encounterItr;
350
351 for (DungeonProgressionRequirementsContainer::iterator itr = _accessRequirementStore.begin(); itr != _accessRequirementStore.end(); ++itr)
352 {
353 std::unordered_map<uint8, DungeonProgressionRequirements*> difficulties = itr->second;
354 for (auto difficultiesItr = difficulties.begin(); difficultiesItr != difficulties.end(); ++difficultiesItr)
355 {
356 for (auto questItr = difficultiesItr->second->quests.begin(); questItr != difficultiesItr->second->quests.end(); ++questItr)
357 {
358 delete* questItr;
359 }
360
361 for (auto achievementItr = difficultiesItr->second->achievements.begin(); achievementItr != difficultiesItr->second->achievements.end(); ++achievementItr)
362 {
363 delete* achievementItr;
364 }
365
366 for (auto itemsItr = difficultiesItr->second->items.begin(); itemsItr != difficultiesItr->second->items.end(); ++itemsItr)
367 {
368 delete* itemsItr;
369 }
370
371 delete difficultiesItr->second;
372 }
373 }
374}
#define sRaceMgr
Definition RaceMgr.h:52
std::vector< std::vector< PlayerInfo * > > _playerInfo
Definition ObjectMgr.h:1616
PetLevelInfoContainer _petInfoStore
Definition ObjectMgr.h:1610
QuestMap _questTemplates
Definition ObjectMgr.h:1540
DungeonProgressionRequirementsContainer _accessRequirementStore
Definition ObjectMgr.h:1554
DungeonEncounterContainer _dungeonEncounterStore
Definition ObjectMgr.h:1555
CacheVendorItemContainer _cacheVendorItemStore
Definition ObjectMgr.h:1679
PlayerClassLevelInfo * levelInfo
Definition Player.h:286

References _accessRequirementStore, _cacheVendorItemStore, _dungeonEncounterStore, _petInfoStore, _playerClassInfo, _playerInfo, _questTemplates, PlayerClassInfo::levelInfo, MAX_CLASSES, and sRaceMgr.

Member Function Documentation

◆ AddCreatureToGrid()

void ObjectMgr::AddCreatureToGrid ( ObjectGuid::LowType  guid,
CreatureData const *  data 
)
2711{
2712 uint8 mask = data->spawnMask;
2713 for (uint8 i = 0; mask != 0; i++, mask >>= 1)
2714 {
2715 if (mask & 1)
2716 {
2717 GridCoord gridCoord = Acore::ComputeGridCoord(data->posX, data->posY);
2718 CellObjectGuids& cell_guids = _mapObjectGuidsStore[MAKE_PAIR32(data->mapid, i)][gridCoord.GetId()];
2719 cell_guids.creatures.insert(guid);
2720 }
2721 }
2722}
uint32 MAKE_PAIR32(uint16 l, uint16 h)
Definition ObjectDefines.h:88
MapObjectGuids _mapObjectGuidsStore
Definition ObjectMgr.h:1637
GridCoord ComputeGridCoord(float x, float y)
Definition GridDefines.h:185
Definition ObjectMgr.h:479
CellGuidSet creatures
Definition ObjectMgr.h:480
Definition GridDefines.h:88
uint32 GetId() const
Definition GridDefines.h:150

References _mapObjectGuidsStore, Acore::ComputeGridCoord(), CellObjectGuids::creatures, CoordPair< LIMIT >::GetId(), MAKE_PAIR32(), SpawnData::mapid, SpawnData::posX, SpawnData::posY, and SpawnData::spawnMask.

Referenced by AddCreData(), and LoadCreatures().

◆ AddCreData()

ObjectGuid::LowType ObjectMgr::AddCreData ( uint32  entry,
uint32  map,
float  x,
float  y,
float  z,
float  o,
uint32  spawntimedelay = 0 
)
2791{
2792 CreatureTemplate const* cInfo = GetCreatureTemplate(entry);
2793 if (!cInfo)
2794 return 0;
2795
2796 uint32 level = cInfo->minlevel == cInfo->maxlevel ? cInfo->minlevel : urand(cInfo->minlevel, cInfo->maxlevel); // Only used for extracting creature base stats
2797 CreatureBaseStats const* stats = GetCreatureBaseStats(level, cInfo->unit_class);
2798 Map* map = sMapMgr->CreateBaseMap(mapId);
2799 if (!map)
2800 return 0;
2801
2803 CreatureData& data = NewOrExistCreatureData(spawnId);
2804 data.spawnMask = spawnId;
2805 data.id1 = entry;
2806 data.id2 = 0;
2807 data.id3 = 0;
2808 data.mapid = mapId;
2809 data.displayid = 0;
2810 data.equipmentId = 0;
2811 data.posX = x;
2812 data.posY = y;
2813 data.posZ = z;
2814 data.orientation = o;
2815 data.spawntimesecs = spawntimedelay;
2816 data.wander_distance = 0;
2817 data.currentwaypoint = 0;
2818 data.curhealth = stats->GenerateHealth(cInfo);
2819 data.curmana = stats->GenerateMana(cInfo);
2820 data.movementType = cInfo->MovementType;
2821 data.spawnMask = 1;
2823 data.dbData = false;
2824 data.npcflag = cInfo->npcflag;
2825 data.unit_flags = cInfo->unit_flags;
2826 data.dynamicflags = cInfo->dynamicflags;
2827
2828 AddCreatureToGrid(spawnId, &data);
2829
2830 // Spawn if necessary (loaded grids only)
2831 if (!map->Instanceable() && map->IsGridLoaded(x, y))
2832 {
2833 Creature* creature = new Creature();
2834 if (!creature->LoadCreatureFromDB(spawnId, map, true, true))
2835 {
2836 LOG_ERROR("sql.sql", "AddCreature: Cannot add creature entry {} to map", entry);
2837 delete creature;
2838 return 0;
2839 }
2840 }
2841
2842 return spawnId;
2843}
std::uint32_t uint32
Definition Define.h:107
#define LOG_ERROR(filterType__,...)
Definition Log.h:158
#define sMapMgr
Definition MapMgr.h:220
@ PHASEMASK_NORMAL
Definition Object.h:63
uint32 urand(uint32 min, uint32 max)
Definition Random.cpp:44
Definition Creature.h:47
bool LoadCreatureFromDB(ObjectGuid::LowType guid, Map *map, bool addToMap=true, bool allowDuplicate=false)
Definition Creature.cpp:1654
Definition Map.h:164
bool IsGridLoaded(GridCoord const &gridCoord) const
Definition Map.cpp:202
bool Instanceable() const
Definition Map.h:294
uint32 LowType
Definition ObjectGuid.h:122
CreatureBaseStats const * GetCreatureBaseStats(uint8 level, uint8 unitClass)
Definition ObjectMgr.cpp:10457
void AddCreatureToGrid(ObjectGuid::LowType guid, CreatureData const *data)
Definition ObjectMgr.cpp:2710
ObjectGuid::LowType GenerateCreatureSpawnId()
Definition ObjectMgr.cpp:7696
CreatureData & NewOrExistCreatureData(ObjectGuid::LowType spawnId)
Definition ObjectMgr.h:1241
CreatureTemplate const * GetCreatureTemplate(uint32 entry)
Definition ObjectMgr.cpp:10822
Definition CreatureData.h:298
uint32 GenerateMana(CreatureTemplate const *info) const
Definition CreatureData.h:318
uint32 GenerateHealth(CreatureTemplate const *info) const
Definition CreatureData.h:313
Definition CreatureData.h:370
float wander_distance
Definition CreatureData.h:378
uint32 spawntimesecs
Definition CreatureData.h:377
uint32 dynamicflags
Definition CreatureData.h:385
uint32 npcflag
Definition CreatureData.h:383
uint32 displayid
Definition CreatureData.h:375
uint8 movementType
Definition CreatureData.h:382
uint32 unit_flags
Definition CreatureData.h:384
uint32 id2
Definition CreatureData.h:373
uint32 curhealth
Definition CreatureData.h:380
uint32 curmana
Definition CreatureData.h:381
uint32 id3
Definition CreatureData.h:374
int8 equipmentId
Definition CreatureData.h:376
uint32 currentwaypoint
Definition CreatureData.h:379
uint32 id1
Definition CreatureData.h:372
Definition CreatureData.h:187
uint32 unit_flags
Definition CreatureData.h:214
uint8 minlevel
Definition CreatureData.h:196
uint8 maxlevel
Definition CreatureData.h:197
uint32 MovementType
Definition CreatureData.h:230
uint32 npcflag
Definition CreatureData.h:200
uint32 unit_class
Definition CreatureData.h:213
uint32 dynamicflags
Definition CreatureData.h:216
float posX
Definition SpawnData.h:66
float posY
Definition SpawnData.h:67
uint32 phaseMask
Definition SpawnData.h:65
uint8 spawnMask
Definition SpawnData.h:70
bool dbData
Definition SpawnData.h:72
float orientation
Definition SpawnData.h:69
uint16 mapid
Definition SpawnData.h:64
float posZ
Definition SpawnData.h:68

References AddCreatureToGrid(), CreatureData::curhealth, CreatureData::curmana, CreatureData::currentwaypoint, SpawnData::dbData, CreatureData::displayid, CreatureTemplate::dynamicflags, CreatureData::dynamicflags, CreatureData::equipmentId, GenerateCreatureSpawnId(), CreatureBaseStats::GenerateHealth(), CreatureBaseStats::GenerateMana(), GetCreatureBaseStats(), GetCreatureTemplate(), CreatureData::id1, CreatureData::id2, CreatureData::id3, Map::Instanceable(), Map::IsGridLoaded(), Creature::LoadCreatureFromDB(), LOG_ERROR, SpawnData::mapid, CreatureTemplate::maxlevel, CreatureTemplate::minlevel, CreatureTemplate::MovementType, CreatureData::movementType, NewOrExistCreatureData(), CreatureTemplate::npcflag, CreatureData::npcflag, SpawnData::orientation, SpawnData::phaseMask, PHASEMASK_NORMAL, SpawnData::posX, SpawnData::posY, SpawnData::posZ, sMapMgr, SpawnData::spawnMask, CreatureData::spawntimesecs, CreatureTemplate::unit_class, CreatureTemplate::unit_flags, CreatureData::unit_flags, urand(), and CreatureData::wander_distance.

◆ AddGameobjectInfo()

void ObjectMgr::AddGameobjectInfo ( GameObjectTemplate goinfo)

◆ AddGameobjectToGrid()

void ObjectMgr::AddGameobjectToGrid ( ObjectGuid::LowType  guid,
GameObjectData const *  data 
)
3155{
3156 uint8 mask = data->spawnMask;
3157 for (uint8 i = 0; mask != 0; i++, mask >>= 1)
3158 {
3159 if (mask & 1)
3160 {
3161 GridCoord gridCoord = Acore::ComputeGridCoord(data->posX, data->posY);
3162 CellObjectGuids& cell_guids = _mapObjectGuidsStore[MAKE_PAIR32(data->mapid, i)][gridCoord.GetId()];
3163 cell_guids.gameobjects.insert(guid);
3164 }
3165 }
3166}
CellGuidSet gameobjects
Definition ObjectMgr.h:481

References _mapObjectGuidsStore, Acore::ComputeGridCoord(), CellObjectGuids::gameobjects, CoordPair< LIMIT >::GetId(), MAKE_PAIR32(), SpawnData::mapid, SpawnData::posX, SpawnData::posY, and SpawnData::spawnMask.

Referenced by AddGOData(), and LoadGameobjects().

◆ AddGameTele()

bool ObjectMgr::AddGameTele ( GameTele data)
9627{
9628 // find max id
9629 uint32 new_id = 0;
9630 for (GameTeleContainer::const_iterator itr = _gameTeleStore.begin(); itr != _gameTeleStore.end(); ++itr)
9631 if (itr->first > new_id)
9632 new_id = itr->first;
9633
9634 // use next
9635 ++new_id;
9636
9637 if (!Utf8toWStr(tele.name, tele.wnameLow))
9638 return false;
9639
9640 wstrToLower(tele.wnameLow);
9641
9642 _gameTeleStore[new_id] = tele;
9643
9645
9646 stmt->SetData(0, new_id);
9647 stmt->SetData(1, tele.position_x);
9648 stmt->SetData(2, tele.position_y);
9649 stmt->SetData(3, tele.position_z);
9650 stmt->SetData(4, tele.orientation);
9651 stmt->SetData(5, uint16(tele.mapId));
9652 stmt->SetData(6, tele.name);
9653
9654 WorldDatabase.Execute(stmt);
9655
9656 return true;
9657}
DatabaseWorkerPool< WorldDatabaseConnection > WorldDatabase
Accessor to the world database.
Definition DatabaseEnv.cpp:20
std::uint16_t uint16
Definition Define.h:108
bool Utf8toWStr(char const *utf8str, std::size_t csize, wchar_t *wstr, std::size_t &wsize)
Definition Util.cpp:281
void wstrToLower(std::wstring &str)
Definition Util.cpp:382
@ WORLD_INS_GAME_TELE
Definition WorldDatabase.h:41
GameTeleContainer _gameTeleStore
Definition ObjectMgr.h:1580
Acore::Types::is_default< T > SetData(const uint8 index, T value)
Definition PreparedStatement.h:77
Definition PreparedStatement.h:157

References _gameTeleStore, GameTele::mapId, GameTele::name, GameTele::orientation, GameTele::position_x, GameTele::position_y, GameTele::position_z, PreparedStatementBase::SetData(), Utf8toWStr(), GameTele::wnameLow, WORLD_INS_GAME_TELE, WorldDatabase, and wstrToLower().

◆ AddGOData()

ObjectGuid::LowType ObjectMgr::AddGOData ( uint32  entry,
uint32  map,
float  x,
float  y,
float  z,
float  o,
uint32  spawntimedelay = 0,
float  rotation0 = 0,
float  rotation1 = 0,
float  rotation2 = 0,
float  rotation3 = 0 
)
2739{
2740 GameObjectTemplate const* goinfo = GetGameObjectTemplate(entry);
2741 if (!goinfo)
2742 return 0;
2743
2744 Map* map = sMapMgr->CreateBaseMap(mapId);
2745 if (!map)
2746 return 0;
2747
2749
2750 GameObjectData& data = NewGOData(spawnId);
2751 data.id = entry;
2752 data.mapid = mapId;
2753 data.posX = x;
2754 data.posY = y;
2755 data.posZ = z;
2756 data.orientation = o;
2757 data.rotation.x = rotation0;
2758 data.rotation.y = rotation1;
2759 data.rotation.z = rotation2;
2760 data.rotation.w = rotation3;
2761 data.spawntimesecs = spawntimedelay;
2762 data.animprogress = 100;
2763 data.spawnMask = 1;
2764 data.go_state = GO_STATE_READY;
2766 data.artKit = goinfo->type == GAMEOBJECT_TYPE_CAPTURE_POINT ? 21 : 0;
2767 data.dbData = false;
2768 data.spawnGroupId = 0;
2769
2770 AddGameobjectToGrid(spawnId, &data);
2771
2772 // Spawn if necessary (loaded grids only)
2773 // We use spawn coords to spawn
2774 if (!map->Instanceable() && map->IsGridLoaded(x, y))
2775 {
2777 if (!go->LoadGameObjectFromDB(spawnId, map))
2778 {
2779 LOG_ERROR("sql.sql", "AddGOData: cannot add gameobject entry {} to map", entry);
2780 delete go;
2781 return 0;
2782 }
2783 }
2784
2785 LOG_DEBUG("maps", "AddGOData: spawnId {} entry {} map {} x {} y {} z {} o {}", spawnId, entry, mapId, x, y, z, o);
2786
2787 return spawnId;
2788}
@ GO_STATE_READY
Definition GameObjectData.h:709
#define LOG_DEBUG(filterType__,...)
Definition Log.h:170
@ GAMEOBJECT_TYPE_CAPTURE_POINT
Definition SharedDefines.h:1595
Definition GameObject.h:120
virtual bool LoadGameObjectFromDB(ObjectGuid::LowType guid, Map *map, bool addToMap=true)
Definition GameObject.cpp:1099
void AddGameobjectToGrid(ObjectGuid::LowType guid, GameObjectData const *data)
Definition ObjectMgr.cpp:3154
GameObjectTemplate const * GetGameObjectTemplate(uint32 entry)
Definition ObjectMgr.cpp:10798
ObjectGuid::LowType GenerateGameObjectSpawnId()
Definition ObjectMgr.cpp:7706
GameObjectData & NewGOData(ObjectGuid::LowType guid)
Definition ObjectMgr.h:1349
bool IsGameObjectStaticTransport(uint32 entry)
Definition ObjectMgr.cpp:10807
Definition Transport.h:115
Definition GameObjectData.h:715
uint8 artKit
Definition GameObjectData.h:722
int32 spawntimesecs
Definition GameObjectData.h:719
G3D::Quat rotation
Definition GameObjectData.h:718
uint32 animprogress
Definition GameObjectData.h:720
uint32 id
Definition GameObjectData.h:717
GOState go_state
Definition GameObjectData.h:721
Definition GameObjectData.h:32
uint32 type
Definition GameObjectData.h:34
uint32 spawnGroupId
Definition SpawnData.h:73

References AddGameobjectToGrid(), GameObjectData::animprogress, GameObjectData::artKit, SpawnData::dbData, GAMEOBJECT_TYPE_CAPTURE_POINT, GenerateGameObjectSpawnId(), GetGameObjectTemplate(), GameObjectData::go_state, GO_STATE_READY, GameObjectData::id, Map::Instanceable(), IsGameObjectStaticTransport(), Map::IsGridLoaded(), GameObject::LoadGameObjectFromDB(), LOG_DEBUG, LOG_ERROR, SpawnData::mapid, NewGOData(), SpawnData::orientation, SpawnData::phaseMask, PHASEMASK_NORMAL, SpawnData::posX, SpawnData::posY, SpawnData::posZ, GameObjectData::rotation, sMapMgr, SpawnData::spawnGroupId, SpawnData::spawnMask, GameObjectData::spawntimesecs, and GameObjectTemplate::type.

◆ AddLocaleString()

◆ AddProfanityPlayerName()

void ObjectMgr::AddProfanityPlayerName ( std::string const &  name)
8994{
8995 if (!IsProfanityName(name))
8996 {
8997 std::wstring wstr;
8998 if (!Utf8toWStr(name, wstr))
8999 {
9000 LOG_ERROR("server", "Could not add invalid name to profanity player names: {}", name);
9001 return;
9002 }
9003 wstrToLower(wstr);
9004
9005 _profanityNamesStore.insert(wstr);
9006
9008 stmt->SetData(0, name);
9009 CharacterDatabase.Execute(stmt);
9010 }
9011}
@ CHAR_INS_PROFANITY_PLAYER_NAME
Definition CharacterDatabase.h:522
DatabaseWorkerPool< CharacterDatabaseConnection > CharacterDatabase
Accessor to the character database.
Definition DatabaseEnv.cpp:21
ProfanityNamesContainer _profanityNamesStore
Definition ObjectMgr.h:1578
bool IsProfanityName(std::string_view name) const
Definition ObjectMgr.cpp:8978

References _profanityNamesStore, CHAR_INS_PROFANITY_PLAYER_NAME, CharacterDatabase, IsProfanityName(), LOG_ERROR, PreparedStatementBase::SetData(), Utf8toWStr(), and wstrToLower().

◆ AddReservedPlayerName()

void ObjectMgr::AddReservedPlayerName ( std::string const &  name)
8891{
8892 if (!IsReservedName(name))
8893 {
8894 std::wstring wstr;
8895 if (!Utf8toWStr(name, wstr))
8896 {
8897 LOG_ERROR("server", "Could not add invalid name to reserved player names: {}", name);
8898 return;
8899 }
8900 wstrToLower(wstr);
8901
8902 _reservedNamesStore.insert(wstr);
8903
8905 stmt->SetData(0, name);
8906 CharacterDatabase.Execute(stmt);
8907 }
8908}
@ CHAR_INS_RESERVED_PLAYER_NAME
Definition CharacterDatabase.h:521
bool IsReservedName(std::string_view name) const
Definition ObjectMgr.cpp:8875
ReservedNamesContainer _reservedNamesStore
Definition ObjectMgr.h:1574

References _reservedNamesStore, CHAR_INS_RESERVED_PLAYER_NAME, CharacterDatabase, IsReservedName(), LOG_ERROR, PreparedStatementBase::SetData(), Utf8toWStr(), and wstrToLower().

◆ AddVendorItem()

void ObjectMgr::AddVendorItem ( uint32  entry,
uint32  item,
uint32  maxcount,
uint32  incrtime,
uint32  extendedCost,
bool  persist = true 
)
10135{
10136 VendorItemData& vList = _cacheVendorItemStore[entry];
10137 vList.AddItem(item, maxcount, incrtime, extendedCost);
10138
10139 if (persist)
10140 {
10142
10143 stmt->SetData(0, entry);
10144 stmt->SetData(1, item);
10145 stmt->SetData(2, maxcount);
10146 stmt->SetData(3, incrtime);
10147 stmt->SetData(4, extendedCost);
10148
10149 WorldDatabase.Execute(stmt);
10150 }
10151}
@ WORLD_INS_NPC_VENDOR
Definition WorldDatabase.h:43
Definition CreatureData.h:460
void AddItem(uint32 item, int32 maxcount, uint32 ptime, uint32 ExtendedCost)
Definition CreatureData.h:472

References _cacheVendorItemStore, VendorItemData::AddItem(), PreparedStatementBase::SetData(), WORLD_INS_NPC_VENDOR, and WorldDatabase.

◆ BuildPlayerLevelInfo()

void ObjectMgr::BuildPlayerLevelInfo ( uint8  race,
uint8  class_,
uint8  level,
PlayerLevelInfo plinfo 
) const
private
4923{
4924 // base data (last known level)
4925 *info = _playerInfo[race][_class]->levelInfo[sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL) - 1];
4926
4927 // if conversion from uint32 to uint8 causes unexpected behaviour, change lvl to uint32
4928 for (uint8 lvl = sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL) - 1; lvl < level; ++lvl)
4929 {
4930 switch (_class)
4931 {
4932 case CLASS_WARRIOR:
4933 info->stats[STAT_STRENGTH] += (lvl > 23 ? 2 : (lvl > 1 ? 1 : 0));
4934 info->stats[STAT_STAMINA] += (lvl > 23 ? 2 : (lvl > 1 ? 1 : 0));
4935 info->stats[STAT_AGILITY] += (lvl > 36 ? 1 : (lvl > 6 && (lvl % 2) ? 1 : 0));
4936 info->stats[STAT_INTELLECT] += (lvl > 9 && !(lvl % 2) ? 1 : 0);
4937 info->stats[STAT_SPIRIT] += (lvl > 9 && !(lvl % 2) ? 1 : 0);
4938 break;
4939 case CLASS_PALADIN:
4940 info->stats[STAT_STRENGTH] += (lvl > 3 ? 1 : 0);
4941 info->stats[STAT_STAMINA] += (lvl > 33 ? 2 : (lvl > 1 ? 1 : 0));
4942 info->stats[STAT_AGILITY] += (lvl > 38 ? 1 : (lvl > 7 && !(lvl % 2) ? 1 : 0));
4943 info->stats[STAT_INTELLECT] += (lvl > 6 && (lvl % 2) ? 1 : 0);
4944 info->stats[STAT_SPIRIT] += (lvl > 7 ? 1 : 0);
4945 break;
4946 case CLASS_HUNTER:
4947 info->stats[STAT_STRENGTH] += (lvl > 4 ? 1 : 0);
4948 info->stats[STAT_STAMINA] += (lvl > 4 ? 1 : 0);
4949 info->stats[STAT_AGILITY] += (lvl > 33 ? 2 : (lvl > 1 ? 1 : 0));
4950 info->stats[STAT_INTELLECT] += (lvl > 8 && (lvl % 2) ? 1 : 0);
4951 info->stats[STAT_SPIRIT] += (lvl > 38 ? 1 : (lvl > 9 && !(lvl % 2) ? 1 : 0));
4952 break;
4953 case CLASS_ROGUE:
4954 info->stats[STAT_STRENGTH] += (lvl > 5 ? 1 : 0);
4955 info->stats[STAT_STAMINA] += (lvl > 4 ? 1 : 0);
4956 info->stats[STAT_AGILITY] += (lvl > 16 ? 2 : (lvl > 1 ? 1 : 0));
4957 info->stats[STAT_INTELLECT] += (lvl > 8 && !(lvl % 2) ? 1 : 0);
4958 info->stats[STAT_SPIRIT] += (lvl > 38 ? 1 : (lvl > 9 && !(lvl % 2) ? 1 : 0));
4959 break;
4960 case CLASS_PRIEST:
4961 info->stats[STAT_STRENGTH] += (lvl > 9 && !(lvl % 2) ? 1 : 0);
4962 info->stats[STAT_STAMINA] += (lvl > 5 ? 1 : 0);
4963 info->stats[STAT_AGILITY] += (lvl > 38 ? 1 : (lvl > 8 && (lvl % 2) ? 1 : 0));
4964 info->stats[STAT_INTELLECT] += (lvl > 22 ? 2 : (lvl > 1 ? 1 : 0));
4965 info->stats[STAT_SPIRIT] += (lvl > 3 ? 1 : 0);
4966 break;
4967 case CLASS_SHAMAN:
4968 info->stats[STAT_STRENGTH] += (lvl > 34 ? 1 : (lvl > 6 && (lvl % 2) ? 1 : 0));
4969 info->stats[STAT_STAMINA] += (lvl > 4 ? 1 : 0);
4970 info->stats[STAT_AGILITY] += (lvl > 7 && !(lvl % 2) ? 1 : 0);
4971 info->stats[STAT_INTELLECT] += (lvl > 5 ? 1 : 0);
4972 info->stats[STAT_SPIRIT] += (lvl > 4 ? 1 : 0);
4973 break;
4974 case CLASS_MAGE:
4975 info->stats[STAT_STRENGTH] += (lvl > 9 && !(lvl % 2) ? 1 : 0);
4976 info->stats[STAT_STAMINA] += (lvl > 5 ? 1 : 0);
4977 info->stats[STAT_AGILITY] += (lvl > 9 && !(lvl % 2) ? 1 : 0);
4978 info->stats[STAT_INTELLECT] += (lvl > 24 ? 2 : (lvl > 1 ? 1 : 0));
4979 info->stats[STAT_SPIRIT] += (lvl > 33 ? 2 : (lvl > 2 ? 1 : 0));
4980 break;
4981 case CLASS_WARLOCK:
4982 info->stats[STAT_STRENGTH] += (lvl > 9 && !(lvl % 2) ? 1 : 0);
4983 info->stats[STAT_STAMINA] += (lvl > 38 ? 2 : (lvl > 3 ? 1 : 0));
4984 info->stats[STAT_AGILITY] += (lvl > 9 && !(lvl % 2) ? 1 : 0);
4985 info->stats[STAT_INTELLECT] += (lvl > 33 ? 2 : (lvl > 2 ? 1 : 0));
4986 info->stats[STAT_SPIRIT] += (lvl > 38 ? 2 : (lvl > 3 ? 1 : 0));
4987 break;
4988 case CLASS_DRUID:
4989 info->stats[STAT_STRENGTH] += (lvl > 38 ? 2 : (lvl > 6 && (lvl % 2) ? 1 : 0));
4990 info->stats[STAT_STAMINA] += (lvl > 32 ? 2 : (lvl > 4 ? 1 : 0));
4991 info->stats[STAT_AGILITY] += (lvl > 38 ? 2 : (lvl > 8 && (lvl % 2) ? 1 : 0));
4992 info->stats[STAT_INTELLECT] += (lvl > 38 ? 3 : (lvl > 4 ? 1 : 0));
4993 info->stats[STAT_SPIRIT] += (lvl > 38 ? 3 : (lvl > 5 ? 1 : 0));
4994 }
4995 }
4996}
@ CLASS_HUNTER
Definition SharedDefines.h:128
@ CLASS_DRUID
Definition SharedDefines.h:136
@ CLASS_SHAMAN
Definition SharedDefines.h:132
@ CLASS_PRIEST
Definition SharedDefines.h:130
@ CLASS_WARRIOR
Definition SharedDefines.h:126
@ CLASS_WARLOCK
Definition SharedDefines.h:134
@ CLASS_MAGE
Definition SharedDefines.h:133
@ CLASS_PALADIN
Definition SharedDefines.h:127
@ CLASS_ROGUE
Definition SharedDefines.h:129
@ STAT_SPIRIT
Definition SharedDefines.h:250
@ STAT_INTELLECT
Definition SharedDefines.h:249
@ STAT_AGILITY
Definition SharedDefines.h:247
@ STAT_STRENGTH
Definition SharedDefines.h:246
@ STAT_STAMINA
Definition SharedDefines.h:248
@ CONFIG_MAX_PLAYER_LEVEL
Definition WorldConfig.h:193
#define sWorld
Definition World.h:316

References _playerInfo, CLASS_DRUID, CLASS_HUNTER, CLASS_MAGE, CLASS_PALADIN, CLASS_PRIEST, CLASS_ROGUE, CLASS_SHAMAN, CLASS_WARLOCK, CLASS_WARRIOR, CONFIG_MAX_PLAYER_LEVEL, STAT_AGILITY, STAT_INTELLECT, STAT_SPIRIT, STAT_STAMINA, STAT_STRENGTH, PlayerLevelInfo::stats, and sWorld.

Referenced by GetPlayerLevelInfo().

◆ ChangeFishingBaseSkillLevel()

void ObjectMgr::ChangeFishingBaseSkillLevel ( uint32  entry,
int32  skill 
)
9446{
9447 AreaTableEntry const* fArea = sAreaTableStore.LookupEntry(entry);
9448 if (!fArea)
9449 {
9450 LOG_ERROR("sql.sql", "AreaId {} defined in `skill_fishing_base_level` does not exist", entry);
9451 return;
9452 }
9453
9454 _fishingBaseForAreaStore[entry] = skill;
9455
9456 LOG_INFO("server.loading", ">> Fishing base skill level of area {} changed to {}", entry, skill);
9457 LOG_INFO("server.loading", " ");
9458}
DBCStorage< AreaTableEntry > sAreaTableStore(AreaTableEntryfmt)
#define LOG_INFO(filterType__,...)
Definition Log.h:166
FishingBaseSkillContainer _fishingBaseForAreaStore
Definition ObjectMgr.h:1625
Definition DBCStructure.h:519

References _fishingBaseForAreaStore, LOG_ERROR, LOG_INFO, and sAreaTableStore.

◆ CheckCreatureMovement()

void ObjectMgr::CheckCreatureMovement ( char const *  table,
uint64  id,
CreatureMovementData creatureMovement 
)
1235{
1236 if (creatureMovement.Ground >= CreatureGroundMovementType::Max)
1237 {
1238 LOG_ERROR("sql.sql", "`{}`.`Ground` wrong value ({}) for Id {}, setting to Run.", table, uint32(creatureMovement.Ground), id);
1239 creatureMovement.Ground = CreatureGroundMovementType::Run;
1240 }
1241
1242 if (creatureMovement.Flight >= CreatureFlightMovementType::Max)
1243 {
1244 LOG_ERROR("sql.sql", "`{}`.`Flight` wrong value ({}) for Id {}, setting to None.", table, uint32(creatureMovement.Flight), id);
1245 creatureMovement.Flight = CreatureFlightMovementType::None;
1246 }
1247
1248 if (creatureMovement.Chase >= CreatureChaseMovementType::Max)
1249 {
1250 LOG_ERROR("sql.sql", "`{}`.`Chase` wrong value ({}) for Id {}, setting to Run.", table, uint32(creatureMovement.Chase), id);
1251 creatureMovement.Chase = CreatureChaseMovementType::Run;
1252 }
1253
1254 if (creatureMovement.Random >= CreatureRandomMovementType::Max)
1255 {
1256 LOG_ERROR("sql.sql", "`{}`.`Random` wrong value ({}) for Id {}, setting to Walk.", table, uint32(creatureMovement.Random), id);
1257 creatureMovement.Random = CreatureRandomMovementType::Walk;
1258 }
1259}
CreatureRandomMovementType Random
Definition CreatureData.h:128
CreatureFlightMovementType Flight
Definition CreatureData.h:124
CreatureChaseMovementType Chase
Definition CreatureData.h:127
CreatureGroundMovementType Ground
Definition CreatureData.h:123

References CreatureMovementData::Chase, CreatureMovementData::Flight, CreatureMovementData::Ground, LOG_ERROR, Max, None, CreatureMovementData::Random, Run, and Walk.

Referenced by CheckCreatureTemplate(), and LoadCreatureMovementOverrides().

◆ CheckCreatureTemplate()

void ObjectMgr::CheckCreatureTemplate ( CreatureTemplate const *  cInfo)
964{
965 if (!cInfo)
966 return;
967
968 bool ok = true; // bool to allow continue outside this loop
969 for (uint32 diff = 0; diff < MAX_DIFFICULTY - 1 && ok; ++diff)
970 {
971 if (!cInfo->DifficultyEntry[diff])
972 continue;
973 ok = false; // will be set to true at the end of this loop again
974
975 CreatureTemplate const* difficultyInfo = GetCreatureTemplate(cInfo->DifficultyEntry[diff]);
976 if (!difficultyInfo)
977 {
978 LOG_ERROR("sql.sql", "Creature (Entry: {}) has `difficulty_entry_{}`={} but creature entry {} does not exist.",
979 cInfo->Entry, diff + 1, cInfo->DifficultyEntry[diff], cInfo->DifficultyEntry[diff]);
980 continue;
981 }
982
983 bool ok2 = true;
984 for (uint32 diff2 = 0; diff2 < MAX_DIFFICULTY - 1 && ok2; ++diff2)
985 {
986 ok2 = false;
987 if (_difficultyEntries[diff2].find(cInfo->Entry) != _difficultyEntries[diff2].end())
988 {
989 LOG_ERROR("sql.sql", "Creature (Entry: {}) is listed as `difficulty_entry_{}` of another creature, but itself lists {} in `difficulty_entry_{}`.",
990 cInfo->Entry, diff2 + 1, cInfo->DifficultyEntry[diff], diff + 1);
991 continue;
992 }
993
994 if (_difficultyEntries[diff2].find(cInfo->DifficultyEntry[diff]) != _difficultyEntries[diff2].end())
995 {
996 LOG_ERROR("sql.sql", "Creature (Entry: {}) already listed as `difficulty_entry_{}` for another entry.", cInfo->DifficultyEntry[diff], diff2 + 1);
997 continue;
998 }
999
1000 if (_hasDifficultyEntries[diff2].find(cInfo->DifficultyEntry[diff]) != _hasDifficultyEntries[diff2].end())
1001 {
1002 LOG_ERROR("sql.sql", "Creature (Entry: {}) has `difficulty_entry_{}`={} but creature entry {} has itself a value in `difficulty_entry_{}`.",
1003 cInfo->Entry, diff + 1, cInfo->DifficultyEntry[diff], cInfo->DifficultyEntry[diff], diff2 + 1);
1004 continue;
1005 }
1006 ok2 = true;
1007 }
1008 if (!ok2)
1009 continue;
1010
1011 if (cInfo->expansion > difficultyInfo->expansion)
1012 {
1013 LOG_ERROR("sql.sql", "Creature (Entry: {}, expansion {}) has different `expansion` in difficulty {} mode (Entry: {}, expansion {}).",
1014 cInfo->Entry, cInfo->expansion, diff + 1, cInfo->DifficultyEntry[diff], difficultyInfo->expansion);
1015 }
1016
1017 if (cInfo->faction != difficultyInfo->faction)
1018 {
1019 LOG_ERROR("sql.sql", "Creature (Entry: {}, faction {}) has different `faction` in difficulty {} mode (Entry: {}, faction {}).",
1020 cInfo->Entry, cInfo->faction, diff + 1, cInfo->DifficultyEntry[diff], difficultyInfo->faction);
1021 }
1022
1023 if (cInfo->unit_class != difficultyInfo->unit_class)
1024 {
1025 LOG_ERROR("sql.sql", "Creature (Entry: {}, class {}) has different `unit_class` in difficulty {} mode (Entry: {}, class {}).",
1026 cInfo->Entry, cInfo->unit_class, diff + 1, cInfo->DifficultyEntry[diff], difficultyInfo->unit_class);
1027 continue;
1028 }
1029
1030 if (cInfo->npcflag != difficultyInfo->npcflag)
1031 {
1032 LOG_ERROR("sql.sql", "Creature (Entry: {}) has different `npcflag` in difficulty {} mode (Entry: {}).", cInfo->Entry, diff + 1, cInfo->DifficultyEntry[diff]);
1033 continue;
1034 }
1035
1036 if (cInfo->family != difficultyInfo->family)
1037 {
1038 LOG_ERROR("sql.sql", "Creature (Entry: {}, family {}) has different `family` in difficulty {} mode (Entry: {}, family {}).",
1039 cInfo->Entry, cInfo->family, diff + 1, cInfo->DifficultyEntry[diff], difficultyInfo->family);
1040 }
1041
1042 if (cInfo->type != difficultyInfo->type)
1043 {
1044 LOG_ERROR("sql.sql", "Creature (Entry: {}, type {}) has different `type` in difficulty {} mode (Entry: {}, type {}).",
1045 cInfo->Entry, cInfo->type, diff + 1, cInfo->DifficultyEntry[diff], difficultyInfo->type);
1046 }
1047
1048 if (!cInfo->VehicleId && difficultyInfo->VehicleId)
1049 {
1050 LOG_ERROR("sql.sql", "Creature (Entry: {}, VehicleId {}) has different `VehicleId` in difficulty {} mode (Entry: {}, VehicleId {}).",
1051 cInfo->Entry, cInfo->VehicleId, diff + 1, cInfo->DifficultyEntry[diff], difficultyInfo->VehicleId);
1052 }
1053
1054 // Xinef: check dmg school
1055 if (cInfo->dmgschool != difficultyInfo->dmgschool)
1056 {
1057 LOG_ERROR("sql.sql", "Creature (Entry: {}) has different `dmgschool` in difficulty {} mode (Entry: {})", cInfo->Entry, diff + 1, cInfo->DifficultyEntry[diff]);
1058 }
1059
1060 if (!difficultyInfo->AIName.empty())
1061 {
1062 LOG_ERROR("sql.sql", "Creature (Entry: {}) lists difficulty {} mode entry {} with `AIName` filled in. `AIName` of difficulty 0 mode creature is always used instead.",
1063 cInfo->Entry, diff + 1, cInfo->DifficultyEntry[diff]);
1064 continue;
1065 }
1066
1067 if (difficultyInfo->ScriptID)
1068 {
1069 LOG_ERROR("sql.sql", "Creature (Entry: {}) lists difficulty {} mode entry {} with `ScriptName` filled in. `ScriptName` of difficulty 0 mode creature is always used instead.",
1070 cInfo->Entry, diff + 1, cInfo->DifficultyEntry[diff]);
1071 continue;
1072 }
1073
1074 _hasDifficultyEntries[diff].insert(cInfo->Entry);
1075 _difficultyEntries[diff].insert(cInfo->DifficultyEntry[diff]);
1076 ok = true;
1077 }
1078
1079 if (!cInfo->AIName.empty() && !sCreatureAIRegistry->HasItem(cInfo->AIName))
1080 {
1081 LOG_ERROR("sql.sql", "Creature (Entry: {}) has non-registered `AIName` '{}' set, removing", cInfo->Entry, cInfo->AIName);
1082 const_cast<CreatureTemplate*>(cInfo)->AIName.clear();
1083 }
1084
1085 FactionTemplateEntry const* factionTemplate = sFactionTemplateStore.LookupEntry(cInfo->faction);
1086 if (!factionTemplate)
1087 LOG_ERROR("sql.sql", "Creature (Entry: {}) has non-existing faction template ({}).", cInfo->Entry, cInfo->faction);
1088
1089 for (int k = 0; k < MAX_KILL_CREDIT; ++k)
1090 {
1091 if (cInfo->KillCredit[k])
1092 {
1093 if (!GetCreatureTemplate(cInfo->KillCredit[k]))
1094 {
1095 LOG_ERROR("sql.sql", "Creature (Entry: {}) lists non-existing creature entry {} in `KillCredit{}`.", cInfo->Entry, cInfo->KillCredit[k], k + 1);
1096 const_cast<CreatureTemplate*>(cInfo)->KillCredit[k] = 0;
1097 }
1098 }
1099 }
1100
1101 if (!cInfo->Models.size())
1102 LOG_ERROR("sql.sql", "Creature (Entry: {}) does not have any existing display id in creature_template_model.", cInfo->Entry);
1103 else
1104 {
1105 float const totalProbability = std::accumulate(cInfo->Models.begin(), cInfo->Models.end(), 0.0f, [](float sum, CreatureModel const& model) { return sum + model.Probability; });
1106
1107 if (totalProbability <= 0.0f)
1108 { // There are many cases in official data of all models having a probability of 0. Believe to be treated equivalent to equal chance ONLY if all are zeroed
1109 if (totalProbability == 0.0f)
1110 LOG_DEBUG("sql.sql", "Creature (Entry: {}) has zero total chance for all models in creature_template_model. Setting all to 1.0.", cInfo->Entry);
1111 else // Custom, likely bad data
1112 LOG_ERROR("sql.sql", "Creature (Entry: {}) has less than zero total chance for all models in creature_template_model. Setting all to 1.0.", cInfo->Entry);
1113
1114 auto& models = const_cast<CreatureTemplate*>(cInfo)->Models;
1115 for (auto& model : models)
1116 model.Probability = 1.0f;
1117 }
1118 }
1119
1120 if (!cInfo->unit_class || ((1 << (cInfo->unit_class - 1)) & CLASSMASK_ALL_CREATURES) == 0)
1121 {
1122 LOG_ERROR("sql.sql", "Creature (Entry: {}) has invalid unit_class ({}) in creature_template. Set to 1 (CLASS_WARRIOR).", cInfo->Entry, cInfo->unit_class);
1123 const_cast<CreatureTemplate*>(cInfo)->unit_class = CLASS_WARRIOR;
1124 }
1125
1126 if (cInfo->dmgschool >= MAX_SPELL_SCHOOL)
1127 {
1128 LOG_ERROR("sql.sql", "Creature (Entry: {}) has invalid spell school value ({}) in `dmgschool`.", cInfo->Entry, cInfo->dmgschool);
1129 const_cast<CreatureTemplate*>(cInfo)->dmgschool = SPELL_SCHOOL_NORMAL;
1130 }
1131
1132 if (cInfo->BaseAttackTime == 0)
1133 const_cast<CreatureTemplate*>(cInfo)->BaseAttackTime = BASE_ATTACK_TIME;
1134
1135 if (cInfo->RangeAttackTime == 0)
1136 const_cast<CreatureTemplate*>(cInfo)->RangeAttackTime = BASE_ATTACK_TIME;
1137
1138 if (cInfo->speed_walk == 0.0f)
1139 {
1140 LOG_ERROR("sql.sql", "Creature (Entry: {}) has wrong value ({}) in speed_walk, set to 1.", cInfo->Entry, cInfo->speed_walk);
1141 const_cast<CreatureTemplate*>(cInfo)->speed_walk = 1.0f;
1142 }
1143
1144 if (cInfo->speed_run == 0.0f)
1145 {
1146 LOG_ERROR("sql.sql", "Creature (Entry: {}) has wrong value ({}) in speed_run, set to 1.14286.", cInfo->Entry, cInfo->speed_run);
1147 const_cast<CreatureTemplate*>(cInfo)->speed_run = 1.14286f;
1148 }
1149
1150 if (cInfo->type && !sCreatureTypeStore.LookupEntry(cInfo->type))
1151 {
1152 LOG_ERROR("sql.sql", "Creature (Entry: {}) has invalid creature type ({}) in `type`.", cInfo->Entry, cInfo->type);
1153 const_cast<CreatureTemplate*>(cInfo)->type = CREATURE_TYPE_HUMANOID;
1154 }
1155
1156 // Must exist in DBC or use hidden miscellaneous family
1157 if (cInfo->family && !sCreatureFamilyStore.LookupEntry(cInfo->family) && cInfo->family != CREATURE_FAMILY_NOT_SPECIFIED)
1158 {
1159 LOG_ERROR("sql.sql", "Creature (Entry: {}) has invalid creature family ({}) in `family`.", cInfo->Entry, cInfo->family);
1160 const_cast<CreatureTemplate*>(cInfo)->family = 0;
1161 }
1162
1163 CheckCreatureMovement("creature_template_movement", cInfo->Entry, const_cast<CreatureTemplate*>(cInfo)->Movement);
1164
1165 if (cInfo->HoverHeight < 0.0f)
1166 {
1167 LOG_ERROR("sql.sql", "Creature (Entry: {}) has wrong value ({}) in `HoverHeight`", cInfo->Entry, cInfo->HoverHeight);
1168 const_cast<CreatureTemplate*>(cInfo)->HoverHeight = 1.0f;
1169 }
1170
1171 if (cInfo->VehicleId)
1172 {
1173 VehicleEntry const* vehId = sVehicleStore.LookupEntry(cInfo->VehicleId);
1174 if (!vehId)
1175 {
1176 LOG_ERROR("sql.sql", "Creature (Entry: {}) has a non-existing VehicleId ({}). This *WILL* cause the client to freeze!", cInfo->Entry, cInfo->VehicleId);
1177 const_cast<CreatureTemplate*>(cInfo)->VehicleId = 0;
1178 }
1179 }
1180
1181 if (cInfo->PetSpellDataId)
1182 {
1183 CreatureSpellDataEntry const* spellDataId = sCreatureSpellDataStore.LookupEntry(cInfo->PetSpellDataId);
1184 if (!spellDataId)
1185 LOG_ERROR("sql.sql", "Creature (Entry: {}) has non-existing PetSpellDataId ({}).", cInfo->Entry, cInfo->PetSpellDataId);
1186 }
1187
1188 for (uint8 j = 0; j < MAX_CREATURE_SPELLS; ++j)
1189 {
1190 if (cInfo->spells[j] && !sSpellMgr->GetSpellInfo(cInfo->spells[j]))
1191 {
1192 LOG_ERROR("sql.sql", "Creature (Entry: {}) has non-existing Spell{} ({}), set to 0.", cInfo->Entry, j + 1, cInfo->spells[j]);
1193 const_cast<CreatureTemplate*>(cInfo)->spells[j] = 0;
1194 }
1195 }
1196
1197 if (cInfo->MovementType >= MAX_DB_MOTION_TYPE)
1198 {
1199 LOG_ERROR("sql.sql", "Creature (Entry: {}) has wrong movement generator type ({}), ignored and set to IDLE.", cInfo->Entry, cInfo->MovementType);
1200 const_cast<CreatureTemplate*>(cInfo)->MovementType = IDLE_MOTION_TYPE;
1201 }
1202
1203 if (cInfo->expansion > (MAX_EXPANSIONS - 1))
1204 {
1205 LOG_ERROR("sql.sql", "Table `creature_template` lists creature (Entry: {}) with expansion {}. Ignored and set to 0.", cInfo->Entry, cInfo->expansion);
1206 const_cast<CreatureTemplate*>(cInfo)->expansion = 0;
1207 }
1208
1209 if (uint32 badFlags = (cInfo->flags_extra & ~CREATURE_FLAG_EXTRA_DB_ALLOWED))
1210 {
1211 LOG_ERROR("sql.sql", "Table `creature_template` lists creature (Entry: {}) with disallowed `flags_extra` {}, removing incorrect flag.", cInfo->Entry, badFlags);
1212 const_cast<CreatureTemplate*>(cInfo)->flags_extra &= CREATURE_FLAG_EXTRA_DB_ALLOWED;
1213 }
1214
1215 const_cast<CreatureTemplate*>(cInfo)->DamageModifier *= Creature::_GetDamageMod(cInfo->rank);
1216
1217 // Hack for modules
1218 for (auto& itr : _creatureCustomIDsStore)
1219 {
1220 if (cInfo->Entry == itr)
1221 return;
1222 }
1223
1224 if ((cInfo->GossipMenuId && !(cInfo->npcflag & UNIT_NPC_FLAG_GOSSIP)) && !(cInfo->flags_extra & CREATURE_FLAG_EXTRA_MODULE))
1225 {
1226 LOG_ERROR("sql.sql", "Creature (Entry: {}) has assigned gossip menu {}, but npcflag does not include UNIT_NPC_FLAG_GOSSIP (1).", cInfo->Entry, cInfo->GossipMenuId);
1227 }
1228 else if ((!cInfo->GossipMenuId && (cInfo->npcflag & UNIT_NPC_FLAG_GOSSIP)) && !(cInfo->flags_extra & CREATURE_FLAG_EXTRA_MODULE))
1229 {
1230 LOG_INFO("sql.sql", "Creature (Entry: {}) has npcflag UNIT_NPC_FLAG_GOSSIP (1), but gossip menu is unassigned.", cInfo->Entry);
1231 }
1232}
#define sCreatureAIRegistry
Definition CreatureAIFactory.h:48
@ CREATURE_FLAG_EXTRA_DB_ALLOWED
Definition CreatureData.h:80
@ CREATURE_FLAG_EXTRA_MODULE
Definition CreatureData.h:70
#define MAX_KILL_CREDIT
Definition CreatureData.h:31
#define MAX_DIFFICULTY
Definition DBCEnums.h:283
DBCStorage< VehicleEntry > sVehicleStore(VehicleEntryfmt)
DBCStorage< CreatureSpellDataEntry > sCreatureSpellDataStore(CreatureSpellDatafmt)
DBCStorage< CreatureFamilyEntry > sCreatureFamilyStore(CreatureFamilyfmt)
DBCStorage< FactionTemplateEntry > sFactionTemplateStore(FactionTemplateEntryfmt)
DBCStorage< CreatureTypeEntry > sCreatureTypeStore(CreatureTypefmt)
@ MAX_DB_MOTION_TYPE
Definition MotionMaster.h:42
@ IDLE_MOTION_TYPE
Definition MotionMaster.h:39
@ SPELL_SCHOOL_NORMAL
Definition SharedDefines.h:271
constexpr auto MAX_SPELL_SCHOOL
Definition SharedDefines.h:280
@ CREATURE_FAMILY_NOT_SPECIFIED
Definition SharedDefines.h:2655
@ CREATURE_TYPE_HUMANOID
Definition SharedDefines.h:2630
#define CLASSMASK_ALL_CREATURES
Definition SharedDefines.h:149
@ MAX_EXPANSIONS
Definition SharedDefines.h:56
#define sSpellMgr
Definition SpellMgr.h:836
@ UNIT_NPC_FLAG_GOSSIP
Definition UnitDefines.h:322
#define BASE_ATTACK_TIME
Definition Unit.h:41
static constexpr uint32 MAX_CREATURE_SPELLS
Definition Unit.h:45
Models
Definition boss_black_knight.cpp:79
spells
Definition boss_krystallus.cpp:26
static float _GetDamageMod(int32 Rank)
Definition Creature.cpp:1554
std::set< uint32 > _difficultyEntries[MAX_DIFFICULTY - 1]
Definition ObjectMgr.h:1684
CreatureCustomIDsContainer _creatureCustomIDsStore
Definition ObjectMgr.h:1642
std::set< uint32 > _hasDifficultyEntries[MAX_DIFFICULTY - 1]
Definition ObjectMgr.h:1685
void CheckCreatureMovement(char const *table, uint64 id, CreatureMovementData &creatureMovement)
Definition ObjectMgr.cpp:1234
Definition CreatureData.h:170
Definition DBCStructure.h:810
uint32 type
Definition CreatureData.h:218
uint32 ScriptID
Definition CreatureData.h:242
uint32 VehicleId
Definition CreatureData.h:226
CreatureMovementData Movement
Definition CreatureData.h:231
uint32 faction
Definition CreatureData.h:199
uint32 dmgschool
Definition CreatureData.h:207
uint32 expansion
Definition CreatureData.h:198
std::string AIName
Definition CreatureData.h:229
uint32 family
Definition CreatureData.h:217
Definition DBCStructure.h:939
Definition DBCStructure.h:2027

References _creatureCustomIDsStore, _difficultyEntries, Creature::_GetDamageMod(), _hasDifficultyEntries, CreatureTemplate::AIName, BASE_ATTACK_TIME, CreatureTemplate::BaseAttackTime, CheckCreatureMovement(), CLASS_WARRIOR, CLASSMASK_ALL_CREATURES, CREATURE_FAMILY_NOT_SPECIFIED, CREATURE_FLAG_EXTRA_DB_ALLOWED, CREATURE_FLAG_EXTRA_MODULE, CREATURE_TYPE_HUMANOID, CreatureTemplate::DifficultyEntry, CreatureTemplate::dmgschool, CreatureTemplate::Entry, CreatureTemplate::expansion, CreatureTemplate::faction, CreatureTemplate::family, CreatureTemplate::flags_extra, GetCreatureTemplate(), CreatureTemplate::GossipMenuId, CreatureTemplate::HoverHeight, IDLE_MOTION_TYPE, CreatureTemplate::KillCredit, LOG_DEBUG, LOG_ERROR, LOG_INFO, MAX_CREATURE_SPELLS, MAX_DB_MOTION_TYPE, MAX_DIFFICULTY, MAX_EXPANSIONS, MAX_KILL_CREDIT, MAX_SPELL_SCHOOL, CreatureTemplate::Models, CreatureTemplate::Movement, CreatureTemplate::MovementType, CreatureTemplate::npcflag, CreatureTemplate::PetSpellDataId, CreatureModel::Probability, CreatureTemplate::RangeAttackTime, CreatureTemplate::rank, sCreatureAIRegistry, sCreatureFamilyStore, sCreatureSpellDataStore, sCreatureTypeStore, CreatureTemplate::ScriptID, sFactionTemplateStore, CreatureTemplate::speed_run, CreatureTemplate::speed_walk, SPELL_SCHOOL_NORMAL, CreatureTemplate::spells, sSpellMgr, sVehicleStore, CreatureTemplate::type, CreatureTemplate::unit_class, UNIT_NPC_FLAG_GOSSIP, and CreatureTemplate::VehicleId.

Referenced by LoadCreatureTemplates().

◆ CheckDeclinedNames()

bool ObjectMgr::CheckDeclinedNames ( std::wstring  w_ownname,
DeclinedName const &  names 
)
static
9461{
9462 // get main part of the name
9463 std::wstring mainpart = GetMainPartOfName(w_ownname, 0);
9464 // prepare flags
9465 bool x = true;
9466 bool y = true;
9467
9468 // check declined names
9469 for (uint8 i = 0; i < MAX_DECLINED_NAME_CASES; ++i)
9470 {
9471 std::wstring wname;
9472 if (!Utf8toWStr(names.name[i], wname))
9473 return false;
9474
9475 if (mainpart != GetMainPartOfName(wname, i + 1))
9476 x = false;
9477
9478 if (w_ownname != wname)
9479 y = false;
9480 }
9481 return (x || y);
9482}
#define MAX_DECLINED_NAME_CASES
Definition Unit.h:546
std::wstring GetMainPartOfName(std::wstring const &wname, uint32_t declension)
Definition Util.cpp:386

References GetMainPartOfName(), MAX_DECLINED_NAME_CASES, DeclinedName::name, and Utf8toWStr().

Referenced by WorldSession::HandlePetRename(), and WorldSession::HandleSetPlayerDeclinedNames().

◆ CheckPetName()

PetNameInvalidReason ObjectMgr::CheckPetName ( std::string_view  name)
static
9166{
9167 std::wstring wname;
9168 if (!Utf8toWStr(name, wname))
9169 return PET_NAME_INVALID;
9170
9171 if (wname.size() > MAX_PET_NAME)
9172 return PET_NAME_TOO_LONG;
9173
9174 uint32 minName = sWorld->getIntConfig(CONFIG_MIN_PET_NAME);
9175 if (wname.size() < minName)
9176 return PET_NAME_TOO_SHORT;
9177
9178 uint32 strictMask = sWorld->getIntConfig(CONFIG_STRICT_PET_NAMES);
9179 if (!isValidString(wname, strictMask, false))
9181
9182 // Check Reserved Name
9183 if (sObjectMgr->IsReservedName(name))
9184 return PET_NAME_RESERVED;
9185
9186 // Check Profanity Name
9187 if (sObjectMgr->IsProfanityName(name))
9188 return PET_NAME_PROFANE;
9189
9190 return PET_NAME_SUCCESS;
9191}
bool isValidString(std::wstring wstr, uint32 strictMask, bool numericOrSpace, bool create=false)
Definition ObjectMgr.cpp:9050
#define sObjectMgr
Definition ObjectMgr.h:1712
#define MAX_PET_NAME
Definition ObjectMgr.h:686
@ PET_NAME_INVALID
Definition SharedDefines.h:3918
@ PET_NAME_RESERVED
Definition SharedDefines.h:3924
@ PET_NAME_SUCCESS
Definition SharedDefines.h:3916
@ PET_NAME_MIXED_LANGUAGES
Definition SharedDefines.h:3922
@ PET_NAME_TOO_SHORT
Definition SharedDefines.h:3920
@ PET_NAME_TOO_LONG
Definition SharedDefines.h:3921
@ PET_NAME_PROFANE
Definition SharedDefines.h:3923
@ CONFIG_STRICT_PET_NAMES
Definition WorldConfig.h:180
@ CONFIG_MIN_PET_NAME
Definition WorldConfig.h:183

References CONFIG_MIN_PET_NAME, CONFIG_STRICT_PET_NAMES, isValidString(), MAX_PET_NAME, PET_NAME_INVALID, PET_NAME_MIXED_LANGUAGES, PET_NAME_PROFANE, PET_NAME_RESERVED, PET_NAME_SUCCESS, PET_NAME_TOO_LONG, PET_NAME_TOO_SHORT, sObjectMgr, sWorld, and Utf8toWStr().

Referenced by WorldSession::HandlePetRename().

◆ CheckPlayerName()

uint8 ObjectMgr::CheckPlayerName ( std::string_view  name,
bool  create = false 
)
static
9087{
9088 std::wstring wname;
9089
9090 // Check for invalid characters
9091 if (!Utf8toWStr(name, wname))
9093
9094 // Check for too long name
9095 if (wname.size() > MAX_PLAYER_NAME)
9096 return CHAR_NAME_TOO_LONG;
9097
9098 // Check for too short name
9099 uint32 minName = sWorld->getIntConfig(CONFIG_MIN_PLAYER_NAME);
9100 if (wname.size() < minName)
9101 return CHAR_NAME_TOO_SHORT;
9102
9103 // Check for mixed languages
9104 uint32 strictMask = sWorld->getIntConfig(CONFIG_STRICT_PLAYER_NAMES);
9105 if (!isValidString(wname, strictMask, false, create))
9107
9108 // Check for three consecutive letters
9109 wstrToLower(wname);
9110 for (std::size_t i = 2; i < wname.size(); ++i)
9111 if (wname[i] == wname[i - 1] && wname[i] == wname[i - 2])
9113
9114 // Check Reserved Name
9115 if (sObjectMgr->IsReservedName(name))
9116 return CHAR_NAME_RESERVED;
9117
9118 // Check Profanity Name
9119 if (sObjectMgr->IsProfanityName(name))
9120 return CHAR_NAME_PROFANE;
9121
9122 return CHAR_NAME_SUCCESS;
9123}
#define MAX_PLAYER_NAME
Definition ObjectMgr.h:684
@ CHAR_NAME_TOO_SHORT
Definition SharedDefines.h:3673
@ CHAR_NAME_THREE_CONSECUTIVE
Definition SharedDefines.h:3681
@ CHAR_NAME_INVALID_CHARACTER
Definition SharedDefines.h:3675
@ CHAR_NAME_TOO_LONG
Definition SharedDefines.h:3674
@ CHAR_NAME_RESERVED
Definition SharedDefines.h:3678
@ CHAR_NAME_MIXED_LANGUAGES
Definition SharedDefines.h:3676
@ CHAR_NAME_PROFANE
Definition SharedDefines.h:3677
@ CHAR_NAME_SUCCESS
Definition SharedDefines.h:3670
@ CONFIG_STRICT_PLAYER_NAMES
Definition WorldConfig.h:177
@ CONFIG_MIN_PLAYER_NAME
Definition WorldConfig.h:181

References CHAR_NAME_INVALID_CHARACTER, CHAR_NAME_MIXED_LANGUAGES, CHAR_NAME_PROFANE, CHAR_NAME_RESERVED, CHAR_NAME_SUCCESS, CHAR_NAME_THREE_CONSECUTIVE, CHAR_NAME_TOO_LONG, CHAR_NAME_TOO_SHORT, CONFIG_MIN_PLAYER_NAME, CONFIG_STRICT_PLAYER_NAMES, isValidString(), MAX_PLAYER_NAME, sObjectMgr, sWorld, Utf8toWStr(), and wstrToLower().

Referenced by character_commandscript::HandleCharacterRenameCommand(), WorldSession::HandleCharCreateOpcode(), WorldSession::HandleCharCustomizeCallback(), WorldSession::HandleCharFactionOrRaceChangeCallback(), WorldSession::HandleCharRenameOpcode(), PlayerDumpReader::LoadDump(), Player::LoadFromDB(), and character_commandscript::ValidatePDumpTarget().

◆ ChooseCreatureFlags()

void ObjectMgr::ChooseCreatureFlags ( CreatureTemplate const *  cinfo,
uint32 npcflag,
uint32 unit_flags,
uint32 dynamicflags,
CreatureData const *  data = nullptr 
)
static
1659{
1660 npcflag = cinfo->npcflag;
1661 unit_flags = cinfo->unit_flags;
1662 dynamicflags = cinfo->dynamicflags;
1663
1664 if (data)
1665 {
1666 if (data->npcflag)
1667 npcflag = data->npcflag;
1668
1669 if (data->unit_flags)
1670 unit_flags = data->unit_flags;
1671
1672 if (data->dynamicflags)
1673 dynamicflags = data->dynamicflags;
1674 }
1675}

References CreatureTemplate::dynamicflags, CreatureData::dynamicflags, CreatureTemplate::npcflag, CreatureData::npcflag, CreatureTemplate::unit_flags, and CreatureData::unit_flags.

Referenced by Creature::UpdateEntry().

◆ ChooseDisplayId()

CreatureModel const * ObjectMgr::ChooseDisplayId ( CreatureTemplate const *  cinfo,
CreatureData const *  data = nullptr 
)
static
1644{
1645 // Load creature model (display id)
1646 if (data && data->displayid)
1647 if (CreatureModel const* model = cinfo->GetModelWithDisplayId(data->displayid))
1648 return model;
1649
1650 if (!cinfo->HasFlagsExtra(CREATURE_FLAG_EXTRA_TRIGGER))
1651 if (CreatureModel const* model = cinfo->GetRandomValidModel())
1652 return model;
1653
1654 // Triggers by default receive the invisible model
1655 return cinfo->GetFirstInvisibleModel();
1656}
@ CREATURE_FLAG_EXTRA_TRIGGER
Definition CreatureData.h:53

References CREATURE_FLAG_EXTRA_TRIGGER, CreatureData::displayid, CreatureTemplate::GetFirstInvisibleModel(), CreatureTemplate::GetModelWithDisplayId(), CreatureTemplate::GetRandomValidModel(), and CreatureTemplate::HasFlagsExtra().

Referenced by npc_shattrath_daily_quest::DoAction(), Creature::GetNativeObjectScale(), AuraEffect::HandleAuraDummy(), AuraEffect::HandleAuraMounted(), AuraEffect::HandleAuraTransform(), Creature::InitEntry(), and SmartScript::ProcessAction().

◆ DeleteCreatureData()

void ObjectMgr::DeleteCreatureData ( ObjectGuid::LowType  spawnId)
8674{
8675 // remove mapid*cellid -> guid_set map
8676 CreatureData const* data = GetCreatureData(guid);
8677 if (data)
8678 RemoveCreatureFromGrid(guid, data);
8679
8680 _creatureDataStore.erase(guid);
8681}
CreatureDataContainer _creatureDataStore
Definition ObjectMgr.h:1640
void RemoveCreatureFromGrid(ObjectGuid::LowType guid, CreatureData const *data)
Definition ObjectMgr.cpp:2724
CreatureData const * GetCreatureData(ObjectGuid::LowType spawnId) const
Definition ObjectMgr.h:1232

References _creatureDataStore, GetCreatureData(), and RemoveCreatureFromGrid().

◆ DeleteGameTele()

bool ObjectMgr::DeleteGameTele ( std::string_view  name)
9660{
9661 // explicit name case
9662 std::wstring wname;
9663 if (!Utf8toWStr(name, wname))
9664 return false;
9665
9666 // converting string that we try to find to lower case
9667 wstrToLower(wname);
9668
9669 for (GameTeleContainer::iterator itr = _gameTeleStore.begin(); itr != _gameTeleStore.end(); ++itr)
9670 {
9671 if (itr->second.wnameLow == wname)
9672 {
9674
9675 stmt->SetData(0, itr->second.name);
9676
9677 WorldDatabase.Execute(stmt);
9678
9679 _gameTeleStore.erase(itr);
9680 return true;
9681 }
9682 }
9683
9684 return false;
9685}
@ WORLD_DEL_GAME_TELE
Definition WorldDatabase.h:42

References _gameTeleStore, PreparedStatementBase::SetData(), Utf8toWStr(), WORLD_DEL_GAME_TELE, WorldDatabase, and wstrToLower().

◆ DeleteGOData()

void ObjectMgr::DeleteGOData ( ObjectGuid::LowType  guid)
8684{
8685 // remove mapid*cellid -> guid_set map
8686 GameObjectData const* data = GetGameObjectData(guid);
8687 if (data)
8688 RemoveGameobjectFromGrid(guid, data);
8689
8690 _gameObjectDataStore.erase(guid);
8691}
GameObjectData const * GetGameObjectData(ObjectGuid::LowType spawnId) const
Definition ObjectMgr.h:1267
GameObjectDataContainer _gameObjectDataStore
Definition ObjectMgr.h:1654
void RemoveGameobjectFromGrid(ObjectGuid::LowType guid, GameObjectData const *data)
Definition ObjectMgr.cpp:3168

References _gameObjectDataStore, GetGameObjectData(), and RemoveGameobjectFromGrid().

◆ GenerateAuctionID()

uint32 ObjectMgr::GenerateAuctionID ( )
7666{
7667 if (_auctionId >= 0xFFFFFFFE)
7668 {
7669 LOG_ERROR("server.worldserver", "Auctions ids overflow!! Can't continue, shutting down server. ");
7671 }
7672 return _auctionId++;
7673}
static void StopNow(uint8 exitcode)
Definition World.h:188
@ ERROR_EXIT_CODE
Definition World.h:54

References _auctionId, ERROR_EXIT_CODE, LOG_ERROR, and World::StopNow().

◆ GenerateCreatureSpawnId()

uint32 ObjectMgr::GenerateCreatureSpawnId ( )
7697{
7698 if (_creatureSpawnId >= uint32(0xFFFFFF))
7699 {
7700 LOG_ERROR("server.worldserver", "Creature spawn id overflow!! Can't continue, shutting down server. Search on forum for TCE00007 for more info.");
7702 }
7703 return _creatureSpawnId++;
7704}

References _creatureSpawnId, ERROR_EXIT_CODE, LOG_ERROR, and World::StopNow().

Referenced by AddCreData().

◆ GenerateEquipmentSetGuid()

uint64 ObjectMgr::GenerateEquipmentSetGuid ( )
7676{
7677 if (_equipmentSetGuid >= uint64(0xFFFFFFFFFFFFFFFELL))
7678 {
7679 LOG_ERROR("server.worldserver", "EquipmentSet guid overflow!! Can't continue, shutting down server. ");
7681 }
7682 return _equipmentSetGuid++;
7683}
std::uint64_t uint64
Definition Define.h:106

References _equipmentSetGuid, ERROR_EXIT_CODE, LOG_ERROR, and World::StopNow().

◆ GenerateGameObjectSpawnId()

uint32 ObjectMgr::GenerateGameObjectSpawnId ( )
7707{
7708 if (_gameObjectSpawnId >= uint32(0xFFFFFF))
7709 {
7710 LOG_ERROR("server.worldserver", "GameObject spawn id overflow!! Can't continue, shutting down server. Search on forum for TCE00007 for more info. ");
7712 }
7713 return _gameObjectSpawnId++;
7714}

References _gameObjectSpawnId, ERROR_EXIT_CODE, LOG_ERROR, and World::StopNow().

Referenced by AddGOData().

◆ GenerateMailID()

uint32 ObjectMgr::GenerateMailID ( )
7686{
7687 if (_mailId >= 0xFFFFFFFE)
7688 {
7689 LOG_ERROR("server.worldserver", "Mail ids overflow!! Can't continue, shutting down server. ");
7691 }
7692 std::lock_guard<std::mutex> guard(_mailIdMutex);
7693 return _mailId++;
7694}
std::mutex _mailIdMutex
Definition ObjectMgr.h:1520

References _mailId, _mailIdMutex, ERROR_EXIT_CODE, LOG_ERROR, and World::StopNow().

◆ GeneratePetName()

std::string ObjectMgr::GeneratePetName ( uint32  entry)
8173{
8174 std::vector<std::string>& list0 = _petHalfName0[entry];
8175 std::vector<std::string>& list1 = _petHalfName1[entry];
8176
8177 if (list0.empty() || list1.empty())
8178 {
8179 CreatureTemplate const* cinfo = GetCreatureTemplate(entry);
8180 char const* petname = GetPetName(cinfo->family, sWorld->GetDefaultDbcLocale());
8181 if (!petname)
8182 return cinfo->Name;
8183
8184 return std::string(petname);
8185 }
8186
8187 return *(list0.begin() + urand(0, list0.size() - 1)) + *(list1.begin() + urand(0, list1.size() - 1));
8188}
char const * GetPetName(uint32 petfamily, uint32 dbclang)
Definition DBCStores.cpp:665
HalfNameContainer _petHalfName1
Definition ObjectMgr.h:1629
HalfNameContainer _petHalfName0
Definition ObjectMgr.h:1628
std::string Name
Definition CreatureData.h:192

References _petHalfName0, _petHalfName1, CreatureTemplate::family, GetCreatureTemplate(), GetPetName(), CreatureTemplate::Name, sWorld, and urand().

Referenced by GeneratePetNameLocale().

◆ GeneratePetNameLocale()

std::string ObjectMgr::GeneratePetNameLocale ( uint32  entry,
LocaleConstant  locale 
)
8160{
8161 std::vector<std::string>& list0 = _petHalfLocaleName0[std::make_pair(entry, locale)];
8162 std::vector<std::string>& list1 = _petHalfLocaleName1[std::make_pair(entry, locale)];
8163
8164 if (list0.empty() || list1.empty())
8165 {
8166 return GeneratePetName(entry);
8167 }
8168
8169 return *(list0.begin() + urand(0, list0.size() - 1)) + *(list1.begin() + urand(0, list1.size() - 1));
8170}
HalfNameContainerLocale _petHalfLocaleName0
Definition ObjectMgr.h:1631
HalfNameContainerLocale _petHalfLocaleName1
Definition ObjectMgr.h:1632
std::string GeneratePetName(uint32 entry)
Definition ObjectMgr.cpp:8172

References _petHalfLocaleName0, _petHalfLocaleName1, GeneratePetName(), and urand().

◆ GeneratePetNumber()

uint32 ObjectMgr::GeneratePetNumber ( )
8191{
8192 std::lock_guard<std::mutex> guard(_hiPetNumberMutex);
8193 return ++_hiPetNumber;
8194}
std::mutex _hiPetNumberMutex
Definition ObjectMgr.h:1522

References _hiPetNumber, and _hiPetNumberMutex.

◆ GetAccessRequirement()

DungeonProgressionRequirements const * ObjectMgr::GetAccessRequirement ( uint32  mapid,
Difficulty  difficulty 
) const
inline
882 {
883 DungeonProgressionRequirementsContainer::const_iterator itr = _accessRequirementStore.find(mapid);
884 if (itr != _accessRequirementStore.end())
885 {
886 std::unordered_map<uint8, DungeonProgressionRequirements*> difficultiesProgressionRequirements = itr->second;
887 auto difficultiesItr = difficultiesProgressionRequirements.find(difficulty);
888 if (difficultiesItr != difficultiesProgressionRequirements.end())
889 {
890 return difficultiesItr->second;
891 }
892 }
893 return nullptr;
894 }

References _accessRequirementStore.

◆ GetAcoreString() [1/2]

AcoreString const * ObjectMgr::GetAcoreString ( uint32  entry) const
inline
1379 {
1380 AcoreStringContainer::const_iterator itr = _acoreStringStore.find(entry);
1381 if (itr == _acoreStringStore.end())
1382 return nullptr;
1383
1384 return &itr->second;
1385 }
AcoreStringContainer _acoreStringStore
Definition ObjectMgr.h:1675

References _acoreStringStore.

Referenced by GetAcoreString(), and GetAcoreStringForDBCLocale().

◆ GetAcoreString() [2/2]

std::string ObjectMgr::GetAcoreString ( uint32  entry,
LocaleConstant  locale 
) const
9392{
9393 AcoreString const* as = GetAcoreString(entry);
9394 if (as && !as->Content.empty())
9395 {
9396 if (as->Content.size() > std::size_t(locale) && !as->Content[locale].empty())
9397 return as->Content[locale];
9398
9399 return as->Content[DEFAULT_LOCALE];
9400 }
9401
9402 std::string msg = Acore::StringFormat("No entry for acore_string ({}) in DB.", entry);
9403 LOG_ERROR("sql.sql", msg);
9404 return msg;
9405}
#define DEFAULT_LOCALE
Definition Common.h:131
AcoreString const * GetAcoreString(uint32 entry) const
Definition ObjectMgr.h:1378
std::string StringFormat(FormatString< Args... > fmt, Args &&... args)
Default AC string format function.
Definition StringFormat.h:44
Definition ObjectMgr.h:502
std::vector< std::string > Content
Definition ObjectMgr.h:503

References AcoreString::Content, DEFAULT_LOCALE, GetAcoreString(), LOG_ERROR, and Acore::StringFormat().

◆ GetAcoreStringForDBCLocale()

std::string ObjectMgr::GetAcoreStringForDBCLocale ( uint32  entry) const
inline
1387{ return GetAcoreString(entry, DBCLocaleIndex); }

References DBCLocaleIndex, and GetAcoreString().

◆ GetAllAreaTriggerScriptData()

AreaTriggerScriptContainer const & ObjectMgr::GetAllAreaTriggerScriptData ( ) const
inline
899{ return _areaTriggerScriptStore; }
AreaTriggerScriptContainer _areaTriggerScriptStore
Definition ObjectMgr.h:1553

References _areaTriggerScriptStore.

◆ GetAllCreatureData()

CreatureDataContainer const & ObjectMgr::GetAllCreatureData ( ) const
inline
1231{ return _creatureDataStore; }

References _creatureDataStore.

◆ GetAllGOData()

GameObjectDataContainer const & ObjectMgr::GetAllGOData ( ) const
inline
1266{ return _gameObjectDataStore; }

References _gameObjectDataStore.

◆ GetAreaTrigger()

AreaTrigger const * ObjectMgr::GetAreaTrigger ( uint32  trigger) const
inline
866 {
867 AreaTriggerContainer::const_iterator itr = _areaTriggerStore.find(trigger);
868 if (itr != _areaTriggerStore.end())
869 return &itr->second;
870 return nullptr;
871 }
AreaTriggerContainer _areaTriggerStore
Definition ObjectMgr.h:1551

References _areaTriggerStore.

Referenced by GetGoBackTrigger(), LoadAreaTriggerScripts(), LoadAreaTriggerTeleports(), LoadQuestAreaTriggers(), and LoadTavernAreaTriggers().

◆ GetAreaTriggerScriptId()

uint32 ObjectMgr::GetAreaTriggerScriptId ( uint32  trigger_id)
9485{
9486 AreaTriggerScriptContainer::const_iterator i = _areaTriggerScriptStore.find(trigger_id);
9487 if (i != _areaTriggerScriptStore.end())
9488 return i->second;
9489 return 0;
9490}

References _areaTriggerScriptStore.

◆ GetAreaTriggerTeleport()

AreaTriggerTeleport const * ObjectMgr::GetAreaTriggerTeleport ( uint32  trigger) const
inline
874 {
875 AreaTriggerTeleportContainer::const_iterator itr = _areaTriggerTeleportStore.find(trigger);
876 if (itr != _areaTriggerTeleportStore.end())
877 return &itr->second;
878 return nullptr;
879 }
AreaTriggerTeleportContainer _areaTriggerTeleportStore
Definition ObjectMgr.h:1552

References _areaTriggerTeleportStore.

◆ GetBaseReputationOf()

int32 ObjectMgr::GetBaseReputationOf ( FactionEntry const *  factionEntry,
uint8  race,
uint8  playerClass 
)
9499{
9500 if (!factionEntry)
9501 return 0;
9502
9503 uint32 raceMask = (1 << (race - 1));
9504 uint32 classMask = (1 << (playerClass - 1));
9505
9506 for (int i = 0; i < 4; i++)
9507 {
9508 if ((!factionEntry->BaseRepClassMask[i] ||
9509 factionEntry->BaseRepClassMask[i] & classMask) &&
9510 (!factionEntry->BaseRepRaceMask[i] ||
9511 factionEntry->BaseRepRaceMask[i] & raceMask))
9512 return factionEntry->BaseRepValue[i];
9513 }
9514
9515 return 0;
9516}

References FactionEntry::BaseRepClassMask, FactionEntry::BaseRepRaceMask, and FactionEntry::BaseRepValue.

◆ GetBaseXP()

uint32 ObjectMgr::GetBaseXP ( uint8  level)
8101{
8102 return _baseXPTable[level] ? _baseXPTable[level] : 0;
8103}
BaseXPContainer _baseXPTable
Definition ObjectMgr.h:1622

References _baseXPTable.

◆ GetBreadcrumbsForQuest()

std::vector< uint32 > const * ObjectMgr::GetBreadcrumbsForQuest ( uint32  questId) const
inline
1156 {
1157 auto itr = _breadcrumbsForQuest.find(questId);
1158 if (itr != _breadcrumbsForQuest.end())
1159 return &itr->second;
1160
1161 return nullptr;
1162 }
BreadcrumbQuestMap _breadcrumbsForQuest
Definition ObjectMgr.h:1153

References _breadcrumbsForQuest.

◆ GetBroadcastText()

BroadcastText const * ObjectMgr::GetBroadcastText ( uint32  id) const
inline
1225 {
1226 BroadcastTextContainer::const_iterator itr = _broadcastTextStore.find(id);
1227 if (itr != _broadcastTextStore.end())
1228 return &itr->second;
1229 return nullptr;
1230 }
BroadcastTextContainer _broadcastTextStore
Definition ObjectMgr.h:1664

References _broadcastTextStore.

Referenced by LoadGossipMenuItems(), LoadGossipText(), and LoadScripts().

◆ GetClassTrainers()

std::vector< Trainer::Trainer const * > const & ObjectMgr::GetClassTrainers ( uint8  classId) const
inline
1431{ return _classTrainers.at(classId); }
std::unordered_map< uint8, std::vector< Trainer::Trainer const * > > _classTrainers
Definition ObjectMgr.h:1681

References _classTrainers.

◆ GetCreatureAddon()

CreatureAddon const * ObjectMgr::GetCreatureAddon ( ObjectGuid::LowType  lowguid)
1431{
1432 CreatureAddonContainer::const_iterator itr = _creatureAddonStore.find(lowguid);
1433 if (itr != _creatureAddonStore.end())
1434 return &(itr->second);
1435
1436 return nullptr;
1437}
CreatureAddonContainer _creatureAddonStore
Definition ObjectMgr.h:1645

References _creatureAddonStore.

◆ GetCreatureBaseStats()

CreatureBaseStats const * ObjectMgr::GetCreatureBaseStats ( uint8  level,
uint8  unitClass 
)
10458{
10459 CreatureBaseStatsContainer::const_iterator it = _creatureBaseStatsStore.find(MAKE_PAIR16(level, unitClass));
10460
10461 if (it != _creatureBaseStatsStore.end())
10462 return &(it->second);
10463
10464 struct DefaultCreatureBaseStats : public CreatureBaseStats
10465 {
10466 DefaultCreatureBaseStats()
10467 {
10468 BaseArmor = 1;
10469 for (uint8 j = 0; j < MAX_EXPANSIONS; ++j)
10470 {
10471 BaseHealth[j] = 1;
10472 BaseDamage[j] = 0.0f;
10473 }
10474 BaseMana = 0;
10475 AttackPower = 0;
10476 RangedAttackPower = 0;
10477 Strength = 0;
10478 Agility = 0;
10479 Stamina = 0;
10480 Intellect = 0;
10481 Spirit = 0;
10482 }
10483 };
10484 static const DefaultCreatureBaseStats defStats;
10485 return &defStats;
10486}
uint16 MAKE_PAIR16(uint8 l, uint8 h)
Definition ObjectDefines.h:83
CreatureBaseStatsContainer _creatureBaseStatsStore
Definition ObjectMgr.h:1606

References _creatureBaseStatsStore, MAKE_PAIR16(), and MAX_EXPANSIONS.

Referenced by AddCreData().

◆ GetCreatureData()

CreatureData const * ObjectMgr::GetCreatureData ( ObjectGuid::LowType  spawnId) const
inline
1233 {
1234 CreatureDataContainer::const_iterator itr = _creatureDataStore.find(spawnId);
1235 if (itr == _creatureDataStore.end()) return nullptr;
1236 return &itr->second;
1237 }

References _creatureDataStore.

Referenced by DeleteCreatureData(), GetSpawnData(), LoadCreatureAddons(), LoadCreatureDataFromDB(), LoadCreatureMovementOverrides(), LoadCreatureSparring(), LoadLinkedRespawn(), and SetCreatureLinkedRespawn().

◆ GetCreatureLocale()

CreatureLocale const * ObjectMgr::GetCreatureLocale ( uint32  entry) const
inline
1282 {
1283 CreatureLocaleContainer::const_iterator itr = _creatureLocaleStore.find(entry);
1284 if (itr == _creatureLocaleStore.end()) return nullptr;
1285 return &itr->second;
1286 }
CreatureLocaleContainer _creatureLocaleStore
Definition ObjectMgr.h:1653

References _creatureLocaleStore.

◆ GetCreatureModelInfo()

CreatureModelInfo const * ObjectMgr::GetCreatureModelInfo ( uint32  modelId) const
1635{
1636 CreatureModelContainer::const_iterator itr = _creatureModelStore.find(modelId);
1637 if (itr != _creatureModelStore.end())
1638 return &(itr->second);
1639
1640 return nullptr;
1641}
CreatureModelContainer _creatureModelStore
Definition ObjectMgr.h:1644

References _creatureModelStore.

Referenced by GetCreatureModelRandomGender(), and LoadCreatureTemplateModels().

◆ GetCreatureModelRandomGender()

CreatureModelInfo const * ObjectMgr::GetCreatureModelRandomGender ( CreatureModel model,
CreatureTemplate const *  creatureTemplate 
) const
1678{
1679 CreatureModelInfo const* modelInfo = GetCreatureModelInfo(model->CreatureDisplayID);
1680 if (!modelInfo)
1681 return nullptr;
1682
1683 // If a model for another gender exists, 50% chance to use it
1684 if (modelInfo->modelid_other_gender != 0 && urand(0, 1) == 0)
1685 {
1686 CreatureModelInfo const* minfo_tmp = GetCreatureModelInfo(modelInfo->modelid_other_gender);
1687 if (!minfo_tmp)
1688 LOG_ERROR("sql.sql", "Model (Entry: {}) has modelid_other_gender {} not found in table `creature_model_info`. ", model->CreatureDisplayID, modelInfo->modelid_other_gender);
1689 else
1690 {
1691 // Model ID changed
1692 model->CreatureDisplayID = modelInfo->modelid_other_gender;
1693 if (creatureTemplate)
1694 {
1695 auto itr = std::find_if(creatureTemplate->Models.begin(), creatureTemplate->Models.end(), [&](CreatureModel const& templateModel)
1696 {
1697 return templateModel.CreatureDisplayID == modelInfo->modelid_other_gender;
1698 });
1699 if (itr != creatureTemplate->Models.end())
1700 *model = *itr;
1701 }
1702 return minfo_tmp;
1703 }
1704 }
1705
1706 return modelInfo;
1707}
CreatureModelInfo const * GetCreatureModelInfo(uint32 modelId) const
Definition ObjectMgr.cpp:1634
Definition CreatureData.h:389
uint32 modelid_other_gender
Definition CreatureData.h:393
uint32 CreatureDisplayID
Definition CreatureData.h:180

References CreatureModel::CreatureDisplayID, GetCreatureModelInfo(), LOG_ERROR, CreatureModelInfo::modelid_other_gender, CreatureTemplate::Models, and urand().

Referenced by GetTaxiMountDisplayId().

◆ GetCreatureMovementOverride()

CreatureMovementData const * ObjectMgr::GetCreatureMovementOverride ( ObjectGuid::LowType  spawnId) const
1449{
1451}
std::unordered_map< ObjectGuid::LowType, CreatureMovementData > _creatureMovementOverrides
Definition ObjectMgr.h:1647
auto MapGetValuePtr(M &map, typename M::key_type const &key) -> decltype(AddressOrSelf(map.find(key) ->second))
Definition Containers.h:216

References _creatureMovementOverrides, and Acore::Containers::MapGetValuePtr().

◆ GetCreatureQuestInvolvedRelationBounds()

QuestRelationBounds ObjectMgr::GetCreatureQuestInvolvedRelationBounds ( uint32  creature_entry)
inline
1011 {
1012 return _creatureQuestInvolvedRelations.equal_range(creature_entry);
1013 }
QuestRelations _creatureQuestInvolvedRelations
Definition ObjectMgr.h:1570

References _creatureQuestInvolvedRelations.

◆ GetCreatureQuestInvolvedRelationMap()

QuestRelations * ObjectMgr::GetCreatureQuestInvolvedRelationMap ( )
inline
1001 {
1003 }

References _creatureQuestInvolvedRelations.

◆ GetCreatureQuestItemList()

CreatureQuestItemList const * ObjectMgr::GetCreatureQuestItemList ( uint32  id) const
inline
829 {
830 CreatureQuestItemMap::const_iterator itr = _creatureQuestItemStore.find(id);
831 if (itr != _creatureQuestItemStore.end())
832 return &itr->second;
833 return nullptr;
834 }
CreatureQuestItemMap _creatureQuestItemStore
Definition ObjectMgr.h:1650

References _creatureQuestItemStore.

◆ GetCreatureQuestItemMap()

CreatureQuestItemMap const * ObjectMgr::GetCreatureQuestItemMap ( ) const
inline
835{ return &_creatureQuestItemStore; }

References _creatureQuestItemStore.

◆ GetCreatureQuestRelationBounds()

QuestRelationBounds ObjectMgr::GetCreatureQuestRelationBounds ( uint32  creature_entry)
inline
1006 {
1007 return _creatureQuestRelations.equal_range(creature_entry);
1008 }
QuestRelations _creatureQuestRelations
Definition ObjectMgr.h:1569

References _creatureQuestRelations.

◆ GetCreatureQuestRelationMap()

QuestRelations * ObjectMgr::GetCreatureQuestRelationMap ( )
inline
996 {
998 }

References _creatureQuestRelations.

◆ GetCreatureTemplate()

◆ GetCreatureTemplateAddon()

CreatureAddon const * ObjectMgr::GetCreatureTemplateAddon ( uint32  entry)
1440{
1441 CreatureAddonContainer::const_iterator itr = _creatureTemplateAddonStore.find(entry);
1442 if (itr != _creatureTemplateAddonStore.end())
1443 return &(itr->second);
1444
1445 return nullptr;
1446}
CreatureAddonContainer _creatureTemplateAddonStore
Definition ObjectMgr.h:1646

References _creatureTemplateAddonStore.

◆ GetCreatureTemplates()

CreatureTemplateContainer const * ObjectMgr::GetCreatureTemplates ( ) const
inline
771{ return &_creatureTemplateStore; }
CreatureTemplateContainer _creatureTemplateStore
Definition ObjectMgr.h:1641

References _creatureTemplateStore.

Referenced by LoadCreatureClassLevelStats(), and LoadNPCSpellClickSpells().

◆ GetDBCLocaleIndex()

LocaleConstant ObjectMgr::GetDBCLocaleIndex ( ) const
inline
1388{ return DBCLocaleIndex; }

References DBCLocaleIndex.

◆ GetDungeonEncounterList()

DungeonEncounterList const * ObjectMgr::GetDungeonEncounterList ( uint32  mapId,
Difficulty  difficulty 
)
inline
950 {
951 std::unordered_map<uint32, DungeonEncounterList>::const_iterator itr = _dungeonEncounterStore.find(MAKE_PAIR32(mapId, difficulty));
952 if (itr != _dungeonEncounterStore.end())
953 return &itr->second;
954 return nullptr;
955 }

References _dungeonEncounterStore, and MAKE_PAIR32().

◆ GetEquipmentInfo()

EquipmentInfo const * ObjectMgr::GetEquipmentInfo ( uint32  entry,
int8 id 
)
1454{
1455 EquipmentInfoContainer::const_iterator itr = _equipmentInfoStore.find(entry);
1456 if (itr == _equipmentInfoStore.end())
1457 return nullptr;
1458
1459 if (itr->second.empty())
1460 return nullptr;
1461
1462 if (id == -1) // select a random element
1463 {
1464 EquipmentInfoContainerInternal::const_iterator ritr = itr->second.begin();
1465 std::advance(ritr, urand(0u, itr->second.size() - 1));
1466 id = std::distance(itr->second.begin(), ritr) + 1;
1467 return &ritr->second;
1468 }
1469 else
1470 {
1471 EquipmentInfoContainerInternal::const_iterator itr2 = itr->second.find(id);
1472 if (itr2 != itr->second.end())
1473 return &itr2->second;
1474 }
1475
1476 return nullptr;
1477}
EquipmentInfoContainer _equipmentInfoStore
Definition ObjectMgr.h:1651

References _equipmentInfoStore, and urand().

Referenced by LoadCreatureDataFromDB(), and LoadCreatures().

◆ GetFishingBaseSkillLevel()

int32 ObjectMgr::GetFishingBaseSkillLevel ( uint32  entry) const
inline
1122 {
1123 FishingBaseSkillContainer::const_iterator itr = _fishingBaseForAreaStore.find(entry);
1124 return itr != _fishingBaseForAreaStore.end() ? itr->second : 0;
1125 }

References _fishingBaseForAreaStore.

◆ GetGameObjectAddon()

GameObjectAddon const * ObjectMgr::GetGameObjectAddon ( ObjectGuid::LowType  lowguid)
1422{
1423 GameObjectAddonContainer::const_iterator itr = _gameObjectAddonStore.find(lowguid);
1424 if (itr != _gameObjectAddonStore.end())
1425 return &(itr->second);
1426
1427 return nullptr;
1428}
GameObjectAddonContainer _gameObjectAddonStore
Definition ObjectMgr.h:1648

References _gameObjectAddonStore.

◆ GetGameObjectData()

GameObjectData const * ObjectMgr::GetGameObjectData ( ObjectGuid::LowType  spawnId) const
inline
1268 {
1269 GameObjectDataContainer::const_iterator itr = _gameObjectDataStore.find(spawnId);
1270 if (itr == _gameObjectDataStore.end()) return nullptr;
1271 return &itr->second;
1272 }

References _gameObjectDataStore.

Referenced by DeleteGOData(), GetSpawnData(), LoadGameObjectAddons(), LoadGameObjectDataFromDB(), LoadLinkedRespawn(), and LoadScripts().

◆ GetGameObjectLocale()

GameObjectLocale const * ObjectMgr::GetGameObjectLocale ( uint32  entry) const
inline
1288 {
1289 GameObjectLocaleContainer::const_iterator itr = _gameObjectLocaleStore.find(entry);
1290 if (itr == _gameObjectLocaleStore.end()) return nullptr;
1291 return &itr->second;
1292 }
GameObjectLocaleContainer _gameObjectLocaleStore
Definition ObjectMgr.h:1656

References _gameObjectLocaleStore.

◆ GetGameObjectQuestItemList()

GameObjectQuestItemList const * ObjectMgr::GetGameObjectQuestItemList ( uint32  id) const
inline
820 {
821 GameObjectQuestItemMap::const_iterator itr = _gameObjectQuestItemStore.find(id);
822 if (itr != _gameObjectQuestItemStore.end())
823 return &itr->second;
824 return nullptr;
825 }
GameObjectQuestItemMap _gameObjectQuestItemStore
Definition ObjectMgr.h:1649

References _gameObjectQuestItemStore.

◆ GetGameObjectQuestItemMap()

GameObjectQuestItemMap const * ObjectMgr::GetGameObjectQuestItemMap ( ) const
inline

◆ GetGameObjectSummonGroup()

std::vector< GameObjectSummonData > const * ObjectMgr::GetGameObjectSummonGroup ( uint32  summonerId,
SummonerType  summonerType,
uint8  group 
) const
inline
1216 {
1217 GameObjectSummonDataContainer::const_iterator itr = _goSummonDataStore.find(TempSummonGroupKey(summonerId, summonerType, group));
1218 if (itr != _goSummonDataStore.end())
1219 return &itr->second;
1220
1221 return nullptr;
1222 }
GameObjectSummonDataContainer _goSummonDataStore
Stores gameobject summon data grouped by summoner's entry, summoner's type and group id.
Definition ObjectMgr.h:1662
Key for storing temp summon data in TempSummonDataContainer.
Definition ObjectMgr.h:65

References _goSummonDataStore.

◆ GetGameObjectTemplate()

GameObjectTemplate const * ObjectMgr::GetGameObjectTemplate ( uint32  entry)
10799{
10800 GameObjectTemplateContainer::const_iterator itr = _gameObjectTemplateStore.find(entry);
10801 if (itr != _gameObjectTemplateStore.end())
10802 return &(itr->second);
10803
10804 return nullptr;
10805}
GameObjectTemplateContainer _gameObjectTemplateStore
Definition ObjectMgr.h:1657

References _gameObjectTemplateStore.

Referenced by AddGOData(), IsGameObjectStaticTransport(), LoadGameObjectDataFromDB(), LoadGameobjectQuestEnders(), LoadGameObjectQuestItems(), LoadGameobjectQuestStarters(), LoadGameobjects(), LoadGameObjectSummons(), LoadGameObjectTemplateAddons(), LoadQuestGreetings(), LoadQuestGreetingsLocales(), LoadQuests(), LoadScripts(), and LoadTempSummons().

◆ GetGameObjectTemplateAddon()

GameObjectTemplateAddon const * ObjectMgr::GetGameObjectTemplateAddon ( uint32  entry) const
10814{
10815 auto itr = _gameObjectTemplateAddonStore.find(entry);
10816 if (itr != _gameObjectTemplateAddonStore.end())
10817 return &itr->second;
10818
10819 return nullptr;
10820}
GameObjectTemplateAddonContainer _gameObjectTemplateAddonStore
Definition ObjectMgr.h:1658

References _gameObjectTemplateAddonStore.

◆ GetGameObjectTemplates()

GameObjectTemplateContainer const * ObjectMgr::GetGameObjectTemplates ( ) const
inline

◆ GetGameTele() [1/2]

GameTele const * ObjectMgr::GetGameTele ( std::string_view  name,
bool  exactSearch = false 
) const
9604{
9605 // explicit name case
9606 std::wstring wname;
9607 if (!Utf8toWStr(name, wname))
9608 return nullptr;
9609
9610 // converting string that we try to find to lower case
9611 wstrToLower(wname);
9612
9613 // Alternative first GameTele what contains wnameLow as substring in case no GameTele location found
9614 const GameTele* alt = nullptr;
9615 for (GameTeleContainer::const_iterator itr = _gameTeleStore.begin(); itr != _gameTeleStore.end(); ++itr)
9616 {
9617 if (itr->second.wnameLow == wname)
9618 return &itr->second;
9619 else if (!exactSearch && !alt && itr->second.wnameLow.find(wname) != std::wstring::npos)
9620 alt = &itr->second;
9621 }
9622
9623 return alt;
9624}
Definition ObjectMgr.h:133

References _gameTeleStore, Utf8toWStr(), GameTele::wnameLow, and wstrToLower().

◆ GetGameTele() [2/2]

GameTele const * ObjectMgr::GetGameTele ( uint32  id) const
inline
1420 {
1421 GameTeleContainer::const_iterator itr = _gameTeleStore.find(id);
1422 if (itr == _gameTeleStore.end()) return nullptr;
1423 return &itr->second;
1424 }

References _gameTeleStore.

◆ GetGameTeleMap()

GameTeleContainer const & ObjectMgr::GetGameTeleMap ( ) const
inline
1426{ return _gameTeleStore; }

References _gameTeleStore.

◆ GetGenerator()

template<HighGuid type>
ObjectGuidGeneratorBase & ObjectMgr::GetGenerator ( )
inline
1135 {
1136 static_assert(ObjectGuidTraits<type>::Global, "Only global guid can be generated in ObjectMgr context");
1137 return GetGuidSequenceGenerator<type>();
1138 }
Definition ObjectGuid.h:76

◆ GetGoBackTrigger()

AreaTriggerTeleport const * ObjectMgr::GetGoBackTrigger ( uint32  Map) const
7565{
7566 bool useParentDbValue = false;
7567 uint32 parentId = 0;
7568 MapEntry const* mapEntry = sMapStore.LookupEntry(Map);
7569 if (!mapEntry || mapEntry->entrance_map < 0)
7570 return nullptr;
7571
7572 if (mapEntry->IsDungeon())
7573 {
7574 InstanceTemplate const* iTemplate = sObjectMgr->GetInstanceTemplate(Map);
7575
7576 if (!iTemplate)
7577 return nullptr;
7578
7579 parentId = iTemplate->Parent;
7580 useParentDbValue = true;
7581 }
7582
7583 uint32 entrance_map = uint32(mapEntry->entrance_map);
7584 for (AreaTriggerTeleportContainer::const_iterator itr = _areaTriggerTeleportStore.begin(); itr != _areaTriggerTeleportStore.end(); ++itr)
7585 if ((!useParentDbValue && itr->second.target_mapId == entrance_map) || (useParentDbValue && itr->second.target_mapId == parentId))
7586 {
7587 AreaTrigger const* atEntry = GetAreaTrigger(itr->first);
7588 if (atEntry && atEntry->map == Map)
7589 return &itr->second;
7590 }
7591 return nullptr;
7592}
DBCStorage< MapEntry > sMapStore(MapEntryfmt)
AreaTrigger const * GetAreaTrigger(uint32 trigger) const
Definition ObjectMgr.h:865
Definition ObjectMgr.h:421
uint32 map
Definition ObjectMgr.h:423
Definition Map.h:122
uint32 Parent
Definition Map.h:123
Definition DBCStructure.h:1325
int32 entrance_map
Definition DBCStructure.h:1340
bool IsDungeon() const
Definition DBCStructure.h:1351

References _areaTriggerTeleportStore, MapEntry::entrance_map, GetAreaTrigger(), MapEntry::IsDungeon(), AreaTrigger::map, InstanceTemplate::Parent, sMapStore, and sObjectMgr.

◆ GetGOQuestInvolvedRelationBounds()

QuestRelationBounds ObjectMgr::GetGOQuestInvolvedRelationBounds ( uint32  go_entry)
inline
991 {
992 return _goQuestInvolvedRelations.equal_range(go_entry);
993 }
QuestRelations _goQuestInvolvedRelations
Definition ObjectMgr.h:1568

References _goQuestInvolvedRelations.

◆ GetGOQuestInvolvedRelationMap()

QuestRelations * ObjectMgr::GetGOQuestInvolvedRelationMap ( )
inline
981 {
983 }

References _goQuestInvolvedRelations.

◆ GetGOQuestRelationBounds()

QuestRelationBounds ObjectMgr::GetGOQuestRelationBounds ( uint32  go_entry)
inline
986 {
987 return _goQuestRelations.equal_range(go_entry);
988 }
QuestRelations _goQuestRelations
Definition ObjectMgr.h:1567

References _goQuestRelations.

◆ GetGOQuestRelationMap()

QuestRelations * ObjectMgr::GetGOQuestRelationMap ( )
inline
976 {
977 return &_goQuestRelations;
978 }

References _goQuestRelations.

◆ GetGossipMenuItemsLocale()

GossipMenuItemsLocale const * ObjectMgr::GetGossipMenuItemsLocale ( uint32  entry) const
inline
1318 {
1319 GossipMenuItemsLocaleContainer::const_iterator itr = _gossipMenuItemsLocaleStore.find(entry);
1320 if (itr == _gossipMenuItemsLocaleStore.end()) return nullptr;
1321 return &itr->second;
1322 }
GossipMenuItemsLocaleContainer _gossipMenuItemsLocaleStore
Definition ObjectMgr.h:1676

References _gossipMenuItemsLocaleStore.

◆ GetGossipMenuItemsMapBounds()

GossipMenuItemsMapBounds ObjectMgr::GetGossipMenuItemsMapBounds ( uint32  uiMenuId) const
inline
1467 {
1468 return _gossipMenuItemsStore.equal_range(uiMenuId);
1469 }
GossipMenuItemsContainer _gossipMenuItemsStore
Definition ObjectMgr.h:1562

References _gossipMenuItemsStore.

◆ GetGossipMenuItemsMapBoundsNonConst()

GossipMenuItemsMapBoundsNonConst ObjectMgr::GetGossipMenuItemsMapBoundsNonConst ( uint32  uiMenuId)
inline
1471 {
1472 return _gossipMenuItemsStore.equal_range(uiMenuId);
1473 }

References _gossipMenuItemsStore.

◆ GetGossipMenusMapBounds()

GossipMenusMapBounds ObjectMgr::GetGossipMenusMapBounds ( uint32  uiMenuId) const
inline
1457 {
1458 return _gossipMenusStore.equal_range(uiMenuId);
1459 }
GossipMenusContainer _gossipMenusStore
Definition ObjectMgr.h:1561

References _gossipMenusStore.

◆ GetGossipMenusMapBoundsNonConst()

GossipMenusMapBoundsNonConst ObjectMgr::GetGossipMenusMapBoundsNonConst ( uint32  uiMenuId)
inline
1462 {
1463 return _gossipMenusStore.equal_range(uiMenuId);
1464 }

References _gossipMenusStore.

◆ GetGossipText()

GossipText const * ObjectMgr::GetGossipText ( uint32  Text_ID) const
6607{
6608 GossipTextContainer::const_iterator itr = _gossipTextStore.find(Text_ID);
6609 if (itr != _gossipTextStore.end())
6610 return &itr->second;
6611 return nullptr;
6612}
GossipTextContainer _gossipTextStore
Definition ObjectMgr.h:1549

References _gossipTextStore.

Referenced by LoadGossipMenu().

◆ GetGridObjectGuids()

CellObjectGuids const & ObjectMgr::GetGridObjectGuids ( uint16  mapid,
uint8  spawnMode,
uint32  gridId 
)
inline
1178 {
1179 MapObjectGuids::const_iterator itr1 = _mapObjectGuidsStore.find(MAKE_PAIR32(mapid, spawnMode));
1180 if (itr1 != _mapObjectGuidsStore.end())
1181 {
1182 CellObjectGuidsMap::const_iterator itr2 = itr1->second.find(gridId);
1183 if (itr2 != itr1->second.end())
1184 return itr2->second;
1185 }
1186 return _emptyCellObjectGuids;
1187 }
CellObjectGuids _emptyCellObjectGuids
Definition ObjectMgr.h:1639

References _emptyCellObjectGuids, _mapObjectGuidsStore, and MAKE_PAIR32().

◆ GetGuidSequenceGenerator()

template<HighGuid high>
ObjectGuidGeneratorBase & ObjectMgr::GetGuidSequenceGenerator ( )
inlineprivate
1530 {
1531 auto itr = _guidGenerators.find(high);
1532 if (itr == _guidGenerators.end())
1533 itr = _guidGenerators.insert(std::make_pair(high, std::unique_ptr<ObjectGuidGenerator<high>>(new ObjectGuidGenerator<high>()))).first;
1534
1535 return *itr->second;
1536 }
Definition ObjectGuid.h:297
std::map< HighGuid, std::unique_ptr< ObjectGuidGeneratorBase > > _guidGenerators
Definition ObjectMgr.h:1538

References _guidGenerators.

◆ GetInstanceTemplate()

InstanceTemplate const * ObjectMgr::GetInstanceTemplate ( uint32  mapId)
6513{
6514 InstanceTemplateContainer::const_iterator itr = _instanceTemplateStore.find(uint16(mapID));
6515 if (itr != _instanceTemplateStore.end())
6516 return &(itr->second);
6517
6518 return nullptr;
6519}
InstanceTemplateContainer _instanceTemplateStore
Definition ObjectMgr.h:1595

References _instanceTemplateStore.

◆ GetItemLocale()

ItemLocale const * ObjectMgr::GetItemLocale ( uint32  entry) const
inline
1294 {
1295 ItemLocaleContainer::const_iterator itr = _itemLocaleStore.find(entry);
1296 if (itr == _itemLocaleStore.end()) return nullptr;
1297 return &itr->second;
1298 }
ItemLocaleContainer _itemLocaleStore
Definition ObjectMgr.h:1667

References _itemLocaleStore.

◆ GetItemSetNameEntry()

ItemSetNameEntry const * ObjectMgr::GetItemSetNameEntry ( uint32  itemId)
inline
791 {
792 ItemSetNameContainer::iterator itr = _itemSetNameStore.find(itemId);
793 if (itr != _itemSetNameStore.end())
794 return &itr->second;
795 return nullptr;
796 }
ItemSetNameContainer _itemSetNameStore
Definition ObjectMgr.h:1635

References _itemSetNameStore.

◆ GetItemSetNameLocale()

ItemSetNameLocale const * ObjectMgr::GetItemSetNameLocale ( uint32  entry) const
inline
1300 {
1301 ItemSetNameLocaleContainer::const_iterator itr = _itemSetNameLocaleStore.find(entry);
1302 if (itr == _itemSetNameLocaleStore.end())return nullptr;
1303 return &itr->second;
1304 }
ItemSetNameLocaleContainer _itemSetNameLocaleStore
Definition ObjectMgr.h:1668

References _itemSetNameLocaleStore.

◆ GetItemTemplate()

ItemTemplate const * ObjectMgr::GetItemTemplate ( uint32  entry)
3852{
3853 return entry < _itemTemplateStoreFast.size() ? _itemTemplateStoreFast[entry] : nullptr;
3854}
std::vector< ItemTemplate * > _itemTemplateStoreFast
Definition ObjectMgr.h:1666

References _itemTemplateStoreFast.

Referenced by LoadAccessRequirements(), LoadFactionChangeItems(), LoadItemSetNames(), LoadItemTemplates(), LoadPlayerInfo(), LoadQuests(), and LoadScripts().

◆ GetItemTemplateStore()

ItemTemplateContainer const * ObjectMgr::GetItemTemplateStore ( ) const
inline
783{ return &_itemTemplateStore; }
ItemTemplateContainer _itemTemplateStore
Definition ObjectMgr.h:1665

References _itemTemplateStore.

◆ GetItemTemplateStoreFast()

std::vector< ItemTemplate * > const * ObjectMgr::GetItemTemplateStoreFast ( ) const
inline
784{ return &_itemTemplateStoreFast; }

References _itemTemplateStoreFast.

◆ GetLinkedRespawnGuid()

ObjectGuid ObjectMgr::GetLinkedRespawnGuid ( ObjectGuid  guid) const
inline
1259 {
1260 LinkedRespawnContainer::const_iterator itr = _linkedRespawnStore.find(guid);
1261 if (itr == _linkedRespawnStore.end())
1262 return ObjectGuid::Empty;
1263 return itr->second;
1264 }
static ObjectGuid const Empty
Definition ObjectGuid.h:120
LinkedRespawnContainer _linkedRespawnStore
Definition ObjectMgr.h:1652

References _linkedRespawnStore, and ObjectGuid::Empty.

◆ GetLocaleString() [1/2]

static void ObjectMgr::GetLocaleString ( const std::vector< std::string > &  data,
int  loc_idx,
std::string &  value 
)
inlinestatic
1484 {
1485 if (data.size() > std::size_t(loc_idx) && !data[loc_idx].empty())
1486 value = data[loc_idx];
1487 }

◆ GetLocaleString() [2/2]

◆ GetMailLevelReward()

MailLevelReward const * ObjectMgr::GetMailLevelReward ( uint32  level,
uint32  raceMask 
)
inline
1165 {
1166 MailLevelRewardContainer::const_iterator map_itr = _mailLevelRewardStore.find(level);
1167 if (map_itr == _mailLevelRewardStore.end())
1168 return nullptr;
1169
1170 for (const auto & set_itr : map_itr->second)
1171 if (set_itr.raceMask & raceMask)
1172 return &set_itr;
1173
1174 return nullptr;
1175 }
MailLevelRewardContainer _mailLevelRewardStore
Definition ObjectMgr.h:1604

References _mailLevelRewardStore.

◆ GetMapEntranceTrigger()

AreaTriggerTeleport const * ObjectMgr::GetMapEntranceTrigger ( uint32  Map) const

Searches for the areatrigger which teleports players to the given map

7598{
7599 for (AreaTriggerTeleportContainer::const_iterator itr = _areaTriggerTeleportStore.begin(); itr != _areaTriggerTeleportStore.end(); ++itr)
7600 {
7601 if (itr->second.target_mapId == Map) // Id is used to determine correct Scarlet Monastery instance
7602 {
7603 // xinef: no need to check, already done at loading
7604 //AreaTriggerEntry const* atEntry = sAreaTriggerStore.LookupEntry(itr->first);
7605 //if (atEntry)
7606 return &itr->second;
7607 }
7608 }
7609 return nullptr;
7610}

References _areaTriggerTeleportStore.

◆ GetMapObjectGuids()

CellObjectGuidsMap const & ObjectMgr::GetMapObjectGuids ( uint16  mapid,
uint8  spawnMode 
)
inline
1190 {
1191 MapObjectGuids::const_iterator itr1 = _mapObjectGuidsStore.find(MAKE_PAIR32(mapid, spawnMode));
1192 if (itr1 != _mapObjectGuidsStore.end())
1193 return itr1->second;
1195 }
CellObjectGuidsMap _emptyCellObjectGuidsMap
Definition ObjectMgr.h:1638

References _emptyCellObjectGuidsMap, _mapObjectGuidsStore, and MAKE_PAIR32().

◆ GetModelForShapeshift()

uint32 ObjectMgr::GetModelForShapeshift ( ShapeshiftForm  form,
Player player 
) const
1889{
1890 uint8 customizationID;
1891
1892 if (player->GetTeamId() == TEAM_ALLIANCE)
1893 customizationID = player->GetByteValue(PLAYER_BYTES, 3); // Use Hair Color
1894 else
1895 customizationID = player->GetByteValue(PLAYER_BYTES, 0); // Use Skin Color
1896
1897 auto itr = _playerShapeshiftModel.find(std::make_tuple(form, player->getRace(), customizationID, player->getGender()));
1898 if (itr != _playerShapeshiftModel.end())
1899 return itr->second; // Explicit combination
1900
1901 itr = _playerShapeshiftModel.find(std::make_tuple(form, player->getRace(), customizationID, GENDER_NONE));
1902 if (itr != _playerShapeshiftModel.end())
1903 return itr->second; // Combination applied to both genders
1904
1905 itr = _playerShapeshiftModel.find(std::make_tuple(form, player->getRace(), 255, player->getGender()));
1906 if (itr != _playerShapeshiftModel.end())
1907 return itr->second; // Default gender-dependent model
1908
1909 itr = _playerShapeshiftModel.find(std::make_tuple(form, player->getRace(), 255, GENDER_NONE));
1910 if (itr != _playerShapeshiftModel.end())
1911 return itr->second; // Last resort
1912
1913 LOG_DEBUG("entities.player", "ShapeshiftForm {} with RaceID ({}) have no shapeshift model data defined, using fallback data.", form, player->getRace());
1914 return 0;
1915}
@ GENDER_NONE
Definition SharedDefines.h:63
@ TEAM_ALLIANCE
Definition SharedDefines.h:748
@ PLAYER_BYTES
Definition UpdateFields.h:181
PlayerShapeshiftModelMap _playerShapeshiftModel
Definition ObjectMgr.h:1699
uint8 GetByteValue(uint16 index, uint8 offset) const
Definition Object.cpp:312
TeamId GetTeamId(bool original=false) const
Definition Player.h:2127
uint8 getGender() const
Definition Unit.h:848
uint8 getRace(bool original=false) const
Definition Unit.cpp:17013

References _playerShapeshiftModel, GENDER_NONE, Object::GetByteValue(), Unit::getGender(), Unit::getRace(), Player::GetTeamId(), LOG_DEBUG, PLAYER_BYTES, and TEAM_ALLIANCE.

◆ GetModelForTotem()

uint32 ObjectMgr::GetModelForTotem ( SummonSlot  totemSlot,
Races  race 
) const
1834{
1835 auto itr = _playerTotemModel.find(std::make_pair(totemSlot, race));
1836 if (itr != _playerTotemModel.end())
1837 return itr->second;
1838
1839 LOG_ERROR("misc", "TotemSlot {} with RaceID ({}) have no totem model data defined, set to default model.", totemSlot, race);
1840 return 0;
1841}
PlayerTotemModelMap _playerTotemModel
Definition ObjectMgr.h:1697

References _playerTotemModel, and LOG_ERROR.

◆ GetModuleString() [1/2]

ModuleString const * ObjectMgr::GetModuleString ( std::string  module,
uint32  id 
) const
inline
1368 {
1369 std::pair<std::string, uint32> pairKey = std::make_pair(module, id);
1370 ModuleStringContainer::const_iterator itr = _moduleStringStore.find(pairKey);
1371 if (itr == _moduleStringStore.end())
1372 return nullptr;
1373
1374 return &itr->second;
1375 }
ModuleStringContainer _moduleStringStore
Definition ObjectMgr.h:1674

References _moduleStringStore.

Referenced by GetModuleString().

◆ GetModuleString() [2/2]

std::string const * ObjectMgr::GetModuleString ( std::string  module,
uint32  id,
LocaleConstant  locale 
) const
9343{
9344 ModuleString const* ms = GetModuleString(module, id);
9345 if (ms && !ms->Content.empty())
9346 {
9347 if (ms->Content.size() > size_t(locale) && !ms->Content[locale].empty())
9348 return &ms->Content[locale];
9349
9350 return &ms->Content[DEFAULT_LOCALE];
9351 }
9352
9353 LOG_ERROR("sql.sql", "Module string module {} id {} not found in DB.", module, id);
9354
9355 return (std::string*)"error";
9356}
ModuleString const * GetModuleString(std::string module, uint32 id) const
Definition ObjectMgr.h:1367
Definition ObjectMgr.h:497
std::vector< std::string > Content
Definition ObjectMgr.h:498

References ModuleString::Content, DEFAULT_LOCALE, GetModuleString(), and LOG_ERROR.

◆ GetNearestTaxiNode() [1/2]

uint32 ObjectMgr::GetNearestTaxiNode ( float  x,
float  y,
float  z,
uint32  mapid,
uint32  teamId 
)
7182{
7183 bool found = false;
7184 float dist = 10000;
7185 uint32 id = 0;
7186
7187 for (uint32 i = 1; i < sTaxiNodesStore.GetNumRows(); ++i)
7188 {
7189 TaxiNodesEntry const* node = sTaxiNodesStore.LookupEntry(i);
7190
7191 if (!node || node->map_id != mapid || (!node->MountCreatureID[teamId == TEAM_ALLIANCE ? 1 : 0] && node->MountCreatureID[0] != 32981)) // dk flight
7192 continue;
7193
7194 uint8 field = (uint8)((i - 1) / 32);
7195 uint32 submask = 1 << ((i - 1) % 32);
7196
7197 // skip not taxi network nodes
7198 if (field >= TaxiMaskSize || (sTaxiNodesMask[field] & submask) == 0)
7199 {
7200 continue;
7201 }
7202
7203 float dist2 = (node->x - x) * (node->x - x) + (node->y - y) * (node->y - y) + (node->z - z) * (node->z - z);
7204 if (found)
7205 {
7206 if (dist2 < dist)
7207 {
7208 dist = dist2;
7209 id = i;
7210 }
7211 }
7212 else
7213 {
7214 found = true;
7215 dist = dist2;
7216 id = i;
7217 }
7218 }
7219
7220 return id;
7221}
TaxiMask sTaxiNodesMask
Definition DBCStores.cpp:176
DBCStorage< TaxiNodesEntry > sTaxiNodesStore(TaxiNodesEntryfmt)
static constexpr std::size_t TaxiMaskSize
Definition DBCStructure.h:2248
Definition DBCStructure.h:1953
float z
Definition DBCStructure.h:1958
uint32 map_id
Definition DBCStructure.h:1955
float x
Definition DBCStructure.h:1956
float y
Definition DBCStructure.h:1957
uint32 MountCreatureID[2]
Definition DBCStructure.h:1961

References TaxiNodesEntry::map_id, TaxiNodesEntry::MountCreatureID, sTaxiNodesMask, sTaxiNodesStore, TaxiMaskSize, TEAM_ALLIANCE, TaxiNodesEntry::x, TaxiNodesEntry::y, and TaxiNodesEntry::z.

Referenced by GetNearestTaxiNode().

◆ GetNearestTaxiNode() [2/2]

uint32 ObjectMgr::GetNearestTaxiNode ( WorldLocation const &  loc,
uint32  teamId 
)
7177{
7178 return GetNearestTaxiNode(loc.GetPositionX(), loc.GetPositionY(), loc.GetPositionZ(), loc.GetMapId(), teamId);
7179}
uint32 GetNearestTaxiNode(float x, float y, float z, uint32 mapid, uint32 teamId)
Definition ObjectMgr.cpp:7181

References WorldLocation::GetMapId(), GetNearestTaxiNode(), Position::GetPositionX(), Position::GetPositionY(), and Position::GetPositionZ().

◆ GetNpcTextLocale()

NpcTextLocale const * ObjectMgr::GetNpcTextLocale ( uint32  entry) const
inline
1342 {
1343 NpcTextLocaleContainer::const_iterator itr = _npcTextLocaleStore.find(entry);
1344 if (itr == _npcTextLocaleStore.end()) return nullptr;
1345 return &itr->second;
1346 }
NpcTextLocaleContainer _npcTextLocaleStore
Definition ObjectMgr.h:1672

References _npcTextLocaleStore.

◆ GetNpcVendorItemList()

VendorItemData const * ObjectMgr::GetNpcVendorItemList ( uint32  entry) const
inline
1434 {
1435 CacheVendorItemContainer::const_iterator iter = _cacheVendorItemStore.find(entry);
1436 if (iter == _cacheVendorItemStore.end())
1437 return nullptr;
1438
1439 return &iter->second;
1440 }

References _cacheVendorItemStore.

Referenced by IsVendorItemValid().

◆ GetPageText()

PageText const * ObjectMgr::GetPageText ( uint32  pageEntry)
6429{
6430 PageTextContainer::const_iterator itr = _pageTextStore.find(pageEntry);
6431 if (itr != _pageTextStore.end())
6432 return &(itr->second);
6433
6434 return nullptr;
6435}
PageTextContainer _pageTextStore
Definition ObjectMgr.h:1594

References _pageTextStore.

Referenced by LoadGameObjectTemplate(), and LoadItemTemplates().

◆ GetPageTextLocale()

PageTextLocale const * ObjectMgr::GetPageTextLocale ( uint32  entry) const
inline
1306 {
1307 PageTextLocaleContainer::const_iterator itr = _pageTextLocaleStore.find(entry);
1308 if (itr == _pageTextLocaleStore.end()) return nullptr;
1309 return &itr->second;
1310 }
PageTextLocaleContainer _pageTextLocaleStore
Definition ObjectMgr.h:1673

References _pageTextLocaleStore.

◆ GetPetLevelInfo()

PetLevelInfo const * ObjectMgr::GetPetLevelInfo ( uint32  creature_id,
uint8  level 
) const
4218{
4219 if (level > sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL))
4220 level = sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL);
4221
4222 PetLevelInfoContainer::const_iterator itr = _petInfoStore.find(creature_id);
4223 if (itr == _petInfoStore.end())
4224 return nullptr;
4225
4226 return &itr->second[level - 1]; // data for level 1 stored in [0] array element, ...
4227}

References _petInfoStore, CONFIG_MAX_PLAYER_LEVEL, and sWorld.

◆ GetPlayerClassInfo()

PlayerClassInfo const * ObjectMgr::GetPlayerClassInfo ( uint32  class_) const
inline
803 {
804 if (class_ >= MAX_CLASSES)
805 return nullptr;
806 return _playerClassInfo[class_];
807 }

References _playerClassInfo, and MAX_CLASSES.

◆ GetPlayerClassLevelInfo()

void ObjectMgr::GetPlayerClassLevelInfo ( uint32  class_,
uint8  level,
PlayerClassLevelInfo info 
) const
4895{
4896 if (level < 1 || class_ >= MAX_CLASSES)
4897 return;
4898
4899 PlayerClassInfo const* pInfo = _playerClassInfo[class_];
4900
4901 if (level > sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL))
4902 level = sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL);
4903
4904 *info = pInfo->levelInfo[level - 1];
4905}
Definition Player.h:283

References _playerClassInfo, CONFIG_MAX_PLAYER_LEVEL, PlayerClassInfo::levelInfo, MAX_CLASSES, and sWorld.

◆ GetPlayerInfo()

PlayerInfo const * ObjectMgr::GetPlayerInfo ( uint32  race,
uint32  class_ 
) const
10845{
10846 if (race >= sRaceMgr->GetMaxRaces())
10847 return nullptr;
10848 if (class_ >= MAX_CLASSES)
10849 return nullptr;
10850 PlayerInfo const* info = _playerInfo[race][class_];
10851 if (!info)
10852 return nullptr;
10853 return info;
10854}
Definition Player.h:322

References _playerInfo, MAX_CLASSES, and sRaceMgr.

◆ GetPlayerLevelInfo()

void ObjectMgr::GetPlayerLevelInfo ( uint32  race,
uint32  class_,
uint8  level,
PlayerLevelInfo info 
) const
4908{
4909 if (level < 1 || race >= sRaceMgr->GetMaxRaces() || class_ >= MAX_CLASSES)
4910 return;
4911
4912 PlayerInfo const* pInfo = _playerInfo[race][class_];
4913 if (!pInfo)
4914 return;
4915
4916 if (level <= sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL))
4917 *info = pInfo->levelInfo[level - 1];
4918 else
4919 BuildPlayerLevelInfo(race, class_, level, info);
4920}
void BuildPlayerLevelInfo(uint8 race, uint8 class_, uint8 level, PlayerLevelInfo *plinfo) const
Definition ObjectMgr.cpp:4922
PlayerLevelInfo * levelInfo
Definition Player.h:340

References _playerInfo, BuildPlayerLevelInfo(), CONFIG_MAX_PLAYER_LEVEL, PlayerInfo::levelInfo, MAX_CLASSES, and sRaceMgr.

◆ GetPointOfInterest()

PointOfInterest const * ObjectMgr::GetPointOfInterest ( uint32  id) const
inline
932 {
933 PointOfInterestContainer::const_iterator itr = _pointsOfInterestStore.find(id);
934 if (itr != _pointsOfInterestStore.end())
935 return &itr->second;
936 return nullptr;
937 }
PointOfInterestContainer _pointsOfInterestStore
Definition ObjectMgr.h:1563

References _pointsOfInterestStore.

Referenced by LoadGossipMenuItems().

◆ GetPointOfInterestLocale()

PointOfInterestLocale const * ObjectMgr::GetPointOfInterestLocale ( uint32  poi_id) const
inline
1324 {
1325 PointOfInterestLocaleContainer::const_iterator itr = _pointOfInterestLocaleStore.find(poi_id);
1326 if (itr == _pointOfInterestLocaleStore.end()) return nullptr;
1327 return &itr->second;
1328 }
PointOfInterestLocaleContainer _pointOfInterestLocaleStore
Definition ObjectMgr.h:1677

References _pointOfInterestLocaleStore.

◆ GetQuestForAreaTrigger()

uint32 ObjectMgr::GetQuestForAreaTrigger ( uint32  Trigger_ID) const
inline
845 {
846 QuestAreaTriggerContainer::const_iterator itr = _questAreaTriggerStore.find(Trigger_ID);
847 if (itr != _questAreaTriggerStore.end())
848 return itr->second;
849 return 0;
850 }
QuestAreaTriggerContainer _questAreaTriggerStore
Definition ObjectMgr.h:1547

References _questAreaTriggerStore.

◆ GetQuestGreeting()

QuestGreeting const * ObjectMgr::GetQuestGreeting ( TypeID  type,
uint32  id 
) const
6907{
6908 uint8 typeIndex;
6909 if (type == TYPEID_UNIT)
6910 typeIndex = 0;
6911 else if (type == TYPEID_GAMEOBJECT)
6912 typeIndex = 1;
6913 else
6914 return nullptr;
6915
6916 std::pair<uint32, uint8> pairKey = std::make_pair(id, typeIndex);
6917 QuestGreetingContainer::const_iterator itr = _questGreetingStore.find(pairKey);
6918 if (itr == _questGreetingStore.end())
6919 return nullptr;
6920
6921 return &itr->second;
6922}
@ TYPEID_GAMEOBJECT
Definition ObjectGuid.h:37
@ TYPEID_UNIT
Definition ObjectGuid.h:35
QuestGreetingContainer _questGreetingStore
Definition ObjectMgr.h:1550

References _questGreetingStore, TYPEID_GAMEOBJECT, and TYPEID_UNIT.

◆ GetQuestLocale()

QuestLocale const * ObjectMgr::GetQuestLocale ( uint32  entry) const
inline
1312 {
1313 QuestLocaleContainer::const_iterator itr = _questLocaleStore.find(entry);
1314 if (itr == _questLocaleStore.end()) return nullptr;
1315 return &itr->second;
1316 }
QuestLocaleContainer _questLocaleStore
Definition ObjectMgr.h:1669

References _questLocaleStore.

◆ GetQuestMoneyReward()

uint32 ObjectMgr::GetQuestMoneyReward ( uint8  level,
uint32  questMoneyDifficulty 
) const
10981{
10982 if (questMoneyDifficulty < MAX_QUEST_MONEY_REWARDS)
10983 {
10984 auto const& itr = _questMoneyRewards.find(level);
10985 if (itr != _questMoneyRewards.end())
10986 {
10987 return itr->second.at(questMoneyDifficulty);
10988 }
10989 }
10990
10991 return 0;
10992}
static constexpr uint32 MAX_QUEST_MONEY_REWARDS
Definition ObjectMgr.h:720
QuestMoneyRewardStore _questMoneyRewards
Definition ObjectMgr.h:1701

References _questMoneyRewards, and MAX_QUEST_MONEY_REWARDS.

◆ GetQuestOfferRewardLocale()

QuestOfferRewardLocale const * ObjectMgr::GetQuestOfferRewardLocale ( uint32  entry) const
inline
1330 {
1331 auto itr = _questOfferRewardLocaleStore.find(entry);
1332 if (itr == _questOfferRewardLocaleStore.end()) return nullptr;
1333 return &itr->second;
1334 }
QuestOfferRewardLocaleContainer _questOfferRewardLocaleStore
Definition ObjectMgr.h:1670

References _questOfferRewardLocaleStore.

◆ GetQuestPOIVector()

QuestPOIVector const * ObjectMgr::GetQuestPOIVector ( uint32  questId)
inline
940 {
941 QuestPOIContainer::const_iterator itr = _questPOIStore.find(questId);
942 if (itr != _questPOIStore.end())
943 return &itr->second;
944 return nullptr;
945 }
QuestPOIContainer _questPOIStore
Definition ObjectMgr.h:1565

References _questPOIStore.

◆ GetQuestRequestItemsLocale()

QuestRequestItemsLocale const * ObjectMgr::GetQuestRequestItemsLocale ( uint32  entry) const
inline
1336 {
1337 auto itr = _questRequestItemsLocaleStore.find(entry);
1338 if (itr == _questRequestItemsLocaleStore.end()) return nullptr;
1339 return &itr->second;
1340 }
QuestRequestItemsLocaleContainer _questRequestItemsLocaleStore
Definition ObjectMgr.h:1671

References _questRequestItemsLocaleStore.

◆ GetQuestTemplate()

Quest const * ObjectMgr::GetQuestTemplate ( uint32  quest_id) const
inline
838 {
839 return quest_id < _questTemplatesFast.size() ? _questTemplatesFast[quest_id] : nullptr;
840 }
std::vector< Quest * > _questTemplatesFast
Definition ObjectMgr.h:1541

References _questTemplatesFast.

Referenced by LoadAccessRequirements(), LoadFactionChangeQuests(), LoadQuestAreaTriggers(), LoadQuests(), and LoadScripts().

◆ GetQuestTemplates()

QuestMap const & ObjectMgr::GetQuestTemplates ( ) const
inline
842{ return _questTemplates; }

References _questTemplates.

◆ GetRepRewardRate()

RepRewardRate const * ObjectMgr::GetRepRewardRate ( uint32  factionId) const
inline
904 {
905 RepRewardRateContainer::const_iterator itr = _repRewardRateStore.find(factionId);
906 if (itr != _repRewardRateStore.end())
907 return &itr->second;
908
909 return nullptr;
910 }
RepRewardRateContainer _repRewardRateStore
Definition ObjectMgr.h:1557

References _repRewardRateStore.

◆ GetRepSpilloverTemplate()

RepSpilloverTemplate const * ObjectMgr::GetRepSpilloverTemplate ( uint32  factionId) const
inline
923 {
924 RepSpilloverTemplateContainer::const_iterator itr = _repSpilloverTemplateStore.find(factionId);
925 if (itr != _repSpilloverTemplateStore.end())
926 return &itr->second;
927
928 return nullptr;
929 }
RepSpilloverTemplateContainer _repSpilloverTemplateStore
Definition ObjectMgr.h:1559

References _repSpilloverTemplateStore.

◆ GetReputationOnKilEntry()

ReputationOnKillEntry const * ObjectMgr::GetReputationOnKilEntry ( uint32  id) const
inline
913 {
914 RepOnKillContainer::const_iterator itr = _repOnKillStore.find(id);
915 if (itr != _repOnKillStore.end())
916 return &itr->second;
917 return nullptr;
918 }
RepOnKillContainer _repOnKillStore
Definition ObjectMgr.h:1558

References _repOnKillStore.

◆ GetScriptId()

uint32 ObjectMgr::GetScriptId ( std::string const &  name)
10318{
10319 // use binary search to find the script name in the sorted vector
10320 // assume "" is the first element
10321 if (name.empty())
10322 return 0;
10323
10324 ScriptNameContainer::const_iterator itr = std::lower_bound(_scriptNamesStore.begin(), _scriptNamesStore.end(), name);
10325 if (itr == _scriptNamesStore.end() || (*itr != name))
10326 return 0;
10327
10328 return uint32(itr - _scriptNamesStore.begin());
10329}
ScriptNameContainer _scriptNamesStore
Definition ObjectMgr.h:1582

References _scriptNamesStore.

Referenced by LoadAreaTriggerScripts(), LoadCreatureDataFromDB(), LoadCreatures(), LoadCreatureTemplate(), LoadGameObjectDataFromDB(), LoadGameobjects(), LoadGameObjectTemplate(), LoadInstanceTemplate(), LoadItemTemplates(), and LoadSpellScriptNames().

◆ GetScriptName()

std::string const & ObjectMgr::GetScriptName ( uint32  id) const
10312{
10313 static std::string const empty = "";
10314 return (id < _scriptNamesStore.size()) ? _scriptNamesStore[id] : empty;
10315}

References _scriptNamesStore.

Referenced by ValidateSpellScripts().

◆ GetScriptNames()

ScriptNameContainer & ObjectMgr::GetScriptNames ( )
inline
1447{ return _scriptNamesStore; }

References _scriptNamesStore.

◆ GetSparringData()

CreatureSparringContainer const & ObjectMgr::GetSparringData ( ) const
inline
1239{ return _creatureSparringStore; }
CreatureSparringContainer _creatureSparringStore
Definition ObjectMgr.h:1597

References _creatureSparringStore.

◆ GetSpawnData()

SpawnData const * ObjectMgr::GetSpawnData ( SpawnObjectType  type,
ObjectGuid::LowType  spawnId 
) const
8694{
8695 switch (type)
8696 {
8698 return GetCreatureData(spawnId);
8700 return GetGameObjectData(spawnId);
8701 default:
8702 return nullptr;
8703 }
8704}
@ SPAWN_TYPE_GAMEOBJECT
Definition SpawnData.h:27
@ SPAWN_TYPE_CREATURE
Definition SpawnData.h:26

References GetCreatureData(), GetGameObjectData(), SPAWN_TYPE_CREATURE, and SPAWN_TYPE_GAMEOBJECT.

◆ GetSpawnGroupData()

SpawnGroupTemplateData const * ObjectMgr::GetSpawnGroupData ( uint32  groupId) const
inline
1276 {
1277 auto itr = _spawnGroupDataStore.find(groupId);
1278 return itr != _spawnGroupDataStore.end() ? &itr->second : nullptr;
1279 }

References _spawnGroupDataStore.

◆ GetSpellClickInfoMapBounds()

SpellClickInfoMapBounds ObjectMgr::GetSpellClickInfoMapBounds ( uint32  creature_id) const
inline
1452 {
1453 return _spellClickInfoStore.equal_range(creature_id);
1454 }
SpellClickInfoContainer _spellClickInfoStore
Definition ObjectMgr.h:1584

References _spellClickInfoStore.

◆ GetSpellScriptsBounds()

SpellScriptsBounds ObjectMgr::GetSpellScriptsBounds ( uint32  spell_id)
9493{
9494 return SpellScriptsBounds(_spellScriptsStore.lower_bound(spell_id), _spellScriptsStore.upper_bound(spell_id));
9495}
std::pair< SpellScriptsContainer::iterator, SpellScriptsContainer::iterator > SpellScriptsBounds
Definition ObjectMgr.h:389
SpellScriptsContainer _spellScriptsStore
Definition ObjectMgr.h:1586

References _spellScriptsStore.

◆ GetSummonGroup()

std::vector< TempSummonData > const * ObjectMgr::GetSummonGroup ( uint32  summonerId,
SummonerType  summonerType,
uint8  group 
) const
inline

Gets temp summon data for all creatures of specified group.

Parameters
summonerIdSummoner's entry.
summonerTypeSummoner's type, see SummonerType for available types.
groupId of required group.
Returns
null if group was not found, otherwise reference to the creature group data
1207 {
1208 TempSummonDataContainer::const_iterator itr = _tempSummonDataStore.find(TempSummonGroupKey(summonerId, summonerType, group));
1209 if (itr != _tempSummonDataStore.end())
1210 return &itr->second;
1211
1212 return nullptr;
1213 }
TempSummonDataContainer _tempSummonDataStore
Stores temp summon data grouped by summoner's entry, summoner's type and group id.
Definition ObjectMgr.h:1660

References _tempSummonDataStore.

◆ GetTaxiMountDisplayId()

uint32 ObjectMgr::GetTaxiMountDisplayId ( uint32  id,
TeamId  teamId,
bool  allowed_alt_team = false 
)
7248{
7249 CreatureModel mountModel;
7250 CreatureTemplate const* mount_info = nullptr;
7251
7252 // select mount creature id
7253 TaxiNodesEntry const* node = sTaxiNodesStore.LookupEntry(id);
7254 if (node)
7255 {
7256 uint32 mount_entry = node->MountCreatureID[teamId == TEAM_ALLIANCE ? 1 : 0];
7257
7258 // Fix for Alliance not being able to use Acherus taxi
7259 // only one mount type for both sides
7260 if (mount_entry == 0 && allowed_alt_team)
7261 {
7262 // Simply reverse the selection. At least one team in theory should have a valid mount ID to choose.
7263 mount_entry = node->MountCreatureID[teamId];
7264 }
7265
7266 mount_info = GetCreatureTemplate(mount_entry);
7267 if (mount_info)
7268 {
7269 CreatureModel const* model = mount_info->GetRandomValidModel();
7270 if (!model)
7271 {
7272 LOG_ERROR("sql.sql", "No displayid found for the taxi mount with the entry {}! Can't load it!", mount_entry);
7273 return 0;
7274 }
7275 mountModel = *model;
7276 }
7277 }
7278
7279 // minfo is not actually used but the mount_id was updated
7280 GetCreatureModelRandomGender(&mountModel, mount_info);
7281
7282 return mountModel.CreatureDisplayID;
7283}
CreatureModelInfo const * GetCreatureModelRandomGender(CreatureModel *model, CreatureTemplate const *creatureTemplate) const
Definition ObjectMgr.cpp:1677
CreatureModel const * GetRandomValidModel() const
Definition Creature.cpp:120

References CreatureModel::CreatureDisplayID, GetCreatureModelRandomGender(), GetCreatureTemplate(), CreatureTemplate::GetRandomValidModel(), LOG_ERROR, TaxiNodesEntry::MountCreatureID, sTaxiNodesStore, and TEAM_ALLIANCE.

◆ GetTaxiPath()

void ObjectMgr::GetTaxiPath ( uint32  source,
uint32  destination,
uint32 path,
uint32 cost 
)
7224{
7225 TaxiPathSetBySource::iterator src_i = sTaxiPathSetBySource.find(source);
7226 if (src_i == sTaxiPathSetBySource.end())
7227 {
7228 path = 0;
7229 cost = 0;
7230 return;
7231 }
7232
7233 TaxiPathSetForSource& pathSet = src_i->second;
7234
7235 TaxiPathSetForSource::iterator dest_i = pathSet.find(destination);
7236 if (dest_i == pathSet.end())
7237 {
7238 path = 0;
7239 cost = 0;
7240 return;
7241 }
7242
7243 cost = dest_i->second->price;
7244 path = dest_i->second->ID;
7245}
TaxiPathSetBySource sTaxiPathSetBySource
Definition DBCStores.cpp:183
std::map< uint32, TaxiPathEntry const * > TaxiPathSetForSource
Definition DBCStructure.h:2242

References TaxiNodesEntry::ID, and sTaxiPathSetBySource.

◆ GetTrainer()

Trainer::Trainer * ObjectMgr::GetTrainer ( uint32  creatureId)
9905{
9906 auto itr = _creatureDefaultTrainers.find(creatureId);
9907 if (itr != _creatureDefaultTrainers.end())
9908 return Acore::Containers::MapGetValuePtr(_trainers, itr->second);
9909
9910 return nullptr;
9911}
std::unordered_map< uint32, uint32 > _creatureDefaultTrainers
Definition ObjectMgr.h:1682
std::unordered_map< uint32, Trainer::Trainer > _trainers
Definition ObjectMgr.h:1680

References _creatureDefaultTrainers, _trainers, and Acore::Containers::MapGetValuePtr().

◆ GetVehicleAccessoryList()

VehicleAccessoryList const * ObjectMgr::GetVehicleAccessoryList ( Vehicle veh) const
10828{
10829 if (Creature* cre = veh->GetBase()->ToCreature())
10830 {
10831 // Give preference to GUID-based accessories
10832 VehicleAccessoryContainer::const_iterator itr = _vehicleAccessoryStore.find(cre->GetSpawnId());
10833 if (itr != _vehicleAccessoryStore.end())
10834 return &itr->second;
10835 }
10836
10837 // Otherwise return entry-based
10838 VehicleAccessoryContainer::const_iterator itr = _vehicleTemplateAccessoryStore.find(veh->GetCreatureEntry());
10839 if (itr != _vehicleTemplateAccessoryStore.end())
10840 return &itr->second;
10841 return nullptr;
10842}
VehicleAccessoryContainer _vehicleAccessoryStore
Definition ObjectMgr.h:1589
VehicleAccessoryContainer _vehicleTemplateAccessoryStore
Definition ObjectMgr.h:1588
Creature * ToCreature()
Definition Object.h:206
Unit * GetBase() const
May be called from scripts.
Definition Vehicle.h:37
uint32 GetCreatureEntry() const
Definition Vehicle.h:39

References _vehicleAccessoryStore, _vehicleTemplateAccessoryStore, Vehicle::GetBase(), Vehicle::GetCreatureEntry(), and Object::ToCreature().

◆ GetVehicleSeatAddon()

VehicleSeatAddon const * ObjectMgr::GetVehicleSeatAddon ( uint32  seatId) const
inline
1506 {
1507 VehicleSeatAddonContainer::const_iterator itr = _vehicleSeatAddonStore.find(seatId);
1508 if (itr == _vehicleSeatAddonStore.end())
1509 return nullptr;
1510
1511 return &itr->second;
1512 }
VehicleSeatAddonContainer _vehicleSeatAddonStore
Definition ObjectMgr.h:1590

References _vehicleSeatAddonStore.

◆ GetXPForLevel()

uint32 ObjectMgr::GetXPForLevel ( uint8  level) const
8106{
8107 if (level < _playerXPperLevel.size())
8108 return _playerXPperLevel[level];
8109 return 0;
8110}
PlayerXPperLevel _playerXPperLevel
Definition ObjectMgr.h:1619

References _playerXPperLevel.

◆ InitializeSpellInfoPrecomputedData()

void ObjectMgr::InitializeSpellInfoPrecomputedData ( )
6376{
6377 uint32 limit = sSpellStore.GetNumRows();
6378 for(uint32 i = 0; i <= limit; ++i)
6379 if (SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(i))
6380 {
6381 const_cast<SpellInfo*>(spellInfo)->SetStackableWithRanks(spellInfo->ComputeIsStackableWithRanks());
6382 const_cast<SpellInfo*>(spellInfo)->SetCritCapable(spellInfo->ComputeIsCritCapable());
6383 const_cast<SpellInfo*>(spellInfo)->SetSpellValid(SpellMgr::ComputeIsSpellValid(spellInfo, false));
6384 }
6385}
DBCStorage< SpellEntry > sSpellStore(SpellEntryfmt)
Definition SpellInfo.h:340
static bool ComputeIsSpellValid(SpellInfo const *spellInfo, bool msg=true)
Some checks for spells, to prevent adding deprecated/broken spells for trainers, spell book,...
Definition SpellMgr.cpp:417

References SpellMgr::ComputeIsSpellValid(), sSpellMgr, and sSpellStore.

◆ instance()

ObjectMgr * ObjectMgr::instance ( )
static
377{
378 static ObjectMgr instance;
379 return &instance;
380}
Definition ObjectMgr.h:727
static ObjectMgr * instance()
Definition ObjectMgr.cpp:376

References instance().

Referenced by instance().

◆ IsGameObjectStaticTransport()

bool ObjectMgr::IsGameObjectStaticTransport ( uint32  entry)
10808{
10809 GameObjectTemplate const* goinfo = GetGameObjectTemplate(entry);
10810 return goinfo && goinfo->type == GAMEOBJECT_TYPE_TRANSPORT;
10811}
@ GAMEOBJECT_TYPE_TRANSPORT
Definition SharedDefines.h:1577

References GAMEOBJECT_TYPE_TRANSPORT, GetGameObjectTemplate(), and GameObjectTemplate::type.

Referenced by AddGOData().

◆ IsProfanityName()

bool ObjectMgr::IsProfanityName ( std::string_view  name) const
8979{
8980 // pussywizard
8981 if (name.size() >= 2 && (name[name.size() - 2] == 'G' || name[name.size() - 2] == 'g') && (name[name.size() - 1] == 'M' || name[name.size() - 1] == 'm'))
8982 return true;
8983
8984 std::wstring wstr;
8985 if (!Utf8toWStr (name, wstr))
8986 return false;
8987
8988 wstrToLower(wstr);
8989
8990 return _profanityNamesStore.find(wstr) != _profanityNamesStore.end();
8991}

References _profanityNamesStore, Utf8toWStr(), and wstrToLower().

Referenced by AddProfanityPlayerName().

◆ IsReservedName()

bool ObjectMgr::IsReservedName ( std::string_view  name) const
8876{
8877 // pussywizard
8878 if (name.size() >= 2 && (name[name.size() - 2] == 'G' || name[name.size() - 2] == 'g') && (name[name.size() - 1] == 'M' || name[name.size() - 1] == 'm'))
8879 return true;
8880
8881 std::wstring wstr;
8882 if (!Utf8toWStr (name, wstr))
8883 return false;
8884
8885 wstrToLower(wstr);
8886
8887 return _reservedNamesStore.find(wstr) != _reservedNamesStore.end();
8888}

References _reservedNamesStore, Utf8toWStr(), and wstrToLower().

Referenced by AddReservedPlayerName().

◆ IsTavernAreaTrigger()

bool ObjectMgr::IsTavernAreaTrigger ( uint32  triggerID,
uint32  faction 
) const
inline
853 {
854 auto itr = _tavernAreaTriggerStore.find(triggerID);
855 if (itr != _tavernAreaTriggerStore.end())
856 {
857 return (itr->second & faction) != 0;
858 }
859
860 return false;
861 }
TavernAreaTriggerContainer _tavernAreaTriggerStore
Definition ObjectMgr.h:1548

References _tavernAreaTriggerStore.

◆ IsTransportMap()

bool ObjectMgr::IsTransportMap ( uint32  mapId) const
inline
1503{ return _transportMaps.count(mapId) != 0; }
std::set< uint32 > _transportMaps
Definition ObjectMgr.h:1695

References _transportMaps.

◆ IsValidChannelName()

bool ObjectMgr::IsValidChannelName ( std::string const &  name)
static
9152{
9153 std::wstring wname;
9154 if (!Utf8toWStr(name, wname))
9155 return false;
9156
9157 if (wname.size() > MAX_CHANNEL_NAME)
9158 return false;
9159
9160 uint32 strictMask = sWorld->getIntConfig(CONFIG_STRICT_CHANNEL_NAMES);
9161
9162 return isValidString(wname, strictMask, true);
9163}
#define MAX_CHANNEL_NAME
Definition ObjectMgr.h:688
@ CONFIG_STRICT_CHANNEL_NAMES
Definition WorldConfig.h:179

References CONFIG_STRICT_CHANNEL_NAMES, isValidString(), MAX_CHANNEL_NAME, sWorld, and Utf8toWStr().

◆ IsValidCharterName()

bool ObjectMgr::IsValidCharterName ( std::string_view  name)
static
9126{
9127 std::wstring wname;
9128 if (!Utf8toWStr(name, wname))
9129 return false;
9130
9131 if (wname.size() > MAX_CHARTER_NAME)
9132 return false;
9133
9134 uint32 minName = sWorld->getIntConfig(CONFIG_MIN_CHARTER_NAME);
9135 if (wname.size() < minName)
9136 return false;
9137
9138 // Check Reserved Name
9139 if (sObjectMgr->IsReservedName(name))
9140 return false;
9141
9142 // Check Profanity Name
9143 if (sObjectMgr->IsProfanityName(name))
9144 return false;
9145
9146 uint32 strictMask = sWorld->getIntConfig(CONFIG_STRICT_CHARTER_NAMES);
9147
9148 return isValidString(wname, strictMask, true);
9149}
#define MAX_CHARTER_NAME
Definition ObjectMgr.h:687
@ CONFIG_MIN_CHARTER_NAME
Definition WorldConfig.h:182
@ CONFIG_STRICT_CHARTER_NAMES
Definition WorldConfig.h:178

References CONFIG_MIN_CHARTER_NAME, CONFIG_STRICT_CHARTER_NAMES, isValidString(), MAX_CHARTER_NAME, sObjectMgr, sWorld, and Utf8toWStr().

Referenced by WorldSession::HandlePetitionBuyOpcode(), WorldSession::HandlePetitionRenameOpcode(), ArenaTeam::SetName(), and Guild::SetName().

◆ IsVendorItemValid()

bool ObjectMgr::IsVendorItemValid ( uint32  vendor_entry,
uint32  item,
uint32  maxcount,
uint32  ptime,
uint32  ExtendedCost,
Player player = nullptr,
std::set< uint32 > *  skip_vendors = nullptr,
uint32  ORnpcflag = 0 
) const
10176{
10177 /*
10178 CreatureTemplate const* cInfo = GetCreatureTemplate(vendor_entry);
10179 if (!cInfo)
10180 {
10181 if (player)
10182 ChatHandler(player->GetSession()).SendSysMessage(LANG_COMMAND_VENDORSELECTION);
10183 else
10184 LOG_ERROR("sql.sql", "Table `(game_event_)npc_vendor` have data for not existed creature template (Entry: {}), ignore", vendor_entry);
10185 return false;
10186 }
10187
10188 if (!((cInfo->npcflag | ORnpcflag) & UNIT_NPC_FLAG_VENDOR))
10189 {
10190 if (!skip_vendors || skip_vendors->count(vendor_entry) == 0)
10191 {
10192 if (player)
10193 ChatHandler(player->GetSession()).SendSysMessage(LANG_COMMAND_VENDORSELECTION);
10194 else
10195 LOG_ERROR("sql.sql", "Table `(game_event_)npc_vendor` have data for not creature template (Entry: {}) without vendor flag, ignore", vendor_entry);
10196
10197 if (skip_vendors)
10198 skip_vendors->insert(vendor_entry);
10199 }
10200 return false;
10201 }
10202 */
10203
10204 if (!sObjectMgr->GetItemTemplate(item_id))
10205 {
10206 if (player)
10208 else
10209 LOG_ERROR("sql.sql", "Table `(game_event_)npc_vendor` for Vendor (Entry: {}) have in item list non-existed item ({}), ignore", vendor_entry, item_id);
10210 return false;
10211 }
10212
10213 if (ExtendedCost && !sItemExtendedCostStore.LookupEntry(ExtendedCost))
10214 {
10215 if (player)
10217 else
10218 LOG_ERROR("sql.sql", "Table `(game_event_)npc_vendor` have Item (Entry: {}) with wrong ExtendedCost ({}) for vendor ({}), ignore", item_id, ExtendedCost, vendor_entry);
10219 return false;
10220 }
10221
10222 if (maxcount > 0 && incrtime == 0)
10223 {
10224 if (player)
10225 ChatHandler(player->GetSession()).PSendSysMessage("MaxCount != 0 ({}) but IncrTime == 0", maxcount);
10226 else
10227 LOG_ERROR("sql.sql", "Table `(game_event_)npc_vendor` has `maxcount` ({}) for item {} of vendor (Entry: {}) but `incrtime`=0, ignore", maxcount, item_id, vendor_entry);
10228 return false;
10229 }
10230 else if (maxcount == 0 && incrtime > 0)
10231 {
10232 if (player)
10233 ChatHandler(player->GetSession()).PSendSysMessage("MaxCount == 0 but IncrTime<>= 0");
10234 else
10235 LOG_ERROR("sql.sql", "Table `(game_event_)npc_vendor` has `maxcount`=0 for item {} of vendor (Entry: {}) but `incrtime`<>0, ignore", item_id, vendor_entry);
10236 return false;
10237 }
10238
10239 VendorItemData const* vItems = GetNpcVendorItemList(vendor_entry);
10240 if (!vItems)
10241 return true; // later checks for non-empty lists
10242
10243 if (vItems->FindItemCostPair(item_id, ExtendedCost))
10244 {
10245 if (player)
10246 ChatHandler(player->GetSession()).PSendSysMessage(LANG_ITEM_ALREADY_IN_LIST, item_id, ExtendedCost);
10247 else
10248 LOG_ERROR("sql.sql", "Table `npc_vendor` has duplicate items {} (with extended cost {}) for vendor (Entry: {}), ignoring", item_id, ExtendedCost, vendor_entry);
10249 return false;
10250 }
10251
10252 return true;
10253}
DBCStorage< ItemExtendedCostEntry > sItemExtendedCostStore(ItemExtendedCostEntryfmt)
@ LANG_ITEM_ALREADY_IN_LIST
Definition Language.h:253
@ LANG_ITEM_NOT_FOUND
Definition Language.h:250
@ LANG_EXTENDED_COST_NOT_EXIST
Definition Language.h:378
Definition Chat.h:37
void PSendSysMessage(std::string_view str, bool escapeCharacters=false)
Definition Chat.cpp:211
VendorItemData const * GetNpcVendorItemList(uint32 entry) const
Definition ObjectMgr.h:1433
WorldSession * GetSession() const
Definition Player.h:2019
VendorItem const * FindItemCostPair(uint32 item_id, uint32 extendedCost) const
Definition Creature.cpp:104

References VendorItemData::FindItemCostPair(), GetNpcVendorItemList(), Player::GetSession(), LANG_EXTENDED_COST_NOT_EXIST, LANG_ITEM_ALREADY_IN_LIST, LANG_ITEM_NOT_FOUND, LOG_ERROR, ChatHandler::PSendSysMessage(), sItemExtendedCostStore, and sObjectMgr.

Referenced by LoadReferenceVendor(), and LoadVendors().

◆ LoadAccessRequirements()

void ObjectMgr::LoadAccessRequirements ( )
7397{
7398 uint32 oldMSTime = getMSTime();
7399
7400 if (!_accessRequirementStore.empty())
7401 {
7402 for (DungeonProgressionRequirementsContainer::iterator itr = _accessRequirementStore.begin(); itr != _accessRequirementStore.end(); ++itr)
7403 {
7404 std::unordered_map<uint8, DungeonProgressionRequirements*> difficulties = itr->second;
7405 for (auto difficultiesItr = difficulties.begin(); difficultiesItr != difficulties.end(); ++difficultiesItr)
7406 {
7407 for (auto questItr = difficultiesItr->second->quests.begin(); questItr != difficultiesItr->second->quests.end(); ++questItr)
7408 {
7409 delete* questItr;
7410 }
7411
7412 for (auto achievementItr = difficultiesItr->second->achievements.begin(); achievementItr != difficultiesItr->second->achievements.end(); ++achievementItr)
7413 {
7414 delete* achievementItr;
7415 }
7416
7417 for (auto itemsItr = difficultiesItr->second->items.begin(); itemsItr != difficultiesItr->second->items.end(); ++itemsItr)
7418 {
7419 delete* itemsItr;
7420 }
7421
7422 delete difficultiesItr->second;
7423 }
7424 }
7425
7426 _accessRequirementStore.clear(); // need for reload case
7427 }
7428 // 0 1 2 3 4 5
7429 QueryResult access_template_result = WorldDatabase.Query("SELECT id, map_id, difficulty, min_level, max_level, min_avg_item_level FROM dungeon_access_template");
7430 if (!access_template_result)
7431 {
7432 LOG_WARN("server.loading", ">> Loaded 0 access requirement definitions. DB table `dungeon_access_template` is empty.");
7433 LOG_INFO("server.loading", " ");
7434 return;
7435 }
7436
7437 uint32 count = 0;
7438 uint32 countProgressionRequirements = 0;
7439
7440 do
7441 {
7442 Field* fields = access_template_result->Fetch();
7443
7444 //Get the common variables for the access requirements
7445 uint8 dungeon_access_id = fields[0].Get<uint8>();
7446 uint32 mapid = fields[1].Get<uint32>();
7447 uint8 difficulty = fields[2].Get<uint8>();
7448
7449 //Set up the access requirements
7451 ar->levelMin = fields[3].Get<uint8>();
7452 ar->levelMax = fields[4].Get<uint8>();
7453 ar->reqItemLevel = fields[5].Get<uint16>();
7454
7455 // 0 1 2 3 4 6
7456 QueryResult progression_requirements_results = WorldDatabase.Query("SELECT requirement_type, requirement_id, requirement_note, faction, priority, leader_only FROM dungeon_access_requirements where dungeon_access_id = {}", dungeon_access_id);
7457 if (progression_requirements_results)
7458 {
7459 do
7460 {
7461 Field* progression_requirement_row = progression_requirements_results->Fetch();
7462
7463 const uint8 requirement_type = progression_requirement_row[0].Get<uint8>();
7464 const uint32 requirement_id = progression_requirement_row[1].Get<uint32>();
7465 const std::string requirement_note = progression_requirement_row[2].Get<std::string>();
7466 const uint8 requirement_faction = progression_requirement_row[3].Get<uint8>();
7467 const uint8 requirement_priority = progression_requirement_row[4].IsNull() ? UINT8_MAX : progression_requirement_row[4].Get<uint8>();
7468 const bool requirement_checkLeaderOnly = progression_requirement_row[5].Get<bool>();
7469
7470 ProgressionRequirement* progression_requirement = new ProgressionRequirement();
7471 progression_requirement->id = requirement_id;
7472 progression_requirement->note = requirement_note;
7473 progression_requirement->faction = (TeamId)requirement_faction;
7474 progression_requirement->priority = requirement_priority;
7475 progression_requirement->checkLeaderOnly = requirement_checkLeaderOnly;
7476
7477 std::vector<ProgressionRequirement*>* currentRequirementsList = nullptr;
7478
7479 switch (requirement_type)
7480 {
7481 case 0:
7482 {
7483 //Achievement
7484 if (!sAchievementStore.LookupEntry(progression_requirement->id))
7485 {
7486 LOG_ERROR("sql.sql", "Required achievement {} for faction {} does not exist for map {} difficulty {}, remove or fix this achievement requirement.", progression_requirement->id, requirement_faction, mapid, difficulty);
7487 break;
7488 }
7489
7490 currentRequirementsList = &ar->achievements;
7491 break;
7492 }
7493 case 1:
7494 {
7495 //Quest
7496 if (!GetQuestTemplate(progression_requirement->id))
7497 {
7498 LOG_ERROR("sql.sql", "Required quest {} for faction {} does not exist for map {} difficulty {}, remove or fix this quest requirement.", progression_requirement->id, requirement_faction, mapid, difficulty);
7499 break;
7500 }
7501
7502 currentRequirementsList = &ar->quests;
7503 break;
7504 }
7505 case 2:
7506 {
7507 //Item
7508 ItemTemplate const* pProto = GetItemTemplate(progression_requirement->id);
7509 if (!pProto)
7510 {
7511 LOG_ERROR("sql.sql", "Required item {} for faction {} does not exist for map {} difficulty {}, remove or fix this item requirement.", progression_requirement->id, requirement_faction, mapid, difficulty);
7512 break;
7513 }
7514
7515 currentRequirementsList = &ar->items;
7516 break;
7517 }
7518 default:
7519 LOG_ERROR("sql.sql", "requirement_type of {} is not valid for map {} difficulty {}. Please use 0 for achievements, 1 for quest, 2 for items or remove this entry from the db.", requirement_type, mapid, difficulty);
7520 break;
7521 }
7522
7523 //Check if array is valid and delete the progression requirement
7524 if (!currentRequirementsList)
7525 {
7526 delete progression_requirement;
7527 continue;
7528 }
7529
7530 //Insert into the array
7531 if (currentRequirementsList->size() > requirement_priority)
7532 {
7533 currentRequirementsList->insert(currentRequirementsList->begin() + requirement_priority, progression_requirement);
7534 }
7535 else
7536 {
7537 currentRequirementsList->push_back(progression_requirement);
7538 }
7539
7540 } while (progression_requirements_results->NextRow());
7541 }
7542
7543 //Sort all arrays for priority
7544 auto sortFunction = [](const ProgressionRequirement* const a, const ProgressionRequirement* const b) {return a->priority > b->priority; };
7545 std::sort(ar->achievements.begin(), ar->achievements.end(), sortFunction);
7546 std::sort(ar->quests.begin(), ar->quests.end(), sortFunction);
7547 std::sort(ar->items.begin(), ar->items.end(), sortFunction);
7548
7549 countProgressionRequirements += ar->achievements.size();
7550 countProgressionRequirements += ar->quests.size();
7551 countProgressionRequirements += ar->items.size();
7552 count++;
7553
7554 _accessRequirementStore[mapid][difficulty] = ar;
7555 } while (access_template_result->NextRow());
7556
7557 LOG_INFO("server.loading", ">> Loaded {} Rows From dungeon_access_template And {} Rows From dungeon_access_requirements in {} ms", count, countProgressionRequirements, GetMSTimeDiffToNow(oldMSTime));
7558 LOG_INFO("server.loading", " ");
7559}
DBCStorage< AchievementEntry > sAchievementStore(Achievementfmt)
std::shared_ptr< ResultSet > QueryResult
Definition DatabaseEnvFwd.h:27
#define LOG_WARN(filterType__,...)
Definition Log.h:162
TeamId
Definition SharedDefines.h:747
uint32 GetMSTimeDiffToNow(uint32 oldMSTime)
Definition Timer.h:131
uint32 getMSTime()
Definition Timer.h:103
Class used to access individual fields of database query result.
Definition Field.h:98
bool IsNull() const
Definition Field.h:106
std::enable_if_t< std::is_arithmetic_v< T >, T > Get() const
Definition Field.h:112
ItemTemplate const * GetItemTemplate(uint32 entry)
Definition ObjectMgr.cpp:3851
Quest const * GetQuestTemplate(uint32 quest_id) const
Definition ObjectMgr.h:837
Definition Player.h:935
Definition ItemTemplate.h:619
Definition Player.h:926
uint32 priority
Definition Player.h:930

References _accessRequirementStore, Field::Get(), GetItemTemplate(), getMSTime(), GetMSTimeDiffToNow(), GetQuestTemplate(), Field::IsNull(), LOG_ERROR, LOG_INFO, LOG_WARN, ProgressionRequirement::priority, sAchievementStore, and WorldDatabase.

◆ LoadAcoreStrings()

bool ObjectMgr::LoadAcoreStrings ( )
9359{
9360 uint32 oldMSTime = getMSTime();
9361
9362 _acoreStringStore.clear(); // for reload case
9363 QueryResult result = WorldDatabase.Query("SELECT entry, content_default, locale_koKR, locale_frFR, locale_deDE, locale_zhCN, locale_zhTW, locale_esES, locale_esMX, locale_ruRU FROM acore_string");
9364 if (!result)
9365 {
9366 LOG_WARN("server.loading", ">> Loaded 0 acore strings. DB table `acore_strings` is empty.");
9367 LOG_INFO("server.loading", " ");
9368 return false;
9369 }
9370
9371 do
9372 {
9373 Field* fields = result->Fetch();
9374
9375 uint32 entry = fields[0].Get<uint32>();
9376
9377 AcoreString& data = _acoreStringStore[entry];
9378
9379 data.Content.resize(DEFAULT_LOCALE + 1);
9380
9381 for (uint8 i = 0; i < TOTAL_LOCALES; ++i)
9382 AddLocaleString(fields[i + 1].Get<std::string>(), LocaleConstant(i), data.Content);
9383 } while (result->NextRow());
9384
9385 LOG_INFO("server.loading", ">> Loaded {} Acore Strings in {} ms", (uint32)_acoreStringStore.size(), GetMSTimeDiffToNow(oldMSTime));
9386 LOG_INFO("server.loading", " ");
9387
9388 return true;
9389}
LocaleConstant
Definition Common.h:117
@ TOTAL_LOCALES
Definition Common.h:128
static void AddLocaleString(std::string &&s, LocaleConstant locale, std::vector< std::string > &data)
Definition ObjectMgr.cpp:382

References _acoreStringStore, AddLocaleString(), AcoreString::Content, DEFAULT_LOCALE, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_INFO, LOG_WARN, TOTAL_LOCALES, and WorldDatabase.

◆ LoadAreaTriggers()

void ObjectMgr::LoadAreaTriggers ( )
7286{
7287 uint32 oldMSTime = getMSTime();
7288
7289 _areaTriggerStore.clear();
7290
7291 QueryResult result = WorldDatabase.Query("SELECT entry, map, x, y, z, radius, length, width, height, orientation FROM areatrigger");
7292
7293 if (!result)
7294 {
7295 LOG_WARN("server.loading", ">> Loaded 0 area trigger definitions. DB table `areatrigger` is empty.");
7296 LOG_INFO("server.loading", " ");
7297 return;
7298 }
7299
7300 uint32 count = 0;
7301
7302 do
7303 {
7304 Field* fields = result->Fetch();
7305
7306 ++count;
7307
7308 AreaTrigger at;
7309
7310 at.entry = fields[0].Get<uint32>();
7311 at.map = fields[1].Get<uint32>();
7312 at.x = fields[2].Get<float>();
7313 at.y = fields[3].Get<float>();
7314 at.z = fields[4].Get<float>();
7315 at.radius = fields[5].Get<float>();
7316 at.length = fields[6].Get<float>();
7317 at.width = fields[7].Get<float>();
7318 at.height = fields[8].Get<float>();
7319 at.orientation = fields[9].Get<float>();
7320
7321 MapEntry const* mapEntry = sMapStore.LookupEntry(at.map);
7322 if (!mapEntry)
7323 {
7324 LOG_ERROR("sql.sql", "Area trigger (ID:{}) map (ID: {}) does not exist in `Map.dbc`.", at.entry, at.map);
7325 continue;
7326 }
7327
7328 _areaTriggerStore[at.entry] = at;
7329 } while (result->NextRow());
7330
7331 LOG_INFO("server.loading", ">> Loaded {} Area Trigger Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
7332 LOG_INFO("server.loading", " ");
7333}
float height
Definition ObjectMgr.h:430
float x
Definition ObjectMgr.h:424
float y
Definition ObjectMgr.h:425
float orientation
Definition ObjectMgr.h:431
float length
Definition ObjectMgr.h:428
uint32 entry
Definition ObjectMgr.h:422
float radius
Definition ObjectMgr.h:427
float z
Definition ObjectMgr.h:426
float width
Definition ObjectMgr.h:429

References _areaTriggerStore, AreaTrigger::entry, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), AreaTrigger::height, AreaTrigger::length, LOG_ERROR, LOG_INFO, LOG_WARN, AreaTrigger::map, AreaTrigger::orientation, AreaTrigger::radius, sMapStore, AreaTrigger::width, WorldDatabase, AreaTrigger::x, AreaTrigger::y, and AreaTrigger::z.

◆ LoadAreaTriggerScripts()

void ObjectMgr::LoadAreaTriggerScripts ( )
7139{
7140 uint32 oldMSTime = getMSTime();
7141
7142 _areaTriggerScriptStore.clear(); // need for reload case
7143 QueryResult result = WorldDatabase.Query("SELECT entry, ScriptName FROM areatrigger_scripts");
7144
7145 if (!result)
7146 {
7147 LOG_WARN("server.loading", ">> Loaded 0 Areatrigger Scripts. DB Table `areatrigger_scripts` Is Empty.");
7148 LOG_INFO("server.loading", " ");
7149 return;
7150 }
7151
7152 uint32 count = 0;
7153
7154 do
7155 {
7156 ++count;
7157
7158 Field* fields = result->Fetch();
7159
7160 uint32 Trigger_ID = fields[0].Get<uint32>();
7161 std::string scriptName = fields[1].Get<std::string>();
7162
7163 AreaTrigger const* atEntry = GetAreaTrigger(Trigger_ID);
7164 if (!atEntry)
7165 {
7166 LOG_ERROR("sql.sql", "Area trigger (ID:{}) does not exist in `AreaTrigger.dbc`.", Trigger_ID);
7167 continue;
7168 }
7169 _areaTriggerScriptStore[Trigger_ID] = GetScriptId(scriptName);
7170 } while (result->NextRow());
7171
7172 LOG_INFO("server.loading", ">> Loaded {} Areatrigger Scripts in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
7173 LOG_INFO("server.loading", " ");
7174}
uint32 GetScriptId(std::string const &name)
Definition ObjectMgr.cpp:10317

References _areaTriggerScriptStore, Field::Get(), GetAreaTrigger(), getMSTime(), GetMSTimeDiffToNow(), GetScriptId(), LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadAreaTriggerTeleports()

void ObjectMgr::LoadAreaTriggerTeleports ( )
7336{
7337 uint32 oldMSTime = getMSTime();
7338
7339 _areaTriggerTeleportStore.clear(); // need for reload case
7340
7341 // 0 1 2 3 4 5
7342 QueryResult result = WorldDatabase.Query("SELECT ID, target_map, target_position_x, target_position_y, target_position_z, target_orientation FROM areatrigger_teleport");
7343
7344 if (!result)
7345 {
7346 LOG_WARN("server.loading", ">> Loaded 0 area trigger teleport definitions. DB table `areatrigger_teleport` is empty.");
7347 LOG_INFO("server.loading", " ");
7348 return;
7349 }
7350
7351 uint32 count = 0;
7352
7353 do
7354 {
7355 Field* fields = result->Fetch();
7356
7357 ++count;
7358
7359 uint32 Trigger_ID = fields[0].Get<uint32>();
7360
7362
7363 at.target_mapId = fields[1].Get<uint16>();
7364 at.target_X = fields[2].Get<float>();
7365 at.target_Y = fields[3].Get<float>();
7366 at.target_Z = fields[4].Get<float>();
7367 at.target_Orientation = fields[5].Get<float>();
7368
7369 AreaTrigger const* atEntry = GetAreaTrigger(Trigger_ID);
7370 if (!atEntry)
7371 {
7372 LOG_ERROR("sql.sql", "Area trigger (ID:{}) does not exist in `AreaTrigger.dbc`.", Trigger_ID);
7373 continue;
7374 }
7375
7376 MapEntry const* mapEntry = sMapStore.LookupEntry(at.target_mapId);
7377 if (!mapEntry)
7378 {
7379 LOG_ERROR("sql.sql", "Area trigger (ID:{}) target map (ID: {}) does not exist in `Map.dbc`.", Trigger_ID, at.target_mapId);
7380 continue;
7381 }
7382
7383 if (at.target_X == 0 && at.target_Y == 0 && at.target_Z == 0)
7384 {
7385 LOG_ERROR("sql.sql", "Area trigger (ID:{}) target coordinates not provided.", Trigger_ID);
7386 continue;
7387 }
7388
7389 _areaTriggerTeleportStore[Trigger_ID] = at;
7390 } while (result->NextRow());
7391
7392 LOG_INFO("server.loading", ">> Loaded {} Area Trigger Teleport Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
7393 LOG_INFO("server.loading", " ");
7394}
Definition ObjectMgr.h:412
uint32 target_mapId
Definition ObjectMgr.h:413

References _areaTriggerTeleportStore, Field::Get(), GetAreaTrigger(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sMapStore, AreaTriggerTeleport::target_mapId, and WorldDatabase.

◆ LoadBroadcastTextLocales()

void ObjectMgr::LoadBroadcastTextLocales ( )
10417{
10418 uint32 oldMSTime = getMSTime();
10419
10420 // 0 1 2 3
10421 QueryResult result = WorldDatabase.Query("SELECT ID, locale, MaleText, FemaleText FROM broadcast_text_locale");
10422
10423 if (!result)
10424 {
10425 LOG_WARN("server.loading", ">> Loaded 0 broadcast text locales. DB table `broadcast_text_locale` is empty.");
10426 LOG_INFO("server.loading", " ");
10427 return;
10428 }
10429
10430 uint32 locales_count = 0;
10431 do
10432 {
10433 Field* fields = result->Fetch();
10434
10435 uint32 id = fields[0].Get<uint32>();
10436
10437 BroadcastTextContainer::iterator bct = _broadcastTextStore.find(id);
10438 if (bct == _broadcastTextStore.end())
10439 {
10440 LOG_ERROR("sql.sql", "BroadcastText (Id: {}) found in table `broadcast_text_locale` but does not exist in `broadcast_text`. Skipped!", id);
10441 continue;
10442 }
10443
10444 LocaleConstant locale = GetLocaleByName(fields[1].Get<std::string>());
10445 if (locale == LOCALE_enUS)
10446 continue;
10447
10448 AddLocaleString(fields[2].Get<std::string>(), locale, bct->second.MaleText);
10449 AddLocaleString(fields[3].Get<std::string>(), locale, bct->second.FemaleText);
10450 locales_count++;
10451 } while (result->NextRow());
10452
10453 LOG_INFO("server.loading", ">> Loaded {} Broadcast Text Locales in {} ms", locales_count, GetMSTimeDiffToNow(oldMSTime));
10454 LOG_INFO("server.loading", " ");
10455}
LocaleConstant GetLocaleByName(const std::string &name)
Definition Common.cpp:42

References _broadcastTextStore, AddLocaleString(), Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadBroadcastTexts()

void ObjectMgr::LoadBroadcastTexts ( )
10332{
10333 uint32 oldMSTime = getMSTime();
10334
10335 _broadcastTextStore.clear(); // for reload case
10336
10337 // 0 1 2 3 4 5 6 7 8 9 10 11 12
10338 QueryResult result = WorldDatabase.Query("SELECT ID, LanguageID, MaleText, FemaleText, EmoteID1, EmoteID2, EmoteID3, EmoteDelay1, EmoteDelay2, EmoteDelay3, SoundEntriesID, EmotesID, Flags FROM broadcast_text");
10339 if (!result)
10340 {
10341 LOG_WARN("server.loading", ">> Loaded 0 broadcast texts. DB table `broadcast_text` is empty.");
10342 LOG_INFO("server.loading", " ");
10343 return;
10344 }
10345
10346 _broadcastTextStore.rehash(result->GetRowCount());
10347
10348 do
10349 {
10350 Field* fields = result->Fetch();
10351
10352 BroadcastText bct;
10353
10354 bct.Id = fields[0].Get<uint32>();
10355 bct.LanguageID = fields[1].Get<uint32>();
10356 bct.MaleText[DEFAULT_LOCALE] = fields[2].Get<std::string>();
10357 bct.FemaleText[DEFAULT_LOCALE] = fields[3].Get<std::string>();
10358 bct.EmoteId1 = fields[4].Get<uint32>();
10359 bct.EmoteId2 = fields[5].Get<uint32>();
10360 bct.EmoteId3 = fields[6].Get<uint32>();
10361 bct.EmoteDelay1 = fields[7].Get<uint32>();
10362 bct.EmoteDelay2 = fields[8].Get<uint32>();
10363 bct.EmoteDelay3 = fields[9].Get<uint32>();
10364 bct.SoundEntriesId = fields[10].Get<uint32>();
10365 bct.EmotesID = fields[11].Get<uint32>();
10366 bct.Flags = fields[12].Get<uint32>();
10367
10368 if (bct.SoundEntriesId)
10369 {
10370 if (!sSoundEntriesStore.LookupEntry(bct.SoundEntriesId))
10371 {
10372 LOG_DEBUG("misc", "BroadcastText (Id: {}) in table `broadcast_text` has SoundEntriesId {} but sound does not exist.", bct.Id, bct.SoundEntriesId);
10373 bct.SoundEntriesId = 0;
10374 }
10375 }
10376
10378 {
10379 LOG_DEBUG("misc", "BroadcastText (Id: {}) in table `broadcast_text` using Language {} but Language does not exist.", bct.Id, bct.LanguageID);
10381 }
10382
10383 if (bct.EmoteId1)
10384 {
10385 if (!sEmotesStore.LookupEntry(bct.EmoteId1))
10386 {
10387 LOG_DEBUG("misc", "BroadcastText (Id: {}) in table `broadcast_text` has EmoteId1 {} but emote does not exist.", bct.Id, bct.EmoteId1);
10388 bct.EmoteId1 = 0;
10389 }
10390 }
10391
10392 if (bct.EmoteId2)
10393 {
10394 if (!sEmotesStore.LookupEntry(bct.EmoteId2))
10395 {
10396 LOG_DEBUG("misc", "BroadcastText (Id: {}) in table `broadcast_text` has EmoteId2 {} but emote does not exist.", bct.Id, bct.EmoteId2);
10397 bct.EmoteId2 = 0;
10398 }
10399 }
10400
10401 if (bct.EmoteId3)
10402 {
10403 if (!sEmotesStore.LookupEntry(bct.EmoteId3))
10404 {
10405 LOG_DEBUG("misc", "BroadcastText (Id: {}) in table `broadcast_text` has EmoteId3 {} but emote does not exist.", bct.Id, bct.EmoteId3);
10406 bct.EmoteId3 = 0;
10407 }
10408 }
10409
10410 _broadcastTextStore[bct.Id] = bct;
10411 } while (result->NextRow());
10412
10413 LOG_INFO("server.loading", ">> Loaded {} Broadcast Texts in {} ms", _broadcastTextStore.size(), GetMSTimeDiffToNow(oldMSTime));
10414}
DBCStorage< SoundEntriesEntry > sSoundEntriesStore(SoundEntriesfmt)
DBCStorage< EmotesEntry > sEmotesStore(EmotesEntryfmt)
LanguageDesc const * GetLanguageDescByID(uint32 lang)
Definition ObjectMgr.cpp:254
@ LANG_UNIVERSAL
Definition SharedDefines.h:723
Definition ObjectMgr.h:435
uint32 EmoteDelay2
Definition ObjectMgr.h:450
uint32 Id
Definition ObjectMgr.h:442
std::vector< std::string > FemaleText
Definition ObjectMgr.h:445
uint32 EmotesID
Definition ObjectMgr.h:453
uint32 LanguageID
Definition ObjectMgr.h:443
uint32 EmoteId2
Definition ObjectMgr.h:447
uint32 EmoteDelay1
Definition ObjectMgr.h:449
uint32 SoundEntriesId
Definition ObjectMgr.h:452
std::vector< std::string > MaleText
Definition ObjectMgr.h:444
uint32 EmoteId3
Definition ObjectMgr.h:448
uint32 EmoteId1
Definition ObjectMgr.h:446
uint32 EmoteDelay3
Definition ObjectMgr.h:451
uint32 Flags
Definition ObjectMgr.h:454

References _broadcastTextStore, DEFAULT_LOCALE, BroadcastText::EmoteDelay1, BroadcastText::EmoteDelay2, BroadcastText::EmoteDelay3, BroadcastText::EmoteId1, BroadcastText::EmoteId2, BroadcastText::EmoteId3, BroadcastText::EmotesID, BroadcastText::FemaleText, BroadcastText::Flags, Field::Get(), GetLanguageDescByID(), getMSTime(), GetMSTimeDiffToNow(), BroadcastText::Id, LANG_UNIVERSAL, BroadcastText::LanguageID, LOG_DEBUG, LOG_INFO, LOG_WARN, BroadcastText::MaleText, sEmotesStore, BroadcastText::SoundEntriesId, sSoundEntriesStore, and WorldDatabase.

◆ LoadCreatureAddons()

void ObjectMgr::LoadCreatureAddons ( )
1262{
1263 uint32 oldMSTime = getMSTime();
1264
1265 // 0 1 2 3 4 5 6 7
1266 QueryResult result = WorldDatabase.Query("SELECT guid, path_id, mount, bytes1, bytes2, emote, visibilityDistanceType, auras FROM creature_addon");
1267
1268 if (!result)
1269 {
1270 LOG_WARN("server.loading", ">> Loaded 0 creature addon definitions. DB table `creature_addon` is empty.");
1271 LOG_INFO("server.loading", " ");
1272 return;
1273 }
1274
1275 uint32 count = 0;
1276 do
1277 {
1278 Field* fields = result->Fetch();
1279
1280 ObjectGuid::LowType guid = fields[0].Get<uint32>();
1281
1282 CreatureData const* creData = GetCreatureData(guid);
1283 if (!creData)
1284 {
1285 LOG_ERROR("sql.sql", "Creature (GUID: {}) does not exist but has a record in `creature_addon`", guid);
1286 continue;
1287 }
1288
1289 CreatureAddon& creatureAddon = _creatureAddonStore[guid];
1290
1291 creatureAddon.path_id = fields[1].Get<uint32>();
1292 if (creData->movementType == WAYPOINT_MOTION_TYPE && !creatureAddon.path_id)
1293 {
1294 const_cast<CreatureData*>(creData)->movementType = IDLE_MOTION_TYPE;
1295 LOG_ERROR("sql.sql", "Creature (GUID {}) has movement type set to WAYPOINT_MOTION_TYPE but no path assigned", guid);
1296 }
1297
1298 creatureAddon.mount = fields[2].Get<uint32>();
1299 creatureAddon.bytes1 = fields[3].Get<uint32>();
1300 creatureAddon.bytes2 = fields[4].Get<uint32>();
1301 creatureAddon.emote = fields[5].Get<uint32>();
1302 creatureAddon.visibilityDistanceType = VisibilityDistanceType(fields[6].Get<uint8>());
1303
1304 for (std::string_view aura : Acore::Tokenize(fields[7].Get<std::string_view>(), ' ', false))
1305 {
1306 SpellInfo const* spellInfo = nullptr;
1307
1308 if (Optional<uint32> spellId = Acore::StringTo<uint32>(aura))
1309 {
1310 spellInfo = sSpellMgr->GetSpellInfo(*spellId);
1311 }
1312
1313 if (!spellInfo)
1314 {
1315 LOG_ERROR("sql.sql", "Creature (GUID: {}) has wrong spell '{}' defined in `auras` field in `creature_addon`.", guid, aura);
1316 continue;
1317 }
1318
1319 if (std::find(creatureAddon.auras.begin(), creatureAddon.auras.end(), spellInfo->Id) != creatureAddon.auras.end())
1320 {
1321 LOG_ERROR("sql.sql", "Creature (GUID: {}) has duplicate aura (spell {}) in `auras` field in `creature_addon`.", guid, spellInfo->Id);
1322 continue;
1323 }
1324
1325 if (spellInfo->GetDuration() > 0)
1326 {
1327 LOG_DEBUG/*ERROR*/("sql.sql", "Creature (Entry: {}) has temporary aura (spell {}) in `auras` field in `creature_template_addon`.", guid, spellInfo->Id);
1328 // continue;
1329 }
1330
1331 creatureAddon.auras.push_back(spellInfo->Id);
1332 }
1333
1334 if (creatureAddon.mount)
1335 {
1336 if (!sCreatureDisplayInfoStore.LookupEntry(creatureAddon.mount))
1337 {
1338 LOG_ERROR("sql.sql", "Creature (GUID: {}) has invalid displayInfoId ({}) for mount defined in `creature_addon`", guid, creatureAddon.mount);
1339 creatureAddon.mount = 0;
1340 }
1341 }
1342
1343 if (!sEmotesStore.LookupEntry(creatureAddon.emote))
1344 {
1345 LOG_ERROR("sql.sql", "Creature (GUID: {}) has invalid emote ({}) defined in `creature_addon`.", guid, creatureAddon.emote);
1346 creatureAddon.emote = 0;
1347 }
1348
1350 {
1351 LOG_ERROR("sql.sql", "Creature (GUID: {}) has invalid visibilityDistanceType ({}) defined in `creature_addon`.", guid, AsUnderlyingType(creatureAddon.visibilityDistanceType));
1353 }
1354
1355 ++count;
1356 } while (result->NextRow());
1357
1358 LOG_INFO("server.loading", ">> Loaded {} Creature Addons in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
1359 LOG_INFO("server.loading", " ");
1360}
DBCStorage< CreatureDisplayInfoEntry > sCreatureDisplayInfoStore(CreatureDisplayInfofmt)
@ WAYPOINT_MOTION_TYPE
Definition MotionMaster.h:41
VisibilityDistanceType
Definition ObjectDefines.h:62
std::optional< T > Optional
Optional helper class to wrap optional values within.
Definition Optional.h:24
constexpr std::underlying_type< E >::type AsUnderlyingType(E enumValue)
Definition Util.h:610
uint32 Id
Definition SpellInfo.h:344
int32 GetDuration() const
Definition SpellInfo.cpp:2738
Definition AsioHacksFwd.h:47
std::vector< std::string_view > Tokenize(std::string_view str, char sep, bool keepEmpty)
Definition Tokenize.cpp:20
STL namespace.
Definition CreatureData.h:431
std::vector< uint32 > auras
Definition CreatureData.h:437
uint32 mount
Definition CreatureData.h:433
uint32 emote
Definition CreatureData.h:436
uint32 path_id
Definition CreatureData.h:432
VisibilityDistanceType visibilityDistanceType
Definition CreatureData.h:438
uint32 bytes1
Definition CreatureData.h:434
uint32 bytes2
Definition CreatureData.h:435

References _creatureAddonStore, AsUnderlyingType(), CreatureAddon::auras, CreatureAddon::bytes1, CreatureAddon::bytes2, CreatureAddon::emote, Field::Get(), GetCreatureData(), SpellInfo::GetDuration(), getMSTime(), GetMSTimeDiffToNow(), SpellInfo::Id, IDLE_MOTION_TYPE, LOG_DEBUG, LOG_ERROR, LOG_INFO, LOG_WARN, Max, CreatureAddon::mount, Normal, CreatureAddon::path_id, sCreatureDisplayInfoStore, sEmotesStore, sSpellMgr, Acore::Tokenize(), CreatureAddon::visibilityDistanceType, WAYPOINT_MOTION_TYPE, and WorldDatabase.

◆ LoadCreatureClassLevelStats()

void ObjectMgr::LoadCreatureClassLevelStats ( )
10489{
10490 uint32 oldMSTime = getMSTime();
10491
10492 QueryResult result = WorldDatabase.Query("SELECT level, class, basehp0, basehp1, basehp2, basemana, basearmor, attackpower, rangedattackpower, damage_base, damage_exp1, damage_exp2, Strength, Agility, Stamina, Intellect, Spirit FROM creature_classlevelstats");
10493
10494 if (!result)
10495 {
10496 LOG_WARN("server.loading", ">> Loaded 0 creature base stats. DB table `creature_classlevelstats` is empty.");
10497 LOG_INFO("server.loading", " ");
10498 return;
10499 }
10500
10501 uint32 count = 0;
10502 do
10503 {
10504 Field* fields = result->Fetch();
10505
10506 uint8 Level = fields[0].Get<uint8>();
10507 uint8 Class = fields[1].Get<uint8>();
10508
10509 if (!Class || ((1 << (Class - 1)) & CLASSMASK_ALL_CREATURES) == 0)
10510 LOG_ERROR("sql.sql", "Creature base stats for level {} has invalid class {}", Level, Class);
10511
10512 CreatureBaseStats stats;
10513
10514 for (uint8 i = 0; i < MAX_EXPANSIONS; ++i)
10515 {
10516 stats.BaseHealth[i] = fields[2 + i].Get<uint32>();
10517
10518 if (stats.BaseHealth[i] == 0)
10519 {
10520 LOG_ERROR("sql.sql", "Creature base stats for class {}, level {} has invalid zero base HP[{}] - set to 1", Class, Level, i);
10521 stats.BaseHealth[i] = 1;
10522 }
10523
10524 // xinef: if no data is available, get them from lower expansions
10525 if (stats.BaseHealth[i] <= 1)
10526 {
10527 for (uint8 j = i; j > 0;)
10528 {
10529 --j;
10530 if (stats.BaseHealth[j] > 1)
10531 {
10532 stats.BaseHealth[i] = stats.BaseHealth[j];
10533 break;
10534 }
10535 }
10536 }
10537
10538 stats.BaseDamage[i] = fields[9 + i].Get<float>();
10539 if (stats.BaseDamage[i] < 0.0f)
10540 {
10541 LOG_ERROR("sql.sql", "Creature base stats for class {}, level {} has invalid negative base damage[{}] - set to 0.0", Class, Level, i);
10542 stats.BaseDamage[i] = 0.0f;
10543 }
10544 }
10545
10546 stats.BaseMana = fields[5].Get<uint32>();
10547 stats.BaseArmor = fields[6].Get<uint32>();
10548
10549 stats.AttackPower = fields[7].Get<uint32>();
10550 stats.RangedAttackPower = fields[8].Get<uint32>();
10551
10552 stats.Strength = fields[12].Get<uint32>();
10553 stats.Agility = fields[13].Get<uint32>();
10554 stats.Stamina = fields[14].Get<uint32>();
10555 stats.Intellect = fields[15].Get<uint32>();
10556 stats.Spirit = fields[16].Get<uint32>();
10557
10558 if (!stats.Strength || !stats.Agility || !stats.Stamina || !stats.Intellect || !stats.Spirit)
10559 {
10560 // Once these attributes are implemented, this should probably be uncommented.
10561 // LOG_WARN("server.loading", "Creature base attributes for class {}, level {} are missing!", Class, Level);
10562 }
10563
10565
10566 ++count;
10567 } while (result->NextRow());
10568
10570 for (CreatureTemplateContainer::const_iterator itr = ctc->begin(); itr != ctc->end(); ++itr)
10571 {
10572 for (uint16 lvl = itr->second.minlevel; lvl <= itr->second.maxlevel; ++lvl)
10573 {
10574 if (_creatureBaseStatsStore.find(MAKE_PAIR16(lvl, itr->second.unit_class)) == _creatureBaseStatsStore.end())
10575 LOG_ERROR("sql.sql", "Missing base stats for creature class {} level {}", itr->second.unit_class, lvl);
10576 }
10577 }
10578
10579 LOG_INFO("server.loading", ">> Loaded {} Creature Base Stats in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10580 LOG_INFO("server.loading", " ");
10581}
std::unordered_map< uint32, CreatureTemplate > CreatureTemplateContainer
Definition CreatureData.h:287
@ Class
Requires the player to be a specific class.
@ Level
Requires the player to be at least a specific level.
CreatureTemplateContainer const * GetCreatureTemplates() const
Definition ObjectMgr.h:771
uint32 BaseMana
Definition CreatureData.h:300
uint32 Agility
Definition CreatureData.h:306
float BaseDamage[MAX_EXPANSIONS]
Definition CreatureData.h:304
uint32 RangedAttackPower
Definition CreatureData.h:303
uint32 AttackPower
Definition CreatureData.h:302
uint32 BaseHealth[MAX_EXPANSIONS]
Definition CreatureData.h:299
uint32 Strength
Definition CreatureData.h:305
float BaseArmor
Definition CreatureData.h:301
uint32 Spirit
Definition CreatureData.h:309
uint32 Stamina
Definition CreatureData.h:307
uint32 Intellect
Definition CreatureData.h:308

References _creatureBaseStatsStore, CreatureBaseStats::Agility, CreatureBaseStats::AttackPower, CreatureBaseStats::BaseArmor, CreatureBaseStats::BaseDamage, CreatureBaseStats::BaseHealth, CreatureBaseStats::BaseMana, Class, CLASSMASK_ALL_CREATURES, Field::Get(), GetCreatureTemplates(), getMSTime(), GetMSTimeDiffToNow(), CreatureBaseStats::Intellect, Level, LOG_ERROR, LOG_INFO, LOG_WARN, MAKE_PAIR16(), MAX_EXPANSIONS, CreatureBaseStats::RangedAttackPower, CreatureBaseStats::Spirit, CreatureBaseStats::Stamina, CreatureBaseStats::Strength, and WorldDatabase.

◆ LoadCreatureCustomIDs()

void ObjectMgr::LoadCreatureCustomIDs ( )

Load config option Creatures.CustomIDs into Store.

952{
953 // Hack for modules
954 std::string stringCreatureIds = sConfigMgr->GetOption<std::string>("Creatures.CustomIDs", "190010,55005,999991,25462,98888,601014,34567,34568");
955 std::vector<std::string_view> CustomCreatures = Acore::Tokenize(stringCreatureIds, ',', false);
956
957 for (auto& itr : CustomCreatures)
958 {
959 _creatureCustomIDsStore.push_back(Acore::StringTo<uint32>(itr).value());
960 }
961}
#define sConfigMgr
Definition Config.h:93

References _creatureCustomIDsStore, sConfigMgr, and Acore::Tokenize().

◆ LoadCreatureDataFromDB()

CreatureData const * ObjectMgr::LoadCreatureDataFromDB ( ObjectGuid::LowType  spawnId)

Loads a single creature spawn entry from the database into the data store cache.

This is needed as a prerequisite for Creature::LoadCreatureFromDB(), which reads from the in-memory cache (via GetCreatureData()) rather than querying the DB itself. For spawns not loaded during server startup, this method populates the cache so that Creature::LoadCreatureFromDB() can then create the live entity.

Returns the cached data if already loaded, or nullptr if the spawn doesn't exist or fails validation.

Parameters
spawnIdThe creature spawn GUID to load.
Returns
Pointer to the cached CreatureData, or nullptr on failure.
2519{
2520 CreatureData const* data = GetCreatureData(spawnId);
2521 if (data)
2522 return data;
2523
2524 QueryResult result = WorldDatabase.Query("SELECT creature.guid, id1, id2, id3, map, equipment_id, "
2525 "position_x, position_y, position_z, orientation, spawntimesecs, wander_distance, "
2526 "currentwaypoint, curhealth, curmana, MovementType, spawnMask, phaseMask, "
2527 "creature.npcflag, creature.unit_flags, creature.dynamicflags, creature.ScriptName "
2528 "FROM creature WHERE creature.guid = {}", spawnId);
2529
2530 if (!result)
2531 return nullptr;
2532
2533 Field* fields = result->Fetch();
2534 uint32 id1 = fields[1].Get<uint32>();
2535 uint32 id2 = fields[2].Get<uint32>();
2536 uint32 id3 = fields[3].Get<uint32>();
2537
2538 CreatureTemplate const* cInfo = GetCreatureTemplate(id1);
2539 if (!cInfo)
2540 {
2541 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) with non-existing creature entry {} in id1 field, skipped.", spawnId, id1);
2542 return nullptr;
2543 }
2544
2545 if (id2 && !GetCreatureTemplate(id2))
2546 {
2547 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) with non-existing creature entry {} in id2 field, skipped.", spawnId, id2);
2548 return nullptr;
2549 }
2550
2551 if (id3 && !GetCreatureTemplate(id3))
2552 {
2553 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) with non-existing creature entry {} in id3 field, skipped.", spawnId, id3);
2554 return nullptr;
2555 }
2556
2557 if (!id2 && id3)
2558 {
2559 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) with creature entry {} in id3 field but no entry in id2 field, skipped.", spawnId, id3);
2560 return nullptr;
2561 }
2562
2564 creatureData.id1 = id1;
2565 creatureData.id2 = id2;
2566 creatureData.id3 = id3;
2567 creatureData.mapid = fields[4].Get<uint16>();
2568 creatureData.equipmentId = fields[5].Get<int8>();
2569 creatureData.posX = fields[6].Get<float>();
2570 creatureData.posY = fields[7].Get<float>();
2571 creatureData.posZ = fields[8].Get<float>();
2572 creatureData.orientation = fields[9].Get<float>();
2573 creatureData.spawntimesecs = fields[10].Get<uint32>();
2574 creatureData.wander_distance = fields[11].Get<float>();
2575 creatureData.currentwaypoint = fields[12].Get<uint32>();
2576 creatureData.curhealth = fields[13].Get<uint32>();
2577 creatureData.curmana = fields[14].Get<uint32>();
2578 creatureData.movementType = fields[15].Get<uint8>();
2579 creatureData.spawnMask = fields[16].Get<uint8>();
2580 creatureData.phaseMask = fields[17].Get<uint32>();
2581 creatureData.npcflag = fields[18].Get<uint32>();
2582 creatureData.unit_flags = fields[19].Get<uint32>();
2583 creatureData.dynamicflags = fields[20].Get<uint32>();
2584 creatureData.ScriptId = GetScriptId(fields[21].Get<std::string>());
2585 creatureData.spawnGroupId = 0;
2586
2587 if (!creatureData.ScriptId)
2588 creatureData.ScriptId = cInfo->ScriptID;
2589
2590 MapEntry const* mapEntry = sMapStore.LookupEntry(creatureData.mapid);
2591 if (!mapEntry)
2592 {
2593 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) that spawned at non-existing map (Id: {}), skipped.", spawnId, creatureData.mapid);
2594 _creatureDataStore.erase(spawnId);
2595 return nullptr;
2596 }
2597
2598 if (mapEntry->IsRaid() && creatureData.spawntimesecs >= 7 * DAY && creatureData.spawntimesecs < 14 * DAY)
2599 creatureData.spawntimesecs = 14 * DAY;
2600
2601 bool ok = true;
2602 for (uint32 diff = 0; diff < MAX_DIFFICULTY - 1 && ok; ++diff)
2603 {
2604 if (_difficultyEntries[diff].find(id1) != _difficultyEntries[diff].end() ||
2605 _difficultyEntries[diff].find(id2) != _difficultyEntries[diff].end() ||
2606 _difficultyEntries[diff].find(id3) != _difficultyEntries[diff].end())
2607 {
2608 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) that is listed as difficulty {} template (Entries: {}, {}, {}) in `creature_template`, skipped.",
2609 spawnId, diff + 1, id1, id2, id3);
2610 ok = false;
2611 }
2612 }
2613
2614 if (!ok)
2615 {
2616 _creatureDataStore.erase(spawnId);
2617 return nullptr;
2618 }
2619
2620 if (creatureData.equipmentId != 0)
2621 {
2622 if (!GetEquipmentInfo(id1, creatureData.equipmentId) ||
2623 (id2 && !GetEquipmentInfo(id2, creatureData.equipmentId)) ||
2624 (id3 && !GetEquipmentInfo(id3, creatureData.equipmentId)))
2625 {
2626 LOG_ERROR("sql.sql", "Table `creature` has creature (Entries: {}, {}, {}) with equipment_id {} not found in table `creature_equip_template`, set to no equipment.",
2627 id1, id2, id3, creatureData.equipmentId);
2628 creatureData.equipmentId = 0;
2629 }
2630 }
2631
2632 if (creatureData.movementType >= MAX_DB_MOTION_TYPE)
2633 {
2634 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {} Entries: {}, {}, {}) with wrong movement generator type ({}), set to IDLE.",
2635 spawnId, id1, id2, id3, creatureData.movementType);
2636 creatureData.movementType = IDLE_MOTION_TYPE;
2637 }
2638
2639 if (creatureData.wander_distance < 0.0f)
2640 {
2641 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {} Entries: {}, {}, {}) with `wander_distance`< 0, set to 0.",
2642 spawnId, id1, id2, id3);
2643 creatureData.wander_distance = 0.0f;
2644 }
2645 else if (creatureData.movementType == RANDOM_MOTION_TYPE)
2646 {
2647 if (creatureData.wander_distance == 0.0f)
2648 {
2649 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {} Entries: {}, {}, {}) with `MovementType`=1 (random movement) but with `wander_distance`=0, replace by idle movement type (0).",
2650 spawnId, id1, id2, id3);
2651 creatureData.movementType = IDLE_MOTION_TYPE;
2652 }
2653 }
2654 else if (creatureData.movementType == IDLE_MOTION_TYPE)
2655 {
2656 if (creatureData.wander_distance != 0.0f)
2657 {
2658 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {} Entries: {}, {}, {}) with `MovementType`=0 (idle) have `wander_distance`<>0, set to 0.",
2659 spawnId, id1, id2, id3);
2660 creatureData.wander_distance = 0.0f;
2661 }
2662 }
2663
2664 if (creatureData.phaseMask == 0)
2665 {
2666 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {} Entries: {}, {}, {}) with `phaseMask`=0 (not visible for anyone), set to 1.",
2667 spawnId, id1, id2, id3);
2668 creatureData.phaseMask = 1;
2669 }
2670
2671 return &creatureData;
2672}
constexpr auto DAY
Definition Common.h:49
std::int8_t int8
Definition Define.h:105
@ RANDOM_MOTION_TYPE
Definition MotionMaster.h:40
EquipmentInfo const * GetEquipmentInfo(uint32 entry, int8 &id)
Definition ObjectMgr.cpp:1453
ObjectData const creatureData[]
Definition instance_blackwing_lair.cpp:45
bool IsRaid() const
Definition DBCStructure.h:1354

References _creatureDataStore, _difficultyEntries, creatureData, DAY, Field::Get(), GetCreatureData(), GetCreatureTemplate(), GetEquipmentInfo(), GetScriptId(), IDLE_MOTION_TYPE, MapEntry::IsRaid(), LOG_ERROR, MAX_DB_MOTION_TYPE, MAX_DIFFICULTY, RANDOM_MOTION_TYPE, sMapStore, and WorldDatabase.

◆ LoadCreatureDefaultTrainers()

void ObjectMgr::LoadCreatureDefaultTrainers ( )
9877{
9878 uint32 oldMSTime = getMSTime();
9879
9881
9882 if (QueryResult result = WorldDatabase.Query("SELECT CreatureId, TrainerId FROM creature_default_trainer"))
9883 {
9884 do
9885 {
9886 Field* fields = result->Fetch();
9887 uint32 creatureId = fields[0].Get<uint32>();
9888 uint32 trainerId = fields[1].Get<uint32>();
9889
9890 if (!GetCreatureTemplate(creatureId))
9891 {
9892 LOG_ERROR("sql.sql", "Table `creature_default_trainer` references non-existing creature template (CreatureId: %u), ignoring", creatureId);
9893 continue;
9894 }
9895
9896 _creatureDefaultTrainers[creatureId] = trainerId;
9897
9898 } while (result->NextRow());
9899 }
9900
9901 LOG_INFO("server.loading", ">> Loaded {} default trainers in {} ms", _creatureDefaultTrainers.size(), GetMSTimeDiffToNow(oldMSTime));
9902}

References _creatureDefaultTrainers, Field::Get(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, and WorldDatabase.

◆ LoadCreatureLocales()

void ObjectMgr::LoadCreatureLocales ( )
394{
395 uint32 oldMSTime = getMSTime();
396
397 _creatureLocaleStore.clear(); // need for reload case
398
399 // 0 1 2 3
400 QueryResult result = WorldDatabase.Query("SELECT entry, locale, Name, Title FROM creature_template_locale");
401 if (!result)
402 return;
403
404 do
405 {
406 Field* fields = result->Fetch();
407
408 uint32 ID = fields[0].Get<uint32>();
409
410 LocaleConstant locale = GetLocaleByName(fields[1].Get<std::string>());
411 if (locale == LOCALE_enUS)
412 continue;
413
415 AddLocaleString(fields[2].Get<std::string>(), locale, data.Name);
416 AddLocaleString(fields[3].Get<std::string>(), locale, data.Title);
417 } while (result->NextRow());
418
419 LOG_INFO("server.loading", ">> Loaded {} Creature Locale Strings in {} ms", (unsigned long)_creatureLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
420}
Definition CreatureData.h:343
std::vector< std::string > Title
Definition CreatureData.h:345
std::vector< std::string > Name
Definition CreatureData.h:344

References _creatureLocaleStore, AddLocaleString(), Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, CreatureLocale::Name, CreatureLocale::Title, and WorldDatabase.

◆ LoadCreatureModelInfo()

void ObjectMgr::LoadCreatureModelInfo ( )
1710{
1711 uint32 oldMSTime = getMSTime();
1712
1713 // 0 1 2 3 4
1714 QueryResult result = WorldDatabase.Query("SELECT DisplayID, BoundingRadius, CombatReach, Gender, DisplayID_Other_Gender FROM creature_model_info");
1715
1716 if (!result)
1717 {
1718 LOG_WARN("server.loading", ">> Loaded 0 creature model definitions. DB table `creature_model_info` is empty.");
1719 LOG_INFO("server.loading", " ");
1720 return;
1721 }
1722
1723 _creatureModelStore.rehash(result->GetRowCount());
1724 uint32 count = 0;
1725
1726 // List of ModelDataIDs that use Invisible models
1727 uint32 triggerCreatureModelDataID[14] = { 1731, 1752, 2206, 2296, 2372, 2382, 2481, 2512, 2513, 2611, 2636, 2790, 3230, 3274 };
1728
1729 do
1730 {
1731 Field* fields = result->Fetch();
1732
1733 uint32 displayId = fields[0].Get<uint32>();
1734 CreatureDisplayInfoEntry const* creatureDisplay = sCreatureDisplayInfoStore.LookupEntry(displayId);
1735 uint32 modelId = fields[0].Get<uint32>();
1736
1737 CreatureModelInfo& modelInfo = _creatureModelStore[modelId];
1738
1739 modelInfo.bounding_radius = fields[1].Get<float>();
1740 modelInfo.combat_reach = fields[2].Get<float>();
1741 modelInfo.gender = fields[3].Get<uint8>();
1742 modelInfo.modelid_other_gender = fields[4].Get<uint32>();
1743 modelInfo.is_trigger = false;
1744
1745 // Checks
1746
1747 if (!sCreatureDisplayInfoStore.LookupEntry(modelId))
1748 LOG_ERROR("sql.sql", "Table `creature_model_info` has model for not existed display id ({}).", modelId);
1749
1750 if (modelInfo.gender > GENDER_NONE)
1751 {
1752 LOG_ERROR("sql.sql", "Table `creature_model_info` has wrong gender ({}) for display id ({}).", uint32(modelInfo.gender), modelId);
1753 modelInfo.gender = GENDER_MALE;
1754 }
1755
1756 if (modelInfo.modelid_other_gender && !sCreatureDisplayInfoStore.LookupEntry(modelInfo.modelid_other_gender))
1757 {
1758 LOG_ERROR("sql.sql", "Table `creature_model_info` has not existed alt.gender model ({}) for existed display id ({}).", modelInfo.modelid_other_gender, modelId);
1759 modelInfo.modelid_other_gender = 0;
1760 }
1761
1762 if (modelInfo.combat_reach < 0.1f)
1763 modelInfo.combat_reach = DEFAULT_COMBAT_REACH;
1764
1765 if (CreatureModelDataEntry const* modelData = sCreatureModelDataStore.LookupEntry(creatureDisplay->ModelId))
1766 {
1767 for (uint32 i = 0; i < 14; i++)
1768 {
1769 if (modelData->Id == triggerCreatureModelDataID[i])
1770 {
1771 modelInfo.is_trigger = true;
1772 break;
1773 }
1774 }
1775 }
1776
1777 ++count;
1778 } while (result->NextRow());
1779
1780 LOG_INFO("server.loading", ">> Loaded {} Creature Model Based Info in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
1781 LOG_INFO("server.loading", " ");
1782}
DBCStorage< CreatureModelDataEntry > sCreatureModelDataStore(CreatureModelDatafmt)
#define DEFAULT_COMBAT_REACH
Definition ObjectDefines.h:45
@ GENDER_MALE
Definition SharedDefines.h:61
Definition DBCStructure.h:721
Definition DBCStructure.h:775
float bounding_radius
Definition CreatureData.h:390

References _creatureModelStore, CreatureModelInfo::bounding_radius, DEFAULT_COMBAT_REACH, GENDER_MALE, GENDER_NONE, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sCreatureDisplayInfoStore, sCreatureModelDataStore, and WorldDatabase.

◆ LoadCreatureMovementOverrides()

void ObjectMgr::LoadCreatureMovementOverrides ( )
1558{
1559 uint32 oldMSTime = getMSTime();
1560
1562
1563 // Load the data from creature_movement_override and if NULL fallback to creature_template_movement
1564 QueryResult result = WorldDatabase.Query("SELECT cmo.SpawnId,"
1565 "COALESCE(cmo.Ground, ctm.Ground),"
1566 "COALESCE(cmo.Swim, ctm.Swim),"
1567 "COALESCE(cmo.Flight, ctm.Flight),"
1568 "COALESCE(cmo.Rooted, ctm.Rooted),"
1569 "COALESCE(cmo.Chase, ctm.Chase),"
1570 "COALESCE(cmo.Random, ctm.Random),"
1571 "COALESCE(cmo.InteractionPauseTimer, ctm.InteractionPauseTimer) "
1572 "FROM creature_movement_override AS cmo "
1573 "LEFT JOIN creature AS c ON c.guid = cmo.SpawnId "
1574 "LEFT JOIN creature_template_movement AS ctm ON ctm.CreatureId = c.id1");
1575 if (!result)
1576 {
1577 LOG_WARN("server.loading", ">> Loaded 0 creature movement overrides. DB table `creature_movement_override` is empty!");
1578 return;
1579 }
1580
1581 do
1582 {
1583 Field* fields = result->Fetch();
1584 ObjectGuid::LowType spawnId = fields[0].Get<uint32>();
1585 if (!GetCreatureData(spawnId))
1586 {
1587 LOG_ERROR("sql.sql", "Creature (GUID: {}) does not exist but has a record in `creature_movement_override`", spawnId);
1588 continue;
1589 }
1590
1592 if (!fields[1].IsNull())
1593 {
1594 movement.Ground = static_cast<CreatureGroundMovementType>(fields[1].Get<uint8>());
1595 }
1596
1597 if (!fields[2].IsNull())
1598 {
1599 movement.Swim = fields[2].Get<bool>();
1600 }
1601
1602 if (!fields[3].IsNull())
1603 {
1604 movement.Flight = static_cast<CreatureFlightMovementType>(fields[3].Get<uint8>());
1605 }
1606
1607 if (!fields[4].IsNull())
1608 {
1609 movement.Rooted = fields[4].Get<bool>();
1610 }
1611
1612 if (!fields[5].IsNull())
1613 {
1614 movement.Chase = static_cast<CreatureChaseMovementType>(fields[5].Get<uint8>());
1615 }
1616
1617 if (!fields[6].IsNull())
1618 {
1619 movement.Random = static_cast<CreatureRandomMovementType>(fields[6].Get<uint8>());
1620 }
1621
1622 if (!fields[7].IsNull())
1623 {
1624 movement.InteractionPauseTimer = fields[7].Get<uint32>();
1625 }
1626
1627 CheckCreatureMovement("creature_movement_override", spawnId, movement);
1628 } while (result->NextRow());
1629
1630 LOG_INFO("server.loading", ">> Loaded {} Movement Overrides in {} ms", _creatureMovementOverrides.size(), GetMSTimeDiffToNow(oldMSTime));
1631 LOG_INFO("server.loading", " ");
1632}
CreatureFlightMovementType
Definition CreatureData.h:93
CreatureChaseMovementType
Definition CreatureData.h:102
CreatureGroundMovementType
Definition CreatureData.h:84
CreatureRandomMovementType
Definition CreatureData.h:111
Definition CreatureData.h:120
bool Swim
Definition CreatureData.h:125
bool Rooted
Definition CreatureData.h:126
uint32 InteractionPauseTimer
Definition CreatureData.h:129

References _creatureMovementOverrides, CreatureMovementData::Chase, CheckCreatureMovement(), CreatureMovementData::Flight, Field::Get(), GetCreatureData(), getMSTime(), GetMSTimeDiffToNow(), CreatureMovementData::Ground, CreatureMovementData::InteractionPauseTimer, LOG_ERROR, LOG_INFO, LOG_WARN, CreatureMovementData::Random, CreatureMovementData::Rooted, CreatureMovementData::Swim, and WorldDatabase.

◆ LoadCreatureQuestEnders()

void ObjectMgr::LoadCreatureQuestEnders ( )
8794{
8795 LoadQuestRelationsHelper(_creatureQuestInvolvedRelations, "creature_questender", false, false);
8796
8797 for (QuestRelations::iterator itr = _creatureQuestInvolvedRelations.begin(); itr != _creatureQuestInvolvedRelations.end(); ++itr)
8798 {
8799 CreatureTemplate const* cInfo = GetCreatureTemplate(itr->first);
8800 if (!cInfo)
8801 LOG_ERROR("sql.sql", "Table `creature_questender` have data for not existed creature entry ({}) and existed quest {}", itr->first, itr->second);
8802 else if (!(cInfo->npcflag & UNIT_NPC_FLAG_QUESTGIVER))
8803 LOG_ERROR("sql.sql", "Table `creature_questender` has creature entry ({}) for quest {}, but npcflag does not include UNIT_NPC_FLAG_QUESTGIVER", itr->first, itr->second);
8804 }
8805}
@ UNIT_NPC_FLAG_QUESTGIVER
Definition UnitDefines.h:323
void LoadQuestRelationsHelper(QuestRelations &map, std::string const &table, bool starter, bool go)
Definition ObjectMgr.cpp:8706

References _creatureQuestInvolvedRelations, GetCreatureTemplate(), LoadQuestRelationsHelper(), LOG_ERROR, CreatureTemplate::npcflag, and UNIT_NPC_FLAG_QUESTGIVER.

Referenced by LoadQuestStartersAndEnders().

◆ LoadCreatureQuestItems()

void ObjectMgr::LoadCreatureQuestItems ( )
10902{
10903 uint32 oldMSTime = getMSTime();
10904
10905 // 0 1 2
10906 QueryResult result = WorldDatabase.Query("SELECT CreatureEntry, ItemId, Idx FROM creature_questitem ORDER BY Idx ASC");
10907
10908 if (!result)
10909 {
10910 LOG_WARN("server.loading", ">> Loaded 0 creature quest items. DB table `creature_questitem` is empty.");
10911 return;
10912 }
10913
10914 uint32 count = 0;
10915 do
10916 {
10917 Field* fields = result->Fetch();
10918
10919 uint32 entry = fields[0].Get<uint32>();
10920 uint32 item = fields[1].Get<uint32>();
10921 uint32 idx = fields[2].Get<uint32>();
10922
10923 CreatureTemplate const* creatureInfo = GetCreatureTemplate(entry);
10924 if (!creatureInfo)
10925 {
10926 LOG_ERROR("sql.sql", "Table `creature_questitem` has data for nonexistent creature (entry: {}, idx: {}), skipped", entry, idx);
10927 continue;
10928 };
10929
10930 ItemEntry const* dbcData = sItemStore.LookupEntry(item);
10931 if (!dbcData)
10932 {
10933 LOG_ERROR("sql.sql", "Table `creature_questitem` has nonexistent item (ID: {}) in creature (entry: {}, idx: {}), skipped", item, entry, idx);
10934 continue;
10935 };
10936
10937 _creatureQuestItemStore[entry].push_back(item);
10938
10939 ++count;
10940 } while (result->NextRow());
10941
10942 LOG_INFO("server.loading", ">> Loaded {} Creature Quest Items in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10943 LOG_INFO("server.loading", " ");
10944}
DBCStorage< ItemEntry > sItemStore(Itemfmt)
Definition DBCStructure.h:1143

References _creatureQuestItemStore, Field::Get(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sItemStore, and WorldDatabase.

◆ LoadCreatureQuestStarters()

void ObjectMgr::LoadCreatureQuestStarters ( )
8780{
8781 LoadQuestRelationsHelper(_creatureQuestRelations, "creature_queststarter", true, false);
8782
8783 for (QuestRelations::iterator itr = _creatureQuestRelations.begin(); itr != _creatureQuestRelations.end(); ++itr)
8784 {
8785 CreatureTemplate const* cInfo = GetCreatureTemplate(itr->first);
8786 if (!cInfo)
8787 LOG_ERROR("sql.sql", "Table `creature_queststarter` have data for not existed creature entry ({}) and existed quest {}", itr->first, itr->second);
8788 else if (!(cInfo->npcflag & UNIT_NPC_FLAG_QUESTGIVER))
8789 LOG_ERROR("sql.sql", "Table `creature_queststarter` has creature entry ({}) for quest {}, but npcflag does not include UNIT_NPC_FLAG_QUESTGIVER", itr->first, itr->second);
8790 }
8791}

References _creatureQuestRelations, GetCreatureTemplate(), LoadQuestRelationsHelper(), LOG_ERROR, CreatureTemplate::npcflag, and UNIT_NPC_FLAG_QUESTGIVER.

Referenced by LoadQuestStartersAndEnders().

◆ LoadCreatures()

void ObjectMgr::LoadCreatures ( )
2317{
2318 uint32 oldMSTime = getMSTime();
2319
2320 // 0 1 2 3 4 5 6 7 8 9 10 11
2321 QueryResult result = WorldDatabase.Query("SELECT creature.guid, id1, id2, id3, map, equipment_id, position_x, position_y, position_z, orientation, spawntimesecs, wander_distance, "
2322 // 12 13 14 15 16 17 18 19 20 21 22
2323 "currentwaypoint, curhealth, curmana, MovementType, spawnMask, phaseMask, eventEntry, pool_entry, creature.npcflag, creature.unit_flags, creature.dynamicflags, "
2324 // 23
2325 "creature.ScriptName "
2326 "FROM creature "
2327 "LEFT OUTER JOIN game_event_creature ON creature.guid = game_event_creature.guid "
2328 "LEFT OUTER JOIN pool_creature ON creature.guid = pool_creature.guid");
2329
2330 if (!result)
2331 {
2332 LOG_WARN("server.loading", ">> Loaded 0 creatures. DB table `creature` is empty.");
2333 LOG_INFO("server.loading", " ");
2334 return;
2335 }
2336
2338 LOG_INFO("server.loading", "Calculating zone and area fields. This may take a moment...");
2339
2340 // Build single time for check spawnmask
2341 std::map<uint32, uint32> spawnMasks;
2342 for (uint32 i = 0; i < sMapStore.GetNumRows(); ++i)
2343 if (sMapStore.LookupEntry(i))
2344 for (int k = 0; k < MAX_DIFFICULTY; ++k)
2346 spawnMasks[i] |= (1 << k);
2347
2348 _creatureDataStore.rehash(result->GetRowCount());
2349 uint32 count = 0;
2350 do
2351 {
2352 Field* fields = result->Fetch();
2353
2354 ObjectGuid::LowType spawnId = fields[0].Get<uint32>();
2355 uint32 id1 = fields[1].Get<uint32>();
2356 uint32 id2 = fields[2].Get<uint32>();
2357 uint32 id3 = fields[3].Get<uint32>();
2358
2359 CreatureTemplate const* cInfo = GetCreatureTemplate(id1);
2360 if (!cInfo)
2361 {
2362 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) with non existing creature entry {} in id1 field, skipped.", spawnId, id1);
2363 continue;
2364 }
2365 CreatureTemplate const* cInfo2 = GetCreatureTemplate(id2);
2366 if (!cInfo2 && id2)
2367 {
2368 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) with non existing creature entry {} in id2 field, skipped.", spawnId, id2);
2369 continue;
2370 }
2371 CreatureTemplate const* cInfo3 = GetCreatureTemplate(id3);
2372 if (!cInfo3 && id3)
2373 {
2374 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) with non existing creature entry {} in id3 field, skipped.", spawnId, id3);
2375 continue;
2376 }
2377 if (!id2 && id3)
2378 {
2379 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {}) with creature entry {} in id3 field but no entry in id2 field, skipped.", spawnId, id3);
2380 continue;
2381 }
2382 CreatureData& data = _creatureDataStore[spawnId];
2383 data.id1 = id1;
2384 data.id2 = id2;
2385 data.id3 = id3;
2386 data.mapid = fields[4].Get<uint16>();
2387 data.equipmentId = fields[5].Get<int8>();
2388 data.posX = fields[6].Get<float>();
2389 data.posY = fields[7].Get<float>();
2390 data.posZ = fields[8].Get<float>();
2391 data.orientation = fields[9].Get<float>();
2392 data.spawntimesecs = fields[10].Get<uint32>();
2393 data.wander_distance = fields[11].Get<float>();
2394 data.currentwaypoint = fields[12].Get<uint32>();
2395 data.curhealth = fields[13].Get<uint32>();
2396 data.curmana = fields[14].Get<uint32>();
2397 data.movementType = fields[15].Get<uint8>();
2398 data.spawnMask = fields[16].Get<uint8>();
2399 data.phaseMask = fields[17].Get<uint32>();
2400 int16 gameEvent = fields[18].Get<int16>();
2401 uint32 PoolId = fields[19].Get<uint32>();
2402 data.npcflag = fields[20].Get<uint32>();
2403 data.unit_flags = fields[21].Get<uint32>();
2404 data.dynamicflags = fields[22].Get<uint32>();
2405 data.ScriptId = GetScriptId(fields[23].Get<std::string>());
2406 data.spawnGroupId = 0;
2407
2408 if (!data.ScriptId)
2409 data.ScriptId = cInfo->ScriptID;
2410
2411 MapEntry const* mapEntry = sMapStore.LookupEntry(data.mapid);
2412 if (!mapEntry)
2413 {
2414 LOG_ERROR("sql.sql", "Table `creature` have creature (SpawnId: {}) that spawned at not existed map (Id: {}), skipped.", spawnId, data.mapid);
2415 continue;
2416 }
2417
2418 // pussywizard: 7 days means no reaspawn, so set it to 14 days, because manual id reset may be late
2419 if (mapEntry->IsRaid() && data.spawntimesecs >= 7 * DAY && data.spawntimesecs < 14 * DAY)
2420 data.spawntimesecs = 14 * DAY;
2421
2422 // Skip spawnMask check for transport maps
2423 if (!_transportMaps.count(data.mapid) && data.spawnMask & ~spawnMasks[data.mapid])
2424 LOG_ERROR("sql.sql", "Table `creature` have creature (SpawnId: {}) that have wrong spawn mask {} including not supported difficulty modes for map (Id: {}).",
2425 spawnId, data.spawnMask, data.mapid);
2426
2427 bool ok = true;
2428 for (uint32 diff = 0; diff < MAX_DIFFICULTY - 1 && ok; ++diff)
2429 {
2430 if ((_difficultyEntries[diff].find(data.id1) != _difficultyEntries[diff].end()) || (_difficultyEntries[diff].find(data.id2) != _difficultyEntries[diff].end()) || (_difficultyEntries[diff].find(data.id3) != _difficultyEntries[diff].end()))
2431 {
2432 LOG_ERROR("sql.sql", "Table `creature` have creature (SpawnId: {}) that listed as difficulty {} template (Entries: {}, {}, {}) in `creature_template`, skipped.",
2433 spawnId, diff + 1, data.id1, data.id2, data.id3);
2434 ok = false;
2435 }
2436 }
2437 if (!ok)
2438 continue;
2439
2440 // -1 random, 0 no equipment,
2441 if (data.equipmentId != 0)
2442 {
2443 if ((!GetEquipmentInfo(data.id1, data.equipmentId)) || (data.id2 && !GetEquipmentInfo(data.id2, data.equipmentId)) || (data.id3 && !GetEquipmentInfo(data.id3, data.equipmentId)))
2444 {
2445 LOG_ERROR("sql.sql", "Table `creature` have creature (Entries: {}, {}, {}) one or more with equipment_id {} not found in table `creature_equip_template`, set to no equipment.",
2446 data.id1, data.id2, data.id3, data.equipmentId);
2447 data.equipmentId = 0;
2448 }
2449 }
2451 {
2452 if (!mapEntry->IsDungeon())
2453 LOG_ERROR("sql.sql", "Table `creature` have creature (SpawnId: {} Entries: {}, {}, {}) with a `creature_template`.`flags_extra` in one or more entries including CREATURE_FLAG_EXTRA_INSTANCE_BIND but creature are not in instance.",
2454 spawnId, data.id1, data.id2, data.id3);
2455 }
2456 if (data.movementType >= MAX_DB_MOTION_TYPE)
2457 {
2458 LOG_ERROR("sql.sql", "Table `creature` has creature (SpawnId: {} Entries: {}, {}, {}) with wrong movement generator type ({}), ignored and set to IDLE.", spawnId, data.id1, data.id2, data.id3, data.movementType);
2460 }
2461 if (data.wander_distance < 0.0f)
2462 {
2463 LOG_ERROR("sql.sql", "Table `creature` have creature (SpawnId: {} Entries: {}, {}, {}) with `wander_distance`< 0, set to 0.", spawnId, data.id1, data.id2, data.id3);
2464 data.wander_distance = 0.0f;
2465 }
2466 else if (data.movementType == RANDOM_MOTION_TYPE)
2467 {
2468 if (data.wander_distance == 0.0f)
2469 {
2470 LOG_ERROR("sql.sql", "Table `creature` have creature (SpawnId: {} Entries: {}, {}, {}) with `MovementType`=1 (random movement) but with `wander_distance`=0, replace by idle movement type (0).",
2471 spawnId, data.id1, data.id2, data.id3);
2473 }
2474 }
2475 else if (data.movementType == IDLE_MOTION_TYPE)
2476 {
2477 if (data.wander_distance != 0.0f)
2478 {
2479 LOG_ERROR("sql.sql", "Table `creature` have creature (SpawnId: {} Entries: {}, {}, {}) with `MovementType`=0 (idle) have `wander_distance`<>0, set to 0.", spawnId, data.id1, data.id2, data.id3);
2480 data.wander_distance = 0.0f;
2481 }
2482 }
2483
2484 if (data.phaseMask == 0)
2485 {
2486 LOG_ERROR("sql.sql", "Table `creature` have creature (SpawnId: {} Entries: {}, {}, {}) with `phaseMask`=0 (not visible for anyone), set to 1.", spawnId, data.id1, data.id2, data.id3);
2487 data.phaseMask = 1;
2488 }
2489
2491 {
2492 uint32 zoneId = sMapMgr->GetZoneId(data.phaseMask, data.mapid, data.posX, data.posY, data.posZ);
2493 uint32 areaId = sMapMgr->GetAreaId(data.phaseMask, data.mapid, data.posX, data.posY, data.posZ);
2494
2496
2497 stmt->SetData(0, zoneId);
2498 stmt->SetData(1, areaId);
2499 stmt->SetData(2, spawnId);
2500
2501 WorldDatabase.Execute(stmt);
2502 }
2503
2504 // Add to grid if not managed by the game event or pool system
2505 if (gameEvent == 0 && PoolId == 0)
2506 AddCreatureToGrid(spawnId, &data);
2507
2508 ++count;
2509 } while (result->NextRow());
2510
2511 LOG_INFO("server.loading", ">> Loaded {} Creatures in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2512 LOG_INFO("server.loading", " ");
2513}
@ CREATURE_FLAG_EXTRA_INSTANCE_BIND
Definition CreatureData.h:46
Difficulty
Definition DBCEnums.h:266
MapDifficulty const * GetMapDifficultyData(uint32 mapId, Difficulty difficulty)
Definition DBCStores.cpp:761
std::int16_t int16
Definition Define.h:104
@ CONFIG_CALCULATE_CREATURE_ZONE_AREA_DATA
Definition WorldConfig.h:115
@ WORLD_UPD_CREATURE_ZONE_AREA_DATA
Definition WorldDatabase.h:114
bool HasFlagsExtra(uint32 flag) const
Definition CreatureData.h:278
uint32 ScriptId
Definition SpawnData.h:71

References _creatureDataStore, _difficultyEntries, _transportMaps, AddCreatureToGrid(), CONFIG_CALCULATE_CREATURE_ZONE_AREA_DATA, CREATURE_FLAG_EXTRA_INSTANCE_BIND, CreatureData::curhealth, CreatureData::curmana, CreatureData::currentwaypoint, DAY, CreatureData::dynamicflags, CreatureData::equipmentId, Field::Get(), GetCreatureTemplate(), GetEquipmentInfo(), GetMapDifficultyData(), getMSTime(), GetMSTimeDiffToNow(), GetScriptId(), CreatureTemplate::HasFlagsExtra(), CreatureData::id1, CreatureData::id2, CreatureData::id3, IDLE_MOTION_TYPE, MapEntry::IsDungeon(), MapEntry::IsRaid(), LOG_ERROR, LOG_INFO, LOG_WARN, SpawnData::mapid, MAX_DB_MOTION_TYPE, MAX_DIFFICULTY, CreatureData::movementType, CreatureData::npcflag, SpawnData::orientation, SpawnData::phaseMask, SpawnData::posX, SpawnData::posY, SpawnData::posZ, RANDOM_MOTION_TYPE, SpawnData::ScriptId, PreparedStatementBase::SetData(), sMapMgr, sMapStore, SpawnData::spawnGroupId, SpawnData::spawnMask, CreatureData::spawntimesecs, sWorld, CreatureData::unit_flags, CreatureData::wander_distance, WORLD_UPD_CREATURE_ZONE_AREA_DATA, and WorldDatabase.

◆ LoadCreatureSparring()

void ObjectMgr::LoadCreatureSparring ( )
2675{
2676 uint32 oldMSTime = getMSTime();
2677
2678 QueryResult result = WorldDatabase.Query("SELECT GUID, SparringPCT FROM creature_sparring");
2679
2680 if (!result)
2681 {
2682 LOG_WARN("server.loading", ">> Loaded 0 sparring data. DB table `creature_sparring` is empty.");
2683 LOG_INFO("server.loading", " ");
2684 return;
2685 }
2686
2687 uint32 count = 0;
2688 do
2689 {
2690 Field* fields = result->Fetch();
2691
2692 ObjectGuid::LowType spawnId = fields[0].Get<uint32>();
2693 float sparringHealthPct = fields[1].Get<float>();
2694
2695 if (!GetCreatureData(spawnId))
2696 {
2697 LOG_ERROR("sql.sql", "Entry {} has a record in `creature_sparring` but doesn't exist in `creatures` table");
2698 continue;
2699 }
2700
2701 _creatureSparringStore[spawnId].push_back(sparringHealthPct);
2702
2703 ++count;
2704 } while (result->NextRow());
2705
2706 LOG_INFO("server.loading", ">> Loaded {} sparring data in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2707 LOG_INFO("server.loading", " ");
2708}

References _creatureSparringStore, Field::Get(), GetCreatureData(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadCreatureTemplate()

void ObjectMgr::LoadCreatureTemplate ( Field fields,
bool  triggerHook = false 
)

Loads a creature template from a database result.

Parameters
fieldsDatabase result
triggerHookIf true, will trigger the OnAfterDatabaseLoadCreatureTemplates hook. Useful if you are not calling the hook yourself.
585{
586 uint32 entry = fields[0].Get<uint32>();
587
588 CreatureTemplate& creatureTemplate = _creatureTemplateStore[entry];
589
590 // enlarge the fast cache as necessary
591 if (_creatureTemplateStoreFast.size() < entry + 1)
592 {
593 _creatureTemplateStoreFast.resize(entry + 1, nullptr);
594 }
595
596 // load a pointer to this creatureTemplate into the fast cache
597 _creatureTemplateStoreFast[entry] = &creatureTemplate;
598
599 // build the creatureTemplate
600 creatureTemplate.Entry = entry;
601
602 for (uint8 i = 0; i < MAX_DIFFICULTY - 1; ++i)
603 {
604 creatureTemplate.DifficultyEntry[i] = fields[1 + i].Get<uint32>();
605 }
606
607 for (uint8 i = 0; i < MAX_KILL_CREDIT; ++i)
608 {
609 creatureTemplate.KillCredit[i] = fields[4 + i].Get<uint32>();
610 }
611 creatureTemplate.Name = fields[6].Get<std::string>();
612 creatureTemplate.SubName = fields[7].Get<std::string>();
613 creatureTemplate.IconName = fields[8].Get<std::string>();
614 creatureTemplate.GossipMenuId = fields[9].Get<uint32>();
615 creatureTemplate.minlevel = fields[10].Get<uint8>();
616 creatureTemplate.maxlevel = fields[11].Get<uint8>();
617 creatureTemplate.expansion = uint32(fields[12].Get<int16>());
618 creatureTemplate.faction = uint32(fields[13].Get<uint16>());
619 creatureTemplate.npcflag = fields[14].Get<uint32>();
620 creatureTemplate.speed_walk = fields[15].Get<float>();
621 creatureTemplate.speed_run = fields[16].Get<float>();
622 creatureTemplate.speed_swim = fields[17].Get<float>();
623 creatureTemplate.speed_flight = fields[18].Get<float>();
624 creatureTemplate.detection_range = fields[19].Get<float>();
625 creatureTemplate.rank = uint32(fields[20].Get<uint8>());
626 creatureTemplate.dmgschool = uint32(fields[21].Get<int8>());
627 creatureTemplate.DamageModifier = fields[22].Get<float>();
628 creatureTemplate.BaseAttackTime = fields[23].Get<uint32>();
629 creatureTemplate.RangeAttackTime = fields[24].Get<uint32>();
630 creatureTemplate.BaseVariance = fields[25].Get<float>();
631 creatureTemplate.RangeVariance = fields[26].Get<float>();
632 creatureTemplate.unit_class = uint32(fields[27].Get<uint8>());
633 creatureTemplate.unit_flags = fields[28].Get<uint32>();
634 creatureTemplate.unit_flags2 = fields[29].Get<uint32>();
635 creatureTemplate.dynamicflags = fields[30].Get<uint32>();
636 creatureTemplate.family = uint32(fields[31].Get<uint8>());
637 creatureTemplate.type = uint32(fields[32].Get<uint8>());
638 creatureTemplate.type_flags = fields[33].Get<uint32>();
639 creatureTemplate.lootid = fields[34].Get<uint32>();
640 creatureTemplate.pickpocketLootId = fields[35].Get<uint32>();
641 creatureTemplate.SkinLootId = fields[36].Get<uint32>();
642
643 for (uint8 i = SPELL_SCHOOL_HOLY; i < MAX_SPELL_SCHOOL; ++i)
644 {
645 creatureTemplate.resistance[i] = 0;
646 }
647
648 for (uint8 i = 0; i < MAX_CREATURE_SPELLS; ++i)
649 {
650 creatureTemplate.spells[i] = 0;
651 }
652
653 creatureTemplate.PetSpellDataId = fields[37].Get<uint32>();
654 creatureTemplate.VehicleId = fields[38].Get<uint32>();
655 creatureTemplate.mingold = fields[39].Get<uint32>();
656 creatureTemplate.maxgold = fields[40].Get<uint32>();
657 creatureTemplate.AIName = fields[41].Get<std::string>();
658 creatureTemplate.MovementType = uint32(fields[42].Get<uint8>());
659 if (!fields[43].IsNull())
660 {
661 creatureTemplate.Movement.Ground = static_cast<CreatureGroundMovementType>(fields[43].Get<uint8>());
662 }
663
664 creatureTemplate.Movement.Swim = fields[44].Get<bool>();
665 if (!fields[45].IsNull())
666 {
667 creatureTemplate.Movement.Flight = static_cast<CreatureFlightMovementType>(fields[45].Get<uint8>());
668 }
669
670 creatureTemplate.Movement.Rooted = fields[46].Get<bool>();
671 if (!fields[47].IsNull())
672 {
673 creatureTemplate.Movement.Chase = static_cast<CreatureChaseMovementType>(fields[47].Get<uint8>());
674 }
675 if (!fields[48].IsNull())
676 {
677 creatureTemplate.Movement.Random = static_cast<CreatureRandomMovementType>(fields[48].Get<uint8>());
678 }
679 if (!fields[49].IsNull())
680 {
681 creatureTemplate.Movement.InteractionPauseTimer = fields[49].Get<uint32>();
682 }
683
684 creatureTemplate.HoverHeight = fields[50].Get<float>();
685 creatureTemplate.ModHealth = fields[51].Get<float>();
686 creatureTemplate.ModMana = fields[52].Get<float>();
687 creatureTemplate.ModArmor = fields[53].Get<float>();
688 creatureTemplate.ModExperience = fields[54].Get<float>();
689 creatureTemplate.RacialLeader = fields[55].Get<bool>();
690 creatureTemplate.movementId = fields[56].Get<uint32>();
691 creatureTemplate.RegenHealth = fields[57].Get<bool>();
692 creatureTemplate.CreatureImmunitiesId = fields[58].Get<int32>();
693 creatureTemplate.flags_extra = fields[59].Get<uint32>();
694 creatureTemplate.ScriptID = GetScriptId(fields[60].Get<std::string>());
695
696 // Warn about deprecated immunity flags that should be moved to `creature_immunities` table
697 if (creatureTemplate.flags_extra & CREATURE_FLAG_EXTRA_NO_TAUNT)
698 LOG_WARN("server.loading", "Creature (Entry: {}) has deprecated flags_extra bit NO_TAUNT (0x100) set. This will be migrated to the `creature_immunities` table in a future update.", entry);
699 if (creatureTemplate.flags_extra & CREATURE_FLAG_EXTRA_AVOID_AOE)
700 LOG_WARN("server.loading", "Creature (Entry: {}) has deprecated flags_extra bit AVOID_AOE (0x400000) set. This will be migrated to the `creature_immunities` table in a future update.", entry);
701 if (creatureTemplate.flags_extra & CREATURE_FLAG_EXTRA_IMMUNITY_KNOCKBACK)
702 LOG_WARN("server.loading", "Creature (Entry: {}) has deprecated flags_extra bit IMMUNITY_KNOCKBACK (0x40000000) set. This will be migrated to the `creature_immunities` table in a future update.", entry);
703
704 // useful if the creature template load is being triggered from outside this class
705 if (triggerHook)
706 {
707 sScriptMgr->OnAfterDatabaseLoadCreatureTemplates(_creatureTemplateStoreFast);
708 }
709}
@ CREATURE_FLAG_EXTRA_IMMUNITY_KNOCKBACK
Definition CreatureData.h:76
@ CREATURE_FLAG_EXTRA_NO_TAUNT
Definition CreatureData.h:54
@ CREATURE_FLAG_EXTRA_AVOID_AOE
Definition CreatureData.h:68
std::int32_t int32
Definition Define.h:103
#define sScriptMgr
Definition ScriptMgr.h:734
@ SPELL_SCHOOL_HOLY
Definition SharedDefines.h:272
uint32 Entry
Definition CreatureData.h:188

References _creatureTemplateStore, _creatureTemplateStoreFast, CREATURE_FLAG_EXTRA_AVOID_AOE, CREATURE_FLAG_EXTRA_IMMUNITY_KNOCKBACK, CREATURE_FLAG_EXTRA_NO_TAUNT, CreatureTemplate::Entry, Field::Get(), GetScriptId(), LOG_WARN, MAX_CREATURE_SPELLS, MAX_DIFFICULTY, MAX_KILL_CREDIT, MAX_SPELL_SCHOOL, SPELL_SCHOOL_HOLY, and sScriptMgr.

Referenced by LoadCreatureTemplates().

◆ LoadCreatureTemplateAddons()

void ObjectMgr::LoadCreatureTemplateAddons ( )
856{
857 uint32 oldMSTime = getMSTime();
858
859 // 0 1 2 3 4 5 6 7
860 QueryResult result = WorldDatabase.Query("SELECT entry, path_id, mount, bytes1, bytes2, emote, visibilityDistanceType, auras FROM creature_template_addon");
861
862 if (!result)
863 {
864 LOG_WARN("server.loading", ">> Loaded 0 creature template addon definitions. DB table `creature_template_addon` is empty.");
865 LOG_INFO("server.loading", " ");
866 return;
867 }
868
869 uint32 count = 0;
870 do
871 {
872 Field* fields = result->Fetch();
873
874 uint32 entry = fields[0].Get<uint32>();
875
876 if (!GetCreatureTemplate(entry))
877 {
878 LOG_ERROR("sql.sql", "Creature template (Entry: {}) does not exist but has a record in `creature_template_addon`", entry);
879 continue;
880 }
881
882 CreatureAddon& creatureAddon = _creatureTemplateAddonStore[entry];
883
884 creatureAddon.path_id = fields[1].Get<uint32>();
885 creatureAddon.mount = fields[2].Get<uint32>();
886 creatureAddon.bytes1 = fields[3].Get<uint32>();
887 creatureAddon.bytes2 = fields[4].Get<uint32>();
888 creatureAddon.emote = fields[5].Get<uint32>();
889 creatureAddon.visibilityDistanceType = VisibilityDistanceType(fields[6].Get<uint8>());
890
891 for (std::string_view aura : Acore::Tokenize(fields[7].Get<std::string_view>(), ' ', false))
892 {
893 SpellInfo const* spellInfo = nullptr;
894
895 if (Optional<uint32> spellId = Acore::StringTo<uint32>(aura))
896 {
897 spellInfo = sSpellMgr->GetSpellInfo(*spellId);
898 }
899
900 if (!spellInfo)
901 {
902 LOG_ERROR("sql.sql", "Creature (Entry: {}) has wrong spell '{}' defined in `auras` field in `creature_template_addon`.", entry, aura);
903 continue;
904 }
905
906 if (std::find(creatureAddon.auras.begin(), creatureAddon.auras.end(), spellInfo->Id) != creatureAddon.auras.end())
907 {
908 LOG_ERROR("sql.sql", "Creature (Entry: {}) has duplicate aura (spell {}) in `auras` field in `creature_template_addon`.", entry, spellInfo->Id);
909 continue;
910 }
911
912 if (spellInfo->GetDuration() > 0)
913 {
914 LOG_DEBUG/*ERROR*/("sql.sql", "Creature (Entry: {}) has temporary aura (spell {}) in `auras` field in `creature_template_addon`.", entry, spellInfo->Id);
915 // continue;
916 }
917
918 creatureAddon.auras.push_back(spellInfo->Id);
919 }
920
921 if (creatureAddon.mount)
922 {
923 if (!sCreatureDisplayInfoStore.LookupEntry(creatureAddon.mount))
924 {
925 LOG_ERROR("sql.sql", "Creature (Entry: {}) has invalid displayInfoId ({}) for mount defined in `creature_template_addon`", entry, creatureAddon.mount);
926 creatureAddon.mount = 0;
927 }
928 }
929
930 if (!sEmotesStore.LookupEntry(creatureAddon.emote))
931 {
932 LOG_ERROR("sql.sql", "Creature (Entry: {}) has invalid emote ({}) defined in `creature_addon`.", entry, creatureAddon.emote);
933 creatureAddon.emote = 0;
934 }
935
937 {
938 LOG_ERROR("sql.sql", "Creature (Entry: {}) has invalid visibilityDistanceType ({}) defined in `creature_template_addon`.", entry, AsUnderlyingType(creatureAddon.visibilityDistanceType));
940 }
941 ++count;
942 } while (result->NextRow());
943
944 LOG_INFO("server.loading", ">> Loaded {} Creature Template Addons in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
945 LOG_INFO("server.loading", " ");
946}

References _creatureTemplateAddonStore, AsUnderlyingType(), CreatureAddon::auras, CreatureAddon::bytes1, CreatureAddon::bytes2, CreatureAddon::emote, Field::Get(), GetCreatureTemplate(), SpellInfo::GetDuration(), getMSTime(), GetMSTimeDiffToNow(), SpellInfo::Id, LOG_DEBUG, LOG_ERROR, LOG_INFO, LOG_WARN, Max, CreatureAddon::mount, Normal, CreatureAddon::path_id, sCreatureDisplayInfoStore, sEmotesStore, sSpellMgr, Acore::Tokenize(), CreatureAddon::visibilityDistanceType, and WorldDatabase.

◆ LoadCreatureTemplateModels()

void ObjectMgr::LoadCreatureTemplateModels ( )
712{
713 uint32 oldMSTime = getMSTime();
714
715 // 0 1 2 3
716 QueryResult result = WorldDatabase.Query("SELECT CreatureID, CreatureDisplayID, DisplayScale, Probability FROM creature_template_model ORDER BY Idx ASC");
717
718 if (!result)
719 {
720 LOG_INFO("server.loading", ">> Loaded 0 creature template model definitions. DB table `creature_template_model` is empty.");
721 return;
722 }
723
724 uint32 count = 0;
725 do
726 {
727 Field* fields = result->Fetch();
728
729 uint32 creatureId = fields[0].Get<uint32>();
730 uint32 creatureDisplayId = fields[1].Get<uint32>();
731 float displayScale = fields[2].Get<float>();
732 float probability = fields[3].Get<float>();
733
734 CreatureTemplate const* cInfo = GetCreatureTemplate(creatureId);
735 if (!cInfo)
736 {
737 LOG_ERROR("sql.sql", "Creature template (Entry: {}) does not exist but has a record in `creature_template_model`", creatureId);
738 continue;
739 }
740
741 CreatureDisplayInfoEntry const* displayEntry = sCreatureDisplayInfoStore.LookupEntry(creatureDisplayId);
742 if (!displayEntry)
743 {
744 LOG_ERROR("sql.sql", "Creature (Entry: {}) lists non-existing CreatureDisplayID id ({}), this can crash the client.", creatureId, creatureDisplayId);
745 continue;
746 }
747
748 CreatureModelInfo const* modelInfo = GetCreatureModelInfo(creatureDisplayId);
749 if (!modelInfo)
750 LOG_ERROR("sql.sql", "No model data exist for `CreatureDisplayID` = {} listed by creature (Entry: {}).", creatureDisplayId, creatureId);
751
752 if (displayScale <= 0.0f)
753 displayScale = 1.0f;
754
755 const_cast<CreatureTemplate*>(cInfo)->Models.emplace_back(creatureDisplayId, displayScale, probability);
756
757 ++count;
758 } while (result->NextRow());
759
760 LOG_INFO("server.loading", ">> Loaded {} creature template models in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
761}

References Field::Get(), GetCreatureModelInfo(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, sCreatureDisplayInfoStore, and WorldDatabase.

Referenced by LoadCreatureTemplates().

◆ LoadCreatureTemplateResistances()

void ObjectMgr::LoadCreatureTemplateResistances ( )
764{
765 uint32 oldMSTime = getMSTime();
766
767 // 0 1 2
768 QueryResult result = WorldDatabase.Query("SELECT CreatureID, School, Resistance FROM creature_template_resistance");
769
770 if (!result)
771 {
772 LOG_WARN("server.loading", ">> Loaded 0 creature template resistance definitions. DB table `creature_template_resistance` is empty.");
773 LOG_INFO("server.loading", " ");
774 return;
775 }
776
777 uint32 count = 0;
778
779 do
780 {
781 Field* fields = result->Fetch();
782
783 uint32 creatureID = fields[0].Get<uint32>();
784 uint8 school = fields[1].Get<uint8>();
785
786 if (school == SPELL_SCHOOL_NORMAL || school >= MAX_SPELL_SCHOOL)
787 {
788 LOG_ERROR("sql.sql", "creature_template_resistance has resistance definitions for creature {} but this school {} doesn't exist", creatureID, school);
789 continue;
790 }
791
792 CreatureTemplateContainer::iterator itr = _creatureTemplateStore.find(creatureID);
793 if (itr == _creatureTemplateStore.end())
794 {
795 LOG_ERROR("sql.sql", "creature_template_resistance has resistance definitions for creature {} but this creature doesn't exist", creatureID);
796 continue;
797 }
798
799 CreatureTemplate& creatureTemplate = itr->second;
800 creatureTemplate.resistance[school] = fields[2].Get<int16>();
801
802 ++count;
803 } while (result->NextRow());
804
805 LOG_INFO("server.loading", ">> Loaded {} Creature Template Resistances in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
806 LOG_INFO("server.loading", " ");
807}
int32 resistance[MAX_SPELL_SCHOOL]
Definition CreatureData.h:223

References _creatureTemplateStore, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, MAX_SPELL_SCHOOL, CreatureTemplate::resistance, SPELL_SCHOOL_NORMAL, and WorldDatabase.

Referenced by LoadCreatureTemplates().

◆ LoadCreatureTemplates()

void ObjectMgr::LoadCreatureTemplates ( )
523{
524 uint32 oldMSTime = getMSTime();
525
526// 0 1 2 3 4 5 6 7 8
527 QueryResult result = WorldDatabase.Query("SELECT entry, difficulty_entry_1, difficulty_entry_2, difficulty_entry_3, KillCredit1, KillCredit2, name, subname, IconName, "
528// 9 10 11 12 13 14 15 16 17 18 19 20 21
529 "gossip_menu_id, minlevel, maxlevel, exp, faction, npcflag, speed_walk, speed_run, speed_swim, speed_flight, detection_range, `rank`, dmgschool, "
530// 22 23 24 25 26 27 28 29 30 31
531 "DamageModifier, BaseAttackTime, RangeAttackTime, BaseVariance, RangeVariance, unit_class, unit_flags, unit_flags2, dynamicflags, family, "
532// 32 33 34 35 36
533 "type, type_flags, lootid, pickpocketloot, skinloot, "
534// 37 38 39 40 41 42 43 44 45 46
535 "PetSpellDataId, VehicleId, mingold, maxgold, AIName, MovementType, ctm.Ground, ctm.Swim, ctm.Flight, ctm.Rooted, "
536// 47 48 49 50 51 52 53 54 55 56 57
537 "ctm.Chase, ctm.Random, ctm.InteractionPauseTimer, HoverHeight, HealthModifier, ManaModifier, ArmorModifier, ExperienceModifier, RacialLeader, movementId, RegenHealth, "
538// 58 59 60
539 "CreatureImmunitiesId, flags_extra, ScriptName "
540 "FROM creature_template ct LEFT JOIN creature_template_movement ctm ON ct.entry = ctm.CreatureId ORDER BY entry DESC;");
541
542 if (!result)
543 {
544 LOG_WARN("server.loading", ">> Loaded 0 creature template definitions. DB table `creature_template` is empty.");
545 return;
546 }
547
548 _creatureTemplateStore.rehash(result->GetRowCount());
550
551 uint32 count = 0;
552 do
553 {
554 Field* fields = result->Fetch();
555 LoadCreatureTemplate(fields);
556 ++count;
557 } while (result->NextRow());
558
559 // We load the creature models after loading but before checking
561
562 sScriptMgr->OnAfterDatabaseLoadCreatureTemplates(_creatureTemplateStoreFast);
563
566
567 // Checking needs to be done after loading because of the difficulty self referencing
568 for (CreatureTemplateContainer::iterator itr = _creatureTemplateStore.begin(); itr != _creatureTemplateStore.end(); ++itr)
569 {
570 CheckCreatureTemplate(&itr->second);
571 itr->second.InitializeQueryData();
572 }
573
574 LOG_INFO("server.loading", ">> Loaded {} Creature Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
575 LOG_INFO("server.loading", " ");
576}
void LoadCreatureTemplateResistances()
Definition ObjectMgr.cpp:763
void LoadCreatureTemplateSpells()
Definition ObjectMgr.cpp:809
void CheckCreatureTemplate(CreatureTemplate const *cInfo)
Definition ObjectMgr.cpp:963
void LoadCreatureTemplate(Field *fields, bool triggerHook=false)
Loads a creature template from a database result.
Definition ObjectMgr.cpp:584
void LoadCreatureTemplateModels()
Definition ObjectMgr.cpp:711

References _creatureTemplateStore, _creatureTemplateStoreFast, CheckCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), LoadCreatureTemplate(), LoadCreatureTemplateModels(), LoadCreatureTemplateResistances(), LoadCreatureTemplateSpells(), LOG_INFO, LOG_WARN, sScriptMgr, and WorldDatabase.

◆ LoadCreatureTemplateSpells()

void ObjectMgr::LoadCreatureTemplateSpells ( )
810{
811 uint32 oldMSTime = getMSTime();
812
813 // 0 1 2
814 QueryResult result = WorldDatabase.Query("SELECT CreatureID, `Index`, Spell FROM creature_template_spell");
815
816 if (!result)
817 {
818 LOG_WARN("server.loading", ">> Loaded 0 creature template spell definitions. DB table `creature_template_spell` is empty.");
819 LOG_INFO("server.loading", " ");
820 return;
821 }
822
823 uint32 count = 0;
824
825 do
826 {
827 Field* fields = result->Fetch();
828
829 uint32 creatureID = fields[0].Get<uint32>();
830 uint8 index = fields[1].Get<uint8>();
831
832 if (index >= MAX_CREATURE_SPELLS)
833 {
834 LOG_ERROR("sql.sql", "creature_template_spell has spell definitions for creature {} with a incorrect index {}", creatureID, index);
835 continue;
836 }
837
838 CreatureTemplateContainer::iterator itr = _creatureTemplateStore.find(creatureID);
839 if (itr == _creatureTemplateStore.end())
840 {
841 LOG_ERROR("sql.sql", "creature_template_spell has spell definitions for creature {} but this creature doesn't exist", creatureID);
842 continue;
843 }
844
845 CreatureTemplate& creatureTemplate = itr->second;
846 creatureTemplate.spells[index] = fields[2].Get<uint32>();
847
848 ++count;
849 } while (result->NextRow());
850
851 LOG_INFO("server.loading", ">> Loaded {} Creature Template Spells in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
852 LOG_INFO("server.loading", " ");
853}
uint32 spells[MAX_CREATURE_SPELLS]
Definition CreatureData.h:224

References _creatureTemplateStore, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, MAX_CREATURE_SPELLS, CreatureTemplate::spells, and WorldDatabase.

Referenced by LoadCreatureTemplates().

◆ LoadEquipmentTemplates()

void ObjectMgr::LoadEquipmentTemplates ( )
1480{
1481 uint32 oldMSTime = getMSTime();
1482
1483 // 0 1 2 3 4
1484 QueryResult result = WorldDatabase.Query("SELECT CreatureID, ID, ItemID1, ItemID2, ItemID3 FROM creature_equip_template");
1485
1486 if (!result)
1487 {
1488 LOG_WARN("server.loading", ">> Loaded 0 creature equipment templates. DB table `creature_equip_template` is empty!");
1489 LOG_INFO("server.loading", " ");
1490 return;
1491 }
1492
1493 uint32 count = 0;
1494 do
1495 {
1496 Field* fields = result->Fetch();
1497
1498 uint32 entry = fields[0].Get<uint32>();
1499
1500 if (!GetCreatureTemplate(entry))
1501 {
1502 LOG_ERROR("sql.sql", "Creature template (CreatureID: {}) does not exist but has a record in `creature_equip_template`", entry);
1503 continue;
1504 }
1505
1506 uint8 id = fields[1].Get<uint8>();
1507 if (!id)
1508 {
1509 LOG_ERROR("sql.sql", "Creature equipment template with id 0 found for creature {}, skipped.", entry);
1510 continue;
1511 }
1512
1513 EquipmentInfo& equipmentInfo = _equipmentInfoStore[entry][id];
1514
1515 equipmentInfo.ItemEntry[0] = fields[2].Get<uint32>();
1516 equipmentInfo.ItemEntry[1] = fields[3].Get<uint32>();
1517 equipmentInfo.ItemEntry[2] = fields[4].Get<uint32>();
1518
1519 for (uint8 i = 0; i < MAX_EQUIPMENT_ITEMS; ++i)
1520 {
1521 if (!equipmentInfo.ItemEntry[i])
1522 continue;
1523
1524 ItemEntry const* dbcItem = sItemStore.LookupEntry(equipmentInfo.ItemEntry[i]);
1525
1526 if (!dbcItem)
1527 {
1528 LOG_ERROR("sql.sql", "Unknown item (ID={}) in creature_equip_template.ItemID{} for CreatureID = {} and ID = {}, forced to 0.",
1529 equipmentInfo.ItemEntry[i], i + 1, entry, id);
1530 equipmentInfo.ItemEntry[i] = 0;
1531 continue;
1532 }
1533
1534 if (dbcItem->InventoryType != INVTYPE_WEAPON &&
1535 dbcItem->InventoryType != INVTYPE_SHIELD &&
1536 dbcItem->InventoryType != INVTYPE_RANGED &&
1537 dbcItem->InventoryType != INVTYPE_2HWEAPON &&
1540 dbcItem->InventoryType != INVTYPE_HOLDABLE &&
1541 dbcItem->InventoryType != INVTYPE_THROWN &&
1543 {
1544 LOG_ERROR("sql.sql", "Item (ID={}) in creature_equip_template.ItemID{} for CreatureID = {} and ID = {} is not equipable in a hand, forced to 0.",
1545 equipmentInfo.ItemEntry[i], i + 1, entry, id);
1546 equipmentInfo.ItemEntry[i] = 0;
1547 }
1548 }
1549
1550 ++count;
1551 } while (result->NextRow());
1552
1553 LOG_INFO("server.loading", ">> Loaded {} Equipment Templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
1554 LOG_INFO("server.loading", " ");
1555}
#define MAX_EQUIPMENT_ITEMS
Definition CreatureData.h:36
@ INVTYPE_HOLDABLE
Definition ItemTemplate.h:279
@ INVTYPE_RANGED
Definition ItemTemplate.h:271
@ INVTYPE_THROWN
Definition ItemTemplate.h:281
@ INVTYPE_RANGEDRIGHT
Definition ItemTemplate.h:282
@ INVTYPE_WEAPON
Definition ItemTemplate.h:269
@ INVTYPE_WEAPONMAINHAND
Definition ItemTemplate.h:277
@ INVTYPE_WEAPONOFFHAND
Definition ItemTemplate.h:278
@ INVTYPE_2HWEAPON
Definition ItemTemplate.h:273
@ INVTYPE_SHIELD
Definition ItemTemplate.h:270
Definition CreatureData.h:360
uint32 ItemEntry[MAX_EQUIPMENT_ITEMS]
Definition CreatureData.h:361
uint32 InventoryType
Definition DBCStructure.h:1150

References _equipmentInfoStore, Field::Get(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), ItemEntry::InventoryType, INVTYPE_2HWEAPON, INVTYPE_HOLDABLE, INVTYPE_RANGED, INVTYPE_RANGEDRIGHT, INVTYPE_SHIELD, INVTYPE_THROWN, INVTYPE_WEAPON, INVTYPE_WEAPONMAINHAND, INVTYPE_WEAPONOFFHAND, EquipmentInfo::ItemEntry, LOG_ERROR, LOG_INFO, LOG_WARN, MAX_EQUIPMENT_ITEMS, sItemStore, and WorldDatabase.

◆ LoadEventScripts()

void ObjectMgr::LoadEventScripts ( )
6187{
6189
6190 std::set<uint32> evt_scripts;
6191 // Load all possible script entries from gameobjects
6193 for (GameObjectTemplateContainer::const_iterator itr = gotc->begin(); itr != gotc->end(); ++itr)
6194 if (uint32 eventId = itr->second.GetEventScriptId())
6195 evt_scripts.insert(eventId);
6196
6197 // Load all possible script entries from spells
6198 for (uint32 i = 1; i < sSpellMgr->GetSpellInfoStoreSize(); ++i)
6199 if (SpellInfo const* spell = sSpellMgr->GetSpellInfo(i))
6200 for (uint8 j = 0; j < MAX_SPELL_EFFECTS; ++j)
6201 if (spell->Effects[j].Effect == SPELL_EFFECT_SEND_EVENT)
6202 if (spell->Effects[j].MiscValue)
6203 evt_scripts.insert(spell->Effects[j].MiscValue);
6204
6205 for (std::size_t path_idx = 0; path_idx < sTaxiPathNodesByPath.size(); ++path_idx)
6206 {
6207 for (std::size_t node_idx = 0; node_idx < sTaxiPathNodesByPath[path_idx].size(); ++node_idx)
6208 {
6209 TaxiPathNodeEntry const* node = sTaxiPathNodesByPath[path_idx][node_idx];
6210
6211 if (node->arrivalEventID)
6212 evt_scripts.insert(node->arrivalEventID);
6213
6214 if (node->departureEventID)
6215 evt_scripts.insert(node->departureEventID);
6216 }
6217 }
6218
6219 // Then check if all scripts are in above list of possible script entries
6220 for (ScriptMapMap::const_iterator itr = sEventScripts.begin(); itr != sEventScripts.end(); ++itr)
6221 {
6222 std::set<uint32>::const_iterator itr2 = evt_scripts.find(itr->first);
6223 if (itr2 == evt_scripts.end())
6224 LOG_ERROR("sql.sql", "Table `event_scripts` has script (Id: {}) not referring to any gameobject_template type 10 data2 field, type 3 data6 field, type 13 data 2 field or any spell effect {}",
6225 itr->first, SPELL_EFFECT_SEND_EVENT);
6226 }
6227}
TaxiPathNodesByPath sTaxiPathNodesByPath
Definition DBCStores.cpp:187
#define MAX_SPELL_EFFECTS
Definition DBCStructure.h:1637
std::unordered_map< uint32, GameObjectTemplate > GameObjectTemplateContainer
Definition GameObject.h:42
ScriptMapMap sEventScripts
Definition ObjectMgr.cpp:61
@ SCRIPTS_EVENT
Definition ObjectMgr.h:150
@ SPELL_EFFECT_SEND_EVENT
Definition SharedDefines.h:827
GameObjectTemplateContainer const * GetGameObjectTemplates() const
Definition ObjectMgr.h:763
void LoadScripts(ScriptsType type)
Definition ObjectMgr.cpp:5844
Definition DBCStructure.h:1973
uint32 arrivalEventID
Definition DBCStructure.h:1983
uint32 departureEventID
Definition DBCStructure.h:1984

References TaxiPathNodeEntry::arrivalEventID, TaxiPathNodeEntry::departureEventID, GetGameObjectTemplates(), LoadScripts(), LOG_ERROR, MAX_SPELL_EFFECTS, SCRIPTS_EVENT, sEventScripts, SPELL_EFFECT_SEND_EVENT, sSpellMgr, and sTaxiPathNodesByPath.

◆ LoadExplorationBaseXP()

void ObjectMgr::LoadExplorationBaseXP ( )
8073{
8074 uint32 oldMSTime = getMSTime();
8075
8076 QueryResult result = WorldDatabase.Query("SELECT level, basexp FROM exploration_basexp");
8077
8078 if (!result)
8079 {
8080 LOG_WARN("server.loading", ">> Loaded 0 BaseXP definitions. DB table `exploration_basexp` is empty.");
8081 LOG_INFO("server.loading", " ");
8082 return;
8083 }
8084
8085 uint32 count = 0;
8086
8087 do
8088 {
8089 Field* fields = result->Fetch();
8090 uint8 level = fields[0].Get<uint8>();
8091 uint32 basexp = fields[1].Get<int32>();
8092 _baseXPTable[level] = basexp;
8093 ++count;
8094 } while (result->NextRow());
8095
8096 LOG_INFO("server.loading", ">> Loaded {} BaseXP Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8097 LOG_INFO("server.loading", " ");
8098}

References _baseXPTable, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadFactionChangeAchievements()

void ObjectMgr::LoadFactionChangeAchievements ( )
10584{
10585 uint32 oldMSTime = getMSTime();
10586
10587 QueryResult result = WorldDatabase.Query("SELECT alliance_id, horde_id FROM player_factionchange_achievement");
10588
10589 if (!result)
10590 {
10591 LOG_WARN("server.loading", ">> Loaded 0 faction change achievement pairs. DB table `player_factionchange_achievement` is empty.");
10592 LOG_INFO("server.loading", " ");
10593 return;
10594 }
10595
10596 uint32 count = 0;
10597
10598 do
10599 {
10600 Field* fields = result->Fetch();
10601
10602 uint32 alliance = fields[0].Get<uint32>();
10603 uint32 horde = fields[1].Get<uint32>();
10604
10605 if (!sAchievementStore.LookupEntry(alliance))
10606 LOG_ERROR("sql.sql", "Achievement {} (alliance_id) referenced in `player_factionchange_achievement` does not exist, pair skipped!", alliance);
10607 else if (!sAchievementStore.LookupEntry(horde))
10608 LOG_ERROR("sql.sql", "Achievement {} (horde_id) referenced in `player_factionchange_achievement` does not exist, pair skipped!", horde);
10609 else
10610 FactionChangeAchievements[alliance] = horde;
10611
10612 ++count;
10613 } while (result->NextRow());
10614
10615 LOG_INFO("server.loading", ">> Loaded {} faction change achievement pairs in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10616 LOG_INFO("server.loading", " ");
10617}
CharacterConversionMap FactionChangeAchievements
Definition ObjectMgr.h:1489

References FactionChangeAchievements, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sAchievementStore, and WorldDatabase.

◆ LoadFactionChangeItems()

void ObjectMgr::LoadFactionChangeItems ( )
10620{
10621 uint32 oldMSTime = getMSTime();
10622
10623 QueryResult result = WorldDatabase.Query("SELECT alliance_id, horde_id FROM player_factionchange_items");
10624
10625 if (!result)
10626 {
10627 LOG_WARN("server.loading", ">> Loaded 0 faction change item pairs. DB table `player_factionchange_items` is empty.");
10628 LOG_INFO("server.loading", " ");
10629 return;
10630 }
10631
10632 uint32 count = 0;
10633
10634 do
10635 {
10636 Field* fields = result->Fetch();
10637
10638 uint32 alliance = fields[0].Get<uint32>();
10639 uint32 horde = fields[1].Get<uint32>();
10640
10641 if (!GetItemTemplate(alliance))
10642 LOG_ERROR("sql.sql", "Item {} (alliance_id) referenced in `player_factionchange_items` does not exist, pair skipped!", alliance);
10643 else if (!GetItemTemplate(horde))
10644 LOG_ERROR("sql.sql", "Item {} (horde_id) referenced in `player_factionchange_items` does not exist, pair skipped!", horde);
10645 else
10646 FactionChangeItems[alliance] = horde;
10647
10648 ++count;
10649 } while (result->NextRow());
10650
10651 LOG_INFO("server.loading", ">> Loaded {} faction change item pairs in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10652 LOG_INFO("server.loading", " ");
10653}
CharacterConversionMap FactionChangeItems
Definition ObjectMgr.h:1490

References FactionChangeItems, Field::Get(), GetItemTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadFactionChangeQuests()

void ObjectMgr::LoadFactionChangeQuests ( )
10656{
10657 uint32 oldMSTime = getMSTime();
10658
10659 QueryResult result = WorldDatabase.Query("SELECT alliance_id, horde_id FROM player_factionchange_quests");
10660
10661 if (!result)
10662 {
10663 LOG_WARN("server.loading", ">> Loaded 0 faction change quest pairs. DB table `player_factionchange_quests` is empty.");
10664 LOG_INFO("server.loading", " ");
10665 return;
10666 }
10667
10668 uint32 count = 0;
10669
10670 do
10671 {
10672 Field* fields = result->Fetch();
10673
10674 uint32 alliance = fields[0].Get<uint32>();
10675 uint32 horde = fields[1].Get<uint32>();
10676
10677 if (!GetQuestTemplate(alliance))
10678 LOG_ERROR("sql.sql", "Quest {} (alliance_id) referenced in `player_factionchange_quests` does not exist, pair skipped!", alliance);
10679 else if (!GetQuestTemplate(horde))
10680 LOG_ERROR("sql.sql", "Quest {} (horde_id) referenced in `player_factionchange_quests` does not exist, pair skipped!", horde);
10681 else
10682 FactionChangeQuests[alliance] = horde;
10683
10684 ++count;
10685 } while (result->NextRow());
10686
10687 LOG_INFO("server.loading", ">> Loaded {} faction change quest pairs in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10688 LOG_INFO("server.loading", " ");
10689}
CharacterConversionMap FactionChangeQuests
Definition ObjectMgr.h:1491

References FactionChangeQuests, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), GetQuestTemplate(), LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadFactionChangeReputations()

void ObjectMgr::LoadFactionChangeReputations ( )
10692{
10693 uint32 oldMSTime = getMSTime();
10694
10695 QueryResult result = WorldDatabase.Query("SELECT alliance_id, horde_id FROM player_factionchange_reputations");
10696
10697 if (!result)
10698 {
10699 LOG_WARN("server.loading", ">> Loaded 0 faction change reputation pairs. DB table `player_factionchange_reputations` is empty.");
10700 LOG_INFO("server.loading", " ");
10701 return;
10702 }
10703
10704 uint32 count = 0;
10705
10706 do
10707 {
10708 Field* fields = result->Fetch();
10709
10710 uint32 alliance = fields[0].Get<uint32>();
10711 uint32 horde = fields[1].Get<uint32>();
10712
10713 if (!sFactionStore.LookupEntry(alliance))
10714 LOG_ERROR("sql.sql", "Reputation {} (alliance_id) referenced in `player_factionchange_reputations` does not exist, pair skipped!", alliance);
10715 else if (!sFactionStore.LookupEntry(horde))
10716 LOG_ERROR("sql.sql", "Reputation {} (horde_id) referenced in `player_factionchange_reputations` does not exist, pair skipped!", horde);
10717 else
10718 FactionChangeReputation[alliance] = horde;
10719
10720 ++count;
10721 } while (result->NextRow());
10722
10723 LOG_INFO("server.loading", ">> Loaded {} faction change reputation pairs in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10724 LOG_INFO("server.loading", " ");
10725}
DBCStorage< FactionEntry > sFactionStore(FactionEntryfmt)
CharacterConversionMap FactionChangeReputation
Definition ObjectMgr.h:1492

References FactionChangeReputation, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sFactionStore, and WorldDatabase.

◆ LoadFactionChangeSpells()

void ObjectMgr::LoadFactionChangeSpells ( )
10728{
10729 uint32 oldMSTime = getMSTime();
10730
10731 QueryResult result = WorldDatabase.Query("SELECT alliance_id, horde_id FROM player_factionchange_spells");
10732
10733 if (!result)
10734 {
10735 LOG_WARN("server.loading", ">> Loaded 0 faction change spell pairs. DB table `player_factionchange_spells` is empty.");
10736 LOG_INFO("server.loading", " ");
10737 return;
10738 }
10739
10740 uint32 count = 0;
10741
10742 do
10743 {
10744 Field* fields = result->Fetch();
10745
10746 uint32 alliance = fields[0].Get<uint32>();
10747 uint32 horde = fields[1].Get<uint32>();
10748
10749 if (!sSpellMgr->GetSpellInfo(alliance))
10750 LOG_ERROR("sql.sql", "Spell {} (alliance_id) referenced in `player_factionchange_spells` does not exist, pair skipped!", alliance);
10751 else if (!sSpellMgr->GetSpellInfo(horde))
10752 LOG_ERROR("sql.sql", "Spell {} (horde_id) referenced in `player_factionchange_spells` does not exist, pair skipped!", horde);
10753 else
10754 FactionChangeSpells[alliance] = horde;
10755
10756 ++count;
10757 } while (result->NextRow());
10758
10759 LOG_INFO("server.loading", ">> Loaded {} faction change spell pairs in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10760 LOG_INFO("server.loading", " ");
10761}
CharacterConversionMap FactionChangeSpells
Definition ObjectMgr.h:1493

References FactionChangeSpells, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sSpellMgr, and WorldDatabase.

◆ LoadFactionChangeTitles()

void ObjectMgr::LoadFactionChangeTitles ( )
10764{
10765 uint32 oldMSTime = getMSTime();
10766
10767 QueryResult result = WorldDatabase.Query("SELECT alliance_id, horde_id FROM player_factionchange_titles");
10768
10769 if (!result)
10770 {
10771 LOG_WARN("server.loading", ">> Loaded 0 faction change title pairs. DB table `player_factionchange_title` is empty.");
10772 return;
10773 }
10774
10775 uint32 count = 0;
10776
10777 do
10778 {
10779 Field* fields = result->Fetch();
10780
10781 uint32 alliance = fields[0].Get<uint32>();
10782 uint32 horde = fields[1].Get<uint32>();
10783
10784 if (!sCharTitlesStore.LookupEntry(alliance))
10785 LOG_ERROR("sql.sql", "Title {} (alliance_id) referenced in `player_factionchange_title` does not exist, pair skipped!", alliance);
10786 else if (!sCharTitlesStore.LookupEntry(horde))
10787 LOG_ERROR("sql.sql", "Title {} (horde_id) referenced in `player_factionchange_title` does not exist, pair skipped!", horde);
10788 else
10789 FactionChangeTitles[alliance] = horde;
10790
10791 ++count;
10792 } while (result->NextRow());
10793
10794 LOG_INFO("server.loading", ">> Loaded {} faction change title pairs in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10795 LOG_INFO("server.loading", " ");
10796}
DBCStorage< CharTitlesEntry > sCharTitlesStore(CharTitlesEntryfmt)
CharacterConversionMap FactionChangeTitles
Definition ObjectMgr.h:1494

References FactionChangeTitles, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sCharTitlesStore, and WorldDatabase.

◆ LoadFishingBaseSkillLevel()

void ObjectMgr::LoadFishingBaseSkillLevel ( )
9408{
9409 uint32 oldMSTime = getMSTime();
9410
9411 _fishingBaseForAreaStore.clear(); // for reload case
9412
9413 QueryResult result = WorldDatabase.Query("SELECT entry, skill FROM skill_fishing_base_level");
9414
9415 if (!result)
9416 {
9417 LOG_WARN("server.loading", ">> Loaded 0 areas for fishing base skill level. DB table `skill_fishing_base_level` is empty.");
9418 LOG_INFO("server.loading", " ");
9419 return;
9420 }
9421
9422 uint32 count = 0;
9423
9424 do
9425 {
9426 Field* fields = result->Fetch();
9427 uint32 entry = fields[0].Get<uint32>();
9428 int32 skill = fields[1].Get<int16>();
9429
9430 AreaTableEntry const* fArea = sAreaTableStore.LookupEntry(entry);
9431 if (!fArea)
9432 {
9433 LOG_ERROR("sql.sql", "AreaId {} defined in `skill_fishing_base_level` does not exist", entry);
9434 continue;
9435 }
9436
9437 _fishingBaseForAreaStore[entry] = skill;
9438 ++count;
9439 } while (result->NextRow());
9440
9441 LOG_INFO("server.loading", ">> Loaded {} areas for fishing base skill level in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
9442 LOG_INFO("server.loading", " ");
9443}

References _fishingBaseForAreaStore, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sAreaTableStore, and WorldDatabase.

◆ LoadGameObjectAddons()

void ObjectMgr::LoadGameObjectAddons ( )
1363{
1364 uint32 oldMSTime = getMSTime();
1365
1366 // 0 1 2 3 4 5 6
1367 QueryResult result = WorldDatabase.Query("SELECT guid, parent_rotation0, parent_rotation1, parent_rotation2, parent_rotation3, invisibilityType, invisibilityValue FROM gameobject_addon");
1368
1369 if (!result)
1370 {
1371 LOG_WARN("server.loading", ">> Loaded 0 gameobject addon definitions. DB table `gameobject_addon` is empty.");
1372 LOG_INFO("server.loading", " ");
1373 return;
1374 }
1375
1376 uint32 count = 0;
1377 do
1378 {
1379 Field* fields = result->Fetch();
1380
1381 ObjectGuid::LowType guid = fields[0].Get<uint32>();
1382
1383 const GameObjectData* goData = GetGameObjectData(guid);
1384 if (!goData)
1385 {
1386 LOG_ERROR("sql.sql", "GameObject (GUID: {}) does not exist but has a record in `gameobject_addon`", guid);
1387 continue;
1388 }
1389
1390 GameObjectAddon& gameObjectAddon = _gameObjectAddonStore[guid];
1391 gameObjectAddon.ParentRotation = QuaternionData(fields[1].Get<float>(), fields[2].Get<float>(), fields[3].Get<float>(), fields[4].Get<float>());
1392 gameObjectAddon.invisibilityType = InvisibilityType(fields[5].Get<uint8>());
1393 gameObjectAddon.InvisibilityValue = fields[6].Get<uint32>();
1394
1395 if (gameObjectAddon.invisibilityType >= TOTAL_INVISIBILITY_TYPES)
1396 {
1397 LOG_ERROR("sql.sql", "GameObject (GUID: {}) has invalid InvisibilityType in `gameobject_addon`", guid);
1398 gameObjectAddon.invisibilityType = INVISIBILITY_GENERAL;
1399 gameObjectAddon.InvisibilityValue = 0;
1400 }
1401
1402 if (gameObjectAddon.invisibilityType && !gameObjectAddon.InvisibilityValue)
1403 {
1404 LOG_ERROR("sql.sql", "GameObject (GUID: {}) has InvisibilityType set but has no InvisibilityValue in `gameobject_addon`, set to 1", guid);
1405 gameObjectAddon.InvisibilityValue = 1;
1406 }
1407
1408 if (!gameObjectAddon.ParentRotation.IsUnit())
1409 {
1410 LOG_ERROR("sql.sql", "GameObject (GUID: {}) has invalid parent rotation in `gameobject_addon`, set to default", guid);
1411 gameObjectAddon.ParentRotation = QuaternionData();
1412 }
1413
1414 ++count;
1415 } while (result->NextRow());
1416
1417 LOG_INFO("server.loading", ">> Loaded {} Gameobject Addons in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
1418 LOG_INFO("server.loading", " ");
1419}
InvisibilityType
Definition SharedDefines.h:1242
@ TOTAL_INVISIBILITY_TYPES
Definition SharedDefines.h:1256
@ INVISIBILITY_GENERAL
Definition SharedDefines.h:1243
Definition GameObjectData.h:699
QuaternionData ParentRotation
Definition GameObjectData.h:700
uint32 InvisibilityValue
Definition GameObjectData.h:702
InvisibilityType invisibilityType
Definition GameObjectData.h:701
Definition GameObjectData.h:683
bool IsUnit() const
Definition GameObject.cpp:41

References _gameObjectAddonStore, Field::Get(), GetGameObjectData(), getMSTime(), GetMSTimeDiffToNow(), INVISIBILITY_GENERAL, GameObjectAddon::invisibilityType, GameObjectAddon::InvisibilityValue, QuaternionData::IsUnit(), LOG_ERROR, LOG_INFO, LOG_WARN, GameObjectAddon::ParentRotation, TOTAL_INVISIBILITY_TYPES, and WorldDatabase.

◆ LoadGameObjectDataFromDB()

GameObjectData const * ObjectMgr::LoadGameObjectDataFromDB ( ObjectGuid::LowType  spawnId)

Loads a single gameobject spawn entry from the database into the data store cache.

This is needed as a prerequisite for GameObject::LoadGameObjectFromDB(), which reads from the in-memory cache (via GetGameObjectData()) rather than querying the DB itself. For spawns not loaded during server startup, this method populates the cache so that GameObject::LoadGameObjectFromDB() can then create the live entity.

Returns the cached data if already loaded, or nullptr if the spawn doesn't exist or fails validation.

Parameters
spawnIdThe gameobject spawn GUID to load.
Returns
Pointer to the cached GameObjectData, or nullptr on failure.
3029{
3030 GameObjectData const* data = GetGameObjectData(spawnId);
3031 if (data)
3032 return data;
3033
3034 QueryResult result = WorldDatabase.Query("SELECT gameobject.guid, id, map, position_x, position_y, position_z, orientation, "
3035 "rotation0, rotation1, rotation2, rotation3, spawntimesecs, animprogress, state, spawnMask, phaseMask, "
3036 "ScriptName "
3037 "FROM gameobject WHERE gameobject.guid = {}", spawnId);
3038
3039 if (!result)
3040 return nullptr;
3041
3042 Field* fields = result->Fetch();
3043 uint32 entry = fields[1].Get<uint32>();
3044
3045 GameObjectTemplate const* gInfo = GetGameObjectTemplate(entry);
3046 if (!gInfo)
3047 {
3048 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {}) with non-existing gameobject entry {}, skipped.", spawnId, entry);
3049 return nullptr;
3050 }
3051
3052 if (gInfo->displayId && !sGameObjectDisplayInfoStore.LookupEntry(gInfo->displayId))
3053 {
3054 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry {} GoType: {}) with an invalid displayId ({}), not loaded.",
3055 spawnId, entry, gInfo->type, gInfo->displayId);
3056 return nullptr;
3057 }
3058
3059 GameObjectData& goData = _gameObjectDataStore[spawnId];
3060 goData.id = entry;
3061 goData.mapid = fields[2].Get<uint16>();
3062 goData.posX = fields[3].Get<float>();
3063 goData.posY = fields[4].Get<float>();
3064 goData.posZ = fields[5].Get<float>();
3065 goData.orientation = fields[6].Get<float>();
3066 goData.rotation.x = fields[7].Get<float>();
3067 goData.rotation.y = fields[8].Get<float>();
3068 goData.rotation.z = fields[9].Get<float>();
3069 goData.rotation.w = fields[10].Get<float>();
3070 goData.spawntimesecs = fields[11].Get<int32>();
3071 goData.animprogress = fields[12].Get<uint8>();
3072 goData.artKit = 0;
3073 goData.ScriptId = GetScriptId(fields[16].Get<std::string>());
3074
3075 if (!goData.ScriptId)
3076 goData.ScriptId = gInfo->ScriptId;
3077
3078 MapEntry const* mapEntry = sMapStore.LookupEntry(goData.mapid);
3079 if (!mapEntry)
3080 {
3081 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) spawned on a non-existing map (Id: {}), skipped.", spawnId, entry, goData.mapid);
3082 _gameObjectDataStore.erase(spawnId);
3083 return nullptr;
3084 }
3085
3086 if (goData.spawntimesecs == 0 && gInfo->IsDespawnAtAction())
3087 {
3088 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with `spawntimesecs` (0) value, but the gameobject is marked as despawnable at action.", spawnId, entry);
3089 }
3090
3091 uint32 go_state = fields[13].Get<uint8>();
3092 if (go_state >= MAX_GO_STATE)
3093 {
3094 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid `state` ({}) value, skipped.", spawnId, entry, go_state);
3095 _gameObjectDataStore.erase(spawnId);
3096 return nullptr;
3097 }
3098 goData.go_state = GOState(go_state);
3099
3100 goData.spawnMask = fields[14].Get<uint8>();
3101 goData.phaseMask = fields[15].Get<uint32>();
3102
3103 if (goData.rotation.x < -1.0f || goData.rotation.x > 1.0f)
3104 {
3105 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotationX ({}) value, skipped.", spawnId, entry, goData.rotation.x);
3106 _gameObjectDataStore.erase(spawnId);
3107 return nullptr;
3108 }
3109
3110 if (goData.rotation.y < -1.0f || goData.rotation.y > 1.0f)
3111 {
3112 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotationY ({}) value, skipped.", spawnId, entry, goData.rotation.y);
3113 _gameObjectDataStore.erase(spawnId);
3114 return nullptr;
3115 }
3116
3117 if (goData.rotation.z < -1.0f || goData.rotation.z > 1.0f)
3118 {
3119 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotationZ ({}) value, skipped.", spawnId, entry, goData.rotation.z);
3120 _gameObjectDataStore.erase(spawnId);
3121 return nullptr;
3122 }
3123
3124 if (goData.rotation.w < -1.0f || goData.rotation.w > 1.0f)
3125 {
3126 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotationW ({}) value, skipped.", spawnId, entry, goData.rotation.w);
3127 _gameObjectDataStore.erase(spawnId);
3128 return nullptr;
3129 }
3130
3131 if (fabs(goData.rotation.x * goData.rotation.x + goData.rotation.y * goData.rotation.y +
3132 goData.rotation.z * goData.rotation.z + goData.rotation.w * goData.rotation.w - 1.0f) >= 1e-5f)
3133 {
3134 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotation quaternion (non-unit), defaulting to orientation on Z axis only", spawnId, entry);
3135 goData.rotation = G3D::Quat(G3D::Matrix3::fromEulerAnglesZYX(goData.orientation, 0.0f, 0.0f));
3136 }
3137
3138 if (!MapMgr::IsValidMapCoord(goData.mapid, goData.posX, goData.posY, goData.posZ, goData.orientation))
3139 {
3140 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid coordinates, skipped.", spawnId, entry);
3141 _gameObjectDataStore.erase(spawnId);
3142 return nullptr;
3143 }
3144
3145 if (goData.phaseMask == 0)
3146 {
3147 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with `phaseMask`=0 (not visible for anyone), set to 1.", spawnId, entry);
3148 goData.phaseMask = 1;
3149 }
3150
3151 return &goData;
3152}
DBCStorage< GameObjectDisplayInfoEntry > sGameObjectDisplayInfoStore(GameObjectDisplayInfofmt)
#define MAX_GO_STATE
Definition GameObjectData.h:28
GOState
Definition GameObjectData.h:707
static bool IsValidMapCoord(uint32 mapid, Position const &pos)
Definition MapMgr.h:90

References _gameObjectDataStore, GameObjectData::animprogress, GameObjectData::artKit, Field::Get(), GetGameObjectData(), GetGameObjectTemplate(), GetScriptId(), GameObjectData::go_state, GameObjectData::id, MapMgr::IsValidMapCoord(), LOG_ERROR, SpawnData::mapid, MAX_GO_STATE, SpawnData::orientation, SpawnData::phaseMask, SpawnData::posX, SpawnData::posY, SpawnData::posZ, GameObjectData::rotation, SpawnData::ScriptId, sGameObjectDisplayInfoStore, sMapStore, SpawnData::spawnMask, GameObjectData::spawntimesecs, and WorldDatabase.

◆ LoadGameObjectForQuests()

void ObjectMgr::LoadGameObjectForQuests ( )
9194{
9195 uint32 oldMSTime = getMSTime();
9196
9197 if (GetGameObjectTemplates()->empty())
9198 {
9199 LOG_WARN("server.loading", ">> Loaded 0 GameObjects for quests");
9200 LOG_INFO("server.loading", " ");
9201 return;
9202 }
9203
9204 uint32 count = 0;
9205
9206 // collect GO entries for GO that must activated
9208 for (GameObjectTemplateContainer::iterator itr = gotc->begin(); itr != gotc->end(); ++itr)
9209 {
9210 itr->second.IsForQuests = false;
9211 switch (itr->second.type)
9212 {
9214 itr->second.IsForQuests = true;
9215 ++count;
9216 break;
9218 {
9219 // scan GO chest with loot including quest items
9220 uint32 loot_id = (itr->second.GetLootId());
9221
9222 // find quest loot for GO
9223 if (itr->second.chest.questId || LootTemplates_Gameobject.HaveQuestLootFor(loot_id))
9224 {
9225 itr->second.IsForQuests = true;
9226 ++count;
9227 }
9228 break;
9229 }
9231 {
9232 if (itr->second._generic.questID > 0) //quests objects
9233 {
9234 itr->second.IsForQuests = true;
9235 ++count;
9236 }
9237 break;
9238 }
9240 {
9241 if (itr->second.spellFocus.questID > 0) //quests objects
9242 {
9243 itr->second.IsForQuests = true;
9244 ++count;
9245 }
9246 break;
9247 }
9249 {
9250 if (itr->second.goober.questId > 0) //quests objects
9251 {
9252 itr->second.IsForQuests = true;
9253 ++count;
9254 }
9255 break;
9256 }
9257 default:
9258 break;
9259 }
9260 }
9261
9262 LOG_INFO("server.loading", ">> Loaded {} GameObjects for quests in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
9263 LOG_INFO("server.loading", " ");
9264}
LootStore LootTemplates_Gameobject("gameobject_loot_template", "gameobject entry", true)
@ GAMEOBJECT_TYPE_SPELL_FOCUS
Definition SharedDefines.h:1574
@ GAMEOBJECT_TYPE_GENERIC
Definition SharedDefines.h:1571
@ GAMEOBJECT_TYPE_CHEST
Definition SharedDefines.h:1569
@ GAMEOBJECT_TYPE_QUESTGIVER
Definition SharedDefines.h:1568
@ GAMEOBJECT_TYPE_GOOBER
Definition SharedDefines.h:1576
bool HaveQuestLootFor(uint32 loot_id) const
Definition LootMgr.cpp:218

References GAMEOBJECT_TYPE_CHEST, GAMEOBJECT_TYPE_GENERIC, GAMEOBJECT_TYPE_GOOBER, GAMEOBJECT_TYPE_QUESTGIVER, GAMEOBJECT_TYPE_SPELL_FOCUS, GetGameObjectTemplates(), getMSTime(), GetMSTimeDiffToNow(), LootStore::HaveQuestLootFor(), LOG_INFO, LOG_WARN, and LootTemplates_Gameobject.

◆ LoadGameObjectLocales()

void ObjectMgr::LoadGameObjectLocales ( )
7717{
7718 uint32 oldMSTime = getMSTime();
7719
7720 _gameObjectLocaleStore.clear(); // need for reload case
7721
7722 // 0 1 2 3
7723 QueryResult result = WorldDatabase.Query("SELECT entry, locale, name, castBarCaption FROM gameobject_template_locale");
7724 if (!result)
7725 return;
7726
7727 do
7728 {
7729 Field* fields = result->Fetch();
7730
7731 uint32 ID = fields[0].Get<uint32>();
7732
7733 LocaleConstant locale = GetLocaleByName(fields[1].Get<std::string>());
7734 if (locale == LOCALE_enUS)
7735 continue;
7736
7738 AddLocaleString(fields[2].Get<std::string>(), locale, data.Name);
7739 AddLocaleString(fields[3].Get<std::string>(), locale, data.CastBarCaption);
7740 } while (result->NextRow());
7741
7742 LOG_INFO("server.loading", ">> Loaded {} Gameobject Locale Strings in {} ms", (uint32)_gameObjectLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
7743}
Definition GameObjectData.h:677
std::vector< std::string > Name
Definition GameObjectData.h:678
std::vector< std::string > CastBarCaption
Definition GameObjectData.h:679

References _gameObjectLocaleStore, AddLocaleString(), GameObjectLocale::CastBarCaption, Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, GameObjectLocale::Name, and WorldDatabase.

◆ LoadGameobjectQuestEnders()

void ObjectMgr::LoadGameobjectQuestEnders ( )
8766{
8767 LoadQuestRelationsHelper(_goQuestInvolvedRelations, "gameobject_questender", false, true);
8768
8769 for (QuestRelations::iterator itr = _goQuestInvolvedRelations.begin(); itr != _goQuestInvolvedRelations.end(); ++itr)
8770 {
8771 GameObjectTemplate const* goInfo = GetGameObjectTemplate(itr->first);
8772 if (!goInfo)
8773 LOG_ERROR("sql.sql", "Table `gameobject_questender` have data for not existed gameobject entry ({}) and existed quest {}", itr->first, itr->second);
8774 else if (goInfo->type != GAMEOBJECT_TYPE_QUESTGIVER)
8775 LOG_ERROR("sql.sql", "Table `gameobject_questender` have data gameobject entry ({}) for quest {}, but GO is not GAMEOBJECT_TYPE_QUESTGIVER", itr->first, itr->second);
8776 }
8777}

References _goQuestInvolvedRelations, GAMEOBJECT_TYPE_QUESTGIVER, GetGameObjectTemplate(), LoadQuestRelationsHelper(), LOG_ERROR, and GameObjectTemplate::type.

Referenced by LoadQuestStartersAndEnders().

◆ LoadGameObjectQuestItems()

void ObjectMgr::LoadGameObjectQuestItems ( )
10857{
10858 uint32 oldMSTime = getMSTime();
10859
10860 // 0 1 2
10861 QueryResult result = WorldDatabase.Query("SELECT GameObjectEntry, ItemId, Idx FROM gameobject_questitem ORDER BY Idx ASC");
10862
10863 if (!result)
10864 {
10865 LOG_WARN("server.loading", ">> Loaded 0 gameobject quest items. DB table `gameobject_questitem` is empty.");
10866 return;
10867 }
10868
10869 uint32 count = 0;
10870 do
10871 {
10872 Field* fields = result->Fetch();
10873
10874 uint32 entry = fields[0].Get<uint32>();
10875 uint32 item = fields[1].Get<uint32>();
10876 uint32 idx = fields[2].Get<uint32>();
10877
10878 GameObjectTemplate const* goInfo = GetGameObjectTemplate(entry);
10879 if (!goInfo)
10880 {
10881 LOG_ERROR("sql.sql", "Table `gameobject_questitem` has data for nonexistent gameobject (entry: {}, idx: {}), skipped", entry, idx);
10882 continue;
10883 };
10884
10885 ItemEntry const* dbcData = sItemStore.LookupEntry(item);
10886 if (!dbcData)
10887 {
10888 LOG_ERROR("sql.sql", "Table `gameobject_questitem` has nonexistent item (ID: {}) in gameobject (entry: {}, idx: {}), skipped", item, entry, idx);
10889 continue;
10890 };
10891
10892 _gameObjectQuestItemStore[entry].push_back(item);
10893
10894 ++count;
10895 } while (result->NextRow());
10896
10897 LOG_INFO("server.loading", ">> Loaded {} Gameobject Quest Items in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10898 LOG_INFO("server.loading", " ");
10899}

References _gameObjectQuestItemStore, Field::Get(), GetGameObjectTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sItemStore, and WorldDatabase.

◆ LoadGameobjectQuestStarters()

void ObjectMgr::LoadGameobjectQuestStarters ( )
8752{
8753 LoadQuestRelationsHelper(_goQuestRelations, "gameobject_queststarter", true, true);
8754
8755 for (QuestRelations::iterator itr = _goQuestRelations.begin(); itr != _goQuestRelations.end(); ++itr)
8756 {
8757 GameObjectTemplate const* goInfo = GetGameObjectTemplate(itr->first);
8758 if (!goInfo)
8759 LOG_ERROR("sql.sql", "Table `gameobject_queststarter` have data for not existed gameobject entry ({}) and existed quest {}", itr->first, itr->second);
8760 else if (goInfo->type != GAMEOBJECT_TYPE_QUESTGIVER)
8761 LOG_ERROR("sql.sql", "Table `gameobject_queststarter` have data gameobject entry ({}) for quest {}, but GO is not GAMEOBJECT_TYPE_QUESTGIVER", itr->first, itr->second);
8762 }
8763}

References _goQuestRelations, GAMEOBJECT_TYPE_QUESTGIVER, GetGameObjectTemplate(), LoadQuestRelationsHelper(), LOG_ERROR, and GameObjectTemplate::type.

Referenced by LoadQuestStartersAndEnders().

◆ LoadGameobjects()

void ObjectMgr::LoadGameobjects ( )
2846{
2847 uint32 oldMSTime = getMSTime();
2848
2849 // 0 1 2 3 4 5 6
2850 QueryResult result = WorldDatabase.Query("SELECT gameobject.guid, id, map, position_x, position_y, position_z, orientation, "
2851 // 7 8 9 10 11 12 13 14 15 16 17
2852 "rotation0, rotation1, rotation2, rotation3, spawntimesecs, animprogress, state, spawnMask, phaseMask, eventEntry, pool_entry, "
2853 // 18
2854 "ScriptName "
2855 "FROM gameobject LEFT OUTER JOIN game_event_gameobject ON gameobject.guid = game_event_gameobject.guid "
2856 "LEFT OUTER JOIN pool_gameobject ON gameobject.guid = pool_gameobject.guid");
2857
2858 if (!result)
2859 {
2860 LOG_WARN("server.loading", ">> Loaded 0 gameobjects. DB table `gameobject` is empty.");
2861 LOG_INFO("server.loading", " ");
2862 return;
2863 }
2864
2866 LOG_INFO("server.loading", "Calculating zone and area fields. This may take a moment...");
2867
2868 // build single time for check spawnmask
2869 std::map<uint32, uint32> spawnMasks;
2870 for (uint32 i = 0; i < sMapStore.GetNumRows(); ++i)
2871 if (sMapStore.LookupEntry(i))
2872 for (int k = 0; k < MAX_DIFFICULTY; ++k)
2874 spawnMasks[i] |= (1 << k);
2875
2876 _gameObjectDataStore.rehash(result->GetRowCount());
2877 do
2878 {
2879 Field* fields = result->Fetch();
2880
2881 ObjectGuid::LowType guid = fields[0].Get<uint32>();
2882 uint32 entry = fields[1].Get<uint32>();
2883
2884 GameObjectTemplate const* gInfo = GetGameObjectTemplate(entry);
2885 if (!gInfo)
2886 {
2887 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {}) with non existing gameobject entry {}, skipped.", guid, entry);
2888 continue;
2889 }
2890
2891 if (!gInfo->displayId)
2892 {
2893 switch (gInfo->type)
2894 {
2897 break;
2898 default:
2899 LOG_ERROR("sql.sql", "Gameobject (GUID: {} Entry {} GoType: {}) doesn't have a displayId ({}), not loaded.", guid, entry, gInfo->type, gInfo->displayId);
2900 break;
2901 }
2902 }
2903
2904 if (gInfo->displayId && !sGameObjectDisplayInfoStore.LookupEntry(gInfo->displayId))
2905 {
2906 LOG_ERROR("sql.sql", "Gameobject (GUID: {} Entry {} GoType: {}) has an invalid displayId ({}), not loaded.", guid, entry, gInfo->type, gInfo->displayId);
2907 continue;
2908 }
2909
2911
2912 data.id = entry;
2913 data.mapid = fields[2].Get<uint16>();
2914 data.posX = fields[3].Get<float>();
2915 data.posY = fields[4].Get<float>();
2916 data.posZ = fields[5].Get<float>();
2917 data.orientation = fields[6].Get<float>();
2918 data.rotation.x = fields[7].Get<float>();
2919 data.rotation.y = fields[8].Get<float>();
2920 data.rotation.z = fields[9].Get<float>();
2921 data.rotation.w = fields[10].Get<float>();
2922 data.spawntimesecs = fields[11].Get<int32>();
2923 data.ScriptId = GetScriptId(fields[18].Get<std::string>());
2924 data.spawnGroupId = 0;
2925 if (!data.ScriptId)
2926 data.ScriptId = gInfo->ScriptId;
2927
2928 MapEntry const* mapEntry = sMapStore.LookupEntry(data.mapid);
2929 if (!mapEntry)
2930 {
2931 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) spawned on a non-existed map (Id: {}), skip", guid, data.id, data.mapid);
2932 continue;
2933 }
2934
2935 if (data.spawntimesecs == 0 && gInfo->IsDespawnAtAction())
2936 {
2937 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with `spawntimesecs` (0) value, but the gameobejct is marked as despawnable at action.", guid, data.id);
2938 }
2939
2940 data.animprogress = fields[12].Get<uint8>();
2941 data.artKit = 0;
2942
2943 uint32 go_state = fields[13].Get<uint8>();
2944 if (go_state >= MAX_GO_STATE)
2945 {
2946 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid `state` ({}) value, skip", guid, data.id, go_state);
2947 continue;
2948 }
2949 data.go_state = GOState(go_state);
2950
2951 data.spawnMask = fields[14].Get<uint8>();
2952
2953 if (!_transportMaps.count(data.mapid) && data.spawnMask & ~spawnMasks[data.mapid])
2954 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) that has wrong spawn mask {} including not supported difficulty modes for map (Id: {}), skip", guid, data.id, data.spawnMask, data.mapid);
2955
2956 data.phaseMask = fields[15].Get<uint32>();
2957 int16 gameEvent = fields[16].Get<int16>();
2958 uint32 PoolId = fields[17].Get<uint32>();
2959
2960 if (data.rotation.x < -1.0f || data.rotation.x > 1.0f)
2961 {
2962 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotationX ({}) value, skip", guid, data.id, data.rotation.x);
2963 continue;
2964 }
2965
2966 if (data.rotation.y < -1.0f || data.rotation.y > 1.0f)
2967 {
2968 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotationY ({}) value, skip", guid, data.id, data.rotation.y);
2969 continue;
2970 }
2971
2972 if (data.rotation.z < -1.0f || data.rotation.z > 1.0f)
2973 {
2974 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotationZ ({}) value, skip", guid, data.id, data.rotation.z);
2975 continue;
2976 }
2977
2978 if (data.rotation.w < -1.0f || data.rotation.w > 1.0f)
2979 {
2980 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotationW ({}) value, skip", guid, data.id, data.rotation.w);
2981 continue;
2982 }
2983
2984 if (fabs(data.rotation.x * data.rotation.x + data.rotation.y * data.rotation.y +
2985 data.rotation.z * data.rotation.z + data.rotation.w * data.rotation.w - 1.0f) >= 1e-5f)
2986 {
2987 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid rotation quaternion (non-unit), defaulting to orientation on Z axis only", guid, data.id);
2988 data.rotation = G3D::Quat(G3D::Matrix3::fromEulerAnglesZYX(data.orientation, 0.0f, 0.0f));
2989 }
2990
2991 if (!MapMgr::IsValidMapCoord(data.mapid, data.posX, data.posY, data.posZ, data.orientation))
2992 {
2993 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with invalid coordinates, skip", guid, data.id);
2994 continue;
2995 }
2996
2997 if (data.phaseMask == 0)
2998 {
2999 LOG_ERROR("sql.sql", "Table `gameobject` has gameobject (GUID: {} Entry: {}) with `phaseMask`=0 (not visible for anyone), set to 1.", guid, data.id);
3000 data.phaseMask = 1;
3001 }
3002
3004 {
3005 uint32 zoneId = sMapMgr->GetZoneId(data.phaseMask, data.mapid, data.posX, data.posY, data.posZ);
3006 uint32 areaId = sMapMgr->GetAreaId(data.phaseMask, data.mapid, data.posX, data.posY, data.posZ);
3007
3009
3010 stmt->SetData(0, zoneId);
3011 stmt->SetData(1, areaId);
3012 stmt->SetData(2, guid);
3013
3014 WorldDatabase.Execute(stmt);
3015 }
3016
3017 if (gameEvent == 0 && PoolId == 0) // if not this is to be managed by GameEvent System or Pool system
3018 AddGameobjectToGrid(guid, &data);
3019 } while (result->NextRow());
3020
3021 LOG_INFO("server.loading", ">> Loaded {} Gameobjects in {} ms", (unsigned long)_gameObjectDataStore.size(), GetMSTimeDiffToNow(oldMSTime));
3022 LOG_INFO("server.loading", " ");
3023}
@ GAMEOBJECT_TYPE_TRAP
Definition SharedDefines.h:1572
@ CONFIG_CALCULATE_GAMEOBJECT_ZONE_AREA_DATA
Definition WorldConfig.h:116
@ WORLD_UPD_GAMEOBJECT_ZONE_AREA_DATA
Definition WorldDatabase.h:115

References _gameObjectDataStore, _transportMaps, AddGameobjectToGrid(), GameObjectData::animprogress, GameObjectData::artKit, CONFIG_CALCULATE_GAMEOBJECT_ZONE_AREA_DATA, GAMEOBJECT_TYPE_SPELL_FOCUS, GAMEOBJECT_TYPE_TRAP, Field::Get(), GetGameObjectTemplate(), GetMapDifficultyData(), getMSTime(), GetMSTimeDiffToNow(), GetScriptId(), GameObjectData::go_state, GameObjectData::id, MapMgr::IsValidMapCoord(), LOG_ERROR, LOG_INFO, LOG_WARN, SpawnData::mapid, MAX_DIFFICULTY, MAX_GO_STATE, SpawnData::orientation, SpawnData::phaseMask, SpawnData::posX, SpawnData::posY, SpawnData::posZ, GameObjectData::rotation, SpawnData::ScriptId, PreparedStatementBase::SetData(), sGameObjectDisplayInfoStore, sMapMgr, sMapStore, SpawnData::spawnGroupId, SpawnData::spawnMask, GameObjectData::spawntimesecs, sWorld, WORLD_UPD_GAMEOBJECT_ZONE_AREA_DATA, and WorldDatabase.

◆ LoadGameObjectSummons()

void ObjectMgr::LoadGameObjectSummons ( )
2236{
2237 uint32 oldMSTime = getMSTime();
2238
2239 _goSummonDataStore.clear();
2240
2241 // 0 1 2 3 4 5 6 7 8 9 10 11 12
2242 QueryResult result = WorldDatabase.Query("SELECT summonerId, summonerType, groupId, entry, position_x, position_y, position_z, orientation, rotation0, rotation1, rotation2, rotation3, respawnTime FROM gameobject_summon_groups");
2243
2244 if (!result)
2245 {
2246 LOG_WARN("server.loading", ">> Loaded 0 gameobject summons. DB table `gameobject_summon_groups` is empty.");
2247 return;
2248 }
2249
2250 uint32 count = 0;
2251 do
2252 {
2253 Field* fields = result->Fetch();
2254
2255 uint32 summonerId = fields[0].Get<uint32>();
2256 SummonerType summonerType = SummonerType(fields[1].Get<uint8>());
2257 uint8 group = fields[2].Get<uint8>();
2258
2259 switch (summonerType)
2260 {
2262 if (!GetCreatureTemplate(summonerId))
2263 {
2264 LOG_ERROR("sql.sql", "Table `gameobject_summon_groups` has summoner with non existing entry {} for creature summoner type, skipped.", summonerId);
2265 continue;
2266 }
2267 break;
2269 if (!GetGameObjectTemplate(summonerId))
2270 {
2271 LOG_ERROR("sql.sql", "Table `gameobject_summon_groups` has summoner with non existing entry {} for gameobject summoner type, skipped.", summonerId);
2272 continue;
2273 }
2274 break;
2275 case SUMMONER_TYPE_MAP:
2276 if (!sMapStore.LookupEntry(summonerId))
2277 {
2278 LOG_ERROR("sql.sql", "Table `gameobject_summon_groups` has summoner with non existing entry {} for map summoner type, skipped.", summonerId);
2279 continue;
2280 }
2281 break;
2282 default:
2283 LOG_ERROR("sql.sql", "Table `gameobject_summon_groups` has unhandled summoner type {} for summoner {}, skipped.", summonerType, summonerId);
2284 continue;
2285 }
2286
2288 data.entry = fields[3].Get<uint32>();
2289
2290 if (!GetGameObjectTemplate(data.entry))
2291 {
2292 LOG_ERROR("sql.sql", "Table `gameobject_summon_groups` has gameobject in group [Summoner ID: {}, Summoner Type: {}, Group ID: {}] with non existing gameobject entry {}, skipped.", summonerId, summonerType, group, data.entry);
2293 continue;
2294 }
2295
2296 float posX = fields[4].Get<float>();
2297 float posY = fields[5].Get<float>();
2298 float posZ = fields[6].Get<float>();
2299 float orientation = fields[7].Get<float>();
2300
2301 data.pos.Relocate(posX, posY, posZ, orientation);
2302
2303 data.rot = G3D::Quat(fields[8].Get<float>(), fields[9].Get<float>(), fields[10].Get<float>(), fields[11].Get<float>());
2304 data.respawnTime = fields[12].Get<uint32>();
2305
2306 TempSummonGroupKey key(summonerId, summonerType, group);
2307 _goSummonDataStore[key].push_back(data);
2308
2309 ++count;
2310 } while (result->NextRow());
2311
2312 LOG_INFO("server.loading", ">> Loaded {} Gameobject Summons in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2313 LOG_INFO("server.loading", " ");
2314}
SummonerType
Definition TemporarySummon.h:25
@ SUMMONER_TYPE_MAP
Definition TemporarySummon.h:28
@ SUMMONER_TYPE_CREATURE
Definition TemporarySummon.h:26
@ SUMMONER_TYPE_GAMEOBJECT
Definition TemporarySummon.h:27
Stores data for temp gameobject summons.
Definition TemporarySummon.h:42
G3D::Quat rot
Definition TemporarySummon.h:45
uint32 respawnTime
Duration in seconds; passed to SummonGameObject's respawnTime parameter.
Definition TemporarySummon.h:46
uint32 entry
Definition TemporarySummon.h:43
Position pos
Definition TemporarySummon.h:44
void Relocate(float x, float y)
Definition Position.h:77

References _goSummonDataStore, GameObjectSummonData::entry, Field::Get(), GetCreatureTemplate(), GetGameObjectTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, GameObjectSummonData::pos, Position::Relocate(), GameObjectSummonData::respawnTime, GameObjectSummonData::rot, sMapStore, SUMMONER_TYPE_CREATURE, SUMMONER_TYPE_GAMEOBJECT, SUMMONER_TYPE_MAP, and WorldDatabase.

◆ LoadGameObjectTemplate()

void ObjectMgr::LoadGameObjectTemplate ( )
7805{
7806 uint32 oldMSTime = getMSTime();
7807
7808 // 0 1 2 3 4 5 6 7
7809 QueryResult result = WorldDatabase.Query("SELECT entry, type, displayId, name, IconName, castBarCaption, unk1, size, "
7810 // 8 9 10 11 12 13 14 15 16 17 18 19 20
7811 "Data0, Data1, Data2, Data3, Data4, Data5, Data6, Data7, Data8, Data9, Data10, Data11, Data12, "
7812 // 21 22 23 24 25 26 27 28 29 30 31 32 33
7813 "Data13, Data14, Data15, Data16, Data17, Data18, Data19, Data20, Data21, Data22, Data23, AIName, ScriptName "
7814 "FROM gameobject_template");
7815
7816 if (!result)
7817 {
7818 LOG_WARN("server.loading", ">> Loaded 0 gameobject definitions. DB table `gameobject_template` is empty.");
7819 LOG_INFO("server.loading", " ");
7820 return;
7821 }
7822
7823 _gameObjectTemplateStore.rehash(result->GetRowCount());
7824 uint32 count = 0;
7825 do
7826 {
7827 Field* fields = result->Fetch();
7828
7829 uint32 entry = fields[0].Get<uint32>();
7830
7832
7833 got.entry = entry;
7834 got.type = uint32(fields[1].Get<uint8>());
7835 got.displayId = fields[2].Get<uint32>();
7836 got.name = fields[3].Get<std::string>();
7837 got.IconName = fields[4].Get<std::string>();
7838 got.castBarCaption = fields[5].Get<std::string>();
7839 got.unk1 = fields[6].Get<std::string>();
7840 got.size = fields[7].Get<float>();
7841
7842 for (uint8 i = 0; i < MAX_GAMEOBJECT_DATA; ++i)
7843 got.raw.data[i] = fields[8 + i].Get<int32>(); // data1 and data6 can be -1
7844
7845 got.AIName = fields[32].Get<std::string>();
7846 got.ScriptId = GetScriptId(fields[33].Get<std::string>());
7847 got.IsForQuests = false;
7848
7849 // Checks
7850 if (!got.AIName.empty() && !sGameObjectAIRegistry->HasItem(got.AIName))
7851 {
7852 LOG_ERROR("sql.sql", "GameObject (Entry: {}) has non-registered `AIName` '{}' set, removing", got.entry, got.AIName);
7853 }
7854
7855 switch (got.type)
7856 {
7857 case GAMEOBJECT_TYPE_DOOR: //0
7858 {
7859 if (got.door.lockId)
7860 CheckGOLockId(&got, got.door.lockId, 1);
7861 CheckGONoDamageImmuneId(&got, got.door.noDamageImmune, 3);
7862 break;
7863 }
7864 case GAMEOBJECT_TYPE_BUTTON: //1
7865 {
7866 if (got.button.lockId)
7867 CheckGOLockId(&got, got.button.lockId, 1);
7868 CheckGONoDamageImmuneId(&got, got.button.noDamageImmune, 4);
7869 break;
7870 }
7872 {
7873 if (got.questgiver.lockId)
7874 CheckGOLockId(&got, got.questgiver.lockId, 0);
7875 CheckGONoDamageImmuneId(&got, got.questgiver.noDamageImmune, 5);
7876 break;
7877 }
7878 case GAMEOBJECT_TYPE_CHEST: //3
7879 {
7880 if (got.chest.lockId)
7881 CheckGOLockId(&got, got.chest.lockId, 0);
7882
7883 CheckGOConsumable(&got, got.chest.consumable, 3);
7884
7885 if (got.chest.linkedTrapId) // linked trap
7886 CheckGOLinkedTrapId(&got, got.chest.linkedTrapId, 7);
7887 break;
7888 }
7889 case GAMEOBJECT_TYPE_TRAP: //6
7890 {
7891 if (got.trap.lockId)
7892 CheckGOLockId(&got, got.trap.lockId, 0);
7893 break;
7894 }
7895 case GAMEOBJECT_TYPE_CHAIR: //7
7896 CheckAndFixGOChairHeightId(&got, got.chair.height, 1);
7897 break;
7899 {
7900 if (got.spellFocus.focusId)
7901 {
7902 if (!sSpellFocusObjectStore.LookupEntry(got.spellFocus.focusId))
7903 LOG_ERROR("sql.sql", "GameObject (Entry: {} GoType: {}) have data0={} but SpellFocus (Id: {}) not exist.",
7904 entry, got.type, got.spellFocus.focusId, got.spellFocus.focusId);
7905 }
7906
7907 if (got.spellFocus.linkedTrapId) // linked trap
7908 CheckGOLinkedTrapId(&got, got.spellFocus.linkedTrapId, 2);
7909 break;
7910 }
7911 case GAMEOBJECT_TYPE_GOOBER: //10
7912 {
7913 if (got.goober.lockId)
7914 CheckGOLockId(&got, got.goober.lockId, 0);
7915
7916 CheckGOConsumable(&got, got.goober.consumable, 3);
7917
7918 if (got.goober.pageId) // pageId
7919 {
7920 if (!GetPageText(got.goober.pageId))
7921 LOG_ERROR("sql.sql", "GameObject (Entry: {} GoType: {}) have data7={} but PageText (Entry {}) not exist.",
7922 entry, got.type, got.goober.pageId, got.goober.pageId);
7923 }
7924 CheckGONoDamageImmuneId(&got, got.goober.noDamageImmune, 11);
7925 if (got.goober.linkedTrapId) // linked trap
7926 CheckGOLinkedTrapId(&got, got.goober.linkedTrapId, 12);
7927 break;
7928 }
7930 {
7931 if (got.areadamage.lockId)
7932 CheckGOLockId(&got, got.areadamage.lockId, 0);
7933 break;
7934 }
7935 case GAMEOBJECT_TYPE_CAMERA: //13
7936 {
7937 if (got.camera.lockId)
7938 CheckGOLockId(&got, got.camera.lockId, 0);
7939 break;
7940 }
7942 {
7943 if (got.moTransport.taxiPathId)
7944 {
7945 if (got.moTransport.taxiPathId >= sTaxiPathNodesByPath.size() || sTaxiPathNodesByPath[got.moTransport.taxiPathId].empty())
7946 LOG_ERROR("sql.sql", "GameObject (Entry: {} GoType: {}) have data0={} but TaxiPath (Id: {}) not exist.",
7947 entry, got.type, got.moTransport.taxiPathId, got.moTransport.taxiPathId);
7948 }
7949 if (uint32 transportMap = got.moTransport.mapID)
7950 _transportMaps.insert(transportMap);
7951 break;
7952 }
7954 break;
7956 {
7957 // always must have spell
7958 CheckGOSpellId(&got, got.spellcaster.spellId, 0);
7959 break;
7960 }
7961 case GAMEOBJECT_TYPE_FLAGSTAND: //24
7962 {
7963 if (got.flagstand.lockId)
7964 CheckGOLockId(&got, got.flagstand.lockId, 0);
7965 CheckGONoDamageImmuneId(&got, got.flagstand.noDamageImmune, 5);
7966 break;
7967 }
7969 {
7970 if (got.fishinghole.lockId)
7971 CheckGOLockId(&got, got.fishinghole.lockId, 4);
7972 break;
7973 }
7974 case GAMEOBJECT_TYPE_FLAGDROP: //26
7975 {
7976 if (got.flagdrop.lockId)
7977 CheckGOLockId(&got, got.flagdrop.lockId, 0);
7978 CheckGONoDamageImmuneId(&got, got.flagdrop.noDamageImmune, 3);
7979 break;
7980 }
7982 CheckAndFixGOChairHeightId(&got, got.barberChair.chairheight, 0);
7983 break;
7984 }
7985
7986 ++count;
7987 } while (result->NextRow());
7988
7989 LOG_INFO("server.loading", ">> Loaded {} Game Object Templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
7990 LOG_INFO("server.loading", " ");
7991}
DBCStorage< SpellFocusObjectEntry > sSpellFocusObjectStore(SpellFocusObjectfmt)
#define sGameObjectAIRegistry
Definition GameObjectAIFactory.h:49
void CheckGONoDamageImmuneId(GameObjectTemplate *goTemplate, uint32 dataN, uint32 N)
Definition ObjectMgr.cpp:7785
void CheckGOSpellId(GameObjectTemplate const *goInfo, uint32 dataN, uint32 N)
Definition ObjectMgr.cpp:7764
void CheckAndFixGOChairHeightId(GameObjectTemplate const *goInfo, uint32 const &dataN, uint32 N)
Definition ObjectMgr.cpp:7773
void CheckGOConsumable(GameObjectTemplate const *goInfo, uint32 dataN, uint32 N)
Definition ObjectMgr.cpp:7794
void CheckGOLinkedTrapId(GameObjectTemplate const *goInfo, uint32 dataN, uint32 N)
Definition ObjectMgr.cpp:7754
void CheckGOLockId(GameObjectTemplate const *goInfo, uint32 dataN, uint32 N)
Definition ObjectMgr.cpp:7745
@ GAMEOBJECT_TYPE_CAMERA
Definition SharedDefines.h:1579
@ GAMEOBJECT_TYPE_BUTTON
Definition SharedDefines.h:1567
@ GAMEOBJECT_TYPE_MO_TRANSPORT
Definition SharedDefines.h:1581
@ GAMEOBJECT_TYPE_SUMMONING_RITUAL
Definition SharedDefines.h:1584
@ GAMEOBJECT_TYPE_FISHINGHOLE
Definition SharedDefines.h:1591
@ GAMEOBJECT_TYPE_FLAGDROP
Definition SharedDefines.h:1592
@ GAMEOBJECT_TYPE_SPELLCASTER
Definition SharedDefines.h:1588
@ GAMEOBJECT_TYPE_FLAGSTAND
Definition SharedDefines.h:1590
@ GAMEOBJECT_TYPE_CHAIR
Definition SharedDefines.h:1573
@ GAMEOBJECT_TYPE_AREADAMAGE
Definition SharedDefines.h:1578
@ GAMEOBJECT_TYPE_BARBER_CHAIR
Definition SharedDefines.h:1598
@ GAMEOBJECT_TYPE_DOOR
Definition SharedDefines.h:1566
#define MAX_GAMEOBJECT_DATA
Definition SharedDefines.h:1605
PageText const * GetPageText(uint32 pageEntry)
Definition ObjectMgr.cpp:6428
uint32 entry
Definition GameObjectData.h:33

References _gameObjectTemplateStore, _transportMaps, CheckAndFixGOChairHeightId(), CheckGOConsumable(), CheckGOLinkedTrapId(), CheckGOLockId(), CheckGONoDamageImmuneId(), CheckGOSpellId(), GameObjectTemplate::entry, GAMEOBJECT_TYPE_AREADAMAGE, GAMEOBJECT_TYPE_BARBER_CHAIR, GAMEOBJECT_TYPE_BUTTON, GAMEOBJECT_TYPE_CAMERA, GAMEOBJECT_TYPE_CHAIR, GAMEOBJECT_TYPE_CHEST, GAMEOBJECT_TYPE_DOOR, GAMEOBJECT_TYPE_FISHINGHOLE, GAMEOBJECT_TYPE_FLAGDROP, GAMEOBJECT_TYPE_FLAGSTAND, GAMEOBJECT_TYPE_GOOBER, GAMEOBJECT_TYPE_MO_TRANSPORT, GAMEOBJECT_TYPE_QUESTGIVER, GAMEOBJECT_TYPE_SPELL_FOCUS, GAMEOBJECT_TYPE_SPELLCASTER, GAMEOBJECT_TYPE_SUMMONING_RITUAL, GAMEOBJECT_TYPE_TRAP, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), GetPageText(), GetScriptId(), LOG_ERROR, LOG_INFO, LOG_WARN, MAX_GAMEOBJECT_DATA, sGameObjectAIRegistry, sSpellFocusObjectStore, sTaxiPathNodesByPath, and WorldDatabase.

◆ LoadGameObjectTemplateAddons()

void ObjectMgr::LoadGameObjectTemplateAddons ( )
7994{
7995 uint32 oldMSTime = getMSTime();
7996
7997 // 0 1 2 3 4 5 6 7 8
7998 QueryResult result = WorldDatabase.Query("SELECT entry, faction, flags, mingold, maxgold, artkit0, artkit1, artkit2, artkit3 FROM gameobject_template_addon");
7999
8000 if (!result)
8001 {
8002 LOG_WARN("server.loading", ">> Loaded 0 gameobject template addon definitions. DB table `gameobject_template_addon` is empty.");
8003 LOG_INFO("server.loading", " ");
8004 return;
8005 }
8006
8007 uint32 count = 0;
8008 do
8009 {
8010 Field* fields = result->Fetch();
8011
8012 uint32 entry = fields[0].Get<uint32>();
8013
8014 GameObjectTemplate const* got = GetGameObjectTemplate(entry);
8015 if (!got)
8016 {
8017 LOG_ERROR("sql.sql",
8018 "GameObject template (Entry: {}) does not exist but has a record in `gameobject_template_addon`",
8019 entry);
8020 continue;
8021 }
8022
8024 gameObjectAddon.faction = uint32(fields[1].Get<uint16>());
8025 gameObjectAddon.flags = fields[2].Get<uint32>();
8026 gameObjectAddon.mingold = fields[3].Get<uint32>();
8027 gameObjectAddon.maxgold = fields[4].Get<uint32>();
8028
8029 for (uint32 i = 0; i < gameObjectAddon.artKits.size(); i++)
8030 {
8031 uint32 artKitID = fields[5 + i].Get<uint32>();
8032 if (!artKitID)
8033 continue;
8034
8035 if (!sGameObjectArtKitStore.LookupEntry(artKitID))
8036 {
8037 LOG_ERROR("sql.sql", "GameObject (Entry: {}) has invalid `artkit{}` {} defined, set to zero instead.", entry, i, artKitID);
8038 continue;
8039 }
8040
8041 gameObjectAddon.artKits[i] = artKitID;
8042 }
8043
8044 // checks
8045 if (gameObjectAddon.faction && !sFactionTemplateStore.LookupEntry(gameObjectAddon.faction))
8046 LOG_ERROR("sql.sql",
8047 "GameObject (Entry: {}) has invalid faction ({}) defined in `gameobject_template_addon`.",
8048 entry, gameObjectAddon.faction);
8049
8050 if (gameObjectAddon.maxgold > 0)
8051 {
8052 switch (got->type)
8053 {
8056 break;
8057 default:
8058 LOG_ERROR("sql.sql",
8059 "GameObject (Entry {} GoType: {}) cannot be looted but has maxgold set in `gameobject_template_addon`.",
8060 entry, got->type);
8061 break;
8062 }
8063 }
8064
8065 ++count;
8066 } while (result->NextRow());
8067
8068 LOG_INFO("server.loading", ">> Loaded {} Game Object Template Addons in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8069 LOG_INFO("server.loading", " ");
8070}
DBCStorage< GameObjectArtKitEntry > sGameObjectArtKitStore(GameObjectArtKitfmt)
Definition GameObjectData.h:667
uint32 mingold
Definition GameObjectData.h:671
uint32 flags
Definition GameObjectData.h:670
uint32 faction
Definition GameObjectData.h:669
std::array< uint32, 4 > artKits
Definition GameObjectData.h:673
uint32 maxgold
Definition GameObjectData.h:672

References _gameObjectTemplateAddonStore, GameObjectTemplateAddon::artKits, GameObjectTemplateAddon::faction, GameObjectTemplateAddon::flags, GAMEOBJECT_TYPE_CHEST, GAMEOBJECT_TYPE_FISHINGHOLE, Field::Get(), GetGameObjectTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, GameObjectTemplateAddon::maxgold, GameObjectTemplateAddon::mingold, sFactionTemplateStore, sGameObjectArtKitStore, and WorldDatabase.

◆ LoadGameTele()

void ObjectMgr::LoadGameTele ( )
9548{
9549 uint32 oldMSTime = getMSTime();
9550
9551 _gameTeleStore.clear(); // for reload case
9552
9553 // 0 1 2 3 4 5 6
9554 QueryResult result = WorldDatabase.Query("SELECT id, position_x, position_y, position_z, orientation, map, name FROM game_tele");
9555
9556 if (!result)
9557 {
9558 LOG_WARN("server.loading", ">> Loaded 0 GameTeleports. DB table `game_tele` is empty!");
9559 LOG_INFO("server.loading", " ");
9560 return;
9561 }
9562
9563 uint32 count = 0;
9564
9565 do
9566 {
9567 Field* fields = result->Fetch();
9568
9569 uint32 id = fields[0].Get<uint32>();
9570
9571 GameTele gt;
9572
9573 gt.position_x = fields[1].Get<float>();
9574 gt.position_y = fields[2].Get<float>();
9575 gt.position_z = fields[3].Get<float>();
9576 gt.orientation = fields[4].Get<float>();
9577 gt.mapId = fields[5].Get<uint16>();
9578 gt.name = fields[6].Get<std::string>();
9579
9580 if (!MapMgr::IsValidMapCoord(gt.mapId, gt.position_x, gt.position_y, gt.position_z, gt.orientation))
9581 {
9582 LOG_ERROR("sql.sql", "Wrong position for id {} (name: {}) in `game_tele` table, ignoring.", id, gt.name);
9583 continue;
9584 }
9585
9586 if (!Utf8toWStr(gt.name, gt.wnameLow))
9587 {
9588 LOG_ERROR("sql.sql", "Wrong UTF8 name for id {} in `game_tele` table, ignoring.", id);
9589 continue;
9590 }
9591
9592 wstrToLower(gt.wnameLow);
9593
9594 _gameTeleStore[id] = gt;
9595
9596 ++count;
9597 } while (result->NextRow());
9598
9599 LOG_INFO("server.loading", ">> Loaded {} GameTeleports in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
9600 LOG_INFO("server.loading", " ");
9601}
float position_x
Definition ObjectMgr.h:134

References _gameTeleStore, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), MapMgr::IsValidMapCoord(), LOG_ERROR, LOG_INFO, LOG_WARN, GameTele::position_x, Utf8toWStr(), WorldDatabase, and wstrToLower().

◆ LoadGossipMenu()

void ObjectMgr::LoadGossipMenu ( )
10004{
10005 uint32 oldMSTime = getMSTime();
10006
10007 _gossipMenusStore.clear();
10008
10009 QueryResult result = WorldDatabase.Query("SELECT MenuID, TextID FROM gossip_menu");
10010
10011 if (!result)
10012 {
10013 LOG_WARN("server.loading", ">> Loaded 0 gossip_menu entries. DB table `gossip_menu` is empty!");
10014 LOG_INFO("server.loading", " ");
10015 return;
10016 }
10017
10018 do
10019 {
10020 Field* fields = result->Fetch();
10021
10022 GossipMenus gMenu;
10023
10024 gMenu.MenuID = fields[0].Get<uint32>();
10025 gMenu.TextID = fields[1].Get<uint32>();
10026
10027 if (!GetGossipText(gMenu.TextID))
10028 {
10029 LOG_ERROR("sql.sql", "Table gossip_menu entry {} are using non-existing TextID {}", gMenu.MenuID, gMenu.TextID);
10030 continue;
10031 }
10032
10033 _gossipMenusStore.insert(GossipMenusContainer::value_type(gMenu.MenuID, gMenu));
10034 } while (result->NextRow());
10035
10036 LOG_INFO("server.loading", ">> Loaded {} gossip_menu entries in {} ms", (uint32)_gossipMenusStore.size(), GetMSTimeDiffToNow(oldMSTime));
10037 LOG_INFO("server.loading", " ");
10038}
GossipText const * GetGossipText(uint32 Text_ID) const
Definition ObjectMgr.cpp:6606
Definition ObjectMgr.h:627
uint32 TextID
Definition ObjectMgr.h:629
uint32 MenuID
Definition ObjectMgr.h:628

References _gossipMenusStore, Field::Get(), GetGossipText(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, GossipMenus::MenuID, GossipMenus::TextID, and WorldDatabase.

◆ LoadGossipMenuItems()

void ObjectMgr::LoadGossipMenuItems ( )
10041{
10042 uint32 oldMSTime = getMSTime();
10043
10044 _gossipMenuItemsStore.clear();
10045
10046 QueryResult result = WorldDatabase.Query(
10047 // 0 1 2 3 4 5 6 7 8 9 10 11 12
10048 "SELECT MenuID, OptionID, OptionIcon, OptionText, OptionBroadcastTextID, OptionType, OptionNpcFlag, ActionMenuID, ActionPoiID, BoxCoded, BoxMoney, BoxText, BoxBroadcastTextID "
10049 "FROM gossip_menu_option ORDER BY MenuID, OptionID");
10050
10051 if (!result)
10052 {
10053 LOG_WARN("server.loading", ">> Loaded 0 gossip_menu_option IDs. DB table `gossip_menu_option` is empty!");
10054 LOG_INFO("server.loading", " ");
10055 return;
10056 }
10057
10058 do
10059 {
10060 Field* fields = result->Fetch();
10061
10062 GossipMenuItems gMenuItem;
10063
10064 gMenuItem.MenuID = fields[0].Get<uint32>();
10065 gMenuItem.OptionID = fields[1].Get<uint16>();
10066 gMenuItem.OptionIcon = fields[2].Get<uint32>();
10067 gMenuItem.OptionText = fields[3].Get<std::string>();
10068 gMenuItem.OptionBroadcastTextID = fields[4].Get<uint32>();
10069 gMenuItem.OptionType = fields[5].Get<uint8>();
10070 gMenuItem.OptionNpcFlag = fields[6].Get<uint32>();
10071 gMenuItem.ActionMenuID = fields[7].Get<uint32>();
10072 gMenuItem.ActionPoiID = fields[8].Get<uint32>();
10073 gMenuItem.BoxCoded = fields[9].Get<bool>();
10074 gMenuItem.BoxMoney = fields[10].Get<uint32>();
10075 gMenuItem.BoxText = fields[11].Get<std::string>();
10076 gMenuItem.BoxBroadcastTextID = fields[12].Get<uint32>();
10077
10078 if (gMenuItem.OptionIcon >= GOSSIP_ICON_MAX)
10079 {
10080 LOG_ERROR("sql.sql", "Table `gossip_menu_option` for menu {}, id {} has unknown icon id {}. Replacing with GOSSIP_ICON_CHAT", gMenuItem.MenuID, gMenuItem.OptionID, gMenuItem.OptionIcon);
10081 gMenuItem.OptionIcon = GOSSIP_ICON_CHAT;
10082 }
10083
10085 {
10086 LOG_ERROR("sql.sql", "Table `gossip_menu_option` for menu {}, id {} has non-existing or incompatible OptionBroadcastTextID {}, ignoring.", gMenuItem.MenuID, gMenuItem.OptionID, gMenuItem.OptionBroadcastTextID);
10087 gMenuItem.OptionBroadcastTextID = 0;
10088 }
10089
10090 if (gMenuItem.OptionType >= GOSSIP_OPTION_MAX)
10091 LOG_ERROR("sql.sql", "Table `gossip_menu_option` for menu {}, id {} has unknown option id {}. Option will not be used", gMenuItem.MenuID, gMenuItem.OptionID, gMenuItem.OptionType);
10092
10093 if (gMenuItem.ActionPoiID && !GetPointOfInterest(gMenuItem.ActionPoiID))
10094 {
10095 LOG_ERROR("sql.sql", "Table `gossip_menu_option` for menu {}, id {} use non-existing ActionPoiID {}, ignoring", gMenuItem.MenuID, gMenuItem.OptionID, gMenuItem.ActionPoiID);
10096 gMenuItem.ActionPoiID = 0;
10097 }
10098
10099 if (gMenuItem.BoxBroadcastTextID && !GetBroadcastText(gMenuItem.BoxBroadcastTextID))
10100 {
10101 LOG_ERROR("sql.sql", "Table `gossip_menu_option` for menu {}, id {} has non-existing or incompatible BoxBroadcastTextID {}, ignoring.", gMenuItem.MenuID, gMenuItem.OptionID, gMenuItem.BoxBroadcastTextID);
10102 gMenuItem.BoxBroadcastTextID = 0;
10103 }
10104
10105 _gossipMenuItemsStore.insert(GossipMenuItemsContainer::value_type(gMenuItem.MenuID, gMenuItem));
10106 } while (result->NextRow());
10107
10108 // Warn if any trainer creature templates reference a GossipMenuId that has no gossip_menu_option entries
10109 // This will cause the gossip menu to fallback to MenuID 0 at runtime which will display: "I wish to unlearn my talents."
10110 std::set<uint32> checkedMenuIds;
10111 for (auto const& [entry, tmpl] : _creatureTemplateStore)
10112 {
10113 uint32 menuId = tmpl.GossipMenuId;
10114 if (!menuId)
10115 continue;
10116
10117 if (!(tmpl.npcflag & UNIT_NPC_FLAG_TRAINER))
10118 continue;
10119
10120 if (checkedMenuIds.contains(menuId))
10121 continue;
10122
10123 checkedMenuIds.insert(menuId);
10124
10125 auto [first, second] = _gossipMenuItemsStore.equal_range(menuId);
10126 if (first == second)
10127 LOG_WARN("server.loading", "Trainer creature template references GossipMenuId {} has no `gossip_menu_option` entries. This will fallback to MenuID 0.", menuId);
10128 }
10129
10130 LOG_INFO("server.loading", ">> Loaded {} gossip_menu_option entries in {} ms", uint32(_gossipMenuItemsStore.size()), GetMSTimeDiffToNow(oldMSTime));
10131 LOG_INFO("server.loading", " ");
10132}
@ GOSSIP_ICON_CHAT
Definition GossipDef.h:61
@ GOSSIP_ICON_MAX
Definition GossipDef.h:82
@ GOSSIP_OPTION_MAX
Definition GossipDef.h:56
@ UNIT_NPC_FLAG_TRAINER
Definition UnitDefines.h:326
PointOfInterest const * GetPointOfInterest(uint32 id) const
Definition ObjectMgr.h:931
BroadcastText const * GetBroadcastText(uint32 id) const
Definition ObjectMgr.h:1224
Definition ObjectMgr.h:609
uint8 OptionIcon
Definition ObjectMgr.h:612
uint32 BoxBroadcastTextID
Definition ObjectMgr.h:623
std::string OptionText
Definition ObjectMgr.h:613
uint32 ActionMenuID
Definition ObjectMgr.h:617
bool BoxCoded
Definition ObjectMgr.h:619
uint32 MenuID
Definition ObjectMgr.h:610
uint32 OptionNpcFlag
Definition ObjectMgr.h:616
uint32 ActionPoiID
Definition ObjectMgr.h:618
uint32 BoxMoney
Definition ObjectMgr.h:620
std::string BoxText
Definition ObjectMgr.h:621
uint32 OptionID
Definition ObjectMgr.h:611
uint32 OptionType
Definition ObjectMgr.h:615
uint32 OptionBroadcastTextID
Definition ObjectMgr.h:614

References _creatureTemplateStore, _gossipMenuItemsStore, GossipMenuItems::ActionMenuID, GossipMenuItems::ActionPoiID, GossipMenuItems::BoxBroadcastTextID, GossipMenuItems::BoxCoded, GossipMenuItems::BoxMoney, GossipMenuItems::BoxText, Field::Get(), GetBroadcastText(), getMSTime(), GetMSTimeDiffToNow(), GetPointOfInterest(), GOSSIP_ICON_CHAT, GOSSIP_ICON_MAX, GOSSIP_OPTION_MAX, LOG_ERROR, LOG_INFO, LOG_WARN, GossipMenuItems::MenuID, GossipMenuItems::OptionBroadcastTextID, GossipMenuItems::OptionIcon, GossipMenuItems::OptionID, GossipMenuItems::OptionNpcFlag, GossipMenuItems::OptionText, GossipMenuItems::OptionType, UNIT_NPC_FLAG_TRAINER, and WorldDatabase.

◆ LoadGossipMenuItemsLocales()

void ObjectMgr::LoadGossipMenuItemsLocales ( )
423{
424 uint32 oldMSTime = getMSTime();
425
426 _gossipMenuItemsLocaleStore.clear(); // need for reload case
427
428 // 0 1 2 3 4
429 QueryResult result = WorldDatabase.Query("SELECT MenuID, OptionID, Locale, OptionText, BoxText FROM gossip_menu_option_locale");
430
431 if (!result)
432 return;
433
434 do
435 {
436 Field* fields = result->Fetch();
437
438 uint32 MenuID = fields[0].Get<uint32>();
439 uint16 OptionID = fields[1].Get<uint16>();
440
441 LocaleConstant locale = GetLocaleByName(fields[2].Get<std::string>());
442 if (locale == LOCALE_enUS)
443 continue;
444
446 AddLocaleString(fields[3].Get<std::string>(), locale, data.OptionText);
447 AddLocaleString(fields[4].Get<std::string>(), locale, data.BoxText);
448 } while (result->NextRow());
449
450 LOG_INFO("server.loading", ">> Loaded {} Gossip Menu Option Locale Strings in {} ms", (uint32)_gossipMenuItemsLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
451}
Definition CreatureData.h:349
std::vector< std::string > BoxText
Definition CreatureData.h:351
std::vector< std::string > OptionText
Definition CreatureData.h:350

References _gossipMenuItemsLocaleStore, AddLocaleString(), GossipMenuItemsLocale::BoxText, Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, MAKE_PAIR32(), GossipMenuItemsLocale::OptionText, and WorldDatabase.

◆ LoadGossipText()

void ObjectMgr::LoadGossipText ( )
6615{
6616 uint32 oldMSTime = getMSTime();
6617
6618 QueryResult result = WorldDatabase.Query("SELECT ID, "
6619 "text0_0, text0_1, BroadcastTextID0, lang0, Probability0, em0_0, em0_1, em0_2, em0_3, em0_4, em0_5, "
6620 "text1_0, text1_1, BroadcastTextID1, lang1, Probability1, em1_0, em1_1, em1_2, em1_3, em1_4, em1_5, "
6621 "text2_0, text2_1, BroadcastTextID2, lang2, Probability2, em2_0, em2_1, em2_2, em2_3, em2_4, em2_5, "
6622 "text3_0, text3_1, BroadcastTextID3, lang3, Probability3, em3_0, em3_1, em3_2, em3_3, em3_4, em3_5, "
6623 "text4_0, text4_1, BroadcastTextID4, lang4, Probability4, em4_0, em4_1, em4_2, em4_3, em4_4, em4_5, "
6624 "text5_0, text5_1, BroadcastTextID5, lang5, Probability5, em5_0, em5_1, em5_2, em5_3, em5_4, em5_5, "
6625 "text6_0, text6_1, BroadcastTextID6, lang6, Probability6, em6_0, em6_1, em6_2, em6_3, em6_4, em6_5, "
6626 "text7_0, text7_1, BroadcastTextID7, lang7, Probability7, em7_0, em7_1, em7_2, em7_3, em7_4, em7_5 "
6627 "FROM npc_text");
6628
6629 if (!result)
6630 {
6631 LOG_WARN("server.loading", ">> Loaded 0 npc texts, table is empty!");
6632 LOG_INFO("server.loading", " ");
6633 return;
6634 }
6635
6636 _gossipTextStore.rehash(result->GetRowCount());
6637
6638 uint32 count = 0;
6639 uint8 cic;
6640
6641 do
6642 {
6643 cic = 0;
6644
6645 Field* fields = result->Fetch();
6646
6647 uint32 id = fields[cic++].Get<uint32>();
6648 if (!id)
6649 {
6650 LOG_ERROR("sql.sql", "Table `npc_text` has record wit reserved id 0, ignore.");
6651 continue;
6652 }
6653
6654 GossipText& gText = _gossipTextStore[id];
6655
6656 for (uint8 i = 0; i < MAX_GOSSIP_TEXT_OPTIONS; ++i)
6657 {
6658 gText.Options[i].Text_0 = fields[cic++].Get<std::string>();
6659 gText.Options[i].Text_1 = fields[cic++].Get<std::string>();
6660 gText.Options[i].BroadcastTextID = fields[cic++].Get<uint32>();
6661 gText.Options[i].Language = fields[cic++].Get<uint8>();
6662 gText.Options[i].Probability = fields[cic++].Get<float>();
6663
6664 for (uint8 j = 0; j < MAX_GOSSIP_TEXT_EMOTES; ++j)
6665 {
6666 gText.Options[i].Emotes[j]._Delay = fields[cic++].Get<uint16>();
6667 gText.Options[i].Emotes[j]._Emote = fields[cic++].Get<uint16>();
6668 }
6669 }
6670
6671 for (uint8 i = 0; i < MAX_GOSSIP_TEXT_OPTIONS; i++)
6672 {
6673 if (gText.Options[i].BroadcastTextID)
6674 {
6676 {
6677 LOG_ERROR("sql.sql", "GossipText (Id: {}) in table `npc_text` has non-existing or incompatible BroadcastTextID{} {}.", id, i, gText.Options[i].BroadcastTextID);
6678 gText.Options[i].BroadcastTextID = 0;
6679 }
6680 }
6681 }
6682
6683 count++;
6684 } while (result->NextRow());
6685
6686 LOG_INFO("server.loading", ">> Loaded {} Npc Texts in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
6687 LOG_INFO("server.loading", " ");
6688}
#define MAX_GOSSIP_TEXT_OPTIONS
Definition NPCHandler.h:42
#define MAX_GOSSIP_TEXT_EMOTES
Definition NPCHandler.h:30
std::string Text_0
Definition NPCHandler.h:34
QEmote Emotes[MAX_GOSSIP_TEXT_EMOTES]
Definition NPCHandler.h:39
uint32 Language
Definition NPCHandler.h:37
float Probability
Definition NPCHandler.h:38
uint32 BroadcastTextID
Definition NPCHandler.h:36
std::string Text_1
Definition NPCHandler.h:35
Definition NPCHandler.h:45
GossipTextOption Options[MAX_GOSSIP_TEXT_OPTIONS]
Definition NPCHandler.h:46
uint32 _Emote
Definition NPCHandler.h:26
uint32 _Delay
Definition NPCHandler.h:27

References QEmote::_Delay, QEmote::_Emote, _gossipTextStore, GossipTextOption::BroadcastTextID, GossipTextOption::Emotes, Field::Get(), GetBroadcastText(), getMSTime(), GetMSTimeDiffToNow(), GossipTextOption::Language, LOG_ERROR, LOG_INFO, LOG_WARN, MAX_GOSSIP_TEXT_EMOTES, MAX_GOSSIP_TEXT_OPTIONS, GossipText::Options, GossipTextOption::Probability, GossipTextOption::Text_0, GossipTextOption::Text_1, and WorldDatabase.

◆ LoadInstanceEncounters()

void ObjectMgr::LoadInstanceEncounters ( )
6522{
6523 uint32 oldMSTime = getMSTime();
6524
6525 // 0 1 2 3
6526 QueryResult result = WorldDatabase.Query("SELECT entry, creditType, creditEntry, lastEncounterDungeon FROM instance_encounters");
6527 if (!result)
6528 {
6529 LOG_WARN("server.loading", ">> Loaded 0 instance encounters, table is empty!");
6530 LOG_INFO("server.loading", " ");
6531 return;
6532 }
6533
6534 uint32 count = 0;
6535 std::map<uint32, DungeonEncounterEntry const*> dungeonLastBosses;
6536 do
6537 {
6538 Field* fields = result->Fetch();
6539 uint32 entry = fields[0].Get<uint32>();
6540 uint8 creditType = fields[1].Get<uint8>();
6541 uint32 creditEntry = fields[2].Get<uint32>();
6542 uint32 lastEncounterDungeon = fields[3].Get<uint16>();
6543 DungeonEncounterEntry const* dungeonEncounter = sDungeonEncounterStore.LookupEntry(entry);
6544 if (!dungeonEncounter)
6545 {
6546 LOG_ERROR("sql.sql", "Table `instance_encounters` has an invalid encounter id {}, skipped!", entry);
6547 continue;
6548 }
6549
6550 if (lastEncounterDungeon && !sLFGMgr->GetLFGDungeonEntry(lastEncounterDungeon))
6551 {
6552 LOG_ERROR("sql.sql", "Table `instance_encounters` has an encounter {} ({}) marked as final for invalid dungeon id {}, skipped!", entry, dungeonEncounter->encounterName[0], lastEncounterDungeon);
6553 continue;
6554 }
6555
6556 std::map<uint32, DungeonEncounterEntry const*>::const_iterator itr = dungeonLastBosses.find(lastEncounterDungeon);
6557 if (lastEncounterDungeon)
6558 {
6559 if (itr != dungeonLastBosses.end())
6560 {
6561 LOG_ERROR("sql.sql", "Table `instance_encounters` specified encounter {} ({}) as last encounter but {} ({}) is already marked as one, skipped!", entry, dungeonEncounter->encounterName[0], itr->second->id, itr->second->encounterName[0]);
6562 continue;
6563 }
6564
6565 dungeonLastBosses[lastEncounterDungeon] = dungeonEncounter;
6566 }
6567
6568 switch (creditType)
6569 {
6571 {
6572 CreatureTemplate const* creatureInfo = GetCreatureTemplate(creditEntry);
6573 if (!creatureInfo)
6574 {
6575 LOG_ERROR("sql.sql", "Table `instance_encounters` has an invalid creature (entry {}) linked to the encounter {} ({}), skipped!", creditEntry, entry, dungeonEncounter->encounterName[0]);
6576 continue;
6577 }
6578 const_cast<CreatureTemplate*>(creatureInfo)->flags_extra |= CREATURE_FLAG_EXTRA_DUNGEON_BOSS;
6579 break;
6580 }
6582 {
6583 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(creditEntry);
6584 if (!spellInfo)
6585 {
6586 LOG_ERROR("sql.sql", "Table `instance_encounters` has an invalid spell (entry {}) linked to the encounter {} ({}), skipped!", creditEntry, entry, dungeonEncounter->encounterName[0]);
6587 continue;
6588 }
6589 const_cast<SpellInfo*>(spellInfo)->AttributesCu |= SPELL_ATTR0_CU_ENCOUNTER_REWARD;
6590 break;
6591 }
6592 default:
6593 LOG_ERROR("sql.sql", "Table `instance_encounters` has an invalid credit type ({}) for encounter {} ({}), skipped!", creditType, entry, dungeonEncounter->encounterName[0]);
6594 continue;
6595 }
6596
6597 DungeonEncounterList& encounters = _dungeonEncounterStore[MAKE_PAIR32(dungeonEncounter->mapId, dungeonEncounter->difficulty)];
6598 encounters.push_back(new DungeonEncounter(dungeonEncounter, EncounterCreditType(creditType), creditEntry, lastEncounterDungeon));
6599 ++count;
6600 } while (result->NextRow());
6601
6602 LOG_INFO("server.loading", ">> Loaded {} Instance Encounters in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
6603 LOG_INFO("server.loading", " ");
6604}
@ CREATURE_FLAG_EXTRA_DUNGEON_BOSS
Definition CreatureData.h:74
DBCStorage< DungeonEncounterEntry > sDungeonEncounterStore(DungeonEncounterfmt)
#define sLFGMgr
Definition LFGMgr.h:658
EncounterCreditType
Definition Map.h:158
@ ENCOUNTER_CREDIT_KILL_CREATURE
Definition Map.h:159
@ ENCOUNTER_CREDIT_CAST_SPELL
Definition Map.h:160
std::list< DungeonEncounter const * > DungeonEncounterList
Definition ObjectMgr.h:713
@ SPELL_ATTR0_CU_ENCOUNTER_REWARD
Definition SpellInfo.h:208
Definition DBCStructure.h:866
Definition ObjectMgr.h:703

References _dungeonEncounterStore, CREATURE_FLAG_EXTRA_DUNGEON_BOSS, ENCOUNTER_CREDIT_CAST_SPELL, ENCOUNTER_CREDIT_KILL_CREATURE, Field::Get(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, MAKE_PAIR32(), sDungeonEncounterStore, sLFGMgr, SPELL_ATTR0_CU_ENCOUNTER_REWARD, sSpellMgr, and WorldDatabase.

◆ LoadInstanceTemplate()

void ObjectMgr::LoadInstanceTemplate ( )
6471{
6472 uint32 oldMSTime = getMSTime();
6473
6474 // 0 1 2 4
6475 QueryResult result = WorldDatabase.Query("SELECT map, parent, script, allowMount FROM instance_template");
6476
6477 if (!result)
6478 {
6479 LOG_WARN("server.loading", ">> Loaded 0 instance templates. DB table `instance_template` is empty!");
6480 LOG_INFO("server.loading", " ");
6481 return;
6482 }
6483
6484 uint32 count = 0;
6485 do
6486 {
6487 Field* fields = result->Fetch();
6488
6489 uint16 mapID = fields[0].Get<uint16>();
6490
6491 if (!MapMgr::IsValidMAP(mapID, true))
6492 {
6493 LOG_ERROR("sql.sql", "ObjectMgr::LoadInstanceTemplate: bad mapid {} for template!", mapID);
6494 continue;
6495 }
6496
6497 InstanceTemplate instanceTemplate;
6498
6499 instanceTemplate.AllowMount = fields[3].Get<bool>();
6500 instanceTemplate.Parent = uint32(fields[1].Get<uint16>());
6501 instanceTemplate.ScriptId = GetScriptId(fields[2].Get<std::string>());
6502
6503 _instanceTemplateStore[mapID] = instanceTemplate;
6504
6505 ++count;
6506 } while (result->NextRow());
6507
6508 LOG_INFO("server.loading", ">> Loaded {} Instance Templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
6509 LOG_INFO("server.loading", " ");
6510}
static bool IsValidMAP(uint32 mapid, bool startUp)
Definition MapMgr.cpp:311
bool AllowMount
Definition Map.h:125
uint32 ScriptId
Definition Map.h:124

References _instanceTemplateStore, InstanceTemplate::AllowMount, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), GetScriptId(), MapMgr::IsValidMAP(), LOG_ERROR, LOG_INFO, LOG_WARN, InstanceTemplate::Parent, InstanceTemplate::ScriptId, and WorldDatabase.

◆ LoadItemLocales()

void ObjectMgr::LoadItemLocales ( )
3183{
3184 uint32 oldMSTime = getMSTime();
3185
3186 _itemLocaleStore.clear(); // need for reload case
3187
3188 QueryResult result = WorldDatabase.Query("SELECT ID, locale, Name, Description FROM item_template_locale");
3189 if (!result)
3190 return;
3191
3192 do
3193 {
3194 Field* fields = result->Fetch();
3195
3196 uint32 ID = fields[0].Get<uint32>();
3197
3198 LocaleConstant locale = GetLocaleByName(fields[1].Get<std::string>());
3199 if (locale == LOCALE_enUS)
3200 continue;
3201
3202 ItemLocale& data = _itemLocaleStore[ID];
3203 AddLocaleString(fields[2].Get<std::string>(), locale, data.Name);
3204 AddLocaleString(fields[3].Get<std::string>(), locale, data.Description);
3205 } while (result->NextRow());
3206
3207 LOG_INFO("server.loading", ">> Loaded {} Item Locale Strings in {} ms", (uint32)_itemLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
3208}
Definition ItemTemplate.h:834
std::vector< std::string > Description
Definition ItemTemplate.h:836
std::vector< std::string > Name
Definition ItemTemplate.h:835

References _itemLocaleStore, AddLocaleString(), ItemLocale::Description, Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, ItemLocale::Name, and WorldDatabase.

◆ LoadItemSetNameLocales()

void ObjectMgr::LoadItemSetNameLocales ( )
3857{
3858 uint32 oldMSTime = getMSTime();
3859
3860 _itemSetNameLocaleStore.clear(); // need for reload case
3861
3862 QueryResult result = WorldDatabase.Query("SELECT ID, locale, Name FROM item_set_names_locale");
3863
3864 if (!result)
3865 return;
3866
3867 do
3868 {
3869 Field* fields = result->Fetch();
3870
3871 uint32 ID = fields[0].Get<uint32>();
3872
3873 LocaleConstant locale = GetLocaleByName(fields[1].Get<std::string>());
3874 if (locale == LOCALE_enUS)
3875 continue;
3876
3878 AddLocaleString(fields[2].Get<std::string>(), locale, data.Name);
3879 } while (result->NextRow());
3880
3881 LOG_INFO("server.loading", ">> Loaded {} Item Set Name Locale Strings in {} ms", uint32(_itemSetNameLocaleStore.size()), GetMSTimeDiffToNow(oldMSTime));
3882}
Definition ItemTemplate.h:846
std::vector< std::string > Name
Definition ItemTemplate.h:847

References _itemSetNameLocaleStore, AddLocaleString(), Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, ItemSetNameLocale::Name, and WorldDatabase.

◆ LoadItemSetNames()

void ObjectMgr::LoadItemSetNames ( )
3885{
3886 uint32 oldMSTime = getMSTime();
3887
3888 _itemSetNameStore.clear(); // needed for reload case
3889
3890 std::set<uint32> itemSetItems;
3891
3892 // fill item set member ids
3893 for (uint32 entryId = 0; entryId < sItemSetStore.GetNumRows(); ++entryId)
3894 {
3895 ItemSetEntry const* setEntry = sItemSetStore.LookupEntry(entryId);
3896 if (!setEntry)
3897 continue;
3898
3899 for (uint32 i = 0; i < MAX_ITEM_SET_ITEMS; ++i)
3900 if (setEntry->itemId[i])
3901 itemSetItems.insert(setEntry->itemId[i]);
3902 }
3903
3904 // 0 1 2
3905 QueryResult result = WorldDatabase.Query("SELECT `entry`, `name`, `InventoryType` FROM `item_set_names`");
3906
3907 if (!result)
3908 {
3909 LOG_WARN("server.loading", ">> Loaded 0 item set names. DB table `item_set_names` is empty.");
3910 LOG_INFO("server.loading", " ");
3911 return;
3912 }
3913
3914 _itemSetNameStore.rehash(result->GetRowCount());
3915 uint32 count = 0;
3916
3917 do
3918 {
3919 Field* fields = result->Fetch();
3920
3921 uint32 entry = fields[0].Get<uint32>();
3922 if (itemSetItems.find(entry) == itemSetItems.end())
3923 {
3924 LOG_ERROR("sql.sql", "Item set name (Entry: {}) not found in ItemSet.dbc, data useless.", entry);
3925 continue;
3926 }
3927
3928 ItemSetNameEntry& data = _itemSetNameStore[entry];
3929 data.name = fields[1].Get<std::string>();
3930
3931 uint32 invType = fields[2].Get<uint8>();
3932 if (invType >= MAX_INVTYPE)
3933 {
3934 LOG_ERROR("sql.sql", "Item set name (Entry: {}) has wrong InventoryType value ({})", entry, invType);
3935 invType = INVTYPE_NON_EQUIP;
3936 }
3937
3938 data.InventoryType = invType;
3939 itemSetItems.erase(entry);
3940 ++count;
3941 } while (result->NextRow());
3942
3943 if (!itemSetItems.empty())
3944 {
3945 ItemTemplate const* pProto;
3946 for (std::set<uint32>::iterator itr = itemSetItems.begin(); itr != itemSetItems.end(); ++itr)
3947 {
3948 uint32 entry = *itr;
3949 // add data from item_template if available
3950 pProto = GetItemTemplate(entry);
3951 if (pProto)
3952 {
3953 LOG_ERROR("sql.sql", "Item set part (Entry: {}) does not have entry in `item_set_names`, adding data from `item_template`.", entry);
3954 ItemSetNameEntry& data = _itemSetNameStore[entry];
3955 data.name = pProto->Name1;
3956 data.InventoryType = pProto->InventoryType;
3957 ++count;
3958 }
3959 else
3960 LOG_ERROR("sql.sql", "Item set part (Entry: {}) does not have entry in `item_set_names`, set will not display properly.", entry);
3961 }
3962 }
3963
3964 LOG_INFO("server.loading", ">> Loaded {} Item Set Names in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
3965 LOG_INFO("server.loading", " ");
3966}
DBCStorage< ItemSetEntry > sItemSetStore(ItemSetEntryfmt)
#define MAX_ITEM_SET_ITEMS
Definition DBCStructure.h:1228
@ INVTYPE_NON_EQUIP
Definition ItemTemplate.h:256
#define MAX_INVTYPE
Definition ItemTemplate.h:287
Definition DBCStructure.h:1232
uint32 itemId[MAX_ITEM_SET_ITEMS]
Definition DBCStructure.h:1236
Definition ItemTemplate.h:840
uint32 InventoryType
Definition ItemTemplate.h:842
std::string name
Definition ItemTemplate.h:841
std::string Name1
Definition ItemTemplate.h:624
uint32 InventoryType
Definition ItemTemplate.h:632

References _itemSetNameStore, Field::Get(), GetItemTemplate(), getMSTime(), GetMSTimeDiffToNow(), ItemTemplate::InventoryType, ItemSetNameEntry::InventoryType, INVTYPE_NON_EQUIP, ItemSetEntry::itemId, LOG_ERROR, LOG_INFO, LOG_WARN, MAX_INVTYPE, MAX_ITEM_SET_ITEMS, ItemSetNameEntry::name, ItemTemplate::Name1, sItemSetStore, and WorldDatabase.

◆ LoadItemTemplates()

void ObjectMgr::LoadItemTemplates ( )
3235{
3236 uint32 oldMSTime = getMSTime();
3237
3238 // 0 1 2 3 4 5 6 7 8 9 10 11 12
3239 QueryResult result = WorldDatabase.Query("SELECT entry, class, subclass, SoundOverrideSubclass, name, displayid, Quality, Flags, FlagsExtra, BuyCount, BuyPrice, SellPrice, InventoryType, "
3240 // 13 14 15 16 17 18 19 20
3241 "AllowableClass, AllowableRace, ItemLevel, RequiredLevel, RequiredSkill, RequiredSkillRank, requiredspell, requiredhonorrank, "
3242 // 21 22 23 24 25 26 27
3243 "RequiredCityRank, RequiredReputationFaction, RequiredReputationRank, maxcount, stackable, ContainerSlots, stat_type1, "
3244 // 28 29 30 31 32 33 34 35 36 37
3245 "stat_value1, stat_type2, stat_value2, stat_type3, stat_value3, stat_type4, stat_value4, stat_type5, stat_value5, stat_type6, "
3246 // 38 39 40 41 42 43 44 45 46
3247 "stat_value6, stat_type7, stat_value7, stat_type8, stat_value8, stat_type9, stat_value9, stat_type10, stat_value10, "
3248 // 47 48 49 50 51 52 53 54 55 56 57
3249 "ScalingStatDistribution, ScalingStatValue, dmg_min1, dmg_max1, dmg_type1, dmg_min2, dmg_max2, dmg_type2, armor, holy_res, fire_res, "
3250 // 58 59 60 61 62 63 64 65 66 67
3251 "nature_res, frost_res, shadow_res, arcane_res, delay, ammo_type, RangedModRange, spellid_1, spelltrigger_1, spellcharges_1, "
3252 // 68 69 70 71 72 73 74
3253 "spellppmRate_1, spellcooldown_1, spellcategory_1, spellcategorycooldown_1, spellid_2, spelltrigger_2, spellcharges_2, "
3254 // 75 76 77 78 79 80 81
3255 "spellppmRate_2, spellcooldown_2, spellcategory_2, spellcategorycooldown_2, spellid_3, spelltrigger_3, spellcharges_3, "
3256 // 82 83 84 85 86 87 88
3257 "spellppmRate_3, spellcooldown_3, spellcategory_3, spellcategorycooldown_3, spellid_4, spelltrigger_4, spellcharges_4, "
3258 // 89 90 91 92 93 94 95
3259 "spellppmRate_4, spellcooldown_4, spellcategory_4, spellcategorycooldown_4, spellid_5, spelltrigger_5, spellcharges_5, "
3260 // 96 97 98 99 100 101 102 103 104
3261 "spellppmRate_5, spellcooldown_5, spellcategory_5, spellcategorycooldown_5, bonding, description, PageText, LanguageID, PageMaterial, "
3262 // 105 106 107 108 109 110 111 112 113 114 115 116
3263 "startquest, lockid, Material, sheath, RandomProperty, RandomSuffix, block, itemset, MaxDurability, area, Map, BagFamily, "
3264 // 117 118 119 120 121 122 123 124
3265 "TotemCategory, socketColor_1, socketContent_1, socketColor_2, socketContent_2, socketColor_3, socketContent_3, socketBonus, "
3266 // 125 126 127 128 129 130 131 132
3267 "GemProperties, RequiredDisenchantSkill, ArmorDamageModifier, duration, ItemLimitCategory, HolidayId, ScriptName, DisenchantID, "
3268 // 133 134 135 136
3269 "FoodType, minMoneyLoot, maxMoneyLoot, flagsCustom FROM item_template");
3270
3271 if (!result)
3272 {
3273 LOG_WARN("server.loading", ">> Loaded 0 item templates. DB table `item_template` is empty.");
3274 LOG_INFO("server.loading", " ");
3275 return;
3276 }
3277
3278 _itemTemplateStore.reserve(result->GetRowCount());
3279 uint32 count = 0;
3280 // original inspiration https://github.com/TrinityCore/TrinityCore/commit/0c44bd33ee7b42c924859139a9f4b04cf2b91261
3281 bool enforceDBCAttributes = sWorld->getBoolConfig(CONFIG_DBC_ENFORCE_ITEM_ATTRIBUTES);
3282
3283 do
3284 {
3285 Field* fields = result->Fetch();
3286
3287 uint32 entry = fields[0].Get<uint32>();
3288
3289 ItemTemplate& itemTemplate = _itemTemplateStore[entry];
3290
3291 itemTemplate.ItemId = entry;
3292 itemTemplate.Class = uint32(fields[1].Get<uint8>());
3293 itemTemplate.SubClass = uint32(fields[2].Get<uint8>());
3294 itemTemplate.SoundOverrideSubclass = int32(fields[3].Get<int8>());
3295 itemTemplate.Name1 = fields[4].Get<std::string>();
3296 itemTemplate.DisplayInfoID = fields[5].Get<uint32>();
3297 itemTemplate.Quality = uint32(fields[6].Get<uint8>());
3298 itemTemplate.Flags = ItemFlags(fields[7].Get<uint32>());
3299 itemTemplate.Flags2 = ItemFlags2(fields[8].Get<uint32>());
3300 itemTemplate.BuyCount = uint32(fields[9].Get<uint8>());
3301 itemTemplate.BuyPrice = int32(fields[10].Get<int64>());
3302 itemTemplate.SellPrice = uint32(fields[11].Get<uint32>());
3303 itemTemplate.InventoryType = uint32(fields[12].Get<uint8>());
3304 itemTemplate.AllowableClass = fields[13].Get<int32>();
3305 itemTemplate.AllowableRace = fields[14].Get<int32>();
3306 itemTemplate.ItemLevel = uint32(fields[15].Get<uint16>());
3307 itemTemplate.RequiredLevel = uint32(fields[16].Get<uint8>());
3308 itemTemplate.RequiredSkill = uint32(fields[17].Get<uint16>());
3309 itemTemplate.RequiredSkillRank = uint32(fields[18].Get<uint16>());
3310 itemTemplate.RequiredSpell = fields[19].Get<uint32>();
3311 itemTemplate.RequiredHonorRank = fields[20].Get<uint32>();
3312 itemTemplate.RequiredCityRank = fields[21].Get<uint32>();
3313 itemTemplate.RequiredReputationFaction = uint32(fields[22].Get<uint16>());
3314 itemTemplate.RequiredReputationRank = uint32(fields[23].Get<uint16>());
3315 itemTemplate.MaxCount = fields[24].Get<int32>();
3316 itemTemplate.Stackable = fields[25].Get<int32>();
3317 itemTemplate.ContainerSlots = uint32(fields[26].Get<uint8>());
3318
3319 uint8 statsCount = 0;
3320 while (statsCount < MAX_ITEM_PROTO_STATS)
3321 {
3322 uint32 statType = uint32(fields[27 + statsCount * 2].Get<uint8>());
3323 int32 statValue = fields[28 + statsCount * 2].Get<int32>();
3324 if (statType == 0)
3325 break;
3326
3327 itemTemplate.ItemStat[statsCount].ItemStatType = statType;
3328 itemTemplate.ItemStat[statsCount].ItemStatValue = statValue;
3329 statsCount++;
3330 }
3331 itemTemplate.StatsCount = statsCount;
3332
3333 itemTemplate.ScalingStatDistribution = uint32(fields[47].Get<uint16>());
3334 itemTemplate.ScalingStatValue = fields[48].Get<int32>();
3335
3336 for (uint8 i = 0; i < MAX_ITEM_PROTO_DAMAGES; ++i)
3337 {
3338 itemTemplate.Damage[i].DamageMin = fields[49 + i * 3].Get<float>();
3339 itemTemplate.Damage[i].DamageMax = fields[50 + i * 3].Get<float>();
3340 itemTemplate.Damage[i].DamageType = uint32(fields[51 + i * 3].Get<uint8>());
3341 }
3342
3343 itemTemplate.Armor = fields[55].Get<uint32>();
3344 itemTemplate.HolyRes = fields[56].Get<int32>();
3345 itemTemplate.FireRes = fields[57].Get<int32>();
3346 itemTemplate.NatureRes = fields[58].Get<int32>();
3347 itemTemplate.FrostRes = fields[59].Get<int32>();
3348 itemTemplate.ShadowRes = fields[60].Get<int32>();
3349 itemTemplate.ArcaneRes = fields[61].Get<int32>();
3350 itemTemplate.Delay = uint32(fields[62].Get<uint16>());
3351 itemTemplate.AmmoType = uint32(fields[63].Get<uint8>());
3352 itemTemplate.RangedModRange = fields[64].Get<float>();
3353
3354 for (uint8 i = 0; i < MAX_ITEM_PROTO_SPELLS; ++i)
3355 {
3356 itemTemplate.Spells[i].SpellId = fields[65 + i * 7 ].Get<int32>();
3357 itemTemplate.Spells[i].SpellTrigger = uint32(fields[66 + i * 7].Get<uint8>());
3358 itemTemplate.Spells[i].SpellCharges = int32(fields[67 + i * 7].Get<int16>());
3359 itemTemplate.Spells[i].SpellPPMRate = fields[68 + i * 7].Get<float>();
3360 itemTemplate.Spells[i].SpellCooldown = fields[69 + i * 7].Get<int32>();
3361 itemTemplate.Spells[i].SpellCategory = uint32(fields[70 + i * 7].Get<uint16>());
3362 itemTemplate.Spells[i].SpellCategoryCooldown = fields[71 + i * 7].Get<int32>();
3363 }
3364
3365 itemTemplate.Bonding = uint32(fields[100].Get<uint8>());
3366 itemTemplate.Description = fields[101].Get<std::string>();
3367 itemTemplate.PageText = fields[102].Get<uint32>();
3368 itemTemplate.LanguageID = uint32(fields[103].Get<uint8>());
3369 itemTemplate.PageMaterial = uint32(fields[104].Get<uint8>());
3370 itemTemplate.StartQuest = fields[105].Get<uint32>();
3371 itemTemplate.LockID = fields[106].Get<uint32>();
3372 itemTemplate.Material = int32(fields[107].Get<int8>());
3373 itemTemplate.Sheath = uint32(fields[108].Get<uint8>());
3374 itemTemplate.RandomProperty = fields[109].Get<int32>();
3375 itemTemplate.RandomSuffix = fields[110].Get<int32>();
3376 itemTemplate.Block = fields[111].Get<uint32>();
3377 itemTemplate.ItemSet = fields[112].Get<uint32>();
3378 itemTemplate.MaxDurability = uint32(fields[113].Get<uint16>());
3379 itemTemplate.Area = fields[114].Get<uint32>();
3380 itemTemplate.Map = uint32(fields[115].Get<uint16>());
3381 itemTemplate.BagFamily = fields[116].Get<uint32>();
3382 itemTemplate.TotemCategory = fields[117].Get<uint32>();
3383
3384 for (uint8 i = 0; i < MAX_ITEM_PROTO_SOCKETS; ++i)
3385 {
3386 itemTemplate.Socket[i].Color = uint32(fields[118 + i * 2].Get<uint8>());
3387 itemTemplate.Socket[i].Content = fields[119 + i * 2].Get<uint32>();
3388 }
3389
3390 itemTemplate.socketBonus = fields[124].Get<uint32>();
3391 itemTemplate.GemProperties = fields[125].Get<uint32>();
3392 itemTemplate.RequiredDisenchantSkill = uint32(fields[126].Get<int16>());
3393 itemTemplate.ArmorDamageModifier = fields[127].Get<float>();
3394 itemTemplate.Duration = fields[128].Get<uint32>();
3395 itemTemplate.ItemLimitCategory = uint32(fields[129].Get<int16>());
3396 itemTemplate.HolidayId = fields[130].Get<uint32>();
3397 itemTemplate.ScriptId = GetScriptId(fields[131].Get<std::string>());
3398 itemTemplate.DisenchantID = fields[132].Get<uint32>();
3399 itemTemplate.FoodType = uint32(fields[133].Get<uint8>());
3400 itemTemplate.MinMoneyLoot = fields[134].Get<uint32>();
3401 itemTemplate.MaxMoneyLoot = fields[135].Get<uint32>();
3402 itemTemplate.FlagsCu = ItemFlagsCustom(fields[136].Get<uint32>());
3403
3404 // Checks
3405 ItemEntry const* dbcitem = sItemStore.LookupEntry(entry);
3406
3407 if (!dbcitem)
3408 {
3409 LOG_DEBUG("sql.sql", "Item (Entry: {}) does not exist in item.dbc! (not correct id?).", entry);
3410 continue;
3411 }
3412
3413 if (enforceDBCAttributes)
3414 {
3415 if (itemTemplate.Class != dbcitem->ClassID)
3416 {
3417 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong Class value ({}), must be ({}).", entry, itemTemplate.Class, dbcitem->ClassID);
3418 itemTemplate.Class = dbcitem->ClassID;
3419 }
3420 if (itemTemplate.SubClass != dbcitem->SubclassID)
3421 {
3422 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong Subclass value ({}) for class {}, must be ({}).", entry, itemTemplate.SubClass, itemTemplate.Class, dbcitem->SubclassID);
3423 itemTemplate.SubClass = dbcitem->SubclassID;
3424 }
3425 if (itemTemplate.SoundOverrideSubclass != dbcitem->SoundOverrideSubclassID)
3426 {
3427 LOG_ERROR("sql.sql", "Item (Entry: {}) does not have a correct SoundOverrideSubclass ({}), must be {}.", entry, itemTemplate.SoundOverrideSubclass, dbcitem->SoundOverrideSubclassID);
3428 itemTemplate.SoundOverrideSubclass = dbcitem->SoundOverrideSubclassID;
3429 }
3430 if (itemTemplate.Material != dbcitem->Material)
3431 {
3432 LOG_ERROR("sql.sql", "Item (Entry: {}) does not have a correct material ({}), must be {}.", entry, itemTemplate.Material, dbcitem->Material);
3433 itemTemplate.Material = dbcitem->Material;
3434 }
3435 if (itemTemplate.InventoryType != dbcitem->InventoryType)
3436 {
3437 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong InventoryType value ({}), must be {}.", entry, itemTemplate.InventoryType, dbcitem->InventoryType);
3438 itemTemplate.InventoryType = dbcitem->InventoryType;
3439 }
3440 if (itemTemplate.DisplayInfoID != dbcitem->DisplayInfoID)
3441 {
3442 LOG_ERROR("sql.sql", "Item (Entry: {}) does not have a correct display id ({}), must be {}.", entry, itemTemplate.DisplayInfoID, dbcitem->DisplayInfoID);
3443 itemTemplate.DisplayInfoID = dbcitem->DisplayInfoID;
3444 }
3445 if (itemTemplate.Sheath != dbcitem->SheatheType)
3446 {
3447 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong Sheath ({}), must be {}.", entry, itemTemplate.Sheath, dbcitem->SheatheType);
3448 itemTemplate.Sheath = dbcitem->SheatheType;
3449 }
3450 }
3451
3452 if (itemTemplate.Quality >= MAX_ITEM_QUALITY)
3453 {
3454 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong Quality value ({})", entry, itemTemplate.Quality);
3455 itemTemplate.Quality = ITEM_QUALITY_NORMAL;
3456 }
3457
3458 if (itemTemplate.HasFlag2(ITEM_FLAG2_FACTION_HORDE))
3459 {
3460 if (FactionEntry const* faction = sFactionStore.LookupEntry(HORDE))
3461 if ((itemTemplate.AllowableRace & faction->BaseRepRaceMask[0]) == 0)
3462 LOG_ERROR("sql.sql", "Item (Entry: {}) has value ({}) in `AllowableRace` races, not compatible with ITEM_FLAG2_FACTION_HORDE ({}) in Flags field, item cannot be equipped or used by these races.",
3463 entry, itemTemplate.AllowableRace, ITEM_FLAG2_FACTION_HORDE);
3464
3465 if (itemTemplate.HasFlag2(ITEM_FLAG2_FACTION_ALLIANCE))
3466 LOG_ERROR("sql.sql", "Item (Entry: {}) has value ({}) in `Flags2` flags (ITEM_FLAG2_FACTION_ALLIANCE) and ITEM_FLAG2_FACTION_HORDE ({}) in Flags field, this is a wrong combination.",
3468 }
3469 else if (itemTemplate.HasFlag2(ITEM_FLAG2_FACTION_ALLIANCE))
3470 {
3471 if (FactionEntry const* faction = sFactionStore.LookupEntry(ALLIANCE))
3472 if ((itemTemplate.AllowableRace & faction->BaseRepRaceMask[0]) == 0)
3473 LOG_ERROR("sql.sql", "Item (Entry: {}) has value ({}) in `AllowableRace` races, not compatible with ITEM_FLAG2_FACTION_ALLIANCE ({}) in Flags field, item cannot be equipped or used by these races.",
3474 entry, itemTemplate.AllowableRace, ITEM_FLAG2_FACTION_ALLIANCE);
3475 }
3476
3477 if (itemTemplate.BuyCount <= 0)
3478 {
3479 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong BuyCount value ({}), set to default(1).", entry, itemTemplate.BuyCount);
3480 itemTemplate.BuyCount = 1;
3481 }
3482
3483 if (itemTemplate.RequiredSkill >= MAX_SKILL_TYPE)
3484 {
3485 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong RequiredSkill value ({})", entry, itemTemplate.RequiredSkill);
3486 itemTemplate.RequiredSkill = 0;
3487 }
3488
3489 {
3490 // can be used in equip slot, as page read use in inventory, or spell casting at use
3491 bool req = itemTemplate.InventoryType != INVTYPE_NON_EQUIP || itemTemplate.PageText;
3492 if (!req)
3493 for (uint8 j = 0; j < MAX_ITEM_PROTO_SPELLS; ++j)
3494 {
3495 if (itemTemplate.Spells[j].SpellId)
3496 {
3497 req = true;
3498 break;
3499 }
3500 }
3501
3502 if (req)
3503 {
3504 if (!(itemTemplate.AllowableClass & CLASSMASK_ALL_PLAYABLE))
3505 LOG_ERROR("sql.sql", "Item (Entry: {}) does not have any playable classes ({}) in `AllowableClass` and can't be equipped or used.", entry, itemTemplate.AllowableClass);
3506
3507 if (!(itemTemplate.AllowableRace & sRaceMgr->GetPlayableRaceMask()))
3508 LOG_ERROR("sql.sql", "Item (Entry: {}) does not have any playable races ({}) in `AllowableRace` and can't be equipped or used.", entry, itemTemplate.AllowableRace);
3509 }
3510 }
3511
3512 if (itemTemplate.RequiredSpell && !sSpellMgr->GetSpellInfo(itemTemplate.RequiredSpell))
3513 {
3514 LOG_ERROR("sql.sql", "Item (Entry: {}) has a wrong (non-existing) spell in RequiredSpell ({})", entry, itemTemplate.RequiredSpell);
3515 itemTemplate.RequiredSpell = 0;
3516 }
3517
3518 if (itemTemplate.RequiredReputationRank >= MAX_REPUTATION_RANK)
3519 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong reputation rank in RequiredReputationRank ({}), item can't be used.", entry, itemTemplate.RequiredReputationRank);
3520
3521 if (itemTemplate.RequiredReputationFaction)
3522 {
3523 if (!sFactionStore.LookupEntry(itemTemplate.RequiredReputationFaction))
3524 {
3525 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong (not existing) faction in RequiredReputationFaction ({})", entry, itemTemplate.RequiredReputationFaction);
3526 itemTemplate.RequiredReputationFaction = 0;
3527 }
3528
3529 if (itemTemplate.RequiredReputationRank == MIN_REPUTATION_RANK)
3530 LOG_ERROR("sql.sql", "Item (Entry: {}) has min. reputation rank in RequiredReputationRank (0) but RequiredReputationFaction > 0, faction setting is useless.", entry);
3531 }
3532
3533 if (itemTemplate.MaxCount < -1)
3534 {
3535 LOG_ERROR("sql.sql", "Item (Entry: {}) has too large negative in maxcount ({}), replace by value (-1) no storing limits.", entry, itemTemplate.MaxCount);
3536 itemTemplate.MaxCount = -1;
3537 }
3538
3539 if (itemTemplate.Stackable == 0)
3540 {
3541 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong value in stackable ({}), replace by default 1.", entry, itemTemplate.Stackable);
3542 itemTemplate.Stackable = 1;
3543 }
3544 else if (itemTemplate.Stackable < -1)
3545 {
3546 LOG_ERROR("sql.sql", "Item (Entry: {}) has too large negative in stackable ({}), replace by value (-1) no stacking limits.", entry, itemTemplate.Stackable);
3547 itemTemplate.Stackable = -1;
3548 }
3549
3550 if (itemTemplate.ContainerSlots > MAX_BAG_SIZE)
3551 {
3552 LOG_ERROR("sql.sql", "Item (Entry: {}) has too large value in ContainerSlots ({}), replace by hardcoded limit ({}).", entry, itemTemplate.ContainerSlots, MAX_BAG_SIZE);
3553 itemTemplate.ContainerSlots = MAX_BAG_SIZE;
3554 }
3555
3556 for (uint8 j = 0; j < itemTemplate.StatsCount; ++j)
3557 {
3558 // for ItemStatValue != 0
3559 if (itemTemplate.ItemStat[j].ItemStatValue && itemTemplate.ItemStat[j].ItemStatType >= MAX_ITEM_MOD)
3560 {
3561 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong (non-existing?) stat_type{} ({})", entry, j + 1, itemTemplate.ItemStat[j].ItemStatType);
3562 itemTemplate.ItemStat[j].ItemStatType = 0;
3563 }
3564
3565 switch (itemTemplate.ItemStat[j].ItemStatType)
3566 {
3569 // Skip warning for specific items: 13113 (Feathermoon Headdress - Blizzard oversight), 34967 (test item)
3570 if (entry != 13113 && entry != 34967)
3571 LOG_WARN("sql.sql", "Item (Entry: {}) has deprecated stat_type{} ({})", entry, j + 1, itemTemplate.ItemStat[j].ItemStatType);
3572
3573 break;
3574 default:
3575 break;
3576 }
3577 }
3578
3579 for (uint8 j = 0; j < MAX_ITEM_PROTO_DAMAGES; ++j)
3580 {
3581 if (itemTemplate.Damage[j].DamageType >= MAX_SPELL_SCHOOL)
3582 {
3583 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong dmg_type{} ({})", entry, j + 1, itemTemplate.Damage[j].DamageType);
3584 itemTemplate.Damage[j].DamageType = 0;
3585 }
3586 }
3587
3588 // special format
3589 if ((itemTemplate.Spells[0].SpellId == 483) || (itemTemplate.Spells[0].SpellId == 55884))
3590 {
3591 // spell_1
3592 if (itemTemplate.Spells[0].SpellTrigger != ITEM_SPELLTRIGGER_ON_USE)
3593 {
3594 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong item spell trigger value in spelltrigger_{} ({}) for special learning format", entry, 0 + 1, itemTemplate.Spells[0].SpellTrigger);
3595 itemTemplate.Spells[0].SpellId = 0;
3596 itemTemplate.Spells[0].SpellTrigger = ITEM_SPELLTRIGGER_ON_USE;
3597 itemTemplate.Spells[1].SpellId = 0;
3598 itemTemplate.Spells[1].SpellTrigger = ITEM_SPELLTRIGGER_ON_USE;
3599 }
3600
3601 // spell_2 have learning spell
3602 if (itemTemplate.Spells[1].SpellTrigger != ITEM_SPELLTRIGGER_LEARN_SPELL_ID)
3603 {
3604 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong item spell trigger value in spelltrigger_{} ({}) for special learning format.", entry, 1 + 1, itemTemplate.Spells[1].SpellTrigger);
3605 itemTemplate.Spells[0].SpellId = 0;
3606 itemTemplate.Spells[1].SpellId = 0;
3607 itemTemplate.Spells[1].SpellTrigger = ITEM_SPELLTRIGGER_ON_USE;
3608 }
3609 else if (!itemTemplate.Spells[1].SpellId)
3610 {
3611 LOG_ERROR("sql.sql", "Item (Entry: {}) does not have an expected spell in spellid_{} in special learning format.", entry, 1 + 1);
3612 itemTemplate.Spells[0].SpellId = 0;
3613 itemTemplate.Spells[1].SpellTrigger = ITEM_SPELLTRIGGER_ON_USE;
3614 }
3615 else if (itemTemplate.Spells[1].SpellId != -1)
3616 {
3617 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(itemTemplate.Spells[1].SpellId);
3618 if (!spellInfo && !sDisableMgr->IsDisabledFor(DISABLE_TYPE_SPELL, itemTemplate.Spells[1].SpellId, nullptr))
3619 {
3620 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong (not existing) spell in spellid_{} ({})", entry, 1 + 1, itemTemplate.Spells[1].SpellId);
3621 itemTemplate.Spells[0].SpellId = 0;
3622 itemTemplate.Spells[1].SpellId = 0;
3623 itemTemplate.Spells[1].SpellTrigger = ITEM_SPELLTRIGGER_ON_USE;
3624 }
3625 // allowed only in special format
3626 else if ((itemTemplate.Spells[1].SpellId == 483) || (itemTemplate.Spells[1].SpellId == 55884))
3627 {
3628 LOG_ERROR("sql.sql", "Item (Entry: {}) has broken spell in spellid_{} ({})", entry, 1 + 1, itemTemplate.Spells[1].SpellId);
3629 itemTemplate.Spells[0].SpellId = 0;
3630 itemTemplate.Spells[1].SpellId = 0;
3631 itemTemplate.Spells[1].SpellTrigger = ITEM_SPELLTRIGGER_ON_USE;
3632 }
3633 }
3634
3635 // spell_3*, spell_4*, spell_5* is empty
3636 for (uint8 j = 2; j < MAX_ITEM_PROTO_SPELLS; ++j)
3637 {
3638 if (itemTemplate.Spells[j].SpellTrigger != ITEM_SPELLTRIGGER_ON_USE)
3639 {
3640 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong item spell trigger value in spelltrigger_{} ({})", entry, j + 1, itemTemplate.Spells[j].SpellTrigger);
3641 itemTemplate.Spells[j].SpellId = 0;
3642 itemTemplate.Spells[j].SpellTrigger = ITEM_SPELLTRIGGER_ON_USE;
3643 }
3644 else if (itemTemplate.Spells[j].SpellId != 0)
3645 {
3646 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong spell in spellid_{} ({}) for learning special format", entry, j + 1, itemTemplate.Spells[j].SpellId);
3647 itemTemplate.Spells[j].SpellId = 0;
3648 }
3649 }
3650 }
3651 // normal spell list
3652 else
3653 {
3654 for (uint8 j = 0; j < MAX_ITEM_PROTO_SPELLS; ++j)
3655 {
3656 if (itemTemplate.Spells[j].SpellTrigger >= MAX_ITEM_SPELLTRIGGER || itemTemplate.Spells[j].SpellTrigger == ITEM_SPELLTRIGGER_LEARN_SPELL_ID)
3657 {
3658 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong item spell trigger value in spelltrigger_{} ({})", entry, j + 1, itemTemplate.Spells[j].SpellTrigger);
3659 itemTemplate.Spells[j].SpellId = 0;
3660 itemTemplate.Spells[j].SpellTrigger = ITEM_SPELLTRIGGER_ON_USE;
3661 }
3662
3663 if (itemTemplate.Spells[j].SpellId && itemTemplate.Spells[j].SpellId != -1)
3664 {
3665 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(itemTemplate.Spells[j].SpellId);
3666 if (!spellInfo && !sDisableMgr->IsDisabledFor(DISABLE_TYPE_SPELL, itemTemplate.Spells[j].SpellId, nullptr))
3667 {
3668 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong (not existing) spell in spellid_{} ({})", entry, j + 1, itemTemplate.Spells[j].SpellId);
3669 itemTemplate.Spells[j].SpellId = 0;
3670 }
3671 // allowed only in special format
3672 else if ((itemTemplate.Spells[j].SpellId == 483) || (itemTemplate.Spells[j].SpellId == 55884))
3673 {
3674 LOG_ERROR("sql.sql", "Item (Entry: {}) has broken spell in spellid_{} ({})", entry, j + 1, itemTemplate.Spells[j].SpellId);
3675 itemTemplate.Spells[j].SpellId = 0;
3676 }
3677 }
3678 }
3679 }
3680
3681 if (itemTemplate.Bonding >= MAX_BIND_TYPE)
3682 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong Bonding value ({})", entry, itemTemplate.Bonding);
3683
3684 if (itemTemplate.PageText && !GetPageText(itemTemplate.PageText))
3685 LOG_ERROR("sql.sql", "Item (Entry: {}) has non existing first page (Id:{})", entry, itemTemplate.PageText);
3686
3687 if (itemTemplate.LockID && !sLockStore.LookupEntry(itemTemplate.LockID))
3688 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong LockID ({})", entry, itemTemplate.LockID);
3689
3690 if (itemTemplate.RandomProperty)
3691 {
3692 // To be implemented later
3693 if (itemTemplate.RandomProperty == -1)
3694 itemTemplate.RandomProperty = 0;
3695
3696 else if (!sItemRandomPropertiesStore.LookupEntry(GetItemEnchantMod(itemTemplate.RandomProperty)))
3697 {
3698 LOG_ERROR("sql.sql", "Item (Entry: {}) has unknown (wrong or not listed in `item_enchantment_template`) RandomProperty ({})", entry, itemTemplate.RandomProperty);
3699 itemTemplate.RandomProperty = 0;
3700 }
3701 }
3702
3703 if (itemTemplate.RandomSuffix && !sItemRandomSuffixStore.LookupEntry(GetItemEnchantMod(itemTemplate.RandomSuffix)))
3704 {
3705 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong RandomSuffix ({})", entry, itemTemplate.RandomSuffix);
3706 itemTemplate.RandomSuffix = 0;
3707 }
3708
3709 if (itemTemplate.ItemSet && !sItemSetStore.LookupEntry(itemTemplate.ItemSet))
3710 {
3711 LOG_ERROR("sql.sql", "Item (Entry: {}) have wrong ItemSet ({})", entry, itemTemplate.ItemSet);
3712 itemTemplate.ItemSet = 0;
3713 }
3714
3715 if (itemTemplate.Area && !sAreaTableStore.LookupEntry(itemTemplate.Area))
3716 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong Area ({})", entry, itemTemplate.Area);
3717
3718 if (itemTemplate.Map && !sMapStore.LookupEntry(itemTemplate.Map))
3719 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong Map ({})", entry, itemTemplate.Map);
3720
3721 if (itemTemplate.BagFamily)
3722 {
3723 // check bits
3724 for (uint32 j = 0; j < sizeof(itemTemplate.BagFamily) * 8; ++j)
3725 {
3726 uint32 mask = 1 << j;
3727 if ((itemTemplate.BagFamily & mask) == 0)
3728 continue;
3729
3730 ItemBagFamilyEntry const* bf = sItemBagFamilyStore.LookupEntry(j + 1);
3731 if (!bf)
3732 {
3733 LOG_ERROR("sql.sql", "Item (Entry: {}) has bag family bit set not listed in ItemBagFamily.dbc, remove bit", entry);
3734 itemTemplate.BagFamily &= ~mask;
3735 continue;
3736 }
3737
3739 {
3740 CurrencyTypesEntry const* ctEntry = sCurrencyTypesStore.LookupEntry(itemTemplate.ItemId);
3741 if (!ctEntry)
3742 {
3743 LOG_ERROR("sql.sql", "Item (Entry: {}) has currency bag family bit set in BagFamily but not listed in CurrencyTypes.dbc, remove bit", entry);
3744 itemTemplate.BagFamily &= ~mask;
3745 }
3746 }
3747 }
3748 }
3749
3750 if (itemTemplate.TotemCategory && !sTotemCategoryStore.LookupEntry(itemTemplate.TotemCategory))
3751 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong TotemCategory ({})", entry, itemTemplate.TotemCategory);
3752
3753 for (uint8 j = 0; j < MAX_ITEM_PROTO_SOCKETS; ++j)
3754 {
3755 if (itemTemplate.Socket[j].Color && (itemTemplate.Socket[j].Color & SOCKET_COLOR_ALL) != itemTemplate.Socket[j].Color)
3756 {
3757 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong socketColor_{} ({})", entry, j + 1, itemTemplate.Socket[j].Color);
3758 itemTemplate.Socket[j].Color = 0;
3759 }
3760 }
3761
3762 if (itemTemplate.GemProperties && !sGemPropertiesStore.LookupEntry(itemTemplate.GemProperties))
3763 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong GemProperties ({})", entry, itemTemplate.GemProperties);
3764
3765 if (itemTemplate.FoodType >= MAX_PET_DIET)
3766 {
3767 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong FoodType value ({})", entry, itemTemplate.FoodType);
3768 itemTemplate.FoodType = 0;
3769 }
3770
3771 if (itemTemplate.ItemLimitCategory && !sItemLimitCategoryStore.LookupEntry(itemTemplate.ItemLimitCategory))
3772 {
3773 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong LimitCategory value ({})", entry, itemTemplate.ItemLimitCategory);
3774 itemTemplate.ItemLimitCategory = 0;
3775 }
3776
3777 if (itemTemplate.HolidayId && !sHolidaysStore.LookupEntry(itemTemplate.HolidayId))
3778 {
3779 LOG_ERROR("sql.sql", "Item (Entry: {}) has wrong HolidayId value ({})", entry, itemTemplate.HolidayId);
3780 itemTemplate.HolidayId = 0;
3781 }
3782
3783 if (itemTemplate.HasFlagCu(ITEM_FLAGS_CU_DURATION_REAL_TIME) && !itemTemplate.Duration)
3784 {
3785 LOG_ERROR("sql.sql", "Item (Entry {}) has flag ITEM_FLAGS_CU_DURATION_REAL_TIME but it does not have duration limit", entry);
3786 itemTemplate.FlagsCu = static_cast<ItemFlagsCustom>(static_cast<uint32>(itemTemplate.FlagsCu) & ~ITEM_FLAGS_CU_DURATION_REAL_TIME);
3787 }
3788
3789 // Set after checks to ensure valid item quality
3790 itemTemplate.BuyPrice *= sWorld->getRate(qualityToBuyValueConfig[itemTemplate.Quality]);
3791 itemTemplate.SellPrice *= sWorld->getRate(qualityToSellValueConfig[itemTemplate.Quality]);
3792
3793 // Fill categories map
3794 for (uint8 i = 0; i < MAX_ITEM_PROTO_SPELLS; ++i)
3795 if (itemTemplate.Spells[i].SpellId && itemTemplate.Spells[i].SpellCategory && itemTemplate.Spells[i].SpellCategoryCooldown)
3796 {
3797 SpellCategoryStore::iterator ct = sSpellsByCategoryStore.find(itemTemplate.Spells[i].SpellCategory);
3798 if (ct != sSpellsByCategoryStore.end())
3799 {
3800 ct->second.emplace(true, itemTemplate.Spells[i].SpellId);
3801 }
3802 else
3803 sSpellsByCategoryStore[itemTemplate.Spells[i].SpellCategory].emplace(true, itemTemplate.Spells[i].SpellId);
3804 }
3805
3806 ++count;
3807 } while (result->NextRow());
3808
3809 // pussywizard:
3810 {
3811 uint32 max = 0;
3812 for (ItemTemplateContainer::const_iterator itr = _itemTemplateStore.begin(); itr != _itemTemplateStore.end(); ++itr)
3813 if (itr->first > max)
3814 max = itr->first;
3815 if (max)
3816 {
3817 _itemTemplateStoreFast.clear();
3818 _itemTemplateStoreFast.resize(max + 1, nullptr);
3819 for (ItemTemplateContainer::iterator itr = _itemTemplateStore.begin(); itr != _itemTemplateStore.end(); ++itr)
3820 _itemTemplateStoreFast[itr->first] = &(itr->second);
3821 }
3822 }
3823
3824 // Check if item templates for DBC referenced character start outfit are present
3825 std::set<uint32> notFoundOutfit;
3826 for (uint32 i = 1; i < sCharStartOutfitStore.GetNumRows(); ++i)
3827 {
3828 CharStartOutfitEntry const* entry = sCharStartOutfitStore.LookupEntry(i);
3829 if (!entry)
3830 continue;
3831
3832 for (int j = 0; j < MAX_OUTFIT_ITEMS; ++j)
3833 {
3834 if (entry->ItemId[j] <= 0)
3835 continue;
3836
3837 uint32 item_id = entry->ItemId[j];
3838
3839 if (!GetItemTemplate(item_id))
3840 notFoundOutfit.insert(item_id);
3841 }
3842 }
3843
3844 for (std::set<uint32>::const_iterator itr = notFoundOutfit.begin(); itr != notFoundOutfit.end(); ++itr)
3845 LOG_ERROR("sql.sql", "Item (Entry: {}) does not exist in `item_template` but is referenced in `CharStartOutfit.dbc`", *itr);
3846
3847 LOG_INFO("server.loading", ">> Loaded {} Item Templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
3848 LOG_INFO("server.loading", " ");
3849}
#define MAX_BAG_SIZE
Definition Bag.h:22
DBCStorage< ItemLimitCategoryEntry > sItemLimitCategoryStore(ItemLimitCategoryEntryfmt)
SpellCategoryStore sSpellsByCategoryStore
Definition DBCStores.cpp:152
DBCStorage< CharStartOutfitEntry > sCharStartOutfitStore(CharStartOutfitEntryfmt)
DBCStorage< LockEntry > sLockStore(LockEntryfmt)
DBCStorage< ItemBagFamilyEntry > sItemBagFamilyStore(ItemBagFamilyfmt)
DBCStorage< HolidaysEntry > sHolidaysStore(Holidaysfmt)
DBCStorage< ItemRandomSuffixEntry > sItemRandomSuffixStore(ItemRandomSuffixfmt)
DBCStorage< TotemCategoryEntry > sTotemCategoryStore(TotemCategoryEntryfmt)
DBCStorage< GemPropertiesEntry > sGemPropertiesStore(GemPropertiesEntryfmt)
DBCStorage< ItemRandomPropertiesEntry > sItemRandomPropertiesStore(ItemRandomPropertiesfmt)
DBCStorage< CurrencyTypesEntry > sCurrencyTypesStore(CurrencyTypesfmt)
#define MAX_OUTFIT_ITEMS
Definition DBCStructure.h:617
#define sDisableMgr
Definition DisableMgr.h:88
@ DISABLE_TYPE_SPELL
Definition DisableMgr.h:28
uint32 GetItemEnchantMod(int32 entry)
Definition ItemEnchantmentMgr.cpp:84
ItemFlags2
Definition ItemTemplate.h:182
@ ITEM_FLAG2_FACTION_HORDE
Definition ItemTemplate.h:183
@ ITEM_FLAG2_FACTION_ALLIANCE
Definition ItemTemplate.h:184
@ ITEM_SPELLTRIGGER_LEARN_SPELL_ID
Definition ItemTemplate.h:88
@ ITEM_SPELLTRIGGER_ON_USE
Definition ItemTemplate.h:77
@ BAG_FAMILY_MASK_CURRENCY_TOKENS
Definition ItemTemplate.h:240
ItemFlags
Definition ItemTemplate.h:146
@ ITEM_MOD_SPELL_HEALING_DONE
Definition ItemTemplate.h:63
@ ITEM_MOD_SPELL_DAMAGE_DONE
Definition ItemTemplate.h:64
#define MAX_ITEM_PROTO_SOCKETS
Definition ItemTemplate.h:614
#define MAX_ITEM_PROTO_DAMAGES
Definition ItemTemplate.h:613
#define MAX_ITEM_PROTO_SPELLS
Definition ItemTemplate.h:615
ItemFlagsCustom
Definition ItemTemplate.h:218
@ ITEM_FLAGS_CU_DURATION_REAL_TIME
Definition ItemTemplate.h:219
#define SOCKET_COLOR_ALL
Definition ItemTemplate.h:252
#define MAX_BIND_TYPE
Definition ItemTemplate.h:103
#define MAX_ITEM_SPELLTRIGGER
Definition ItemTemplate.h:91
#define MAX_ITEM_PROTO_STATS
Definition ItemTemplate.h:616
#define MAX_ITEM_MOD
Definition ItemTemplate.h:73
ServerConfigs const qualityToSellValueConfig[MAX_ITEM_QUALITY]
Definition ObjectMgr.cpp:3222
ServerConfigs const qualityToBuyValueConfig[MAX_ITEM_QUALITY]
Definition ObjectMgr.cpp:3210
#define MAX_REPUTATION_RANK
Definition SharedDefines.h:233
#define MIN_REPUTATION_RANK
Definition SharedDefines.h:232
#define MAX_PET_DIET
Definition SharedDefines.h:3466
@ ITEM_QUALITY_NORMAL
Definition SharedDefines.h:318
#define MAX_ITEM_QUALITY
Definition SharedDefines.h:327
#define MAX_SKILL_TYPE
Definition SharedDefines.h:3253
@ ALLIANCE
Definition SharedDefines.h:756
@ HORDE
Definition SharedDefines.h:755
#define CLASSMASK_ALL_PLAYABLE
Definition SharedDefines.h:142
@ CONFIG_DBC_ENFORCE_ITEM_ATTRIBUTES
Definition WorldConfig.h:100
Definition DBCStructure.h:620
int32 ItemId[MAX_OUTFIT_ITEMS]
Definition DBCStructure.h:626
Definition DBCStructure.h:835
Definition DBCStructure.h:907
Definition DBCStructure.h:1155
int32 SoundOverrideSubclassID
Definition DBCStructure.h:1147
uint32 SheatheType
Definition DBCStructure.h:1151
uint32 DisplayInfoID
Definition DBCStructure.h:1149
uint32 ClassID
Definition DBCStructure.h:1145
int32 Material
Definition DBCStructure.h:1148
uint32 SubclassID
Definition DBCStructure.h:1146
uint32 ItemId
Definition ItemTemplate.h:620

References _itemTemplateStore, _itemTemplateStoreFast, ALLIANCE, BAG_FAMILY_MASK_CURRENCY_TOKENS, ItemEntry::ClassID, CLASSMASK_ALL_PLAYABLE, CONFIG_DBC_ENFORCE_ITEM_ATTRIBUTES, DISABLE_TYPE_SPELL, ItemEntry::DisplayInfoID, Field::Get(), GetItemEnchantMod(), GetItemTemplate(), getMSTime(), GetMSTimeDiffToNow(), GetPageText(), GetScriptId(), HORDE, ItemEntry::InventoryType, INVTYPE_NON_EQUIP, ITEM_FLAG2_FACTION_ALLIANCE, ITEM_FLAG2_FACTION_HORDE, ITEM_FLAGS_CU_DURATION_REAL_TIME, ITEM_MOD_SPELL_DAMAGE_DONE, ITEM_MOD_SPELL_HEALING_DONE, ITEM_QUALITY_NORMAL, ITEM_SPELLTRIGGER_LEARN_SPELL_ID, ITEM_SPELLTRIGGER_ON_USE, ItemTemplate::ItemId, CharStartOutfitEntry::ItemId, LOG_DEBUG, LOG_ERROR, LOG_INFO, LOG_WARN, ItemEntry::Material, MAX_BAG_SIZE, MAX_BIND_TYPE, MAX_ITEM_MOD, MAX_ITEM_PROTO_DAMAGES, MAX_ITEM_PROTO_SOCKETS, MAX_ITEM_PROTO_SPELLS, MAX_ITEM_PROTO_STATS, MAX_ITEM_QUALITY, MAX_ITEM_SPELLTRIGGER, MAX_OUTFIT_ITEMS, MAX_PET_DIET, MAX_REPUTATION_RANK, MAX_SKILL_TYPE, MAX_SPELL_SCHOOL, MIN_REPUTATION_RANK, qualityToBuyValueConfig, qualityToSellValueConfig, sAreaTableStore, sCharStartOutfitStore, sCurrencyTypesStore, sDisableMgr, sFactionStore, sGemPropertiesStore, ItemEntry::SheatheType, sHolidaysStore, sItemBagFamilyStore, sItemLimitCategoryStore, sItemRandomPropertiesStore, sItemRandomSuffixStore, sItemSetStore, sItemStore, sLockStore, sMapStore, SOCKET_COLOR_ALL, ItemEntry::SoundOverrideSubclassID, sRaceMgr, sSpellMgr, sSpellsByCategoryStore, sTotemCategoryStore, ItemEntry::SubclassID, sWorld, and WorldDatabase.

◆ LoadLinkedRespawn()

void ObjectMgr::LoadLinkedRespawn ( )
1918{
1919 uint32 oldMSTime = getMSTime();
1920
1921 _linkedRespawnStore.clear();
1922 // 0 1 2
1923 QueryResult result = WorldDatabase.Query("SELECT guid, linkedGuid, linkType FROM linked_respawn ORDER BY guid ASC");
1924
1925 if (!result)
1926 {
1927 LOG_WARN("server.loading", ">> Loaded 0 linked respawns. DB table `linked_respawn` is empty.");
1928 LOG_INFO("server.loading", " ");
1929 return;
1930 }
1931
1932 do
1933 {
1934 Field* fields = result->Fetch();
1935
1936 ObjectGuid::LowType guidLow = fields[0].Get<uint32>();
1937 ObjectGuid::LowType linkedGuidLow = fields[1].Get<uint32>();
1938 uint8 linkType = fields[2].Get<uint8>();
1939
1940 ObjectGuid guid, linkedGuid;
1941 bool error = false;
1942 switch (linkType)
1943 {
1945 {
1946 const CreatureData* slave = GetCreatureData(guidLow);
1947 if (!slave)
1948 {
1949 LOG_ERROR("sql.sql", "LinkedRespawn: Creature (guid) {} not found in creature table", guidLow);
1950 error = true;
1951 break;
1952 }
1953
1954 const CreatureData* master = GetCreatureData(linkedGuidLow);
1955 if (!master)
1956 {
1957 LOG_ERROR("sql.sql", "LinkedRespawn: Creature (linkedGuid) {} not found in creature table", linkedGuidLow);
1958 error = true;
1959 break;
1960 }
1961
1962 MapEntry const* const map = sMapStore.LookupEntry(master->mapid);
1963 if (!map || !map->Instanceable() || (master->mapid != slave->mapid))
1964 {
1965 LOG_ERROR("sql.sql", "LinkedRespawn: Creature '{}' linking to Creature '{}' on an unpermitted map.", guidLow, linkedGuidLow);
1966 error = true;
1967 break;
1968 }
1969
1970 if (!(master->spawnMask & slave->spawnMask)) // they must have a possibility to meet (normal/heroic difficulty)
1971 {
1972 LOG_ERROR("sql.sql", "LinkedRespawn: Creature '{}' linking to Creature '{}' with not corresponding spawnMask", guidLow, linkedGuidLow);
1973 error = true;
1974 break;
1975 }
1976
1977 guid = ObjectGuid::Create<HighGuid::Unit>(slave->id1, guidLow);
1978 linkedGuid = ObjectGuid::Create<HighGuid::Unit>(master->id1, linkedGuidLow);
1979 break;
1980 }
1981 case CREATURE_TO_GO:
1982 {
1983 const CreatureData* slave = GetCreatureData(guidLow);
1984 if (!slave)
1985 {
1986 LOG_ERROR("sql.sql", "LinkedRespawn: Creature (guid) {} not found in creature table", guidLow);
1987 error = true;
1988 break;
1989 }
1990
1991 const GameObjectData* master = GetGameObjectData(linkedGuidLow);
1992 if (!master)
1993 {
1994 LOG_ERROR("sql.sql", "LinkedRespawn: Gameobject (linkedGuid) {} not found in gameobject table", linkedGuidLow);
1995 error = true;
1996 break;
1997 }
1998
1999 MapEntry const* const map = sMapStore.LookupEntry(master->mapid);
2000 if (!map || !map->Instanceable() || (master->mapid != slave->mapid))
2001 {
2002 LOG_ERROR("sql.sql", "LinkedRespawn: Creature '{}' linking to Gameobject '{}' on an unpermitted map.", guidLow, linkedGuidLow);
2003 error = true;
2004 break;
2005 }
2006
2007 if (!(master->spawnMask & slave->spawnMask)) // they must have a possibility to meet (normal/heroic difficulty)
2008 {
2009 LOG_ERROR("sql.sql", "LinkedRespawn: Creature '{}' linking to Gameobject '{}' with not corresponding spawnMask", guidLow, linkedGuidLow);
2010 error = true;
2011 break;
2012 }
2013
2014 guid = ObjectGuid::Create<HighGuid::Unit>(slave->id1, guidLow);
2015 linkedGuid = ObjectGuid::Create<HighGuid::GameObject>(master->id, linkedGuidLow);
2016 break;
2017 }
2018 case GO_TO_GO:
2019 {
2020 const GameObjectData* slave = GetGameObjectData(guidLow);
2021 if (!slave)
2022 {
2023 LOG_ERROR("sql.sql", "LinkedRespawn: Gameobject (guid) {} not found in gameobject table", guidLow);
2024 error = true;
2025 break;
2026 }
2027
2028 const GameObjectData* master = GetGameObjectData(linkedGuidLow);
2029 if (!master)
2030 {
2031 LOG_ERROR("sql.sql", "LinkedRespawn: Gameobject (linkedGuid) {} not found in gameobject table", linkedGuidLow);
2032 error = true;
2033 break;
2034 }
2035
2036 MapEntry const* const map = sMapStore.LookupEntry(master->mapid);
2037 if (!map || !map->Instanceable() || (master->mapid != slave->mapid))
2038 {
2039 LOG_ERROR("sql.sql", "LinkedRespawn: Gameobject '{}' linking to Gameobject '{}' on an unpermitted map.", guidLow, linkedGuidLow);
2040 error = true;
2041 break;
2042 }
2043
2044 if (!(master->spawnMask & slave->spawnMask)) // they must have a possibility to meet (normal/heroic difficulty)
2045 {
2046 LOG_ERROR("sql.sql", "LinkedRespawn: Gameobject '{}' linking to Gameobject '{}' with not corresponding spawnMask", guidLow, linkedGuidLow);
2047 error = true;
2048 break;
2049 }
2050
2051 guid = ObjectGuid::Create<HighGuid::GameObject>(slave->id, guidLow);
2052 linkedGuid = ObjectGuid::Create<HighGuid::GameObject>(master->id, linkedGuidLow);
2053 break;
2054 }
2055 case GO_TO_CREATURE:
2056 {
2057 const GameObjectData* slave = GetGameObjectData(guidLow);
2058 if (!slave)
2059 {
2060 LOG_ERROR("sql.sql", "LinkedRespawn: Gameobject (guid) {} not found in gameobject table", guidLow);
2061 error = true;
2062 break;
2063 }
2064
2065 const CreatureData* master = GetCreatureData(linkedGuidLow);
2066 if (!master)
2067 {
2068 LOG_ERROR("sql.sql", "LinkedRespawn: Creature (linkedGuid) {} not found in creature table", linkedGuidLow);
2069 error = true;
2070 break;
2071 }
2072
2073 MapEntry const* const map = sMapStore.LookupEntry(master->mapid);
2074 if (!map || !map->Instanceable() || (master->mapid != slave->mapid))
2075 {
2076 LOG_ERROR("sql.sql", "LinkedRespawn: Gameobject '{}' linking to Creature '{}' on an unpermitted map.", guidLow, linkedGuidLow);
2077 error = true;
2078 break;
2079 }
2080
2081 if (!(master->spawnMask & slave->spawnMask)) // they must have a possibility to meet (normal/heroic difficulty)
2082 {
2083 LOG_ERROR("sql.sql", "LinkedRespawn: Gameobject '{}' linking to Creature '{}' with not corresponding spawnMask", guidLow, linkedGuidLow);
2084 error = true;
2085 break;
2086 }
2087
2088 guid = ObjectGuid::Create<HighGuid::GameObject>(slave->id, guidLow);
2089 linkedGuid = ObjectGuid::Create<HighGuid::Unit>(master->id1, linkedGuidLow);
2090 break;
2091 }
2092 }
2093
2094 if (!error)
2095 _linkedRespawnStore[guid] = linkedGuid;
2096 } while (result->NextRow());
2097
2098 LOG_INFO("server.loading", ">> Loaded {} Linked Respawns In {} ms", uint64(_linkedRespawnStore.size()), GetMSTimeDiffToNow(oldMSTime));
2099 LOG_INFO("server.loading", " ");
2100}
Definition ObjectGuid.h:118
bool Instanceable() const
Definition DBCStructure.h:1353

References _linkedRespawnStore, CREATURE_TO_CREATURE, CREATURE_TO_GO, Field::Get(), GetCreatureData(), GetGameObjectData(), getMSTime(), GetMSTimeDiffToNow(), GO_TO_CREATURE, GO_TO_GO, GameObjectData::id, CreatureData::id1, MapEntry::Instanceable(), LOG_ERROR, LOG_INFO, LOG_WARN, SpawnData::mapid, sMapStore, SpawnData::spawnMask, and WorldDatabase.

◆ LoadMailLevelRewards()

void ObjectMgr::LoadMailLevelRewards ( )
9688{
9689 uint32 oldMSTime = getMSTime();
9690
9691 _mailLevelRewardStore.clear(); // for reload case
9692
9693 // 0 1 2 3
9694 QueryResult result = WorldDatabase.Query("SELECT level, raceMask, mailTemplateId, senderEntry FROM mail_level_reward");
9695
9696 if (!result)
9697 {
9698 LOG_WARN("server.loading", ">> Loaded 0 level dependent mail rewards. DB table `mail_level_reward` is empty.");
9699 LOG_INFO("server.loading", " ");
9700 return;
9701 }
9702
9703 uint32 count = 0;
9704
9705 do
9706 {
9707 Field* fields = result->Fetch();
9708
9709 uint8 level = fields[0].Get<uint8>();
9710 uint32 raceMask = fields[1].Get<uint32>();
9711 uint32 mailTemplateId = fields[2].Get<uint32>();
9712 uint32 senderEntry = fields[3].Get<uint32>();
9713
9714 if (level > MAX_LEVEL)
9715 {
9716 LOG_ERROR("sql.sql", "Table `mail_level_reward` have data for level {} that more supported by client ({}), ignoring.", level, MAX_LEVEL);
9717 continue;
9718 }
9719
9720 if (!(raceMask & sRaceMgr->GetPlayableRaceMask()))
9721 {
9722 LOG_ERROR("sql.sql", "Table `mail_level_reward` have raceMask ({}) for level {} that not include any player races, ignoring.", raceMask, level);
9723 continue;
9724 }
9725
9726 if (!sMailTemplateStore.LookupEntry(mailTemplateId))
9727 {
9728 LOG_ERROR("sql.sql", "Table `mail_level_reward` have invalid mailTemplateId ({}) for level {} that invalid not include any player races, ignoring.", mailTemplateId, level);
9729 continue;
9730 }
9731
9732 if (!GetCreatureTemplate(senderEntry))
9733 {
9734 LOG_ERROR("sql.sql", "Table `mail_level_reward` have not existed sender creature entry ({}) for level {} that invalid not include any player races, ignoring.", senderEntry, level);
9735 continue;
9736 }
9737
9738 _mailLevelRewardStore[level].push_back(MailLevelReward(raceMask, mailTemplateId, senderEntry));
9739
9740 ++count;
9741 } while (result->NextRow());
9742
9743 LOG_INFO("server.loading", ">> Loaded {} Level Dependent Mail Rewards in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
9744 LOG_INFO("server.loading", " ");
9745}
#define MAX_LEVEL
Definition DBCEnums.h:39
DBCStorage< MailTemplateEntry > sMailTemplateStore(MailTemplateEntryfmt)
Definition ObjectMgr.h:546

References _mailLevelRewardStore, Field::Get(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, MAX_LEVEL, sMailTemplateStore, sRaceMgr, and WorldDatabase.

◆ LoadModuleStrings()

bool ObjectMgr::LoadModuleStrings ( )
9267{
9268 uint32 oldMSTime = getMSTime();
9269
9270 _moduleStringStore.clear(); // for reload case
9271 QueryResult result = WorldDatabase.Query("SELECT module, id, string FROM module_string");
9272 if (!result)
9273 {
9274 LOG_WARN("server.loading", ">> Loaded 0 module strings. DB table `module_string` is empty.");
9275 LOG_INFO("server.loading", " ");
9276 return false;
9277 }
9278
9279 do
9280 {
9281 Field* fields = result->Fetch();
9282
9283 std::string module = fields[0].Get<std::string>();
9284 uint32 id = fields[1].Get<uint32>();
9285
9286 std::pair<std::string, uint32> pairKey = std::make_pair(module, id);
9287 ModuleString& data = _moduleStringStore[pairKey];
9288
9289 AddLocaleString(fields[2].Get<std::string>(), LOCALE_enUS, data.Content);
9290 } while (result->NextRow());
9291
9292 LOG_INFO("server.loading", ">> Loaded {} Module Strings in {} ms", _moduleStringStore.size(), GetMSTimeDiffToNow(oldMSTime));
9293 LOG_INFO("server.loading", " ");
9294
9295 return true;
9296}

References _moduleStringStore, AddLocaleString(), ModuleString::Content, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadModuleStringsLocale()

bool ObjectMgr::LoadModuleStringsLocale ( )
9299{
9300 uint32 oldMSTime = getMSTime();
9301
9302 QueryResult result = WorldDatabase.Query("SELECT module, id, locale, string FROM module_string_locale");
9303 if (!result)
9304 {
9305 LOG_WARN("server.loading", ">> Loaded 0 module strings locale. DB table `module_string_locale` is empty.");
9306 LOG_INFO("server.loading", " ");
9307 return false;
9308 }
9309
9310 uint32 localeCount = 0;
9311 do
9312 {
9313 Field* fields = result->Fetch();
9314
9315 std::string module = fields[0].Get<std::string>();
9316 uint32 id = fields[1].Get<uint32>();
9317
9318 std::pair<std::string, uint32> pairKey = std::make_pair(module, id);
9319 ModuleString& data = _moduleStringStore[pairKey];
9320
9321 ModuleStringContainer::iterator ms = _moduleStringStore.find(pairKey);
9322 if (ms == _moduleStringStore.end())
9323 {
9324 LOG_ERROR("sql.sql", "ModuleString (Module: {} Id: {}) found in table `module_string_locale` but does not exist in `module_string`. Skipped!", module, id);
9325 continue;
9326 }
9327
9328 LocaleConstant locale = GetLocaleByName(fields[2].Get<std::string>());
9329 if (locale == LOCALE_enUS)
9330 continue;
9331
9332 AddLocaleString(fields[3].Get<std::string>(), locale, data.Content);
9333 localeCount++;
9334 } while (result->NextRow());
9335
9336 LOG_INFO("server.loading", ">> Loaded {} Module Strings Locales in {} ms", localeCount, GetMSTimeDiffToNow(oldMSTime));
9337 LOG_INFO("server.loading", " ");
9338
9339 return true;
9340}

References _moduleStringStore, AddLocaleString(), ModuleString::Content, Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadNPCSpellClickSpells()

void ObjectMgr::LoadNPCSpellClickSpells ( )
8607{
8608 uint32 oldMSTime = getMSTime();
8609
8610 _spellClickInfoStore.clear();
8611 // 0 1 2 3
8612 QueryResult result = WorldDatabase.Query("SELECT npc_entry, spell_id, cast_flags, user_type FROM npc_spellclick_spells");
8613
8614 if (!result)
8615 {
8616 LOG_WARN("server.loading", ">> Loaded 0 spellclick spells. DB table `npc_spellclick_spells` is empty.");
8617 LOG_INFO("server.loading", " ");
8618 return;
8619 }
8620
8621 uint32 count = 0;
8622
8623 do
8624 {
8625 Field* fields = result->Fetch();
8626
8627 uint32 npc_entry = fields[0].Get<uint32>();
8628 CreatureTemplate const* cInfo = GetCreatureTemplate(npc_entry);
8629 if (!cInfo)
8630 {
8631 LOG_ERROR("sql.sql", "Table npc_spellclick_spells references unknown creature_template {}. Skipping entry.", npc_entry);
8632 continue;
8633 }
8634
8635 uint32 spellid = fields[1].Get<uint32>();
8636 SpellInfo const* spellinfo = sSpellMgr->GetSpellInfo(spellid);
8637 if (!spellinfo)
8638 {
8639 LOG_ERROR("sql.sql", "Table npc_spellclick_spells references unknown spellid {}. Skipping entry.", spellid);
8640 continue;
8641 }
8642
8643 uint8 userType = fields[3].Get<uint16>();
8644 if (userType >= SPELL_CLICK_USER_MAX)
8645 LOG_ERROR("sql.sql", "Table npc_spellclick_spells references unknown user type {}. Skipping entry.", uint32(userType));
8646
8647 uint8 castFlags = fields[2].Get<uint8>();
8648 SpellClickInfo info;
8649 info.spellId = spellid;
8650 info.castFlags = castFlags;
8651 info.userType = SpellClickUserTypes(userType);
8652 _spellClickInfoStore.insert(SpellClickInfoContainer::value_type(npc_entry, info));
8653
8654 ++count;
8655 } while (result->NextRow());
8656
8657 // all spellclick data loaded, now we check if there are creatures with NPC_FLAG_SPELLCLICK but with no data
8658 // NOTE: It *CAN* be the other way around: no spellclick flag but with spellclick data, in case of creature-only vehicle accessories
8660 for (CreatureTemplateContainer::const_iterator itr = ctc->begin(); itr != ctc->end(); ++itr)
8661 {
8662 if ((itr->second.npcflag & UNIT_NPC_FLAG_SPELLCLICK) && _spellClickInfoStore.find(itr->second.Entry) == _spellClickInfoStore.end())
8663 {
8664 LOG_ERROR("sql.sql", "npc_spellclick_spells: Creature template {} has UNIT_NPC_FLAG_SPELLCLICK but no data in spellclick table! Removing flag", itr->second.Entry);
8665 const_cast<CreatureTemplate*>(&itr->second)->npcflag &= ~UNIT_NPC_FLAG_SPELLCLICK;
8666 }
8667 }
8668
8669 LOG_INFO("server.loading", ">> Loaded {} Spellclick Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8670 LOG_INFO("server.loading", " ");
8671}
SpellClickUserTypes
Definition SharedDefines.h:668
@ SPELL_CLICK_USER_MAX
Definition SharedDefines.h:673
@ UNIT_NPC_FLAG_SPELLCLICK
Definition UnitDefines.h:346
Definition ObjectMgr.h:399
uint32 spellId
Definition ObjectMgr.h:400

References _spellClickInfoStore, Field::Get(), GetCreatureTemplate(), GetCreatureTemplates(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, SPELL_CLICK_USER_MAX, SpellClickInfo::spellId, sSpellMgr, UNIT_NPC_FLAG_SPELLCLICK, and WorldDatabase.

◆ LoadNpcTextLocales()

void ObjectMgr::LoadNpcTextLocales ( )
6691{
6692 uint32 oldMSTime = getMSTime();
6693
6694 _npcTextLocaleStore.clear(); // need for reload case
6695
6696 QueryResult result = WorldDatabase.Query("SELECT ID, Locale, "
6697 // 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
6698 "Text0_0, Text0_1, Text1_0, Text1_1, Text2_0, Text2_1, Text3_0, Text3_1, Text4_0, Text4_1, Text5_0, Text5_1, Text6_0, Text6_1, Text7_0, Text7_1 "
6699 "FROM npc_text_locale");
6700
6701 if (!result)
6702 return;
6703
6704 do
6705 {
6706 Field* fields = result->Fetch();
6707
6708 uint32 ID = fields[0].Get<uint32>();
6709
6710 LocaleConstant locale = GetLocaleByName(fields[1].Get<std::string>());
6711 if (locale == LOCALE_enUS)
6712 continue;
6713
6715 for (uint8 i = 0; i < MAX_GOSSIP_TEXT_OPTIONS; ++i)
6716 {
6717 AddLocaleString(fields[2 + i * 2].Get<std::string>(), locale, data.Text_0[i]);
6718 AddLocaleString(fields[3 + i * 2].Get<std::string>(), locale, data.Text_1[i]);
6719 }
6720 } while (result->NextRow());
6721
6722 LOG_INFO("server.loading", ">> Loaded {} Npc Text Locale Strings in {} ms", (uint32)_npcTextLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
6723}
Definition NPCHandler.h:55
std::vector< std::vector< std::string > > Text_1
Definition NPCHandler.h:59
std::vector< std::vector< std::string > > Text_0
Definition NPCHandler.h:58

References _npcTextLocaleStore, AddLocaleString(), Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, MAX_GOSSIP_TEXT_OPTIONS, NpcTextLocale::Text_0, NpcTextLocale::Text_1, and WorldDatabase.

◆ LoadPageTextLocales()

void ObjectMgr::LoadPageTextLocales ( )
6438{
6439 uint32 oldMSTime = getMSTime();
6440
6441 _pageTextLocaleStore.clear(); // need for reload case
6442
6443 // 0 1 2
6444 QueryResult result = WorldDatabase.Query("SELECT ID, locale, Text FROM page_text_locale");
6445
6446 if (!result)
6447 {
6448 LOG_WARN("server.loading", ">> Loaded 0 page texts. DB table `page_text_locale` is empty!");
6449 LOG_INFO("server.loading", " ");
6450 return;
6451 }
6452
6453 do
6454 {
6455 Field* fields = result->Fetch();
6456
6457 uint32 ID = fields[0].Get<uint32>();
6458
6459 LocaleConstant locale = GetLocaleByName(fields[1].Get<std::string>());
6460 if (locale == LOCALE_enUS)
6461 continue;
6462
6464 AddLocaleString(fields[2].Get<std::string>(), locale, data.Text);
6465 } while (result->NextRow());
6466
6467 LOG_INFO("server.loading", ">> Loaded {} Page Text Locale Strings in {} ms", (uint32)_pageTextLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
6468}
Definition NPCHandler.h:50
std::vector< std::string > Text
Definition NPCHandler.h:51

References _pageTextLocaleStore, AddLocaleString(), Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, LOG_WARN, PageTextLocale::Text, and WorldDatabase.

◆ LoadPageTexts()

void ObjectMgr::LoadPageTexts ( )
6388{
6389 uint32 oldMSTime = getMSTime();
6390
6391 // 0 1 2
6392 QueryResult result = WorldDatabase.Query("SELECT ID, Text, NextPageID FROM page_text");
6393
6394 if (!result)
6395 {
6396 LOG_WARN("server.loading", ">> Loaded 0 page texts. DB table `page_text` is empty!");
6397 LOG_INFO("server.loading", " ");
6398 return;
6399 }
6400
6401 uint32 count = 0;
6402 do
6403 {
6404 Field* fields = result->Fetch();
6405
6406 PageText& pageText = _pageTextStore[fields[0].Get<uint32>()];
6407
6408 pageText.Text = fields[1].Get<std::string>();
6409 pageText.NextPage = fields[2].Get<uint32>();
6410
6411 ++count;
6412 } while (result->NextRow());
6413
6414 for (PageTextContainer::const_iterator itr = _pageTextStore.begin(); itr != _pageTextStore.end(); ++itr)
6415 {
6416 if (itr->second.NextPage)
6417 {
6418 PageTextContainer::const_iterator itr2 = _pageTextStore.find(itr->second.NextPage);
6419 if (itr2 == _pageTextStore.end())
6420 LOG_ERROR("sql.sql", "Page text (Id: {}) has not existing next page (Id: {})", itr->first, itr->second.NextPage);
6421 }
6422 }
6423
6424 LOG_INFO("server.loading", ">> Loaded {} Page Texts in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
6425 LOG_INFO("server.loading", " ");
6426}
Definition ObjectMgr.h:58
std::string Text
Definition ObjectMgr.h:59
uint32 NextPage
Definition ObjectMgr.h:60

References _pageTextStore, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, PageText::NextPage, PageText::Text, and WorldDatabase.

◆ LoadPetLevelInfo()

void ObjectMgr::LoadPetLevelInfo ( )
4125{
4126 uint32 oldMSTime = getMSTime();
4127
4128 // 0 1 2 3 4 5 6 7 8 9 10 11
4129 QueryResult result = WorldDatabase.Query("SELECT creature_entry, level, hp, mana, str, agi, sta, inte, spi, armor, min_dmg, max_dmg FROM pet_levelstats");
4130
4131 if (!result)
4132 {
4133 LOG_WARN("server.loading", ">> Loaded 0 level pet stats definitions. DB table `pet_levelstats` is empty.");
4134 LOG_INFO("server.loading", " ");
4135 return;
4136 }
4137
4138 uint32 count = 0;
4139
4140 do
4141 {
4142 Field* fields = result->Fetch();
4143
4144 uint32 creature_id = fields[0].Get<uint32>();
4145 if (!GetCreatureTemplate(creature_id))
4146 {
4147 LOG_ERROR("sql.sql", "Wrong creature id {} in `pet_levelstats` table, ignoring.", creature_id);
4148 continue;
4149 }
4150
4151 uint32 current_level = fields[1].Get<uint8>();
4152 if (current_level > sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL))
4153 {
4154 if (current_level > STRONG_MAX_LEVEL) // hardcoded level maximum
4155 LOG_ERROR("sql.sql", "Wrong (> {}) level {} in `pet_levelstats` table, ignoring.", STRONG_MAX_LEVEL, current_level);
4156 else
4157 {
4158 LOG_DEBUG("sql.sql", "Unused (> MaxPlayerLevel in worldserver.conf) level {} in `pet_levelstats` table, ignoring.", current_level);
4159 ++count; // make result loading percent "expected" correct in case disabled detail mode for example.
4160 }
4161 continue;
4162 }
4163 else if (current_level < 1)
4164 {
4165 LOG_ERROR("sql.sql", "Wrong (<1) level {} in `pet_levelstats` table, ignoring.", current_level);
4166 continue;
4167 }
4168
4169 PetLevelInfo*& pInfoMapEntry = _petInfoStore[creature_id];
4170
4171 if (!pInfoMapEntry)
4172 pInfoMapEntry = new PetLevelInfo[sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL)];
4173
4174 // data for level 1 stored in [0] array element, ...
4175 PetLevelInfo* pLevelInfo = &pInfoMapEntry[current_level - 1];
4176
4177 pLevelInfo->health = fields[2].Get<uint32>();
4178 pLevelInfo->mana = fields[3].Get<uint32>();
4179 pLevelInfo->armor = fields[9].Get<uint32>();
4180 pLevelInfo->min_dmg = fields[10].Get<uint32>();
4181 pLevelInfo->max_dmg = fields[11].Get<uint32>();
4182 for (uint8 i = 0; i < MAX_STATS; i++)
4183 {
4184 pLevelInfo->stats[i] = fields[i + 4].Get<uint32>();
4185 }
4186
4187 ++count;
4188 } while (result->NextRow());
4189
4190 // Fill gaps and check integrity
4191 for (PetLevelInfoContainer::iterator itr = _petInfoStore.begin(); itr != _petInfoStore.end(); ++itr)
4192 {
4193 PetLevelInfo* pInfo = itr->second;
4194
4195 // fatal error if no level 1 data
4196 if (!pInfo || pInfo[0].health == 0)
4197 {
4198 LOG_ERROR("sql.sql", "Creature {} does not have pet stats data for Level 1!", itr->first);
4199 exit(1);
4200 }
4201
4202 // fill level gaps
4203 for (uint8 level = 1; level < sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL); ++level)
4204 {
4205 if (pInfo[level].health == 0)
4206 {
4207 LOG_ERROR("sql.sql", "Creature {} has no data for Level {} pet stats data, using data of Level {}.", itr->first, level + 1, level);
4208 pInfo[level] = pInfo[level - 1];
4209 }
4210 }
4211 }
4212
4213 LOG_INFO("server.loading", ">> Loaded {} Level Pet Stats Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4214 LOG_INFO("server.loading", " ");
4215}
#define STRONG_MAX_LEVEL
Definition DBCEnums.h:43
#define MAX_STATS
Definition SharedDefines.h:253
Definition ObjectMgr.h:531
uint32 max_dmg
Definition ObjectMgr.h:542
uint32 mana
Definition ObjectMgr.h:539
uint32 min_dmg
Definition ObjectMgr.h:541
uint32 health
Definition ObjectMgr.h:538
std::array< uint32, MAX_STATS > stats
Definition ObjectMgr.h:537
uint32 armor
Definition ObjectMgr.h:540

References _petInfoStore, PetLevelInfo::armor, CONFIG_MAX_PLAYER_LEVEL, Field::Get(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), PetLevelInfo::health, LOG_DEBUG, LOG_ERROR, LOG_INFO, LOG_WARN, PetLevelInfo::mana, PetLevelInfo::max_dmg, MAX_STATS, PetLevelInfo::min_dmg, PetLevelInfo::stats, STRONG_MAX_LEVEL, sWorld, and WorldDatabase.

◆ LoadPetNames()

void ObjectMgr::LoadPetNames ( )
8113{
8114 uint32 oldMSTime = getMSTime();
8115 // 0 1 2
8116 QueryResult result = WorldDatabase.Query("SELECT word, entry, half FROM pet_name_generation");
8117
8118 if (!result)
8119 {
8120 LOG_WARN("server.loading", ">> Loaded 0 pet name parts. DB table `pet_name_generation` is empty!");
8121 LOG_INFO("server.loading", " ");
8122 return;
8123 }
8124
8125 uint32 count = 0;
8126
8127 do
8128 {
8129 Field* fields = result->Fetch();
8130 std::string word = fields[0].Get<std::string>();
8131 uint32 entry = fields[1].Get<uint32>();
8132 bool half = fields[2].Get<bool>();
8133 if (half)
8134 _petHalfName1[entry].push_back(word);
8135 else
8136 _petHalfName0[entry].push_back(word);
8137 ++count;
8138 } while (result->NextRow());
8139
8140 LOG_INFO("server.loading", ">> Loaded {} Pet Name Parts in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8141 LOG_INFO("server.loading", " ");
8142}

References _petHalfName0, _petHalfName1, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadPetNamesLocales()

void ObjectMgr::LoadPetNamesLocales ( )
454{
455 uint32 oldMSTime = getMSTime();
456
457 // 0 1 2 3
458 QueryResult result = WorldDatabase.Query("SELECT Locale, Word, Entry, Half FROM pet_name_generation_locale");
459
460 if (!result)
461 {
462 LOG_WARN("server.loading", ">> Loaded 0 pet name locales parts. DB table `pet_name_generation_locale` is empty!");
463 LOG_INFO("server.loading", " ");
464 return;
465 }
466
467 uint32 count = 0;
468
469 do
470 {
471 Field* fields = result->Fetch();
472 LocaleConstant locale = GetLocaleByName(fields[0].Get<std::string>());
473 std::string word = fields[1].Get<std::string>();
474
475 uint32 entry = fields[2].Get<uint32>();
476 bool half = fields[3].Get<bool>();
477 std::pair<uint32, LocaleConstant> pairkey = std::make_pair(entry, locale);
478 if (half)
479 {
480 _petHalfLocaleName1[pairkey].push_back(word);
481 }
482 else
483 {
484 _petHalfLocaleName0[pairkey].push_back(word);
485 }
486 ++count;
487 } while (result->NextRow());
488
489 LOG_INFO("server.loading", ">> Loaded {} Pet Name Locales Parts in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
490 LOG_INFO("server.loading", " ");
491}

References _petHalfLocaleName0, _petHalfLocaleName1, Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadPetNumber()

void ObjectMgr::LoadPetNumber ( )
8145{
8146 uint32 oldMSTime = getMSTime();
8147
8148 QueryResult result = CharacterDatabase.Query("SELECT MAX(id) FROM character_pet");
8149 if (result)
8150 {
8151 Field* fields = result->Fetch();
8152 _hiPetNumber = fields[0].Get<uint32>() + 1;
8153 }
8154
8155 LOG_INFO("server.loading", ">> Loaded The Max Pet Number: {} in {} ms", _hiPetNumber - 1, GetMSTimeDiffToNow(oldMSTime));
8156 LOG_INFO("server.loading", " ");
8157}

References _hiPetNumber, CharacterDatabase, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), and LOG_INFO.

◆ LoadPlayerInfo()

void ObjectMgr::LoadPlayerInfo ( )
4264{
4265 // Load playercreate
4266 {
4267 if (_playerInfo.empty() || _playerInfo.size() != sRaceMgr->GetMaxRaces())
4268 {
4269 _playerInfo.clear();
4270 _playerInfo.resize(sRaceMgr->GetMaxRaces());
4271 for (auto& classVec : _playerInfo)
4272 classVec.resize(MAX_CLASSES, nullptr);
4273 }
4274
4275 uint32 oldMSTime = getMSTime();
4276 // 0 1 2 3 4 5 6
4277 QueryResult result = WorldDatabase.Query("SELECT race, class, map, zone, position_x, position_y, position_z, orientation FROM playercreateinfo");
4278
4279 if (!result)
4280 {
4281 LOG_INFO("server.loading", " ");
4282 LOG_WARN("server.loading", ">> Loaded 0 player create definitions. DB table `playercreateinfo` is empty.");
4283 exit(1);
4284 }
4285 else
4286 {
4287 uint32 count = 0;
4288
4289 do
4290 {
4291 Field* fields = result->Fetch();
4292
4293 uint32 current_race = fields[0].Get<uint8>();
4294 uint32 current_class = fields[1].Get<uint8>();
4295 uint32 mapId = fields[2].Get<uint16>();
4296 uint32 areaId = fields[3].Get<uint32>(); // zone
4297 float positionX = fields[4].Get<float>();
4298 float positionY = fields[5].Get<float>();
4299 float positionZ = fields[6].Get<float>();
4300 float orientation = fields[7].Get<float>();
4301
4302 if (current_race >= sRaceMgr->GetMaxRaces())
4303 {
4304 LOG_ERROR("sql.sql", "Wrong race {} in `playercreateinfo` table, ignoring.", current_race);
4305 continue;
4306 }
4307
4308 ChrRacesEntry const* rEntry = sChrRacesStore.LookupEntry(current_race);
4309 if (!rEntry)
4310 {
4311 LOG_ERROR("sql.sql", "Wrong race {} in `playercreateinfo` table, ignoring.", current_race);
4312 continue;
4313 }
4314
4315 if (current_class >= MAX_CLASSES)
4316 {
4317 LOG_ERROR("sql.sql", "Wrong class {} in `playercreateinfo` table, ignoring.", current_class);
4318 continue;
4319 }
4320
4321 if (!sChrClassesStore.LookupEntry(current_class))
4322 {
4323 LOG_ERROR("sql.sql", "Wrong class {} in `playercreateinfo` table, ignoring.", current_class);
4324 continue;
4325 }
4326
4327 // accept DB data only for valid position (and non instanceable)
4328 if (!MapMgr::IsValidMapCoord(mapId, positionX, positionY, positionZ, orientation))
4329 {
4330 LOG_ERROR("sql.sql", "Wrong home position for class {} race {} pair in `playercreateinfo` table, ignoring.", current_class, current_race);
4331 continue;
4332 }
4333
4334 if (sMapStore.LookupEntry(mapId)->Instanceable())
4335 {
4336 LOG_ERROR("sql.sql", "Home position in instanceable map for class {} race {} pair in `playercreateinfo` table, ignoring.", current_class, current_race);
4337 continue;
4338 }
4339
4340 PlayerInfo* info = new PlayerInfo();
4341 info->mapId = mapId;
4342 info->areaId = areaId;
4343 info->positionX = positionX;
4344 info->positionY = positionY;
4345 info->positionZ = positionZ;
4346 info->orientation = orientation;
4347 info->displayId_m = rEntry->model_m;
4348 info->displayId_f = rEntry->model_f;
4349 _playerInfo[current_race][current_class] = info;
4350
4351 ++count;
4352 } while (result->NextRow());
4353
4354 LOG_INFO("server.loading", ">> Loaded {} Player Create Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4355 LOG_INFO("server.loading", " ");
4356 }
4357 }
4358
4359 // Load playercreate items
4360 LOG_INFO("server.loading", "Loading Player Create Items Data...");
4361 {
4362 uint32 oldMSTime = getMSTime();
4363 // 0 1 2 3
4364 QueryResult result = WorldDatabase.Query("SELECT race, class, itemid, amount FROM playercreateinfo_item");
4365
4366 if (!result)
4367 {
4368 LOG_WARN("server.loading", ">> Loaded 0 Custom Player Create Items. DB Table `playercreateinfo_item` Is Empty.");
4369 LOG_INFO("server.loading", " ");
4370 }
4371 else
4372 {
4373 uint32 count = 0;
4374
4375 do
4376 {
4377 Field* fields = result->Fetch();
4378
4379 uint32 current_race = fields[0].Get<uint8>();
4380 if (current_race >= sRaceMgr->GetMaxRaces())
4381 {
4382 LOG_ERROR("sql.sql", "Wrong race {} in `playercreateinfo_item` table, ignoring.", current_race);
4383 continue;
4384 }
4385
4386 uint32 current_class = fields[1].Get<uint8>();
4387 if (current_class >= MAX_CLASSES)
4388 {
4389 LOG_ERROR("sql.sql", "Wrong class {} in `playercreateinfo_item` table, ignoring.", current_class);
4390 continue;
4391 }
4392
4393 uint32 item_id = fields[2].Get<uint32>();
4394
4395 if (!GetItemTemplate(item_id))
4396 {
4397 LOG_ERROR("sql.sql", "Item id {} (race {} class {}) in `playercreateinfo_item` table but not listed in `item_template`, ignoring.", item_id, current_race, current_class);
4398 continue;
4399 }
4400
4401 int32 amount = fields[3].Get<int32>();
4402
4403 if (!amount)
4404 {
4405 LOG_ERROR("sql.sql", "Item id {} (class {} race {}) have amount == 0 in `playercreateinfo_item` table, ignoring.", item_id, current_race, current_class);
4406 continue;
4407 }
4408
4409 if (!current_race || !current_class)
4410 {
4411 uint32 min_race = current_race ? current_race : 1;
4412 uint32 max_race = current_race ? current_race + 1 : sRaceMgr->GetMaxRaces();
4413 uint32 min_class = current_class ? current_class : 1;
4414 uint32 max_class = current_class ? current_class + 1 : MAX_CLASSES;
4415 for (uint32 r = min_race; r < max_race; ++r)
4416 for (uint32 c = min_class; c < max_class; ++c)
4417 PlayerCreateInfoAddItemHelper(r, c, item_id, amount);
4418 }
4419 else
4420 PlayerCreateInfoAddItemHelper(current_race, current_class, item_id, amount);
4421
4422 ++count;
4423 } while (result->NextRow());
4424
4425 LOG_INFO("server.loading", ">> Loaded {} Custom Player Create Items in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4426 LOG_INFO("server.loading", " ");
4427 }
4428 }
4429
4430 // Load playercreate skills
4431 LOG_INFO("server.loading", "Loading Player Create Skill Data...");
4432 {
4433 uint32 oldMSTime = getMSTime();
4434
4435 QueryResult result = WorldDatabase.Query("SELECT raceMask, classMask, skill, `rank` FROM playercreateinfo_skills");
4436
4437 if (!result)
4438 {
4439 LOG_WARN("server.loading", ">> Loaded 0 Player Create Skills. DB Table `playercreateinfo_skills` Is Empty.");
4440 }
4441 else
4442 {
4443 uint32 count = 0;
4444
4445 do
4446 {
4447 Field* fields = result->Fetch();
4448 uint32 raceMask = fields[0].Get<uint32>();
4449 uint32 classMask = fields[1].Get<uint32>();
4451 skill.SkillId = fields[2].Get<uint16>();
4452 skill.Rank = fields[3].Get<uint16>();
4453
4454 if (skill.Rank >= MAX_SKILL_STEP)
4455 {
4456 LOG_ERROR("sql.sql", "Skill rank value {} set for skill {} raceMask {} classMask {} is too high, max allowed value is {}", skill.Rank, skill.SkillId, raceMask, classMask, MAX_SKILL_STEP);
4457 continue;
4458 }
4459
4460 if (raceMask != 0 && !(raceMask & sRaceMgr->GetPlayableRaceMask()))
4461 {
4462 LOG_ERROR("sql.sql", "Wrong race mask {} in `playercreateinfo_skills` table, ignoring.", raceMask);
4463 continue;
4464 }
4465
4466 if (classMask != 0 && !(classMask & CLASSMASK_ALL_PLAYABLE))
4467 {
4468 LOG_ERROR("sql.sql", "Wrong class mask {} in `playercreateinfo_skills` table, ignoring.", classMask);
4469 continue;
4470 }
4471
4472 if (!sSkillLineStore.LookupEntry(skill.SkillId))
4473 {
4474 LOG_ERROR("sql.sql", "Wrong skill id {} in `playercreateinfo_skills` table, ignoring.", skill.SkillId);
4475 continue;
4476 }
4477
4478 for (uint32 raceIndex = RACE_HUMAN; raceIndex < sRaceMgr->GetMaxRaces(); ++raceIndex)
4479 {
4480 if (raceMask == 0 || ((1 << (raceIndex - 1)) & raceMask))
4481 {
4482 for (uint32 classIndex = CLASS_WARRIOR; classIndex < MAX_CLASSES; ++classIndex)
4483 {
4484 if (classMask == 0 || ((1 << (classIndex - 1)) & classMask))
4485 {
4486 if (!GetSkillRaceClassInfo(skill.SkillId, raceIndex, classIndex))
4487 continue;
4488
4489 if (PlayerInfo* info = _playerInfo[raceIndex][classIndex])
4490 {
4491 info->skills.push_back(skill);
4492 ++count;
4493 }
4494 }
4495 }
4496 }
4497 }
4498 } while (result->NextRow());
4499
4500 LOG_INFO("server.loading", ">> Loaded {} Player Create Skills in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4501 LOG_INFO("server.loading", " ");
4502 }
4503 }
4504
4505 // Load playercreate spells
4506 LOG_INFO("server.loading", "Loading Player Create Spell Data...");
4507 {
4508 uint32 oldMSTime = getMSTime();
4509
4510 QueryResult result = WorldDatabase.Query("SELECT racemask, classmask, Spell FROM playercreateinfo_spell_custom");
4511
4512 if (!result)
4513 {
4514 LOG_WARN("server.loading", ">> Loaded 0 player create spells. DB table `playercreateinfo_spell_custom` is empty.");
4515 }
4516 else
4517 {
4518 uint32 count = 0;
4519
4520 do
4521 {
4522 Field* fields = result->Fetch();
4523 uint32 raceMask = fields[0].Get<uint32>();
4524 uint32 classMask = fields[1].Get<uint32>();
4525 uint32 spellId = fields[2].Get<uint32>();
4526
4527 if (raceMask != 0 && !(raceMask & sRaceMgr->GetPlayableRaceMask()))
4528 {
4529 LOG_ERROR("sql.sql", "Wrong race mask {} in `playercreateinfo_spell_custom` table, ignoring.", raceMask);
4530 continue;
4531 }
4532
4533 if (classMask != 0 && !(classMask & CLASSMASK_ALL_PLAYABLE))
4534 {
4535 LOG_ERROR("sql.sql", "Wrong class mask {} in `playercreateinfo_spell_custom` table, ignoring.", classMask);
4536 continue;
4537 }
4538
4539 for (uint32 raceIndex = RACE_HUMAN; raceIndex < sRaceMgr->GetMaxRaces(); ++raceIndex)
4540 {
4541 if (raceMask == 0 || ((1 << (raceIndex - 1)) & raceMask))
4542 {
4543 for (uint32 classIndex = CLASS_WARRIOR; classIndex < MAX_CLASSES; ++classIndex)
4544 {
4545 if (classMask == 0 || ((1 << (classIndex - 1)) & classMask))
4546 {
4547 if (PlayerInfo* info = _playerInfo[raceIndex][classIndex])
4548 {
4549 info->customSpells.push_back(spellId);
4550 ++count;
4551 }
4552 }
4553 }
4554 }
4555 }
4556 } while (result->NextRow());
4557
4558 LOG_INFO("server.loading", ">> Loaded {} Custom Player Create Spells in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4559 LOG_INFO("server.loading", " ");
4560 }
4561 }
4562
4563 // Load playercreate cast spell
4564 LOG_INFO("server.loading", "Loading Player Create Cast Spell Data...");
4565 {
4566 uint32 oldMSTime = getMSTime();
4567
4568 QueryResult result = WorldDatabase.Query("SELECT raceMask, classMask, spell FROM playercreateinfo_cast_spell");
4569
4570 if (!result)
4571 {
4572 LOG_WARN("server.loading", ">> Loaded 0 Player Create Cast Spells. DB Table `playercreateinfo_cast_spell` Is Empty.");
4573 }
4574 else
4575 {
4576 uint32 count = 0;
4577
4578 do
4579 {
4580 Field* fields = result->Fetch();
4581 uint32 raceMask = fields[0].Get<uint32>();
4582 uint32 classMask = fields[1].Get<uint32>();
4583 uint32 spellId = fields[2].Get<uint32>();
4584
4585 if (raceMask != 0 && !(raceMask & sRaceMgr->GetPlayableRaceMask()))
4586 {
4587 LOG_ERROR("sql.sql", "Wrong race mask {} in `playercreateinfo_cast_spell` table, ignoring.", raceMask);
4588 continue;
4589 }
4590
4591 if (classMask != 0 && !(classMask & CLASSMASK_ALL_PLAYABLE))
4592 {
4593 LOG_ERROR("sql.sql", "Wrong class mask {} in `playercreateinfo_cast_spell` table, ignoring.", classMask);
4594 continue;
4595 }
4596
4597 for (uint32 raceIndex = RACE_HUMAN; raceIndex < sRaceMgr->GetMaxRaces(); ++raceIndex)
4598 {
4599 if (raceMask == 0 || ((1 << (raceIndex - 1)) & raceMask))
4600 {
4601 for (uint32 classIndex = CLASS_WARRIOR; classIndex < MAX_CLASSES; ++classIndex)
4602 {
4603 if (classMask == 0 || ((1 << (classIndex - 1)) & classMask))
4604 {
4605 if (PlayerInfo* info = _playerInfo[raceIndex][classIndex])
4606 {
4607 info->castSpells.push_back(spellId);
4608 ++count;
4609 }
4610 }
4611 }
4612 }
4613 }
4614 } while (result->NextRow());
4615
4616 LOG_INFO("server.loading", ">> Loaded {} Player Create Cast Spells in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4617 LOG_INFO("server.loading", " ");
4618 }
4619 }
4620
4621 // Load playercreate actions
4622 LOG_INFO("server.loading", "Loading Player Create Action Data...");
4623 {
4624 uint32 oldMSTime = getMSTime();
4625
4626 // 0 1 2 3 4
4627 QueryResult result = WorldDatabase.Query("SELECT race, class, button, action, type FROM playercreateinfo_action");
4628
4629 if (!result)
4630 {
4631 LOG_WARN("server.loading", ">> Loaded 0 Player Create Actions. DB Table `playercreateinfo_action` Is Empty.");
4632 LOG_INFO("server.loading", " ");
4633 }
4634 else
4635 {
4636 uint32 count = 0;
4637
4638 do
4639 {
4640 Field* fields = result->Fetch();
4641
4642 uint32 current_race = fields[0].Get<uint8>();
4643 if (current_race >= sRaceMgr->GetMaxRaces())
4644 {
4645 LOG_ERROR("sql.sql", "Wrong race {} in `playercreateinfo_action` table, ignoring.", current_race);
4646 continue;
4647 }
4648
4649 uint32 current_class = fields[1].Get<uint8>();
4650 if (current_class >= MAX_CLASSES)
4651 {
4652 LOG_ERROR("sql.sql", "Wrong class {} in `playercreateinfo_action` table, ignoring.", current_class);
4653 continue;
4654 }
4655
4656 if (PlayerInfo* info = _playerInfo[current_race][current_class])
4657 info->action.push_back(PlayerCreateInfoAction(fields[2].Get<uint16>(), fields[3].Get<uint32>(), fields[4].Get<uint16>()));
4658
4659 ++count;
4660 } while (result->NextRow());
4661
4662 LOG_INFO("server.loading", ">> Loaded {} Player Create Actions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4663 LOG_INFO("server.loading", " ");
4664 }
4665 }
4666
4667 // Loading levels data (class/race dependent)
4668 LOG_INFO("server.loading", "Loading Player Create Level Stats Data...");
4669 {
4670 struct RaceStats
4671 {
4672 int16 StatModifier[MAX_STATS];
4673 };
4674
4675 std::vector<RaceStats> raceStatModifiers;
4676
4677 raceStatModifiers.resize(sRaceMgr->GetMaxRaces());
4678
4679 uint32 oldMSTime = getMSTime();
4680
4681 // 0 1 2 3 4 5
4682 QueryResult raceStatsResult = WorldDatabase.Query("SELECT Race, Strength, Agility, Stamina, Intellect, Spirit FROM player_race_stats");
4683
4684 if (!raceStatsResult)
4685 {
4686 LOG_WARN("server.loading", ">> Loaded 0 race stats definitions. DB table `player_race_stats` is empty.");
4687 LOG_INFO("server.loading", " ");
4688 exit(1);
4689 }
4690
4691 do
4692 {
4693 Field* fields = raceStatsResult->Fetch();
4694
4695 uint32 current_race = fields[0].Get<uint8>();
4696 if (current_race >= sRaceMgr->GetMaxRaces())
4697 {
4698 LOG_ERROR("sql.sql", "Wrong race {} in `player_race_stats` table, ignoring.", current_race);
4699 continue;
4700 }
4701
4702 for (uint32 i = 0; i < MAX_STATS; ++i)
4703 raceStatModifiers[current_race].StatModifier[i] = fields[i + 1].Get<int16>();
4704
4705 } while (raceStatsResult->NextRow());
4706
4707 // 0 1 2 3 4 5 6 7 8
4708 QueryResult result = WorldDatabase.Query("SELECT Class, Level, Strength, Agility, Stamina, Intellect, Spirit, BaseHP, BaseMana FROM player_class_stats");
4709
4710 if (!result)
4711 {
4712 LOG_ERROR("server.loading", ">> Loaded 0 level stats definitions. DB table `player_class_stats` is empty.");
4713 exit(1);
4714 }
4715
4716 uint32 count = 0;
4717
4718 do
4719 {
4720 Field* fields = result->Fetch();
4721
4722 uint32 current_class = fields[0].Get<uint8>();
4723 if (current_class >= MAX_CLASSES)
4724 {
4725 LOG_ERROR("sql.sql", "Wrong class {} in `player_class_stats` table, ignoring.", current_class);
4726 continue;
4727 }
4728
4729 uint32 current_level = fields[1].Get<uint8>();
4730 if (current_level > sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL))
4731 {
4732 if (current_level > STRONG_MAX_LEVEL) // hardcoded level maximum
4733 LOG_ERROR("sql.sql", "Wrong (> {}) level {} in `player_class_stats` table, ignoring.", STRONG_MAX_LEVEL, current_level);
4734 else
4735 LOG_DEBUG("sql.sql", "Unused (> MaxPlayerLevel in worldserver.conf) level {} in `player_class_stats` table, ignoring.", current_level);
4736
4737 continue;
4738 }
4739
4740 for (std::size_t race = 0; race < raceStatModifiers.size(); ++race)
4741 {
4742 if (PlayerInfo* info = _playerInfo[race][current_class])
4743 {
4744 if (!info->levelInfo)
4745 info->levelInfo = new PlayerLevelInfo[sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL)];
4746
4747 PlayerLevelInfo& levelInfo = info->levelInfo[current_level - 1];
4748 for (int i = 0; i < MAX_STATS; ++i)
4749 levelInfo.stats[i] = fields[i + 2].Get<uint16>() + raceStatModifiers[race].StatModifier[i];
4750 }
4751 }
4752
4753 PlayerClassInfo* info = _playerClassInfo[current_class];
4754 if (!info)
4755 {
4756 info = new PlayerClassInfo();
4758 _playerClassInfo[current_class] = info;
4759 }
4760
4761 PlayerClassLevelInfo& levelInfo = info->levelInfo[current_level - 1];
4762
4763 levelInfo.basehealth = fields[7].Get<uint32>();
4764 levelInfo.basemana = fields[8].Get<uint32>();
4765
4766 ++count;
4767 } while (result->NextRow());
4768
4769 // Fill gaps and check integrity
4770 for (int race = RACE_HUMAN; race < sRaceMgr->GetMaxRaces(); ++race)
4771 {
4772 // skip non existed races
4773 if (!sChrRacesStore.LookupEntry(race))
4774 continue;
4775
4776 for (int class_ = 0; class_ < MAX_CLASSES; ++class_)
4777 {
4778 // skip non existed classes
4779 if (!sChrClassesStore.LookupEntry(class_))
4780 continue;
4781
4782 PlayerClassInfo* pClassInfo = _playerClassInfo[class_];
4783 PlayerInfo* info = _playerInfo[race][class_];
4784 if (!info)
4785 continue;
4786
4787 // skip expansion races if not playing with expansion
4788 if (sWorld->getIntConfig(CONFIG_EXPANSION) < EXPANSION_THE_BURNING_CRUSADE && (race == RACE_BLOODELF || race == RACE_DRAENEI))
4789 continue;
4790
4791 // skip expansion classes if not playing with expansion
4793 continue;
4794
4795 // fatal error if no initial stats data
4796 if (!info->levelInfo || (info->levelInfo[sWorld->getIntConfig(CONFIG_START_PLAYER_LEVEL) - 1].stats[0] == 0 && class_ != CLASS_DEATH_KNIGHT) || (info->levelInfo[sWorld->getIntConfig(CONFIG_START_HEROIC_PLAYER_LEVEL) - 1].stats[0] == 0 && class_ == CLASS_DEATH_KNIGHT))
4797 {
4798 LOG_ERROR("sql.sql", "Race {} class {} initial level does not have stats data!", race, class_);
4799 exit(1);
4800 }
4801
4802 // fatal error if no initial health/mana data
4803 if (!pClassInfo->levelInfo || (pClassInfo->levelInfo[sWorld->getIntConfig(CONFIG_START_PLAYER_LEVEL) - 1].basehealth == 0 && class_ != CLASS_DEATH_KNIGHT) || (pClassInfo->levelInfo[sWorld->getIntConfig(CONFIG_START_HEROIC_PLAYER_LEVEL) - 1].basehealth == 0 && class_ == CLASS_DEATH_KNIGHT))
4804 {
4805 LOG_ERROR("sql.sql", "Class {} initial level does not have health/mana data!", class_);
4806 exit(1);
4807 }
4808
4809 // fill level gaps for stats
4810 for (uint8 level = 1; level < sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL); ++level)
4811 {
4812 if ((info->levelInfo[level].stats[0] == 0 && class_ != CLASS_DEATH_KNIGHT) || (level >= sWorld->getIntConfig(CONFIG_START_HEROIC_PLAYER_LEVEL) && info->levelInfo[level].stats[0] == 0 && class_ == CLASS_DEATH_KNIGHT))
4813 {
4814 LOG_ERROR("sql.sql", "Race {} class {} level {} does not have stats data. Using stats data of level {}.", race, class_, level + 1, level);
4815 info->levelInfo[level] = info->levelInfo[level - 1];
4816 }
4817 }
4818
4819 // fill level gaps for health/mana
4820 for (uint8 level = 1; level < sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL); ++level)
4821 {
4822 if ((pClassInfo->levelInfo[level].basehealth == 0 && class_ != CLASS_DEATH_KNIGHT) || (level >= sWorld->getIntConfig(CONFIG_START_HEROIC_PLAYER_LEVEL) && pClassInfo->levelInfo[level].basehealth == 0 && class_ == CLASS_DEATH_KNIGHT))
4823 {
4824 LOG_ERROR("sql.sql", "Class {} level {} does not have health/mana data. Using stats data of level {}.", class_, level + 1, level);
4825 pClassInfo->levelInfo[level] = pClassInfo->levelInfo[level - 1];
4826 }
4827 }
4828 }
4829 }
4830
4831 LOG_INFO("server.loading", ">> Loaded {} Level Stats Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4832 LOG_INFO("server.loading", " ");
4833 }
4834
4835 // Loading xp per level data
4836 LOG_INFO("server.loading", "Loading Player Create XP Data...");
4837 {
4838 uint32 oldMSTime = getMSTime();
4839
4840 _playerXPperLevel.resize(sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL));
4841 for (uint8 level = 0; level < sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL); ++level)
4842 _playerXPperLevel[level] = 0;
4843
4844 // 0 1
4845 QueryResult result = WorldDatabase.Query("SELECT Level, Experience FROM player_xp_for_level");
4846
4847 if (!result)
4848 {
4849 LOG_WARN("server.loading", ">> Loaded 0 xp for level definitions. DB table `player_xp_for_level` is empty.");
4850 LOG_INFO("server.loading", " ");
4851 exit(1);
4852 }
4853
4854 uint32 count = 0;
4855
4856 do
4857 {
4858 Field* fields = result->Fetch();
4859
4860 uint32 current_level = fields[0].Get<uint8>();
4861 uint32 current_xp = fields[1].Get<uint32>();
4862
4863 if (current_level >= sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL))
4864 {
4865 if (current_level > STRONG_MAX_LEVEL) // hardcoded level maximum
4866 LOG_ERROR("sql.sql", "Wrong (> {}) level {} in `player_xp_for_level` table, ignoring.", STRONG_MAX_LEVEL, current_level);
4867 else
4868 {
4869 LOG_DEBUG("sql.sql", "Unused (> MaxPlayerLevel in worldserver.conf) level {} in `player_xp_for_levels` table, ignoring.", current_level);
4870 ++count; // make result loading percent "expected" correct in case disabled detail mode for example.
4871 }
4872 continue;
4873 }
4874 //PlayerXPperLevel
4875 _playerXPperLevel[current_level] = current_xp;
4876 ++count;
4877 } while (result->NextRow());
4878
4879 // fill level gaps
4880 for (uint8 level = 1; level < sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL); ++level)
4881 {
4882 if (_playerXPperLevel[level] == 0)
4883 {
4884 LOG_ERROR("sql.sql", "Level {} does not have XP for level data. Using data of level [{}] + 100.", level + 1, level);
4885 _playerXPperLevel[level] = _playerXPperLevel[level - 1] + 100;
4886 }
4887 }
4888
4889 LOG_INFO("server.loading", ">> Loaded {} XP For Level Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4890 LOG_INFO("server.loading", " ");
4891 }
4892}
SkillRaceClassInfoEntry const * GetSkillRaceClassInfo(uint32 skill, uint8 race, uint8 class_)
Definition DBCStores.cpp:895
DBCStorage< ChrRacesEntry > sChrRacesStore(ChrRacesEntryfmt)
DBCStorage< SkillLineEntry > sSkillLineStore(SkillLinefmt)
DBCStorage< ChrClassesEntry > sChrClassesStore(ChrClassesEntryfmt)
#define MAX_SKILL_STEP
Definition DBCStructure.h:1580
@ CLASS_DEATH_KNIGHT
Definition SharedDefines.h:131
@ RACE_DRAENEI
Definition SharedDefines.h:81
@ RACE_BLOODELF
Definition SharedDefines.h:80
@ RACE_HUMAN
Definition SharedDefines.h:71
@ EXPANSION_THE_BURNING_CRUSADE
Definition SharedDefines.h:54
@ EXPANSION_WRATH_OF_THE_LICH_KING
Definition SharedDefines.h:55
@ CONFIG_START_HEROIC_PLAYER_LEVEL
Definition WorldConfig.h:196
@ CONFIG_START_PLAYER_LEVEL
Definition WorldConfig.h:195
@ CONFIG_EXPANSION
Definition WorldConfig.h:232
void PlayerCreateInfoAddItemHelper(uint32 race_, uint32 class_, uint32 itemId, int32 count)
Definition ObjectMgr.cpp:4229
Definition DBCStructure.h:679
uint32 model_f
Definition DBCStructure.h:685
uint32 model_m
Definition DBCStructure.h:684
Definition Player.h:276
uint32 basehealth
Definition Player.h:278
uint32 basemana
Definition Player.h:279
Definition Player.h:302
Definition Player.h:314
uint16 SkillId
Definition Player.h:315
float orientation
Definition Player.h:331
uint16 displayId_m
Definition Player.h:332
float positionX
Definition Player.h:328
uint32 areaId
Definition Player.h:327
float positionY
Definition Player.h:329
float positionZ
Definition Player.h:330
uint32 mapId
Definition Player.h:326
uint16 displayId_f
Definition Player.h:333
Definition Player.h:290
std::array< uint32, MAX_STATS > stats
Definition Player.h:296

References _playerClassInfo, _playerInfo, _playerXPperLevel, PlayerInfo::areaId, PlayerClassLevelInfo::basehealth, PlayerClassLevelInfo::basemana, CLASS_DEATH_KNIGHT, CLASS_WARRIOR, CLASSMASK_ALL_PLAYABLE, CONFIG_EXPANSION, CONFIG_MAX_PLAYER_LEVEL, CONFIG_START_HEROIC_PLAYER_LEVEL, CONFIG_START_PLAYER_LEVEL, PlayerInfo::displayId_f, PlayerInfo::displayId_m, EXPANSION_THE_BURNING_CRUSADE, EXPANSION_WRATH_OF_THE_LICH_KING, Field::Get(), GetItemTemplate(), getMSTime(), GetMSTimeDiffToNow(), GetSkillRaceClassInfo(), MapMgr::IsValidMapCoord(), PlayerClassInfo::levelInfo, PlayerInfo::levelInfo, LOG_DEBUG, LOG_ERROR, LOG_INFO, LOG_WARN, PlayerInfo::mapId, MAX_CLASSES, MAX_SKILL_STEP, MAX_STATS, ChrRacesEntry::model_f, ChrRacesEntry::model_m, PlayerInfo::orientation, PlayerCreateInfoAddItemHelper(), PlayerInfo::positionX, PlayerInfo::positionY, PlayerInfo::positionZ, RACE_BLOODELF, RACE_DRAENEI, RACE_HUMAN, sChrClassesStore, sChrRacesStore, PlayerCreateInfoSkill::SkillId, sMapStore, sRaceMgr, sSkillLineStore, PlayerLevelInfo::stats, STRONG_MAX_LEVEL, sWorld, and WorldDatabase.

◆ LoadPlayerShapeshiftModels()

void ObjectMgr::LoadPlayerShapeshiftModels ( )
1844{
1845 uint32 oldMSTime = getMSTime();
1846
1847 QueryResult result = WorldDatabase.Query("SELECT ShapeshiftID, RaceID, CustomizationID, GenderID, ModelID from player_shapeshift_model");
1848
1849 if (!result)
1850 {
1851 LOG_INFO("server.loading", ">> Loaded 0 player shapeshift model records. DB table `player_shapeshift_model` is empty.");
1852 return;
1853 }
1854
1855 uint32 count = 0;
1856 do
1857 {
1858 Field* fields = result->Fetch();
1859
1860 ShapeshiftForm shapeshiftForm = ShapeshiftForm(fields[0].Get<uint8>());
1861 uint8 race = fields[1].Get<uint8>();
1862 uint8 customizationID = fields[2].Get<uint8>();
1863 uint8 genderID = Gender(fields[3].Get<uint8>());
1864 uint32 modelId = fields[4].Get<uint32>();
1865
1866 ChrRacesEntry const* raceEntry = sChrRacesStore.LookupEntry(race);
1867 if (!raceEntry)
1868 {
1869 LOG_ERROR("sql.sql", "Race {} defined in `player_shapeshift_model` does not exists, skipped.", uint32(race));
1870 continue;
1871 }
1872
1873 CreatureDisplayInfoEntry const* displayEntry = sCreatureDisplayInfoStore.LookupEntry(modelId);
1874 if (!displayEntry)
1875 {
1876 LOG_ERROR("sql.sql", "ShapeshiftForm: {}, Race: {} defined in `player_shapeshift_model` has non-existing model ({}), skipped.", shapeshiftForm, race, modelId);
1877 continue;
1878 }
1879
1880 _playerShapeshiftModel[std::make_tuple(shapeshiftForm, race, customizationID, genderID)] = modelId;
1881 ++count;
1882 } while (result->NextRow());
1883
1884 LOG_INFO("server.loading", ">> Loaded {} player totem model records in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
1885 LOG_INFO("server.loading", " ");
1886}
Gender
Definition SharedDefines.h:60
ShapeshiftForm
Definition UnitDefines.h:71

References _playerShapeshiftModel, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, sChrRacesStore, sCreatureDisplayInfoStore, and WorldDatabase.

◆ LoadPlayerTotemModels()

void ObjectMgr::LoadPlayerTotemModels ( )
1785{
1786 uint32 oldMSTime = getMSTime();
1787
1788 QueryResult result = WorldDatabase.Query("SELECT TotemID, RaceID, ModelID from player_totem_model");
1789
1790 if (!result)
1791 {
1792 LOG_INFO("server.loading", ">> Loaded 0 player totem model records. DB table `player_totem_model` is empty.");
1793 return;
1794 }
1795
1796 uint32 count = 0;
1797 do
1798 {
1799 Field* fields = result->Fetch();
1800
1801 SummonSlot totemSlot = SummonSlot(fields[0].Get<uint8>());
1802 uint8 race = fields[1].Get<uint8>();
1803 uint32 displayId = fields[2].Get<uint32>();
1804
1805 if (totemSlot < SUMMON_SLOT_TOTEM_FIRE || totemSlot >= MAX_TOTEM_SLOT)
1806 {
1807 LOG_ERROR("sql.sql", "Wrong TotemSlot {} in `player_totem_model` table, skipped.", totemSlot);
1808 continue;
1809 }
1810
1811 ChrRacesEntry const* raceEntry = sChrRacesStore.LookupEntry(race);
1812 if (!raceEntry)
1813 {
1814 LOG_ERROR("sql.sql", "Race {} defined in `player_totem_model` does not exists, skipped.", uint32(race));
1815 continue;
1816 }
1817
1818 CreatureDisplayInfoEntry const* displayEntry = sCreatureDisplayInfoStore.LookupEntry(displayId);
1819 if (!displayEntry)
1820 {
1821 LOG_ERROR("sql.sql", "TotemSlot: {} defined in `player_totem_model` has non-existing model ({}), skipped.", totemSlot, displayId);
1822 continue;
1823 }
1824
1825 _playerTotemModel[std::make_pair(totemSlot, Races(race))] = displayId;
1826 ++count;
1827 } while (result->NextRow());
1828
1829 LOG_INFO("server.loading", ">> Loaded {} player totem model records in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
1830 LOG_INFO("server.loading", " ");
1831}
#define MAX_TOTEM_SLOT
Definition SharedDefines.h:3557
SummonSlot
Definition SharedDefines.h:3545
Races
Definition SharedDefines.h:69

References _playerTotemModel, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, MAX_TOTEM_SLOT, sChrRacesStore, sCreatureDisplayInfoStore, and WorldDatabase.

◆ LoadPointOfInterestLocales()

void ObjectMgr::LoadPointOfInterestLocales ( )
494{
495 uint32 oldMSTime = getMSTime();
496
497 _pointOfInterestLocaleStore.clear(); // need for reload case
498
499 // 0 1 2
500 QueryResult result = WorldDatabase.Query("SELECT ID, locale, Name FROM points_of_interest_locale");
501
502 if (!result)
503 return;
504
505 do
506 {
507 Field* fields = result->Fetch();
508
509 uint32 ID = fields[0].Get<uint32>();
510
511 LocaleConstant locale = GetLocaleByName(fields[1].Get<std::string>());
512 if (locale == LOCALE_enUS)
513 continue;
514
516 AddLocaleString(fields[2].Get<std::string>(), locale, data.Name);
517 } while (result->NextRow());
518
519 LOG_INFO("server.loading", ">> Loaded {} Points Of Interest Locale Strings in {} ms", (uint32)_pointOfInterestLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
520}
Definition CreatureData.h:355
std::vector< std::string > Name
Definition CreatureData.h:356

References _pointOfInterestLocaleStore, AddLocaleString(), Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, PointOfInterestLocale::Name, and WorldDatabase.

◆ LoadPointsOfInterest()

void ObjectMgr::LoadPointsOfInterest ( )
8476{
8477 uint32 oldMSTime = getMSTime();
8478
8479 _pointsOfInterestStore.clear(); // need for reload case
8480
8481 uint32 count = 0;
8482
8483 // 0 1 2 3 4 5 6
8484 QueryResult result = WorldDatabase.Query("SELECT ID, PositionX, PositionY, Icon, Flags, Importance, Name FROM points_of_interest");
8485
8486 if (!result)
8487 {
8488 LOG_WARN("server.loading", ">> Loaded 0 Points of Interest definitions. DB table `points_of_interest` is empty.");
8489 LOG_INFO("server.loading", " ");
8490 return;
8491 }
8492
8493 do
8494 {
8495 Field* fields = result->Fetch();
8496
8497 uint32 point_id = fields[0].Get<uint32>();
8498
8499 PointOfInterest POI;
8500 POI.ID = point_id;
8501 POI.PositionX = fields[1].Get<float>();
8502 POI.PositionY = fields[2].Get<float>();
8503 POI.Icon = fields[3].Get<uint32>();
8504 POI.Flags = fields[4].Get<uint32>();
8505 POI.Importance = fields[5].Get<uint32>();
8506 POI.Name = fields[6].Get<std::string>();
8507
8508 if (!Acore::IsValidMapCoord(POI.PositionX, POI.PositionY))
8509 {
8510 LOG_ERROR("sql.sql", "Table `points_of_interest` (ID: {}) have invalid coordinates (X: {} Y: {}), ignored.", point_id, POI.PositionX, POI.PositionY);
8511 continue;
8512 }
8513
8514 _pointsOfInterestStore[point_id] = POI;
8515
8516 ++count;
8517 } while (result->NextRow());
8518
8519 LOG_INFO("server.loading", ">> Loaded {} Points of Interest Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8520 LOG_INFO("server.loading", " ");
8521}
bool IsValidMapCoord(float c)
Definition GridDefines.h:210
Definition ObjectMgr.h:591
uint32 ID
Definition ObjectMgr.h:592

References _pointsOfInterestStore, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), PointOfInterest::ID, Acore::IsValidMapCoord(), LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadProfanityNamesFromDB()

void ObjectMgr::LoadProfanityNamesFromDB ( )
8911{
8912 uint32 oldMSTime = getMSTime();
8913
8914 _profanityNamesStore.clear(); // need for reload case
8915
8916 QueryResult result = CharacterDatabase.Query("SELECT name FROM profanity_name");
8917
8918 if (!result)
8919 {
8920 LOG_WARN("server.loading", ">> Loaded 0 profanity names. DB table `profanity_name` is empty!");
8921 return;
8922 }
8923
8924 uint32 count = 0;
8925
8926 Field* fields;
8927 do
8928 {
8929 fields = result->Fetch();
8930 std::string name = fields[0].Get<std::string>();
8931
8932 std::wstring wstr;
8933 if (!Utf8toWStr (name, wstr))
8934 {
8935 LOG_ERROR("sql.sql", "Table `profanity_name` have invalid name: {}", name);
8936 continue;
8937 }
8938
8939 wstrToLower(wstr);
8940
8941 _profanityNamesStore.insert(wstr);
8942 ++count;
8943 } while (result->NextRow());
8944
8945 LOG_INFO("server.loading", ">> Loaded {} profanity names from DB in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8946}

References _profanityNamesStore, CharacterDatabase, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, Utf8toWStr(), and wstrToLower().

◆ LoadProfanityNamesFromDBC()

void ObjectMgr::LoadProfanityNamesFromDBC ( )
8949{
8950 if (!sWorld->getBoolConfig(CONFIG_STRICT_NAMES_PROFANITY))
8951 {
8952 LOG_WARN("server.loading", ">> Loaded 0 profanity names from DBC. Config option disabled.");
8953 return;
8954 }
8955
8956 uint32 oldMSTime = getMSTime();
8957
8958 uint32 count = 0;
8959
8960 for (NamesProfanityEntry const* profanityStore : sNamesProfanityStore)
8961 {
8962 std::wstring wstr;
8963
8964 Utf8toWStr(profanityStore->Pattern, wstr);
8965
8966 // DBC does not have clean entries, remove the junk.
8967 boost::algorithm::replace_all(wstr, "\\<", "");
8968 boost::algorithm::replace_all(wstr, "\\>", "");
8969
8970 _profanityNamesStore.insert(wstr);
8971 count++;
8972 }
8973
8974 LOG_INFO("server.loading", ">> Loaded {} profanity names from DBC in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8975 LOG_INFO("server.loading", " ");
8976}
DBCStorage< NamesProfanityEntry > sNamesProfanityStore(NamesProfanityfmt)
@ CONFIG_STRICT_NAMES_PROFANITY
Definition WorldConfig.h:145
Definition DBCStructure.h:1405

References _profanityNamesStore, CONFIG_STRICT_NAMES_PROFANITY, getMSTime(), GetMSTimeDiffToNow(), LOG_INFO, LOG_WARN, sNamesProfanityStore, sWorld, and Utf8toWStr().

◆ LoadQuestAreaTriggers()

void ObjectMgr::LoadQuestAreaTriggers ( )
6849{
6850 uint32 oldMSTime = getMSTime();
6851
6852 _questAreaTriggerStore.clear(); // need for reload case
6853
6854 QueryResult result = WorldDatabase.Query("SELECT id, quest FROM areatrigger_involvedrelation");
6855
6856 if (!result)
6857 {
6858 LOG_WARN("server.loading", ">> Loaded 0 quest trigger points. DB table `areatrigger_involvedrelation` is empty.");
6859 LOG_INFO("server.loading", " ");
6860 return;
6861 }
6862
6863 uint32 count = 0;
6864
6865 do
6866 {
6867 ++count;
6868
6869 Field* fields = result->Fetch();
6870
6871 uint32 trigger_ID = fields[0].Get<uint32>();
6872 uint32 quest_ID = fields[1].Get<uint32>();
6873
6874 AreaTrigger const* atEntry = GetAreaTrigger(trigger_ID);
6875 if (!atEntry)
6876 {
6877 LOG_ERROR("sql.sql", "Area trigger (ID:{}) does not exist in `AreaTrigger.dbc`.", trigger_ID);
6878 continue;
6879 }
6880
6881 Quest const* quest = GetQuestTemplate(quest_ID);
6882
6883 if (!quest)
6884 {
6885 LOG_ERROR("sql.sql", "Table `areatrigger_involvedrelation` has record (id: {}) for not existing quest {}", trigger_ID, quest_ID);
6886 continue;
6887 }
6888
6890 {
6891 LOG_ERROR("sql.sql", "Table `areatrigger_involvedrelation` has record (id: {}) for not quest {}, but quest not have specialflag QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT. Trigger or quest flags must be fixed, quest modified to require objective.", trigger_ID, quest_ID);
6892
6893 // this will prevent quest completing without objective
6894 const_cast<Quest*>(quest)->SetSpecialFlag(QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT);
6895
6896 // continue; - quest modified to required objective and trigger can be allowed.
6897 }
6898
6899 _questAreaTriggerStore[trigger_ID] = quest_ID;
6900 } while (result->NextRow());
6901
6902 LOG_INFO("server.loading", ">> Loaded {} Quest Trigger Points in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
6903 LOG_INFO("server.loading", " ");
6904}
@ QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT
Definition QuestDef.h:161
Definition QuestDef.h:210
bool HasSpecialFlag(uint32 flag) const
Definition QuestDef.h:224

References _questAreaTriggerStore, Field::Get(), GetAreaTrigger(), getMSTime(), GetMSTimeDiffToNow(), GetQuestTemplate(), Quest::HasSpecialFlag(), LOG_ERROR, LOG_INFO, LOG_WARN, QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT, and WorldDatabase.

◆ LoadQuestGreetings()

void ObjectMgr::LoadQuestGreetings ( )
6925{
6926 uint32 oldMSTime = getMSTime();
6927
6928 _questGreetingStore.clear(); // For reload case
6929
6930 // 0 1 2 3 4
6931 QueryResult result = WorldDatabase.Query("SELECT ID, Type, GreetEmoteType, GreetEmoteDelay, Greeting FROM quest_greeting");
6932 if (!result)
6933 {
6934 LOG_WARN("server.loading", ">> Loaded 0 quest greetings. DB table `quest_greeting` is empty.");
6935 return;
6936 }
6937
6938 do
6939 {
6940 Field* fields = result->Fetch();
6941
6942 uint32 id = fields[0].Get<uint32>();
6943 uint8 type = fields[1].Get<uint8>();
6944 switch (type)
6945 {
6946 case 0: // Creature
6947 if (!GetCreatureTemplate(id))
6948 {
6949 LOG_ERROR("sql.sql", "Table `quest_greeting`: creature template entry {} does not exist.", id);
6950 continue;
6951 }
6952 break;
6953 case 1: // GameObject
6954 if (!GetGameObjectTemplate(id))
6955 {
6956 LOG_ERROR("sql.sql", "Table `quest_greeting`: gameobject template entry {} does not exist.", id);
6957 continue;
6958 }
6959 break;
6960 default:
6961 LOG_ERROR("sql.sql", "Table `quest_greeting` has unknown type {} for id {}, skipped.", type, id);
6962 continue;
6963 }
6964
6965 std::pair<uint32, uint8> pairKey = std::make_pair(id, type);
6966 QuestGreeting& data = _questGreetingStore[pairKey];
6967
6968 data.EmoteType = fields[2].Get<uint16>();
6969 data.EmoteDelay = fields[3].Get<uint32>();
6970 AddLocaleString(fields[4].Get<std::string>(), LOCALE_enUS, data.Greeting);
6971 }
6972 while (result->NextRow());
6973
6974 LOG_INFO("server.loading", ">> Loaded {} quest_greeting in {} ms", _questGreetingStore.size(), GetMSTimeDiffToNow(oldMSTime));
6975 LOG_INFO("server.loading", " ");
6976}
Definition ObjectMgr.h:602
uint32 EmoteDelay
Definition ObjectMgr.h:604
std::vector< std::string > Greeting
Definition ObjectMgr.h:605
uint16 EmoteType
Definition ObjectMgr.h:603

References _questGreetingStore, AddLocaleString(), QuestGreeting::EmoteDelay, QuestGreeting::EmoteType, Field::Get(), GetCreatureTemplate(), GetGameObjectTemplate(), getMSTime(), GetMSTimeDiffToNow(), QuestGreeting::Greeting, LOCALE_enUS, LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadQuestGreetingsLocales()

void ObjectMgr::LoadQuestGreetingsLocales ( )
6979{
6980 uint32 oldMSTime = getMSTime();
6981
6982 // 0 1 2 3
6983 QueryResult result = WorldDatabase.Query("SELECT ID, Type, Locale, Greeting FROM quest_greeting_locale");
6984 if (!result)
6985 {
6986 LOG_WARN("server.loading", ">> Loaded 0 quest_greeting locales. DB table `quest_greeting_locale` is empty.");
6987 return;
6988 }
6989
6990 uint32 localeCount = 0;
6991 do
6992 {
6993 Field* fields = result->Fetch();
6994
6995 uint32 id = fields[0].Get<uint32>();
6996 uint8 type = fields[1].Get<uint8>();
6997 switch (type)
6998 {
6999 case 0: // Creature
7000 if (!GetCreatureTemplate(id))
7001 {
7002 LOG_ERROR("sql.sql", "Table `quest_greeting_locale`: creature template entry {} does not exist.", id);
7003 continue;
7004 }
7005 break;
7006 case 1: // GameObject
7007 if (!GetGameObjectTemplate(id))
7008 {
7009 LOG_ERROR("sql.sql", "Table `quest_greeting_locale`: gameobject template entry {} does not exist.", id);
7010 continue;
7011 }
7012 break;
7013 default:
7014 continue;
7015 }
7016
7017 std::pair<uint32, uint8> pairKey = std::make_pair(id, type);
7018 QuestGreeting& data = _questGreetingStore[pairKey];
7019
7020 QuestGreetingContainer::iterator qgc = _questGreetingStore.find(pairKey);
7021 if (qgc == _questGreetingStore.end())
7022 {
7023 LOG_ERROR("sql.sql", "QuestGreeting (Id: {} Type: {}) found in table `quest_greeting_locale` but does not exist in `quest_greeting`. Skipped!", id, type);
7024 continue;
7025 }
7026
7027 LocaleConstant locale = GetLocaleByName(fields[2].Get<std::string>());
7028 if (locale == LOCALE_enUS)
7029 continue;
7030
7031 AddLocaleString(fields[3].Get<std::string>(), locale, data.Greeting);
7032 localeCount++;
7033 } while (result->NextRow());
7034
7035 LOG_INFO("server.loading", ">> Loaded {} quest greeting Locale Strings in {} ms", localeCount, GetMSTimeDiffToNow(oldMSTime));
7036 LOG_INFO("server.loading", " ");
7037}

References _questGreetingStore, AddLocaleString(), Field::Get(), GetCreatureTemplate(), GetGameObjectTemplate(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), QuestGreeting::Greeting, LOCALE_enUS, LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadQuestLocales()

void ObjectMgr::LoadQuestLocales ( )
5809{
5810 uint32 oldMSTime = getMSTime();
5811
5812 _questLocaleStore.clear(); // need for reload case
5813
5814 // 0 1 2 3 4 5 6 7 8 9 10
5815 QueryResult result = WorldDatabase.Query("SELECT ID, locale, Title, Details, Objectives, EndText, CompletedText, ObjectiveText1, ObjectiveText2, ObjectiveText3, ObjectiveText4 FROM quest_template_locale");
5816
5817 if (!result)
5818 return;
5819
5820 do
5821 {
5822 Field* fields = result->Fetch();
5823
5824 uint32 ID = fields[0].Get<uint32>();
5825
5826 LocaleConstant locale = GetLocaleByName(fields[1].Get<std::string>());
5827 if (locale == LOCALE_enUS)
5828 continue;
5829
5830 QuestLocale& data = _questLocaleStore[ID];
5831 AddLocaleString(fields[2].Get<std::string>(), locale, data.Title);
5832 AddLocaleString(fields[3].Get<std::string>(), locale, data.Details);
5833 AddLocaleString(fields[4].Get<std::string>(), locale, data.Objectives);
5834 AddLocaleString(fields[5].Get<std::string>(), locale, data.AreaDescription);
5835 AddLocaleString(fields[6].Get<std::string>(), locale, data.CompletedText);
5836
5837 for (uint8 i = 0; i < 4; ++i)
5838 AddLocaleString(fields[i + 7].Get<std::string>(), locale, data.ObjectiveText[i]);
5839 } while (result->NextRow());
5840
5841 LOG_INFO("server.loading", ">> Loaded {} Quest Locale Strings in {} ms", (uint32)_questLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
5842}
Definition QuestDef.h:183
std::vector< std::string > AreaDescription
Definition QuestDef.h:191
std::vector< std::string > CompletedText
Definition QuestDef.h:192
std::vector< std::string > Title
Definition QuestDef.h:186
std::vector< std::string > Objectives
Definition QuestDef.h:188
std::vector< std::vector< std::string > > ObjectiveText
Definition QuestDef.h:193
std::vector< std::string > Details
Definition QuestDef.h:187

References _questLocaleStore, AddLocaleString(), QuestLocale::AreaDescription, QuestLocale::CompletedText, QuestLocale::Details, Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, QuestLocale::Objectives, QuestLocale::ObjectiveText, QuestLocale::Title, and WorldDatabase.

◆ LoadQuestMoneyRewards()

void ObjectMgr::LoadQuestMoneyRewards ( )
10947{
10948 uint32 oldMSTime = getMSTime();
10949
10950 _questMoneyRewards.clear();
10951
10952 // 0 1 2 3 4 5 6 7 8 9 10
10953 QueryResult result = WorldDatabase.Query("SELECT `Level`, Money0, Money1, Money2, Money3, Money4, Money5, Money6, Money7, Money8, Money9 FROM `quest_money_reward` ORDER BY `Level`");
10954 if (!result)
10955 {
10956 LOG_WARN("server.loading", ">> Loaded 0 quest money rewards. DB table `quest_money_reward` is empty.");
10957 return;
10958 }
10959
10960 uint32 count = 0;
10961 do
10962 {
10963 Field* fields = result->Fetch();
10964 uint32 Level = fields[0].Get<uint32>();
10965
10966 QuestMoneyRewardArray& questMoneyReward = _questMoneyRewards[Level];
10967 questMoneyReward.fill(0);
10968
10969 for (uint8 i = 0; i < MAX_QUEST_MONEY_REWARDS; ++i)
10970 {
10971 questMoneyReward[i] = fields[1 + i].Get<uint32>();
10972 ++count;
10973 }
10974 } while (result->NextRow());
10975
10976 LOG_INFO("server.loading", ">> Loaded {} Quest Money Rewards in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10977 LOG_INFO("server.loading", " ");
10978}
std::array< uint32, MAX_QUEST_MONEY_REWARDS > QuestMoneyRewardArray
Definition ObjectMgr.h:721

References _questMoneyRewards, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), Level, LOG_INFO, LOG_WARN, MAX_QUEST_MONEY_REWARDS, and WorldDatabase.

◆ LoadQuestOfferRewardLocale()

void ObjectMgr::LoadQuestOfferRewardLocale ( )
7040{
7041 uint32 oldMSTime = getMSTime();
7042
7043 _questOfferRewardLocaleStore.clear(); // need for reload case
7044
7045 // 0 1 2
7046 QueryResult result = WorldDatabase.Query("SELECT Id, locale, RewardText FROM quest_offer_reward_locale");
7047 if (!result)
7048 return;
7049
7050 do
7051 {
7052 Field* fields = result->Fetch();
7053
7054 uint32 id = fields[0].Get<uint32>();
7055 std::string localeName = fields[1].Get<std::string>();
7056
7057 LocaleConstant locale = GetLocaleByName(localeName);
7058 if (locale == LOCALE_enUS)
7059 continue;
7060
7062 AddLocaleString(fields[2].Get<std::string>(), locale, data.RewardText);
7063 } while (result->NextRow());
7064
7065 LOG_INFO("server.loading", ">> Loaded {} Quest Offer Reward Locale Strings in {} ms", _questOfferRewardLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
7066}
Definition QuestDef.h:202
std::vector< std::string > RewardText
Definition QuestDef.h:203

References _questOfferRewardLocaleStore, AddLocaleString(), Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, QuestOfferRewardLocale::RewardText, and WorldDatabase.

◆ LoadQuestPOI()

void ObjectMgr::LoadQuestPOI ( )
8524{
8525 if (!sWorld->getBoolConfig(CONFIG_QUEST_POI_ENABLED))
8526 {
8527 LOG_INFO("server.loading", ">> Loaded 0 quest POI definitions. Disabled by config.");
8528 LOG_INFO("server.loading", " ");
8529 return;
8530 }
8531
8532 uint32 oldMSTime = getMSTime();
8533
8534 _questPOIStore.clear(); // need for reload case
8535
8536 uint32 count = 0;
8537
8538 // 0 1 2 3 4 5 6 7
8539 QueryResult result = WorldDatabase.Query("SELECT QuestID, id, ObjectiveIndex, MapID, WorldMapAreaId, Floor, Priority, Flags FROM quest_poi order by QuestID");
8540
8541 if (!result)
8542 {
8543 LOG_WARN("server.loading", ">> Loaded 0 quest POI definitions. DB table `quest_poi` is empty.");
8544 LOG_INFO("server.loading", " ");
8545 return;
8546 }
8547
8548 // 0 1 2 3
8549 QueryResult points = WorldDatabase.Query("SELECT QuestID, Idx1, X, Y FROM quest_poi_points ORDER BY QuestID DESC, Idx2");
8550
8551 std::vector<std::vector<std::vector<QuestPOIPoint> > > POIs;
8552
8553 if (points)
8554 {
8555 // The first result should have the highest questId
8556 Field* fields = points->Fetch();
8557 uint32 questIdMax = fields[0].Get<uint32>();
8558 POIs.resize(questIdMax + 1);
8559
8560 do
8561 {
8562 fields = points->Fetch();
8563
8564 uint32 questId = fields[0].Get<uint32>();
8565 uint32 id = fields[1].Get<uint32>();
8566 int32 x = fields[2].Get<int32>();
8567 int32 y = fields[3].Get<int32>();
8568
8569 if (POIs[questId].size() <= id + 1)
8570 POIs[questId].resize(id + 10);
8571
8572 QuestPOIPoint point(x, y);
8573 POIs[questId][id].push_back(point);
8574 } while (points->NextRow());
8575 }
8576
8577 do
8578 {
8579 Field* fields = result->Fetch();
8580
8581 uint32 questId = fields[0].Get<uint32>();
8582 uint32 id = fields[1].Get<uint32>();
8583 int32 objIndex = fields[2].Get<int32>();
8584 uint32 mapId = fields[3].Get<uint32>();
8585 uint32 WorldMapAreaId = fields[4].Get<uint32>();
8586 uint32 FloorId = fields[5].Get<uint32>();
8587 uint32 unk3 = fields[6].Get<uint32>();
8588 uint32 unk4 = fields[7].Get<uint32>();
8589
8590 QuestPOI POI(id, objIndex, mapId, WorldMapAreaId, FloorId, unk3, unk4);
8591 if (questId < POIs.size() && id < POIs[questId].size())
8592 {
8593 POI.points = POIs[questId][id];
8594 _questPOIStore[questId].push_back(POI);
8595 }
8596 else
8597 LOG_ERROR("sql.sql", "Table quest_poi references unknown quest points for quest {} POI id {}", questId, id);
8598
8599 ++count;
8600 } while (result->NextRow());
8601
8602 LOG_INFO("server.loading", ">> Loaded {} Quest POI definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8603 LOG_INFO("server.loading", " ");
8604}
@ CONFIG_QUEST_POI_ENABLED
Definition WorldConfig.h:138
Definition ObjectMgr.h:641
Definition ObjectMgr.h:650

References _questPOIStore, CONFIG_QUEST_POI_ENABLED, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sWorld, and WorldDatabase.

◆ LoadQuestRelationsHelper()

void ObjectMgr::LoadQuestRelationsHelper ( QuestRelations map,
std::string const &  table,
bool  starter,
bool  go 
)
private
8707{
8708 uint32 oldMSTime = getMSTime();
8709
8710 map.clear(); // need for reload case
8711
8712 uint32 count = 0;
8713
8714 QueryResult result = WorldDatabase.Query("SELECT id, quest, pool_entry FROM {} qr LEFT JOIN pool_quest pq ON qr.quest = pq.entry", table);
8715
8716 if (!result)
8717 {
8718 LOG_WARN("server.loading", ">> Loaded 0 quest relations from `{}`, table is empty.", table);
8719 LOG_INFO("server.loading", " ");
8720 return;
8721 }
8722
8723 PooledQuestRelation* poolRelationMap = go ? &sPoolMgr->mQuestGORelation : &sPoolMgr->mQuestCreatureRelation;
8724 if (starter)
8725 poolRelationMap->clear();
8726
8727 do
8728 {
8729 uint32 id = result->Fetch()[0].Get<uint32>();
8730 uint32 quest = result->Fetch()[1].Get<uint32>();
8731 uint32 poolId = result->Fetch()[2].Get<uint32>();
8732
8733 if (_questTemplates.find(quest) == _questTemplates.end())
8734 {
8735 LOG_ERROR("sql.sql", "Table `{}`: Quest {} listed for entry {} does not exist.", table, quest, id);
8736 continue;
8737 }
8738
8739 if (!poolId || !starter)
8740 map.insert(QuestRelations::value_type(id, quest));
8741 else if (starter)
8742 poolRelationMap->insert(PooledQuestRelation::value_type(quest, id));
8743
8744 ++count;
8745 } while (result->NextRow());
8746
8747 LOG_INFO("server.loading", ">> Loaded {} Quest Relations From {} in {} ms", count, table, GetMSTimeDiffToNow(oldMSTime));
8748 LOG_INFO("server.loading", " ");
8749}
#define sPoolMgr
Definition PoolMgr.h:165
std::multimap< uint32, uint32 > PooledQuestRelation
Definition PoolMgr.h:98

References _questTemplates, getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, sPoolMgr, and WorldDatabase.

Referenced by LoadCreatureQuestEnders(), LoadCreatureQuestStarters(), LoadGameobjectQuestEnders(), and LoadGameobjectQuestStarters().

◆ LoadQuestRequestItemsLocale()

void ObjectMgr::LoadQuestRequestItemsLocale ( )
7069{
7070 uint32 oldMSTime = getMSTime();
7071
7072 _questRequestItemsLocaleStore.clear(); // need for reload case
7073
7074 // 0 1 2
7075 QueryResult result = WorldDatabase.Query("SELECT Id, locale, CompletionText FROM quest_request_items_locale");
7076 if (!result)
7077 return;
7078
7079 do
7080 {
7081 Field* fields = result->Fetch();
7082
7083 uint32 id = fields[0].Get<uint32>();
7084 std::string localeName = fields[1].Get<std::string>();
7085
7086 LocaleConstant locale = GetLocaleByName(localeName);
7087 if (locale == LOCALE_enUS)
7088 continue;
7089
7091 AddLocaleString(fields[2].Get<std::string>(), locale, data.CompletionText);
7092 } while (result->NextRow());
7093
7094 LOG_INFO("server.loading", ">> Loaded {} Quest Request Items Locale Strings in {} ms", _questRequestItemsLocaleStore.size(), GetMSTimeDiffToNow(oldMSTime));
7095}
Definition QuestDef.h:197
std::vector< std::string > CompletionText
Definition QuestDef.h:198

References _questRequestItemsLocaleStore, AddLocaleString(), QuestRequestItemsLocale::CompletionText, Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), LOCALE_enUS, LOG_INFO, and WorldDatabase.

◆ LoadQuests()

void ObjectMgr::LoadQuests ( )
4999{
5000 uint32 oldMSTime = getMSTime();
5001
5002 // For reload case
5003 for (QuestMap::const_iterator itr = _questTemplates.begin(); itr != _questTemplates.end(); ++itr)
5004 delete itr->second;
5005 _questTemplates.clear();
5006
5007 mExclusiveQuestGroups.clear();
5008
5009 QueryResult result = WorldDatabase.Query("SELECT "
5010 //0 1 2 3 4 5 6 7 8
5011 "ID, QuestType, QuestLevel, MinLevel, QuestSortID, QuestInfoID, SuggestedGroupNum, TimeAllowed, AllowableRaces,"
5012 // 9 10 11 12
5013 "RequiredFactionId1, RequiredFactionId2, RequiredFactionValue1, RequiredFactionValue2, "
5014 // 13 14 15 16 17 18 19 20
5015 "RewardNextQuest, RewardXPDifficulty, RewardMoney, RewardMoneyDifficulty, RewardDisplaySpell, RewardSpell, RewardHonor, RewardKillHonor, "
5016 // 21 22 23 24 25 26
5017 "StartItem, Flags, RewardTitle, RequiredPlayerKills, RewardTalents, RewardArenaPoints, "
5018 // 27 28 29 30 31 32 33 34
5019 "RewardItem1, RewardAmount1, RewardItem2, RewardAmount2, RewardItem3, RewardAmount3, RewardItem4, RewardAmount4, "
5020 // 35 36 37 38 39 40 41 42 43 44 45 46
5021 "RewardChoiceItemID1, RewardChoiceItemQuantity1, RewardChoiceItemID2, RewardChoiceItemQuantity2, RewardChoiceItemID3, RewardChoiceItemQuantity3, RewardChoiceItemID4, RewardChoiceItemQuantity4, RewardChoiceItemID5, RewardChoiceItemQuantity5, RewardChoiceItemID6, RewardChoiceItemQuantity6, "
5022 // 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61
5023 "RewardFactionID1, RewardFactionValue1, RewardFactionOverride1, RewardFactionID2, RewardFactionValue2, RewardFactionOverride2, RewardFactionID3, RewardFactionValue3, RewardFactionOverride3, RewardFactionID4, RewardFactionValue4, RewardFactionOverride4, RewardFactionID5, RewardFactionValue5, RewardFactionOverride5,"
5024 // 61 63 64 65
5025 "POIContinent, POIx, POIy, POIPriority, "
5026 // 66 67 68 69 70
5027 "LogTitle, LogDescription, QuestDescription, AreaDescription, QuestCompletionLog, "
5028 // 71 72 73 74 75 76 77 78
5029 "RequiredNpcOrGo1, RequiredNpcOrGo2, RequiredNpcOrGo3, RequiredNpcOrGo4, RequiredNpcOrGoCount1, RequiredNpcOrGoCount2, RequiredNpcOrGoCount3, RequiredNpcOrGoCount4, "
5030 // 79 80 81 82 83 84 85 86
5031 "ItemDrop1, ItemDrop2, ItemDrop3, ItemDrop4, ItemDropQuantity1, ItemDropQuantity2, ItemDropQuantity3, ItemDropQuantity4, "
5032 // 87 88 89 90 91 92 93 94 95 96 97 98
5033 "RequiredItemId1, RequiredItemId2, RequiredItemId3, RequiredItemId4, RequiredItemId5, RequiredItemId6, RequiredItemCount1, RequiredItemCount2, RequiredItemCount3, RequiredItemCount4, RequiredItemCount5, RequiredItemCount6, "
5034 // 99 100 101 102 103
5035 "Unknown0, ObjectiveText1, ObjectiveText2, ObjectiveText3, ObjectiveText4"
5036 " FROM quest_template");
5037 if (!result)
5038 {
5039 LOG_WARN("server.loading", ">> Loaded 0 quests definitions. DB table `quest_template` is empty.");
5040 LOG_INFO("server.loading", " ");
5041 return;
5042 }
5043
5044 // create multimap previous quest for each existed quest
5045 // some quests can have many previous maps set by NextQuestId in previous quest
5046 // for example set of race quests can lead to single not race specific quest
5047 do
5048 {
5049 Field* fields = result->Fetch();
5050
5051 Quest* newQuest = new Quest(fields);
5052 _questTemplates[newQuest->GetQuestId()] = newQuest;
5053 } while (result->NextRow());
5054
5055 // pussywizard:
5056 {
5057 uint32 max = 0;
5058 for (QuestMap::const_iterator itr = _questTemplates.begin(); itr != _questTemplates.end(); ++itr)
5059 if (itr->first > max)
5060 max = itr->first;
5061 if (max)
5062 {
5063 _questTemplatesFast.clear();
5064 _questTemplatesFast.resize(max + 1, nullptr);
5065 for (QuestMap::iterator itr = _questTemplates.begin(); itr != _questTemplates.end(); ++itr)
5066 _questTemplatesFast[itr->first] = itr->second;
5067 }
5068 }
5069
5070 for (QuestMap::iterator itr = _questTemplates.begin(); itr != _questTemplates.end(); ++itr)
5071 itr->second->InitializeQueryData();
5072
5073 std::map<uint32, uint32> usedMailTemplates;
5074
5075 // Load `quest_details`
5076 // 0 1 2 3 4 5 6 7 8
5077 result = WorldDatabase.Query("SELECT ID, Emote1, Emote2, Emote3, Emote4, EmoteDelay1, EmoteDelay2, EmoteDelay3, EmoteDelay4 FROM quest_details");
5078
5079 if (!result)
5080 {
5081 LOG_WARN("server.loading", ">> Loaded 0 quest details. DB table `quest_details` is empty.");
5082 }
5083 else
5084 {
5085 do
5086 {
5087 Field* fields = result->Fetch();
5088 uint32 questId = fields[0].Get<uint32>();
5089
5090 auto itr = _questTemplates.find(questId);
5091 if (itr != _questTemplates.end())
5092 itr->second->LoadQuestDetails(fields);
5093 else
5094 LOG_ERROR("sql.sql", "Table `quest_details` has data for quest {} but such quest does not exist", questId);
5095 } while (result->NextRow());
5096 }
5097
5098 // Load `quest_request_items`
5099 // 0 1 2 3
5100 result = WorldDatabase.Query("SELECT ID, EmoteOnComplete, EmoteOnIncomplete, CompletionText FROM quest_request_items");
5101
5102 if (!result)
5103 {
5104 LOG_WARN("server.loading", ">> Loaded 0 quest request items. DB table `quest_request_items` is empty.");
5105 }
5106 else
5107 {
5108 do
5109 {
5110 Field* fields = result->Fetch();
5111 uint32 questId = fields[0].Get<uint32>();
5112
5113 auto itr = _questTemplates.find(questId);
5114 if (itr != _questTemplates.end())
5115 itr->second->LoadQuestRequestItems(fields);
5116 else
5117 LOG_ERROR("sql.sql", "Table `quest_request_items` has data for quest {} but such quest does not exist", questId);
5118 } while (result->NextRow());
5119 }
5120
5121 // Load `quest_offer_reward`
5122 // 0 1 2 3 4 5 6 7 8 9
5123 result = WorldDatabase.Query("SELECT ID, Emote1, Emote2, Emote3, Emote4, EmoteDelay1, EmoteDelay2, EmoteDelay3, EmoteDelay4, RewardText FROM quest_offer_reward");
5124
5125 if (!result)
5126 {
5127 LOG_WARN("server.loading", ">> Loaded 0 quest reward emotes. DB table `quest_offer_reward` is empty.");
5128 }
5129 else
5130 {
5131 do
5132 {
5133 Field* fields = result->Fetch();
5134 uint32 questId = fields[0].Get<uint32>();
5135
5136 auto itr = _questTemplates.find(questId);
5137 if (itr != _questTemplates.end())
5138 itr->second->LoadQuestOfferReward(fields);
5139 else
5140 LOG_ERROR("sql.sql", "Table `quest_offer_reward` has data for quest {} but such quest does not exist", questId);
5141 } while (result->NextRow());
5142 }
5143
5144 // Load `quest_template_addon`
5145 // 0 1 2 3 4 5 6 7 8
5146 result = WorldDatabase.Query("SELECT ID, MaxLevel, AllowableClasses, SourceSpellID, PrevQuestID, NextQuestID, ExclusiveGroup, BreadcrumbForQuestId, RewardMailTemplateID, "
5147 //9 10 11 12 13 14 15 16 17 18
5148 "RewardMailDelay, RequiredSkillID, RequiredSkillPoints, RequiredMinRepFaction, RequiredMaxRepFaction, RequiredMinRepValue, RequiredMaxRepValue, ProvidedItemCount, RewardMailSenderEntry, SpecialFlags FROM quest_template_addon LEFT JOIN quest_mail_sender ON Id=QuestId");
5149
5150 if (!result)
5151 {
5152 LOG_WARN("server.loading", ">> Loaded 0 quest template addons. DB table `quest_template_addon` is empty.");
5153 }
5154 else
5155 {
5156 do
5157 {
5158 Field* fields = result->Fetch();
5159 uint32 questId = fields[0].Get<uint32>();
5160
5161 auto itr = _questTemplates.find(questId);
5162 if (itr != _questTemplates.end())
5163 itr->second->LoadQuestTemplateAddon(fields);
5164 else
5165 LOG_ERROR("sql.sql", "Table `quest_template_addon` has data for quest {} but such quest does not exist", questId);
5166 } while (result->NextRow());
5167 }
5168
5169 // Post processing
5170 for (QuestMap::iterator iter = _questTemplates.begin(); iter != _questTemplates.end(); ++iter)
5171 {
5172 // skip post-loading checks for disabled quests
5173 if (sDisableMgr->IsDisabledFor(DISABLE_TYPE_QUEST, iter->first, nullptr))
5174 continue;
5175
5176 Quest* qinfo = iter->second;
5177
5178 // additional quest integrity checks (GO, creature_template and item_template must be loaded already)
5179
5180 if (qinfo->GetQuestMethod() >= 3)
5181 LOG_ERROR("sql.sql", "Quest {} has `Method` = {}, expected values are 0, 1 or 2.", qinfo->GetQuestId(), qinfo->GetQuestMethod());
5182
5184 {
5185 LOG_ERROR("sql.sql", "Quest {} has `SpecialFlags` = {} > max allowed value. Correct `SpecialFlags` to value <= {}",
5188 }
5189
5190 if (qinfo->Flags & QUEST_FLAGS_DAILY && qinfo->Flags & QUEST_FLAGS_WEEKLY)
5191 {
5192 LOG_ERROR("sql.sql", "Weekly Quest {} is marked as daily quest in `Flags`, removed daily flag.", qinfo->GetQuestId());
5193 qinfo->Flags &= ~QUEST_FLAGS_DAILY;
5194 }
5195
5196 if (qinfo->Flags & QUEST_FLAGS_DAILY)
5197 {
5199 {
5200 LOG_ERROR("sql.sql", "Daily Quest {} not marked as repeatable in `SpecialFlags`, added.", qinfo->GetQuestId());
5202 }
5203 }
5204
5205 if (qinfo->Flags & QUEST_FLAGS_WEEKLY)
5206 {
5208 {
5209 LOG_ERROR("sql.sql", "Weekly Quest {} not marked as repeatable in `SpecialFlags`, added.", qinfo->GetQuestId());
5211 }
5212 }
5213
5215 {
5217 {
5218 LOG_ERROR("sql.sql", "Monthly quest {} not marked as repeatable in `SpecialFlags`, added.", qinfo->GetQuestId());
5220 }
5221 }
5222
5223 if (qinfo->Flags & QUEST_FLAGS_TRACKING)
5224 {
5225 // at auto-reward can be rewarded only RewardChoiceItemId[0]
5226 for (int j = 1; j < QUEST_REWARD_CHOICES_COUNT; ++j )
5227 {
5228 if (uint32 id = qinfo->RewardChoiceItemId[j])
5229 {
5230 LOG_ERROR("sql.sql", "Quest {} has `RewardChoiceItemId{}` = {} but item from `RewardChoiceItemId{}` can't be rewarded with quest flag QUEST_FLAGS_TRACKING.",
5231 qinfo->GetQuestId(), j + 1, id, j + 1);
5232 // no changes, quest ignore this data
5233 }
5234 }
5235 }
5236
5237 // client quest log visual (area case)
5238 if (qinfo->ZoneOrSort > 0)
5239 {
5240 if (!sAreaTableStore.LookupEntry(qinfo->ZoneOrSort))
5241 {
5242 LOG_ERROR("sql.sql", "Quest {} has `ZoneOrSort` = {} (zone case) but zone with this id does not exist.",
5243 qinfo->GetQuestId(), qinfo->ZoneOrSort);
5244 // no changes, quest not dependent from this value but can have problems at client
5245 }
5246 }
5247 // client quest log visual (sort case)
5248 if (qinfo->ZoneOrSort < 0)
5249 {
5250 QuestSortEntry const* qSort = sQuestSortStore.LookupEntry(-int32(qinfo->ZoneOrSort));
5251 if (!qSort)
5252 {
5253 LOG_ERROR("sql.sql", "Quest {} has `ZoneOrSort` = {} (sort case) but quest sort with this id does not exist.",
5254 qinfo->GetQuestId(), qinfo->ZoneOrSort);
5255 // no changes, quest not dependent from this value but can have problems at client (note some may be 0, we must allow this so no check)
5256 }
5257 //check for proper RequiredSkillId value (skill case)
5258 if (uint32 skill_id = SkillByQuestSort(-int32(qinfo->ZoneOrSort)))
5259 {
5260 if (qinfo->RequiredSkillId != skill_id)
5261 {
5262 LOG_ERROR("sql.sql", "Quest {} has `ZoneOrSort` = {} but `RequiredSkillId` does not have a corresponding value ({}).",
5263 qinfo->GetQuestId(), qinfo->ZoneOrSort, skill_id);
5264 //override, and force proper value here?
5265 }
5266 }
5267 }
5268
5269 // RequiredClasses, can be 0/CLASSMASK_ALL_PLAYABLE to allow any class
5270 if (qinfo->RequiredClasses)
5271 {
5273 {
5274 LOG_ERROR("sql.sql", "Quest {} does not contain any playable classes in `RequiredClasses` ({}), value set to 0 (all classes).", qinfo->GetQuestId(), qinfo->RequiredClasses);
5275 qinfo->RequiredClasses = 0;
5276 }
5277 }
5278 // AllowableRaces, can be 0/PlayableRaceMask to allow any race
5279 if (qinfo->AllowableRaces)
5280 {
5281 if (!(qinfo->AllowableRaces & sRaceMgr->GetPlayableRaceMask()))
5282 {
5283 LOG_ERROR("sql.sql", "Quest {} does not contain any playable races in `AllowableRaces` ({}), value set to 0 (all races).", qinfo->GetQuestId(), qinfo->AllowableRaces);
5284 qinfo->AllowableRaces = 0;
5285 }
5286 }
5287 // RequiredSkillId, can be 0
5288 if (qinfo->RequiredSkillId)
5289 {
5290 if (!sSkillLineStore.LookupEntry(qinfo->RequiredSkillId))
5291 {
5292 LOG_ERROR("sql.sql", "Quest {} has `RequiredSkillId` = {} but this skill does not exist",
5293 qinfo->GetQuestId(), qinfo->RequiredSkillId);
5294 }
5295 }
5296
5297 if (qinfo->RequiredSkillPoints)
5298 {
5299 if (qinfo->RequiredSkillPoints > sWorld->GetConfigMaxSkillValue())
5300 {
5301 LOG_ERROR("sql.sql", "Quest {} has `RequiredSkillPoints` = {} but max possible skill is {}, quest can't be done.",
5302 qinfo->GetQuestId(), qinfo->RequiredSkillPoints, sWorld->GetConfigMaxSkillValue());
5303 // no changes, quest can't be done for this requirement
5304 }
5305 }
5306 // else Skill quests can have 0 skill level, this is ok
5307
5308 if (qinfo->RequiredFactionId2 && !sFactionStore.LookupEntry(qinfo->RequiredFactionId2))
5309 {
5310 LOG_ERROR("sql.sql", "Quest {} has `RequiredFactionId2` = {} but faction template {} does not exist, quest can't be done.",
5311 qinfo->GetQuestId(), qinfo->RequiredFactionId2, qinfo->RequiredFactionId2);
5312 // no changes, quest can't be done for this requirement
5313 }
5314
5315 if (qinfo->RequiredFactionId1 && !sFactionStore.LookupEntry(qinfo->RequiredFactionId1))
5316 {
5317 LOG_ERROR("sql.sql", "Quest {} has `RequiredFactionId1` = {} but faction template {} does not exist, quest can't be done.",
5318 qinfo->GetQuestId(), qinfo->RequiredFactionId1, qinfo->RequiredFactionId1);
5319 // no changes, quest can't be done for this requirement
5320 }
5321
5322 if (qinfo->RequiredMinRepFaction && !sFactionStore.LookupEntry(qinfo->RequiredMinRepFaction))
5323 {
5324 LOG_ERROR("sql.sql", "Quest {} has `RequiredMinRepFaction` = {} but faction template {} does not exist, quest can't be done.",
5325 qinfo->GetQuestId(), qinfo->RequiredMinRepFaction, qinfo->RequiredMinRepFaction);
5326 // no changes, quest can't be done for this requirement
5327 }
5328
5329 if (qinfo->RequiredMaxRepFaction && !sFactionStore.LookupEntry(qinfo->RequiredMaxRepFaction))
5330 {
5331 LOG_ERROR("sql.sql", "Quest {} has `RequiredMaxRepFaction` = {} but faction template {} does not exist, quest can't be done.",
5332 qinfo->GetQuestId(), qinfo->RequiredMaxRepFaction, qinfo->RequiredMaxRepFaction);
5333 // no changes, quest can't be done for this requirement
5334 }
5335
5337 {
5338 LOG_ERROR("sql.sql", "Quest {} has `RequiredMinRepValue` = {} but max reputation is {}, quest can't be done.",
5340 // no changes, quest can't be done for this requirement
5341 }
5342
5343 if (qinfo->RequiredMinRepValue && qinfo->RequiredMaxRepValue && qinfo->RequiredMaxRepValue <= qinfo->RequiredMinRepValue)
5344 {
5345 LOG_ERROR("sql.sql", "Quest {} has `RequiredMaxRepValue` = {} and `RequiredMinRepValue` = {}, quest can't be done.",
5346 qinfo->GetQuestId(), qinfo->RequiredMaxRepValue, qinfo->RequiredMinRepValue);
5347 // no changes, quest can't be done for this requirement
5348 }
5349
5350 if (!qinfo->RequiredFactionId1 && qinfo->RequiredFactionValue1 != 0)
5351 {
5352 LOG_ERROR("sql.sql", "Quest {} has `RequiredFactionValue1` = {} but `RequiredFactionId1` is 0, value has no effect",
5353 qinfo->GetQuestId(), qinfo->RequiredFactionValue1);
5354 // warning
5355 }
5356
5357 if (!qinfo->RequiredFactionId2 && qinfo->RequiredFactionValue2 != 0)
5358 {
5359 LOG_ERROR("sql.sql", "Quest {} has `RequiredFactionValue2` = {} but `RequiredFactionId2` is 0, value has no effect",
5360 qinfo->GetQuestId(), qinfo->RequiredFactionValue2);
5361 // warning
5362 }
5363
5364 if (!qinfo->RequiredMinRepFaction && qinfo->RequiredMinRepValue != 0)
5365 {
5366 LOG_ERROR("sql.sql", "Quest {} has `RequiredMinRepValue` = {} but `RequiredMinRepFaction` is 0, value has no effect",
5367 qinfo->GetQuestId(), qinfo->RequiredMinRepValue);
5368 // warning
5369 }
5370
5371 if (!qinfo->RequiredMaxRepFaction && qinfo->RequiredMaxRepValue != 0)
5372 {
5373 LOG_ERROR("sql.sql", "Quest {} has `RequiredMaxRepValue` = {} but `RequiredMaxRepFaction` is 0, value has no effect",
5374 qinfo->GetQuestId(), qinfo->RequiredMaxRepValue);
5375 // warning
5376 }
5377
5378 if (qinfo->RewardTitleId && !sCharTitlesStore.LookupEntry(qinfo->RewardTitleId))
5379 {
5380 LOG_ERROR("sql.sql", "Quest {} has `RewardTitleId` = {} but CharTitle Id {} does not exist, quest can't be rewarded with title.",
5381 qinfo->GetQuestId(), qinfo->GetCharTitleId(), qinfo->GetCharTitleId());
5382 qinfo->RewardTitleId = 0;
5383 // quest can't reward this title
5384 }
5385
5386 if (qinfo->StartItem)
5387 {
5388 if (!GetItemTemplate(qinfo->StartItem))
5389 {
5390 LOG_ERROR("sql.sql", "Quest {} has `StartItem` = {} but item with entry {} does not exist, quest can't be done.",
5391 qinfo->GetQuestId(), qinfo->StartItem, qinfo->StartItem);
5392 qinfo->StartItem = 0; // quest can't be done for this requirement
5393 }
5394 else if (qinfo->StartItemCount == 0)
5395 {
5396 LOG_ERROR("sql.sql", "Quest {} has `StartItem` = {} but `StartItemCount` = 0, set to 1 but need fix in DB.",
5397 qinfo->GetQuestId(), qinfo->StartItem);
5398 qinfo->StartItemCount = 1; // update to 1 for allow quest work for backward compatibility with DB
5399 }
5400 }
5401 else if (qinfo->StartItemCount > 0)
5402 {
5403 LOG_ERROR("sql.sql", "Quest {} has `StartItem` = 0 but `StartItemCount` = {}, useless value.",
5404 qinfo->GetQuestId(), qinfo->StartItemCount);
5405 qinfo->StartItemCount = 0; // no quest work changes in fact
5406 }
5407
5408 if (qinfo->SourceSpellid)
5409 {
5410 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(qinfo->SourceSpellid);
5411 if (!spellInfo)
5412 {
5413 LOG_ERROR("sql.sql", "Quest {} has `SourceSpellid` = {} but spell {} doesn't exist, quest can't be done.",
5414 qinfo->GetQuestId(), qinfo->SourceSpellid, qinfo->SourceSpellid);
5415 qinfo->SourceSpellid = 0; // quest can't be done for this requirement
5416 }
5417 else if (!SpellMgr::ComputeIsSpellValid(spellInfo))
5418 {
5419 LOG_ERROR("sql.sql", "Quest {} has `SourceSpellid` = {} but spell {} is broken, quest can't be done.",
5420 qinfo->GetQuestId(), qinfo->SourceSpellid, qinfo->SourceSpellid);
5421 qinfo->SourceSpellid = 0; // quest can't be done for this requirement
5422 }
5423 }
5424
5425 for (uint8 j = 0; j < QUEST_ITEM_OBJECTIVES_COUNT; ++j)
5426 {
5427 uint32 id = qinfo->RequiredItemId[j];
5428 if (id)
5429 {
5430 if (qinfo->RequiredItemCount[j] == 0)
5431 {
5432 LOG_ERROR("sql.sql", "Quest {} has `RequiredItemId{}` = {} but `RequiredItemCount{}` = 0, quest can't be done.",
5433 qinfo->GetQuestId(), j + 1, id, j + 1);
5434 // no changes, quest can't be done for this requirement
5435 }
5436
5438
5439 if (!GetItemTemplate(id))
5440 {
5441 LOG_ERROR("sql.sql", "Quest {} has `RequiredItemId{}` = {} but item with entry {} does not exist, quest can't be done.",
5442 qinfo->GetQuestId(), j + 1, id, id);
5443 qinfo->RequiredItemCount[j] = 0; // prevent incorrect work of quest
5444 }
5445 }
5446 else if (qinfo->RequiredItemCount[j] > 0)
5447 {
5448 LOG_ERROR("sql.sql", "Quest {} has `RequiredItemId{}` = 0 but `RequiredItemCount{}` = {}, quest can't be done.",
5449 qinfo->GetQuestId(), j + 1, j + 1, qinfo->RequiredItemCount[j]);
5450 qinfo->RequiredItemCount[j] = 0; // prevent incorrect work of quest
5451 }
5452 }
5453
5454 for (uint8 j = 0; j < QUEST_SOURCE_ITEM_IDS_COUNT; ++j)
5455 {
5456 uint32 id = qinfo->ItemDrop[j];
5457 if (id)
5458 {
5459 if (!GetItemTemplate(id))
5460 {
5461 LOG_ERROR("sql.sql", "Quest {} has `ItemDrop{}` = {} but item with entry {} does not exist, quest can't be done.",
5462 qinfo->GetQuestId(), j + 1, id, id);
5463 // no changes, quest can't be done for this requirement
5464 }
5465 }
5466 else
5467 {
5468 if (qinfo->ItemDropQuantity[j] > 0)
5469 {
5470 LOG_ERROR("sql.sql", "Quest {} has `ItemDrop{}` = 0 but `ItemDropQuantity{}` = {}.",
5471 qinfo->GetQuestId(), j + 1, j + 1, qinfo->ItemDropQuantity[j]);
5472 // no changes, quest ignore this data
5473 }
5474 }
5475 }
5476
5477 for (uint8 j = 0; j < QUEST_OBJECTIVES_COUNT; ++j)
5478 {
5479 int32 id = qinfo->RequiredNpcOrGo[j];
5480 if (id < 0 && !GetGameObjectTemplate(-id))
5481 {
5482 LOG_ERROR("sql.sql", "Quest {} has `RequiredNpcOrGo{}` = {} but gameobject {} does not exist, quest can't be done.",
5483 qinfo->GetQuestId(), j + 1, id, uint32(-id));
5484 qinfo->RequiredNpcOrGo[j] = 0; // quest can't be done for this requirement
5485 }
5486
5487 if (id > 0 && !GetCreatureTemplate(id))
5488 {
5489 LOG_ERROR("sql.sql", "Quest {} has `RequiredNpcOrGo{}` = {} but creature with entry {} does not exist, quest can't be done.",
5490 qinfo->GetQuestId(), j + 1, id, uint32(id));
5491 qinfo->RequiredNpcOrGo[j] = 0; // quest can't be done for this requirement
5492 }
5493
5494 if (id)
5495 {
5496 // In fact SpeakTo and Kill are quite same: either you can speak to mob:SpeakTo or you can't:Kill/Cast
5497
5499
5500 if (!qinfo->RequiredNpcOrGoCount[j])
5501 {
5502 LOG_ERROR("sql.sql", "Quest {} has `RequiredNpcOrGo{}` = {} but `RequiredNpcOrGoCount{}` = 0, quest can't be done.",
5503 qinfo->GetQuestId(), j + 1, id, j + 1);
5504 // no changes, quest can be incorrectly done, but we already report this
5505 }
5506 }
5507 else if (qinfo->RequiredNpcOrGoCount[j] > 0)
5508 {
5509 LOG_ERROR("sql.sql", "Quest {} has `RequiredNpcOrGo{}` = 0 but `RequiredNpcOrGoCount{}` = {}.",
5510 qinfo->GetQuestId(), j + 1, j + 1, qinfo->RequiredNpcOrGoCount[j]);
5511 // no changes, quest ignore this data
5512 }
5513 }
5514
5515 for (uint8 j = 0; j < QUEST_REWARD_CHOICES_COUNT; ++j)
5516 {
5517 uint32 id = qinfo->RewardChoiceItemId[j];
5518 if (id)
5519 {
5520 if (!GetItemTemplate(id))
5521 {
5522 LOG_ERROR("sql.sql", "Quest {} has `RewardChoiceItemId{}` = {} but item with entry {} does not exist, quest will not reward this item.",
5523 qinfo->GetQuestId(), j + 1, id, id);
5524 qinfo->RewardChoiceItemId[j] = 0; // no changes, quest will not reward this
5525 }
5526
5527 if (!qinfo->RewardChoiceItemCount[j])
5528 {
5529 LOG_ERROR("sql.sql", "Quest {} has `RewardChoiceItemId{}` = {} but `RewardChoiceItemCount{}` = 0, quest can't be done.",
5530 qinfo->GetQuestId(), j + 1, id, j + 1);
5531 // no changes, quest can't be done
5532 }
5533 }
5534 else if (qinfo->RewardChoiceItemCount[j] > 0)
5535 {
5536 LOG_ERROR("sql.sql", "Quest {} has `RewardChoiceItemId{}` = 0 but `RewardChoiceItemCount{}` = {}.",
5537 qinfo->GetQuestId(), j + 1, j + 1, qinfo->RewardChoiceItemCount[j]);
5538 // no changes, quest ignore this data
5539 }
5540 }
5541
5542 for (uint8 j = 0; j < QUEST_REWARDS_COUNT; ++j)
5543 {
5544 if (!qinfo->RewardItemId[0] && qinfo->RewardItemId[j])
5545 {
5546 LOG_ERROR("sql.sql", "Quest {} has no `RewardItemId1` but has `RewardItem{}`. Reward item will not be loaded.",
5547 qinfo->GetQuestId(), j + 1);
5548 }
5549 if (!qinfo->RewardItemId[1] && j > 1 && qinfo->RewardItemId[j])
5550 {
5551 LOG_ERROR("sql.sql", "Quest {} has no `RewardItemId2` but has `RewardItem{}`. Reward item will not be loaded.",
5552 qinfo->GetQuestId(), j + 1);
5553 }
5554 if (!qinfo->RewardItemId[2] && j > 2 && qinfo->RewardItemId[j])
5555 {
5556 LOG_ERROR("sql.sql", "Quest {} has no `RewardItemId3` but has `RewardItem{}`. Reward item will not be loaded.",
5557 qinfo->GetQuestId(), j + 1);
5558 }
5559 }
5560
5561 for (uint8 j = 0; j < QUEST_REWARDS_COUNT; ++j)
5562 {
5563 uint32 id = qinfo->RewardItemId[j];
5564 if (id)
5565 {
5566 if (!GetItemTemplate(id))
5567 {
5568 LOG_ERROR("sql.sql", "Quest {} has `RewardItemId{}` = {} but item with entry {} does not exist, quest will not reward this item.",
5569 qinfo->GetQuestId(), j + 1, id, id);
5570 qinfo->RewardItemId[j] = 0; // no changes, quest will not reward this item
5571 }
5572
5573 if (!qinfo->RewardItemIdCount[j])
5574 {
5575 LOG_ERROR("sql.sql", "Quest {} has `RewardItemId{}` = {} but `RewardItemIdCount{}` = 0, quest will not reward this item.",
5576 qinfo->GetQuestId(), j + 1, id, j + 1);
5577 // no changes
5578 }
5579 }
5580 else if (qinfo->RewardItemIdCount[j] > 0)
5581 {
5582 LOG_ERROR("sql.sql", "Quest {} has `RewardItemId{}` = 0 but `RewardItemIdCount{}` = {}.",
5583 qinfo->GetQuestId(), j + 1, j + 1, qinfo->RewardItemIdCount[j]);
5584 // no changes, quest ignore this data
5585 }
5586 }
5587
5588 for (uint8 j = 0; j < QUEST_REPUTATIONS_COUNT; ++j)
5589 {
5590 if (qinfo->RewardFactionId[j])
5591 {
5592 if (std::abs(qinfo->RewardFactionValueId[j]) > 9)
5593 {
5594 LOG_ERROR("sql.sql", "Quest {} has RewardFactionValueId{} = {}. That is outside the range of valid values (-9 to 9).", qinfo->GetQuestId(), j + 1, qinfo->RewardFactionValueId[j]);
5595 }
5596 if (!sFactionStore.LookupEntry(qinfo->RewardFactionId[j]))
5597 {
5598 LOG_ERROR("sql.sql", "Quest {} has `RewardFactionId{}` = {} but raw faction (faction.dbc) {} does not exist, quest will not reward reputation for this faction.", qinfo->GetQuestId(), j + 1, qinfo->RewardFactionId[j], qinfo->RewardFactionId[j]);
5599 qinfo->RewardFactionId[j] = 0; // quest will not reward this
5600 }
5601 }
5602
5603 else if (qinfo->RewardFactionValueIdOverride[j] != 0)
5604 {
5605 LOG_ERROR("sql.sql", "Quest {} has `RewardFactionId{}` = 0 but `RewardFactionValueIdOverride{}` = {}.",
5606 qinfo->GetQuestId(), j + 1, j + 1, qinfo->RewardFactionValueIdOverride[j]);
5607 // no changes, quest ignore this data
5608 }
5609 }
5610
5611 if (qinfo->RewardDisplaySpell)
5612 {
5613 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(qinfo->RewardDisplaySpell);
5614
5615 if (!spellInfo)
5616 {
5617 LOG_ERROR("sql.sql", "Quest {} has `RewardDisplaySpell` = {} but spell {} does not exist, spell removed as display reward.",
5618 qinfo->GetQuestId(), qinfo->RewardDisplaySpell, qinfo->RewardDisplaySpell);
5619 qinfo->RewardDisplaySpell = 0; // no spell reward will display for this quest
5620 }
5621
5622 else if (!SpellMgr::ComputeIsSpellValid(spellInfo))
5623 {
5624 LOG_ERROR("sql.sql", "Quest {} has `RewardDisplaySpell` = {} but spell {} is broken, quest will not have a spell reward.",
5625 qinfo->GetQuestId(), qinfo->RewardDisplaySpell, qinfo->RewardDisplaySpell);
5626 qinfo->RewardDisplaySpell = 0; // no spell reward will display for this quest
5627 }
5628
5629 else if (GetTalentSpellCost(qinfo->RewardDisplaySpell))
5630 {
5631 LOG_ERROR("sql.sql", "Quest {} has `RewardDisplaySpell` = {} but spell {} is talent, quest will not have a spell reward.",
5632 qinfo->GetQuestId(), qinfo->RewardDisplaySpell, qinfo->RewardDisplaySpell);
5633 qinfo->RewardDisplaySpell = 0; // no spell reward will display for this quest
5634 }
5635 }
5636
5637 if (qinfo->RewardSpell > 0)
5638 {
5639 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(qinfo->RewardSpell);
5640
5641 if (!spellInfo)
5642 {
5643 LOG_ERROR("sql.sql", "Quest {} has `RewardSpell` = {} but spell {} does not exist, quest will not have a spell reward.",
5644 qinfo->GetQuestId(), qinfo->RewardSpell, qinfo->RewardSpell);
5645 qinfo->RewardSpell = 0; // no spell will be casted on player
5646 }
5647
5648 else if (!SpellMgr::ComputeIsSpellValid(spellInfo))
5649 {
5650 LOG_ERROR("sql.sql", "Quest {} has `RewardSpell` = {} but spell {} is broken, quest will not have a spell reward.",
5651 qinfo->GetQuestId(), qinfo->RewardSpell, qinfo->RewardSpell);
5652 qinfo->RewardSpell = 0; // no spell will be casted on player
5653 }
5654
5655 else if (GetTalentSpellCost(qinfo->RewardSpell))
5656 {
5657 LOG_ERROR("sql.sql", "Quest {} has `RewardDisplaySpell` = {} but spell {} is talent, quest will not have a spell reward.",
5658 qinfo->GetQuestId(), qinfo->RewardSpell, qinfo->RewardSpell);
5659 qinfo->RewardSpell = 0; // no spell will be casted on player
5660 }
5661 }
5662
5663 if (qinfo->RewardMailTemplateId)
5664 {
5665 if (!sMailTemplateStore.LookupEntry(qinfo->RewardMailTemplateId))
5666 {
5667 LOG_ERROR("sql.sql", "Quest {} has `RewardMailTemplateId` = {} but mail template {} does not exist, quest will not have a mail reward.",
5668 qinfo->GetQuestId(), qinfo->RewardMailTemplateId, qinfo->RewardMailTemplateId);
5669 qinfo->RewardMailTemplateId = 0; // no mail will send to player
5670 qinfo->RewardMailDelay = 0; // no mail will send to player
5671 qinfo->RewardMailSenderEntry = 0;
5672 }
5673 else if (usedMailTemplates.find(qinfo->RewardMailTemplateId) != usedMailTemplates.end())
5674 {
5675 std::map<uint32, uint32>::const_iterator used_mt_itr = usedMailTemplates.find(qinfo->RewardMailTemplateId);
5676 LOG_ERROR("sql.sql", "Quest {} has `RewardMailTemplateId` = {} but mail template {} already used for quest {}, quest will not have a mail reward.",
5677 qinfo->GetQuestId(), qinfo->RewardMailTemplateId, qinfo->RewardMailTemplateId, used_mt_itr->second);
5678 qinfo->RewardMailTemplateId = 0; // no mail will send to player
5679 qinfo->RewardMailDelay = 0; // no mail will send to player
5680 qinfo->RewardMailSenderEntry = 0;
5681 }
5682 else
5683 usedMailTemplates[qinfo->RewardMailTemplateId] = qinfo->GetQuestId();
5684 }
5685
5686 if (qinfo->RewardNextQuest)
5687 {
5688 QuestMap::iterator qNextItr = _questTemplates.find(qinfo->RewardNextQuest);
5689 if (qNextItr == _questTemplates.end())
5690 {
5691 LOG_ERROR("sql.sql", "Quest {} has `RewardNextQuest` = {} but quest {} does not exist, quest chain will not work.",
5692 qinfo->GetQuestId(), qinfo->RewardNextQuest, qinfo->RewardNextQuest);
5693 qinfo->RewardNextQuest = 0;
5694 }
5695 else
5696 qNextItr->second->prevChainQuests.push_back(qinfo->GetQuestId());
5697 }
5698
5699 // fill additional data stores
5700 if (qinfo->PrevQuestId)
5701 {
5702 if (_questTemplates.find(std::abs(qinfo->GetPrevQuestId())) == _questTemplates.end())
5703 {
5704 LOG_ERROR("sql.sql", "Quest {} has PrevQuestId {}, but no such quest", qinfo->GetQuestId(), qinfo->GetPrevQuestId());
5705 }
5706 else
5707 {
5708 qinfo->prevQuests.push_back(qinfo->PrevQuestId);
5709 }
5710 }
5711
5712 if (qinfo->NextQuestId)
5713 {
5714 QuestMap::iterator qNextItr = _questTemplates.find(qinfo->GetNextQuestId());
5715 if (qNextItr == _questTemplates.end())
5716 {
5717 LOG_ERROR("sql.sql", "Quest {} has NextQuestId {}, but no such quest", qinfo->GetQuestId(), qinfo->GetNextQuestId());
5718 }
5719 else
5720 qNextItr->second->prevQuests.push_back(static_cast<int32>(qinfo->GetQuestId()));
5721 }
5722
5723 if (qinfo->ExclusiveGroup)
5724 mExclusiveQuestGroups.insert(std::pair<int32, uint32>(qinfo->ExclusiveGroup, qinfo->GetQuestId()));
5725
5726 if (uint32 breadcrumbForQuestId = qinfo->GetBreadcrumbForQuestId())
5727 {
5728 if (_questTemplates.find(breadcrumbForQuestId) == _questTemplates.end())
5729 LOG_ERROR("sql.sql", "Quest {} has BreadcrumbForQuestId {}, but no such quest exists", qinfo->GetQuestId(), breadcrumbForQuestId);
5730 else
5731 _breadcrumbsForQuest[breadcrumbForQuestId].push_back(qinfo->GetQuestId());
5732
5733 if (qinfo->GetNextQuestId())
5734 LOG_ERROR("sql.sql", "Quest {} is a breadcrumb quest but also has NextQuestID {} set", qinfo->GetQuestId(), qinfo->GetNextQuestId());
5735 if (qinfo->GetExclusiveGroup())
5736 LOG_ERROR("sql.sql", "Quest {} is a breadcrumb quest but also has ExclusiveGroup {} set", qinfo->GetQuestId(), qinfo->GetExclusiveGroup());
5737 }
5738
5739 if (qinfo->TimeAllowed)
5741 if (qinfo->RequiredPlayerKills)
5743 }
5744
5745 for (auto const& [questId, quest] : _questTemplates)
5746 {
5747 if (sDisableMgr->IsDisabledFor(DISABLE_TYPE_QUEST, questId, nullptr))
5748 continue;
5749
5750 uint32 breadcrumbForQuestId = quest->GetBreadcrumbForQuestId();
5751 if (!breadcrumbForQuestId)
5752 continue;
5753
5754 std::set<uint32> visitedQuests;
5755 visitedQuests.insert(questId);
5756
5757 while (breadcrumbForQuestId)
5758 {
5759 if (!visitedQuests.insert(breadcrumbForQuestId).second)
5760 {
5761 LOG_ERROR("sql.sql", "Breadcrumb quests {} and {} form a loop", questId, breadcrumbForQuestId);
5762 break;
5763 }
5764
5765 Quest const* targetQuest = GetQuestTemplate(breadcrumbForQuestId);
5766 if (!targetQuest)
5767 break;
5768
5769 breadcrumbForQuestId = targetQuest->GetBreadcrumbForQuestId();
5770 }
5771 }
5772
5773 // check QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT for spell with SPELL_EFFECT_QUEST_COMPLETE
5774 for (uint32 i = 0; i < sSpellMgr->GetSpellInfoStoreSize(); ++i)
5775 {
5776 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(i);
5777 if (!spellInfo)
5778 continue;
5779
5780 for (uint8 j = 0; j < MAX_SPELL_EFFECTS; ++j)
5781 {
5782 if (spellInfo->Effects[j].Effect != SPELL_EFFECT_QUEST_COMPLETE)
5783 continue;
5784
5785 uint32 quest_id = spellInfo->Effects[j].MiscValue;
5786
5787 Quest const* quest = GetQuestTemplate(quest_id);
5788
5789 // some quest referenced in spells not exist (outdated spells)
5790 if (!quest)
5791 continue;
5792
5794 {
5795 LOG_ERROR("sql.sql", "Spell (id: {}) have SPELL_EFFECT_QUEST_COMPLETE for quest {}, but quest not have specialflag QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT. Quest flags must be fixed, quest modified to enable objective.", spellInfo->Id, quest_id);
5796
5797 // this will prevent quest completing without objective
5798 // xinef: remove this, leave error but do not break the quest
5799 // const_cast<Quest*>(quest)->SetSpecialFlag(QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT);
5800 }
5801 }
5802 }
5803
5804 LOG_INFO("server.loading", ">> Loaded {} Quests Definitions in {} ms", (unsigned long)_questTemplates.size(), GetMSTimeDiffToNow(oldMSTime));
5805 LOG_INFO("server.loading", " ");
5806}
uint32 GetTalentSpellCost(uint32 spellId)
Definition DBCStores.cpp:686
DBCStorage< QuestSortEntry > sQuestSortStore(QuestSortEntryfmt)
@ DISABLE_TYPE_QUEST
Definition DisableMgr.h:29
#define QUEST_REWARDS_COUNT
Definition QuestDef.h:39
#define QUEST_ITEM_OBJECTIVES_COUNT
Definition QuestDef.h:36
#define QUEST_OBJECTIVES_COUNT
Definition QuestDef.h:35
@ QUEST_FLAGS_TRACKING
Definition QuestDef.h:142
@ QUEST_FLAGS_DAILY
Definition QuestDef.h:144
@ QUEST_FLAGS_WEEKLY
Definition QuestDef.h:147
#define QUEST_REPUTATIONS_COUNT
Definition QuestDef.h:41
#define QUEST_SOURCE_ITEM_IDS_COUNT
Definition QuestDef.h:37
#define QUEST_REWARD_CHOICES_COUNT
Definition QuestDef.h:38
@ QUEST_SPECIAL_FLAGS_CAST
Definition QuestDef.h:165
@ QUEST_SPECIAL_FLAGS_TIMED
Definition QuestDef.h:178
@ QUEST_SPECIAL_FLAGS_DELIVER
Definition QuestDef.h:175
@ QUEST_SPECIAL_FLAGS_REPEATABLE
Definition QuestDef.h:160
@ QUEST_SPECIAL_FLAGS_KILL
Definition QuestDef.h:177
@ QUEST_SPECIAL_FLAGS_DB_ALLOWED
Definition QuestDef.h:171
@ QUEST_SPECIAL_FLAGS_SPEAKTO
Definition QuestDef.h:176
@ QUEST_SPECIAL_FLAGS_MONTHLY
Definition QuestDef.h:164
@ QUEST_SPECIAL_FLAGS_PLAYER_KILL
Definition QuestDef.h:179
@ SPELL_EFFECT_QUEST_COMPLETE
Definition SharedDefines.h:782
uint32 SkillByQuestSort(int32 QuestSort)
Definition SharedDefines.h:3275
ExclusiveQuestGroups mExclusiveQuestGroups
Definition ObjectMgr.h:1150
uint32 ItemDropQuantity[QUEST_SOURCE_ITEM_IDS_COUNT]
Definition QuestDef.h:304
uint32 RewardMailDelay
Definition QuestDef.h:396
uint32 RewardMailSenderEntry
Definition QuestDef.h:404
int32 RequiredNpcOrGo[QUEST_OBJECTIVES_COUNT]
Definition QuestDef.h:305
uint32 RequiredMaxRepFaction
Definition QuestDef.h:401
uint32 SourceSpellid
Definition QuestDef.h:390
uint32 RequiredMinRepFaction
Definition QuestDef.h:399
int32 RequiredFactionValue2
Definition QuestDef.h:356
int32 RequiredFactionValue1
Definition QuestDef.h:354
int32 ZoneOrSort
Definition QuestDef.h:348
uint32 RequiredNpcOrGoCount[QUEST_OBJECTIVES_COUNT]
Definition QuestDef.h:306
uint32 StartItemCount
Definition QuestDef.h:403
void SetSpecialFlag(uint32 flag)
Definition QuestDef.h:225
uint32 GetCharTitleId() const
Definition QuestDef.h:254
uint32 RewardTitleId
Definition QuestDef.h:360
uint32 RewardItemIdCount[QUEST_REWARDS_COUNT]
Definition QuestDef.h:310
uint32 RewardChoiceItemId[QUEST_REWARD_CHOICES_COUNT]
Definition QuestDef.h:307
uint32 NextQuestId
Definition QuestDef.h:392
uint32 RewardMailTemplateId
Definition QuestDef.h:395
uint32 ItemDrop[QUEST_SOURCE_ITEM_IDS_COUNT]
Definition QuestDef.h:303
int32 RewardFactionValueIdOverride[QUEST_REPUTATIONS_COUNT]
Definition QuestDef.h:313
uint32 RequiredSkillPoints
Definition QuestDef.h:398
int32 RewardSpell
Definition QuestDef.h:379
uint32 RewardChoiceItemCount[QUEST_REWARD_CHOICES_COUNT]
Definition QuestDef.h:308
uint32 AllowableRaces
Definition QuestDef.h:352
uint32 RewardNextQuest
Definition QuestDef.h:364
uint32 RequiredPlayerKills
Definition QuestDef.h:361
int32 GetPrevQuestId() const
Definition QuestDef.h:249
uint32 StartItem
Definition QuestDef.h:366
uint32 GetQuestId() const
Definition QuestDef.h:228
int32 RequiredMaxRepValue
Definition QuestDef.h:402
uint32 RequiredClasses
Definition QuestDef.h:389
uint32 Flags
Definition QuestDef.h:359
uint32 RequiredItemCount[QUEST_ITEM_OBJECTIVES_COUNT]
Definition QuestDef.h:302
uint32 GetBreadcrumbForQuestId() const
Definition QuestDef.h:252
int32 GetExclusiveGroup() const
Definition QuestDef.h:251
uint32 TimeAllowed
Definition QuestDef.h:358
uint32 RequiredFactionId1
Definition QuestDef.h:353
uint32 RequiredFactionId2
Definition QuestDef.h:355
PrevQuests prevQuests
Definition QuestDef.h:325
uint32 RewardDisplaySpell
Definition QuestDef.h:378
uint32 RequiredItemId[QUEST_ITEM_OBJECTIVES_COUNT]
Definition QuestDef.h:301
int32 PrevQuestId
Definition QuestDef.h:391
uint32 GetNextQuestId() const
Definition QuestDef.h:250
uint32 RewardFactionId[QUEST_REPUTATIONS_COUNT]
Definition QuestDef.h:311
int32 ExclusiveGroup
Definition QuestDef.h:393
uint32 RequiredSkillId
Definition QuestDef.h:397
int32 RewardFactionValueId[QUEST_REPUTATIONS_COUNT]
Definition QuestDef.h:312
uint32 RewardItemId[QUEST_REWARDS_COUNT]
Definition QuestDef.h:309
uint32 GetQuestMethod() const
Definition QuestDef.h:229
int32 RequiredMinRepValue
Definition QuestDef.h:400
uint32 SpecialFlags
Definition QuestDef.h:405
static const int32 Reputation_Cap
Definition ReputationMgr.h:67
std::array< SpellEffectInfo, MAX_SPELL_EFFECTS > Effects
Definition SpellInfo.h:417
Definition DBCStructure.h:1445

References _breadcrumbsForQuest, _questTemplates, _questTemplatesFast, Quest::AllowableRaces, CLASSMASK_ALL_PLAYABLE, SpellMgr::ComputeIsSpellValid(), DISABLE_TYPE_QUEST, SpellInfo::Effects, Quest::ExclusiveGroup, Quest::Flags, Field::Get(), Quest::GetBreadcrumbForQuestId(), Quest::GetCharTitleId(), GetCreatureTemplate(), Quest::GetExclusiveGroup(), GetGameObjectTemplate(), GetItemTemplate(), getMSTime(), GetMSTimeDiffToNow(), Quest::GetNextQuestId(), Quest::GetPrevQuestId(), Quest::GetQuestId(), Quest::GetQuestMethod(), GetQuestTemplate(), GetTalentSpellCost(), Quest::HasSpecialFlag(), SpellInfo::Id, Quest::ItemDrop, Quest::ItemDropQuantity, LOG_ERROR, LOG_INFO, LOG_WARN, MAX_SPELL_EFFECTS, mExclusiveQuestGroups, Quest::NextQuestId, Quest::PrevQuestId, Quest::prevQuests, QUEST_FLAGS_DAILY, QUEST_FLAGS_TRACKING, QUEST_FLAGS_WEEKLY, QUEST_ITEM_OBJECTIVES_COUNT, QUEST_OBJECTIVES_COUNT, QUEST_REPUTATIONS_COUNT, QUEST_REWARD_CHOICES_COUNT, QUEST_REWARDS_COUNT, QUEST_SOURCE_ITEM_IDS_COUNT, QUEST_SPECIAL_FLAGS_CAST, QUEST_SPECIAL_FLAGS_DB_ALLOWED, QUEST_SPECIAL_FLAGS_DELIVER, QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT, QUEST_SPECIAL_FLAGS_KILL, QUEST_SPECIAL_FLAGS_MONTHLY, QUEST_SPECIAL_FLAGS_PLAYER_KILL, QUEST_SPECIAL_FLAGS_REPEATABLE, QUEST_SPECIAL_FLAGS_SPEAKTO, QUEST_SPECIAL_FLAGS_TIMED, ReputationMgr::Reputation_Cap, Quest::RequiredClasses, Quest::RequiredFactionId1, Quest::RequiredFactionId2, Quest::RequiredFactionValue1, Quest::RequiredFactionValue2, Quest::RequiredItemCount, Quest::RequiredItemId, Quest::RequiredMaxRepFaction, Quest::RequiredMaxRepValue, Quest::RequiredMinRepFaction, Quest::RequiredMinRepValue, Quest::RequiredNpcOrGo, Quest::RequiredNpcOrGoCount, Quest::RequiredPlayerKills, Quest::RequiredSkillId, Quest::RequiredSkillPoints, Quest::RewardChoiceItemCount, Quest::RewardChoiceItemId, Quest::RewardDisplaySpell, Quest::RewardFactionId, Quest::RewardFactionValueId, Quest::RewardFactionValueIdOverride, Quest::RewardItemId, Quest::RewardItemIdCount, Quest::RewardMailDelay, Quest::RewardMailSenderEntry, Quest::RewardMailTemplateId, Quest::RewardNextQuest, Quest::RewardSpell, Quest::RewardTitleId, sAreaTableStore, sCharTitlesStore, sDisableMgr, Quest::SetSpecialFlag(), sFactionStore, SkillByQuestSort(), sMailTemplateStore, Quest::SourceSpellid, Quest::SpecialFlags, SPELL_EFFECT_QUEST_COMPLETE, sQuestSortStore, sRaceMgr, sSkillLineStore, sSpellMgr, Quest::StartItem, Quest::StartItemCount, sWorld, Quest::TimeAllowed, WorldDatabase, and Quest::ZoneOrSort.

◆ LoadQuestStartersAndEnders()

void ObjectMgr::LoadQuestStartersAndEnders ( )
inline
960 {
961 LOG_INFO("server.loading", "Loading GO Start Quest Data...");
963 LOG_INFO("server.loading", "Loading GO End Quest Data...");
965 LOG_INFO("server.loading", "Loading Creature Start Quest Data...");
967 LOG_INFO("server.loading", "Loading Creature End Quest Data...");
969 }
void LoadCreatureQuestEnders()
Definition ObjectMgr.cpp:8793
void LoadGameobjectQuestEnders()
Definition ObjectMgr.cpp:8765
void LoadGameobjectQuestStarters()
Definition ObjectMgr.cpp:8751
void LoadCreatureQuestStarters()
Definition ObjectMgr.cpp:8779

References LoadCreatureQuestEnders(), LoadCreatureQuestStarters(), LoadGameobjectQuestEnders(), LoadGameobjectQuestStarters(), and LOG_INFO.

◆ LoadReferenceVendor()

int ObjectMgr::LoadReferenceVendor ( int32  vendor,
int32  item_id,
std::set< uint32 > *  skip_vendors 
)
9914{
9915 // find all items from the reference vendor
9917 stmt->SetData(0, uint32(item));
9918 PreparedQueryResult result = WorldDatabase.Query(stmt);
9919
9920 if (!result)
9921 return 0;
9922
9923 uint32 count = 0;
9924 do
9925 {
9926 Field* fields = result->Fetch();
9927
9928 int32 item_id = fields[0].Get<int32>();
9929
9930 // if item is a negative, its a reference
9931 if (item_id < 0)
9932 count += LoadReferenceVendor(vendor, -item_id, skip_vendors);
9933 else
9934 {
9935 uint32 maxcount = fields[1].Get<uint32>();
9936 uint32 incrtime = fields[2].Get<uint32>();
9937 uint32 ExtendedCost = fields[3].Get<uint32>();
9938
9939 if (!IsVendorItemValid(vendor, item_id, maxcount, incrtime, ExtendedCost, nullptr, skip_vendors))
9940 continue;
9941
9942 VendorItemData& vList = _cacheVendorItemStore[vendor];
9943
9944 vList.AddItem(item_id, maxcount, incrtime, ExtendedCost);
9945 ++count;
9946 }
9947 } while (result->NextRow());
9948
9949 return count;
9950}
std::shared_ptr< PreparedResultSet > PreparedQueryResult
Definition DatabaseEnvFwd.h:45
@ WORLD_SEL_NPC_VENDOR_REF
Definition WorldDatabase.h:45
bool IsVendorItemValid(uint32 vendor_entry, uint32 item, uint32 maxcount, uint32 ptime, uint32 ExtendedCost, Player *player=nullptr, std::set< uint32 > *skip_vendors=nullptr, uint32 ORnpcflag=0) const
Definition ObjectMgr.cpp:10175
int LoadReferenceVendor(int32 vendor, int32 item_id, std::set< uint32 > *skip_vendors)
Definition ObjectMgr.cpp:9913

References _cacheVendorItemStore, VendorItemData::AddItem(), Field::Get(), IsVendorItemValid(), LoadReferenceVendor(), PreparedStatementBase::SetData(), WORLD_SEL_NPC_VENDOR_REF, and WorldDatabase.

Referenced by LoadReferenceVendor(), and LoadVendors().

◆ LoadReputationOnKill()

void ObjectMgr::LoadReputationOnKill ( )
8285{
8286 uint32 oldMSTime = getMSTime();
8287
8288 // For reload case
8289 _repOnKillStore.clear();
8290
8291 uint32 count = 0;
8292
8293 // 0 1 2
8294 QueryResult result = WorldDatabase.Query("SELECT creature_id, RewOnKillRepFaction1, RewOnKillRepFaction2, "
8295 // 3 4 5 6 7 8 9
8296 "IsTeamAward1, MaxStanding1, RewOnKillRepValue1, IsTeamAward2, MaxStanding2, RewOnKillRepValue2, TeamDependent "
8297 "FROM creature_onkill_reputation");
8298
8299 if (!result)
8300 {
8301 LOG_WARN("server.loading", ">> Loaded 0 creature award reputation definitions. DB table `creature_onkill_reputation` is empty.");
8302 LOG_INFO("server.loading", " ");
8303 return;
8304 }
8305
8306 do
8307 {
8308 Field* fields = result->Fetch();
8309
8310 uint32 creature_id = fields[0].Get<uint32>();
8311
8312 ReputationOnKillEntry repOnKill;
8313 repOnKill.RepFaction1 = fields[1].Get<int16>();
8314 repOnKill.RepFaction2 = fields[2].Get<int16>();
8315 repOnKill.IsTeamAward1 = fields[3].Get<bool>();
8316 repOnKill.ReputationMaxCap1 = fields[4].Get<uint8>();
8317 repOnKill.RepValue1 = fields[5].Get<float>();
8318 repOnKill.IsTeamAward2 = fields[6].Get<bool>();
8319 repOnKill.ReputationMaxCap2 = fields[7].Get<uint8>();
8320 repOnKill.RepValue2 = fields[8].Get<float>();
8321 repOnKill.TeamDependent = fields[9].Get<uint8>();
8322
8323 if (!GetCreatureTemplate(creature_id))
8324 {
8325 LOG_ERROR("sql.sql", "Table `creature_onkill_reputation` have data for not existed creature entry ({}), skipped", creature_id);
8326 continue;
8327 }
8328
8329 if (repOnKill.RepFaction1)
8330 {
8331 FactionEntry const* factionEntry1 = sFactionStore.LookupEntry(repOnKill.RepFaction1);
8332 if (!factionEntry1)
8333 {
8334 LOG_ERROR("sql.sql", "Faction (faction.dbc) {} does not exist but is used in `creature_onkill_reputation`", repOnKill.RepFaction1);
8335 continue;
8336 }
8337 }
8338
8339 if (repOnKill.RepFaction2)
8340 {
8341 FactionEntry const* factionEntry2 = sFactionStore.LookupEntry(repOnKill.RepFaction2);
8342 if (!factionEntry2)
8343 {
8344 LOG_ERROR("sql.sql", "Faction (faction.dbc) {} does not exist but is used in `creature_onkill_reputation`", repOnKill.RepFaction2);
8345 continue;
8346 }
8347 }
8348
8349 _repOnKillStore[creature_id] = repOnKill;
8350
8351 ++count;
8352 } while (result->NextRow());
8353
8354 LOG_INFO("server.loading", ">> Loaded {} Creature Award Reputation Definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8355 LOG_INFO("server.loading", " ");
8356}
Definition ObjectMgr.h:571
uint32 RepFaction1
Definition ObjectMgr.h:572

References _repOnKillStore, Field::Get(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, ReputationOnKillEntry::RepFaction1, sFactionStore, and WorldDatabase.

◆ LoadReputationRewardRate()

void ObjectMgr::LoadReputationRewardRate ( )
8197{
8198 uint32 oldMSTime = getMSTime();
8199
8200 _repRewardRateStore.clear(); // for reload case
8201
8202 uint32 count = 0; // 0 1 2 3 4 5 6 7
8203 QueryResult result = WorldDatabase.Query("SELECT faction, quest_rate, quest_daily_rate, quest_weekly_rate, quest_monthly_rate, quest_repeatable_rate, creature_rate, spell_rate FROM reputation_reward_rate");
8204 if (!result)
8205 {
8206 LOG_INFO("server.loading", ">> Loaded `reputation_reward_rate`, table is empty!");
8207 return;
8208 }
8209
8210 do
8211 {
8212 Field* fields = result->Fetch();
8213
8214 uint32 factionId = fields[0].Get<uint32>();
8215
8216 RepRewardRate repRate;
8217
8218 repRate.questRate = fields[1].Get<float>();
8219 repRate.questDailyRate = fields[2].Get<float>();
8220 repRate.questWeeklyRate = fields[3].Get<float>();
8221 repRate.questMonthlyRate = fields[4].Get<float>();
8222 repRate.questRepeatableRate = fields[5].Get<float>();
8223 repRate.creatureRate = fields[6].Get<float>();
8224 repRate.spellRate = fields[7].Get<float>();
8225
8226 FactionEntry const* factionEntry = sFactionStore.LookupEntry(factionId);
8227 if (!factionEntry)
8228 {
8229 LOG_ERROR("sql.sql", "Faction (faction.dbc) {} does not exist but is used in `reputation_reward_rate`", factionId);
8230 continue;
8231 }
8232
8233 if (repRate.questRate < 0.0f)
8234 {
8235 LOG_ERROR("sql.sql", "Table reputation_reward_rate has quest_rate with invalid rate {}, skipping data for faction {}", repRate.questRate, factionId);
8236 continue;
8237 }
8238
8239 if (repRate.questDailyRate < 0.0f)
8240 {
8241 LOG_ERROR("sql.sql", "Table reputation_reward_rate has quest_daily_rate with invalid rate {}, skipping data for faction {}", repRate.questDailyRate, factionId);
8242 continue;
8243 }
8244
8245 if (repRate.questWeeklyRate < 0.0f)
8246 {
8247 LOG_ERROR("sql.sql", "Table reputation_reward_rate has quest_weekly_rate with invalid rate {}, skipping data for faction {}", repRate.questWeeklyRate, factionId);
8248 continue;
8249 }
8250
8251 if (repRate.questMonthlyRate < 0.0f)
8252 {
8253 LOG_ERROR("sql.sql", "Table reputation_reward_rate has quest_monthly_rate with invalid rate {}, skipping data for faction {}", repRate.questMonthlyRate, factionId);
8254 continue;
8255 }
8256
8257 if (repRate.questRepeatableRate < 0.0f)
8258 {
8259 LOG_ERROR("sql.sql", "Table reputation_reward_rate has quest_repeatable_rate with invalid rate {}, skipping data for faction {}", repRate.questRepeatableRate, factionId);
8260 continue;
8261 }
8262
8263 if (repRate.creatureRate < 0.0f)
8264 {
8265 LOG_ERROR("sql.sql", "Table reputation_reward_rate has creature_rate with invalid rate {}, skipping data for faction {}", repRate.creatureRate, factionId);
8266 continue;
8267 }
8268
8269 if (repRate.spellRate < 0.0f)
8270 {
8271 LOG_ERROR("sql.sql", "Table reputation_reward_rate has spell_rate with invalid rate {}, skipping data for faction {}", repRate.spellRate, factionId);
8272 continue;
8273 }
8274
8275 _repRewardRateStore[factionId] = repRate;
8276
8277 ++count;
8278 } while (result->NextRow());
8279
8280 LOG_INFO("server.loading", ">> Loaded {} Reputation Reward Rate in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8281 LOG_INFO("server.loading", " ");
8282}
Definition ObjectMgr.h:560
float questRate
Definition ObjectMgr.h:561

References _repRewardRateStore, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, RepRewardRate::questRate, sFactionStore, and WorldDatabase.

◆ LoadReputationSpilloverTemplate()

void ObjectMgr::LoadReputationSpilloverTemplate ( )
8359{
8360 uint32 oldMSTime = getMSTime();
8361
8362 _repSpilloverTemplateStore.clear(); // for reload case
8363
8364 uint32 count = 0; // 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
8365 QueryResult result = WorldDatabase.Query("SELECT faction, faction1, rate_1, rank_1, faction2, rate_2, rank_2, faction3, rate_3, rank_3, faction4, rate_4, rank_4, faction5, rate_5, rank_5, faction6, rate_6, rank_6 FROM reputation_spillover_template");
8366
8367 if (!result)
8368 {
8369 LOG_INFO("server.loading", ">> Loaded `reputation_spillover_template`, table is empty.");
8370 LOG_INFO("server.loading", " ");
8371 return;
8372 }
8373
8374 do
8375 {
8376 Field* fields = result->Fetch();
8377
8378 uint32 factionId = fields[0].Get<uint16>();
8379
8380 RepSpilloverTemplate repTemplate;
8381
8382 repTemplate.faction[0] = fields[1].Get<uint16>();
8383 repTemplate.faction_rate[0] = fields[2].Get<float>();
8384 repTemplate.faction_rank[0] = fields[3].Get<uint8>();
8385 repTemplate.faction[1] = fields[4].Get<uint16>();
8386 repTemplate.faction_rate[1] = fields[5].Get<float>();
8387 repTemplate.faction_rank[1] = fields[6].Get<uint8>();
8388 repTemplate.faction[2] = fields[7].Get<uint16>();
8389 repTemplate.faction_rate[2] = fields[8].Get<float>();
8390 repTemplate.faction_rank[2] = fields[9].Get<uint8>();
8391 repTemplate.faction[3] = fields[10].Get<uint16>();
8392 repTemplate.faction_rate[3] = fields[11].Get<float>();
8393 repTemplate.faction_rank[3] = fields[12].Get<uint8>();
8394 repTemplate.faction[4] = fields[13].Get<uint16>();
8395 repTemplate.faction_rate[4] = fields[14].Get<float>();
8396 repTemplate.faction_rank[4] = fields[15].Get<uint8>();
8397 repTemplate.faction[5] = fields[16].Get<uint16>();
8398 repTemplate.faction_rate[5] = fields[17].Get<float>();
8399 repTemplate.faction_rank[5] = fields[18].Get<uint8>();
8400
8401 FactionEntry const* factionEntry = sFactionStore.LookupEntry(factionId);
8402
8403 if (!factionEntry)
8404 {
8405 LOG_ERROR("sql.sql", "Faction (faction.dbc) {} does not exist but is used in `reputation_spillover_template`", factionId);
8406 continue;
8407 }
8408
8409 if (factionEntry->team == 0)
8410 {
8411 LOG_ERROR("sql.sql", "Faction (faction.dbc) {} in `reputation_spillover_template` does not belong to any team, skipping", factionId);
8412 continue;
8413 }
8414
8415 for (uint32 i = 0; i < MAX_SPILLOVER_FACTIONS; ++i)
8416 {
8417 if (repTemplate.faction[i])
8418 {
8419 FactionEntry const* factionSpillover = sFactionStore.LookupEntry(repTemplate.faction[i]);
8420
8421 if (!factionSpillover)
8422 {
8423 LOG_ERROR("sql.sql", "Spillover faction (faction.dbc) {} does not exist but is used in `reputation_spillover_template` for faction {}, skipping", repTemplate.faction[i], factionId);
8424 continue;
8425 }
8426
8427 if (factionSpillover->reputationListID < 0)
8428 {
8429 LOG_ERROR("sql.sql", "Spillover faction (faction.dbc) {} for faction {} in `reputation_spillover_template` can not be listed for client, and then useless, skipping", repTemplate.faction[i], factionId);
8430 continue;
8431 }
8432
8433 if (repTemplate.faction_rank[i] >= MAX_REPUTATION_RANK)
8434 {
8435 LOG_ERROR("sql.sql", "Rank {} used in `reputation_spillover_template` for spillover faction {} is not valid, skipping", repTemplate.faction_rank[i], repTemplate.faction[i]);
8436 continue;
8437 }
8438 }
8439 }
8440
8441 FactionEntry const* factionEntry0 = sFactionStore.LookupEntry(repTemplate.faction[0]);
8442 if (repTemplate.faction[0] && !factionEntry0)
8443 {
8444 LOG_ERROR("sql.sql", "Faction (faction.dbc) {} does not exist but is used in `reputation_spillover_template`", repTemplate.faction[0]);
8445 continue;
8446 }
8447 FactionEntry const* factionEntry1 = sFactionStore.LookupEntry(repTemplate.faction[1]);
8448 if (repTemplate.faction[1] && !factionEntry1)
8449 {
8450 LOG_ERROR("sql.sql", "Faction (faction.dbc) {} does not exist but is used in `reputation_spillover_template`", repTemplate.faction[1]);
8451 continue;
8452 }
8453 FactionEntry const* factionEntry2 = sFactionStore.LookupEntry(repTemplate.faction[2]);
8454 if (repTemplate.faction[2] && !factionEntry2)
8455 {
8456 LOG_ERROR("sql.sql", "Faction (faction.dbc) {} does not exist but is used in `reputation_spillover_template`", repTemplate.faction[2]);
8457 continue;
8458 }
8459 FactionEntry const* factionEntry3 = sFactionStore.LookupEntry(repTemplate.faction[3]);
8460 if (repTemplate.faction[3] && !factionEntry3)
8461 {
8462 LOG_ERROR("sql.sql", "Faction (faction.dbc) {} does not exist but is used in `reputation_spillover_template`", repTemplate.faction[3]);
8463 continue;
8464 }
8465
8466 _repSpilloverTemplateStore[factionId] = repTemplate;
8467
8468 ++count;
8469 } while (result->NextRow());
8470
8471 LOG_INFO("server.loading", ">> Loaded {} Reputation Spillover Template in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8472 LOG_INFO("server.loading", " ");
8473}
#define MAX_SPILLOVER_FACTIONS
Definition SharedDefines.h:235
int32 reputationListID
Definition DBCStructure.h:909
Definition ObjectMgr.h:584
uint32 faction[MAX_SPILLOVER_FACTIONS]
Definition ObjectMgr.h:585

References _repSpilloverTemplateStore, RepSpilloverTemplate::faction, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, MAX_REPUTATION_RANK, MAX_SPILLOVER_FACTIONS, FactionEntry::reputationListID, sFactionStore, and WorldDatabase.

◆ LoadReservedPlayerNamesDB()

void ObjectMgr::LoadReservedPlayerNamesDB ( )
8808{
8809 uint32 oldMSTime = getMSTime();
8810
8811 _reservedNamesStore.clear(); // need for reload case
8812
8813 QueryResult result = CharacterDatabase.Query("SELECT name FROM reserved_name");
8814
8815 if (!result)
8816 {
8817 LOG_WARN("server.loading", ">> Loaded 0 reserved names. DB table `reserved_name` is empty!");
8818 return;
8819 }
8820
8821 uint32 count = 0;
8822
8823 Field* fields;
8824 do
8825 {
8826 fields = result->Fetch();
8827 std::string name = fields[0].Get<std::string>();
8828
8829 std::wstring wstr;
8830 if (!Utf8toWStr (name, wstr))
8831 {
8832 LOG_ERROR("sql.sql", "Table `reserved_name` have invalid name: {}", name);
8833 continue;
8834 }
8835
8836 wstrToLower(wstr);
8837
8838 _reservedNamesStore.insert(wstr);
8839 ++count;
8840 } while (result->NextRow());
8841
8842 LOG_INFO("server.loading", ">> Loaded {} reserved names from DB in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8843}

References _reservedNamesStore, CharacterDatabase, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, Utf8toWStr(), and wstrToLower().

◆ LoadReservedPlayerNamesDBC()

void ObjectMgr::LoadReservedPlayerNamesDBC ( )
8846{
8847 if (!sWorld->getBoolConfig(CONFIG_STRICT_NAMES_RESERVED))
8848 {
8849 LOG_WARN("server.loading", ">> Loaded 0 reserved names from DBC. Config option disabled.");
8850 return;
8851 }
8852
8853 uint32 oldMSTime = getMSTime();
8854
8855 uint32 count = 0;
8856
8857 for (NamesReservedEntry const* reservedStore : sNamesReservedStore)
8858 {
8859 std::wstring wstr;
8860
8861 Utf8toWStr(reservedStore->Pattern, wstr);
8862
8863 // DBC does not have clean entries, remove the junk.
8864 boost::algorithm::replace_all(wstr, "\\<", "");
8865 boost::algorithm::replace_all(wstr, "\\>", "");
8866
8867 _reservedNamesStore.insert(wstr);
8868 count++;
8869 }
8870
8871 LOG_INFO("server.loading", ">> Loaded {} reserved names from DBC in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
8872 LOG_INFO("server.loading", " ");
8873}
DBCStorage< NamesReservedEntry > sNamesReservedStore(NamesReservedfmt)
@ CONFIG_STRICT_NAMES_RESERVED
Definition WorldConfig.h:144
Definition DBCStructure.h:1398

References _reservedNamesStore, CONFIG_STRICT_NAMES_RESERVED, getMSTime(), GetMSTimeDiffToNow(), LOG_INFO, LOG_WARN, sNamesReservedStore, sWorld, and Utf8toWStr().

◆ LoadScriptNames()

void ObjectMgr::LoadScriptNames ( )
10256{
10257 uint32 oldMSTime = getMSTime();
10258
10259 // We insert an empty placeholder here so we can use the
10260 // script id 0 as dummy for "no script found".
10261 _scriptNamesStore.emplace_back("");
10262
10263 QueryResult result = WorldDatabase.Query(
10264 "SELECT DISTINCT(ScriptName) FROM achievement_criteria_data WHERE ScriptName <> '' AND type = 11 "
10265 "UNION "
10266 "SELECT DISTINCT(ScriptName) FROM battleground_template WHERE ScriptName <> '' "
10267 "UNION "
10268 "SELECT DISTINCT(ScriptName) FROM creature WHERE ScriptName <> '' "
10269 "UNION "
10270 "SELECT DISTINCT(ScriptName) FROM creature_template WHERE ScriptName <> '' "
10271 "UNION "
10272 "SELECT DISTINCT(ScriptName) FROM gameobject WHERE ScriptName <> '' "
10273 "UNION "
10274 "SELECT DISTINCT(ScriptName) FROM gameobject_template WHERE ScriptName <> '' "
10275 "UNION "
10276 "SELECT DISTINCT(ScriptName) FROM item_template WHERE ScriptName <> '' "
10277 "UNION "
10278 "SELECT DISTINCT(ScriptName) FROM areatrigger_scripts WHERE ScriptName <> '' "
10279 "UNION "
10280 "SELECT DISTINCT(ScriptName) FROM spell_script_names WHERE ScriptName <> '' "
10281 "UNION "
10282 "SELECT DISTINCT(ScriptName) FROM transports WHERE ScriptName <> '' "
10283 "UNION "
10284 "SELECT DISTINCT(ScriptName) FROM game_weather WHERE ScriptName <> '' "
10285 "UNION "
10286 "SELECT DISTINCT(ScriptName) FROM conditions WHERE ScriptName <> '' "
10287 "UNION "
10288 "SELECT DISTINCT(ScriptName) FROM outdoorpvp_template WHERE ScriptName <> '' "
10289 "UNION "
10290 "SELECT DISTINCT(script) FROM instance_template WHERE script <> ''");
10291
10292 if (!result)
10293 {
10294 LOG_INFO("server.loading", " ");
10295 LOG_ERROR("sql.sql", ">> Loaded empty set of Script Names!");
10296 return;
10297 }
10298
10299 _scriptNamesStore.reserve(result->GetRowCount() + 1);
10300
10301 do
10302 {
10303 _scriptNamesStore.push_back((*result)[0].Get<std::string>());
10304 } while (result->NextRow());
10305
10306 std::sort(_scriptNamesStore.begin(), _scriptNamesStore.end());
10307 LOG_INFO("server.loading", ">> Loaded {} ScriptNames in {} ms", _scriptNamesStore.size(), GetMSTimeDiffToNow(oldMSTime));
10308 LOG_INFO("server.loading", " ");
10309}

References _scriptNamesStore, getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, and WorldDatabase.

◆ LoadScripts()

void ObjectMgr::LoadScripts ( ScriptsType  type)
private
5845{
5846 uint32 oldMSTime = getMSTime();
5847
5848 ScriptMapMap* scripts = GetScriptsMapByType(type);
5849 if (!scripts)
5850 return;
5851
5852 std::string tableName = GetScriptsTableNameByType(type);
5853 if (tableName.empty())
5854 return;
5855
5856 if (sScriptMgr->IsScriptScheduled()) // function cannot be called when scripts are in use.
5857 return;
5858
5859 LOG_INFO("server.loading", "Loading {}...", tableName);
5860
5861 scripts->clear(); // need for reload support
5862
5863 bool isSpellScriptTable = (type == SCRIPTS_SPELL);
5864 // 0 1 2 3 4 5 6 7 8 9
5865 QueryResult result = WorldDatabase.Query("SELECT id, delay, command, datalong, datalong2, dataint, x, y, z, o{} FROM {}", isSpellScriptTable ? ", effIndex" : "", tableName);
5866
5867 if (!result)
5868 {
5869 LOG_WARN("server.loading", ">> Loaded 0 script definitions. DB table `{}` is empty!", tableName);
5870 LOG_INFO("server.loading", " ");
5871 return;
5872 }
5873
5874 uint32 count = 0;
5875
5876 do
5877 {
5878 Field* fields = result->Fetch();
5879 ScriptInfo tmp;
5880 tmp.type = type;
5881 tmp.id = fields[0].Get<uint32>();
5882 if (isSpellScriptTable)
5883 tmp.id |= fields[10].Get<uint8>() << 24;
5884 tmp.delay = fields[1].Get<uint32>();
5885 tmp.command = ScriptCommands(fields[2].Get<uint32>());
5886 tmp.Raw.nData[0] = fields[3].Get<uint32>();
5887 tmp.Raw.nData[1] = fields[4].Get<uint32>();
5888 tmp.Raw.nData[2] = fields[5].Get<int32>();
5889 tmp.Raw.fData[0] = fields[6].Get<float>();
5890 tmp.Raw.fData[1] = fields[7].Get<float>();
5891 tmp.Raw.fData[2] = fields[8].Get<float>();
5892 tmp.Raw.fData[3] = fields[9].Get<float>();
5893
5894 // generic command args check
5895 switch (tmp.command)
5896 {
5898 {
5900 {
5901 LOG_ERROR("sql.sql", "Table `{}` has invalid talk type (datalong = {}) in SCRIPT_COMMAND_TALK for script id {}",
5902 tableName, tmp.Talk.ChatType, tmp.id);
5903 continue;
5904 }
5906 {
5907 LOG_ERROR("sql.sql", "Table `{}` has invalid talk text id (dataint = {}) in SCRIPT_COMMAND_TALK for script id {}",
5908 tableName, tmp.Talk.TextID, tmp.id);
5909 continue;
5910 }
5911 break;
5912 }
5913
5915 {
5916 if (!sEmotesStore.LookupEntry(tmp.Emote.EmoteID))
5917 {
5918 LOG_ERROR("sql.sql", "Table `{}` has invalid emote id (datalong = {}) in SCRIPT_COMMAND_EMOTE for script id {}",
5919 tableName, tmp.Emote.EmoteID, tmp.id);
5920 continue;
5921 }
5922 break;
5923 }
5924
5926 {
5927 if (!sMapStore.LookupEntry(tmp.TeleportTo.MapID))
5928 {
5929 LOG_ERROR("sql.sql", "Table `{}` has invalid map (Id: {}) in SCRIPT_COMMAND_TELEPORT_TO for script id {}",
5930 tableName, tmp.TeleportTo.MapID, tmp.id);
5931 continue;
5932 }
5933
5935 {
5936 LOG_ERROR("sql.sql", "Table `{}` has invalid coordinates (X: {} Y: {} Z: {} O: {}) in SCRIPT_COMMAND_TELEPORT_TO for script id {}",
5937 tableName, tmp.TeleportTo.DestX, tmp.TeleportTo.DestY, tmp.TeleportTo.DestZ, tmp.TeleportTo.Orientation, tmp.id);
5938 continue;
5939 }
5940 break;
5941 }
5942
5944 {
5945 Quest const* quest = GetQuestTemplate(tmp.QuestExplored.QuestID);
5946 if (!quest)
5947 {
5948 LOG_ERROR("sql.sql", "Table `{}` has invalid quest (ID: {}) in SCRIPT_COMMAND_QUEST_EXPLORED in `datalong` for script id {}",
5949 tableName, tmp.QuestExplored.QuestID, tmp.id);
5950 continue;
5951 }
5952
5954 {
5955 LOG_ERROR("sql.sql", "Table `{}` has quest (ID: {}) in SCRIPT_COMMAND_QUEST_EXPLORED in `datalong` for script id {}, but quest not have specialflag QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT in quest flags. Script command or quest flags wrong. Quest modified to require objective.",
5956 tableName, tmp.QuestExplored.QuestID, tmp.id);
5957
5958 // this will prevent quest completing without objective
5959 const_cast<Quest*>(quest)->SetSpecialFlag(QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT);
5960
5961 // continue; - quest objective requirement set and command can be allowed
5962 }
5963
5965 {
5966 LOG_ERROR("sql.sql", "Table `{}` has too large distance ({}) for exploring objective complete in `datalong2` in SCRIPT_COMMAND_QUEST_EXPLORED in `datalong` for script id {}",
5967 tableName, tmp.QuestExplored.Distance, tmp.id);
5968 continue;
5969 }
5970
5972 {
5973 LOG_ERROR("sql.sql", "Table `{}` has too large distance ({}) for exploring objective complete in `datalong2` in SCRIPT_COMMAND_QUEST_EXPLORED in `datalong` for script id {}, max distance is {} or 0 for disable distance check",
5975 continue;
5976 }
5977
5979 {
5980 LOG_ERROR("sql.sql", "Table `{}` has too small distance ({}) for exploring objective complete in `datalong2` in SCRIPT_COMMAND_QUEST_EXPLORED in `datalong` for script id {}, min distance is {} or 0 for disable distance check",
5981 tableName, tmp.QuestExplored.Distance, tmp.id, INTERACTION_DISTANCE);
5982 continue;
5983 }
5984
5985 break;
5986 }
5987
5989 {
5991 {
5992 LOG_ERROR("sql.sql", "Table `{}` has invalid creature (Entry: {}) in SCRIPT_COMMAND_KILL_CREDIT for script id {}",
5993 tableName, tmp.KillCredit.CreatureEntry, tmp.id);
5994 continue;
5995 }
5996 break;
5997 }
5998
6000 {
6002 if (!data)
6003 {
6004 LOG_ERROR("sql.sql", "Table `{}` has invalid gameobject (GUID: {}) in SCRIPT_COMMAND_RESPAWN_GAMEOBJECT for script id {}",
6005 tableName, tmp.RespawnGameobject.GOGuid, tmp.id);
6006 continue;
6007 }
6008
6009 GameObjectTemplate const* info = GetGameObjectTemplate(data->id);
6010 if (!info)
6011 {
6012 LOG_ERROR("sql.sql", "Table `{}` has gameobject with invalid entry (GUID: {} Entry: {}) in SCRIPT_COMMAND_RESPAWN_GAMEOBJECT for script id {}",
6013 tableName, tmp.RespawnGameobject.GOGuid, data->id, tmp.id);
6014 continue;
6015 }
6016
6017 if (info->type == GAMEOBJECT_TYPE_FISHINGNODE ||
6019 info->type == GAMEOBJECT_TYPE_DOOR ||
6020 info->type == GAMEOBJECT_TYPE_BUTTON ||
6021 info->type == GAMEOBJECT_TYPE_TRAP)
6022 {
6023 LOG_ERROR("sql.sql", "Table `{}` have gameobject type ({}) unsupported by command SCRIPT_COMMAND_RESPAWN_GAMEOBJECT for script id {}",
6024 tableName, info->entry, tmp.id);
6025 continue;
6026 }
6027 break;
6028 }
6029
6031 {
6033 {
6034 LOG_ERROR("sql.sql", "Table `{}` has invalid coordinates (X: {} Y: {} Z: {} O: {}) in SCRIPT_COMMAND_TEMP_SUMMON_CREATURE for script id {}",
6036 continue;
6037 }
6038
6040 if (!GetCreatureTemplate(entry))
6041 {
6042 LOG_ERROR("sql.sql", "Table `{}` has invalid creature (Entry: {}) in SCRIPT_COMMAND_TEMP_SUMMON_CREATURE for script id {}",
6043 tableName, tmp.TempSummonCreature.CreatureEntry, tmp.id);
6044 continue;
6045 }
6046 break;
6047 }
6048
6051 {
6053 if (!data)
6054 {
6055 LOG_ERROR("sql.sql", "Table `{}` has invalid gameobject (GUID: {}) in {} for script id {}",
6056 tableName, tmp.ToggleDoor.GOGuid, GetScriptCommandName(tmp.command), tmp.id);
6057 continue;
6058 }
6059
6060 GameObjectTemplate const* info = GetGameObjectTemplate(data->id);
6061 if (!info)
6062 {
6063 LOG_ERROR("sql.sql", "Table `{}` has gameobject with invalid entry (GUID: {} Entry: {}) in {} for script id {}",
6064 tableName, tmp.ToggleDoor.GOGuid, data->id, GetScriptCommandName(tmp.command), tmp.id);
6065 continue;
6066 }
6067
6068 if (info->type != GAMEOBJECT_TYPE_DOOR)
6069 {
6070 LOG_ERROR("sql.sql", "Table `{}` has gameobject type ({}) non supported by command {} for script id {}",
6071 tableName, info->entry, GetScriptCommandName(tmp.command), tmp.id);
6072 continue;
6073 }
6074
6075 break;
6076 }
6077
6079 {
6080 if (!sSpellMgr->GetSpellInfo(tmp.RemoveAura.SpellID))
6081 {
6082 LOG_ERROR("sql.sql", "Table `{}` using non-existent spell (id: {}) in SCRIPT_COMMAND_REMOVE_AURA for script id {}",
6083 tableName, tmp.RemoveAura.SpellID, tmp.id);
6084 continue;
6085 }
6086 if (tmp.RemoveAura.Flags & ~0x1) // 1 bits (0, 1)
6087 {
6088 LOG_ERROR("sql.sql", "Table `{}` using unknown flags in datalong2 ({}) in SCRIPT_COMMAND_REMOVE_AURA for script id {}",
6089 tableName, tmp.RemoveAura.Flags, tmp.id);
6090 continue;
6091 }
6092 break;
6093 }
6094
6096 {
6097 if (!sSpellMgr->GetSpellInfo(tmp.CastSpell.SpellID))
6098 {
6099 LOG_ERROR("sql.sql", "Table `{}` using non-existent spell (id: {}) in SCRIPT_COMMAND_CAST_SPELL for script id {}",
6100 tableName, tmp.CastSpell.SpellID, tmp.id);
6101 continue;
6102 }
6103 if (tmp.CastSpell.Flags > 4) // targeting type
6104 {
6105 LOG_ERROR("sql.sql", "Table `{}` using unknown target in datalong2 ({}) in SCRIPT_COMMAND_CAST_SPELL for script id {}",
6106 tableName, tmp.CastSpell.Flags, tmp.id);
6107 continue;
6108 }
6109 if (tmp.CastSpell.Flags != 4 && tmp.CastSpell.CreatureEntry & ~0x1) // 1 bit (0, 1)
6110 {
6111 LOG_ERROR("sql.sql", "Table `{}` using unknown flags in dataint ({}) in SCRIPT_COMMAND_CAST_SPELL for script id {}",
6112 tableName, tmp.CastSpell.CreatureEntry, tmp.id);
6113 continue;
6114 }
6115 else if (tmp.CastSpell.Flags == 4 && !GetCreatureTemplate(tmp.CastSpell.CreatureEntry))
6116 {
6117 LOG_ERROR("sql.sql", "Table `{}` using invalid creature entry in dataint ({}) in SCRIPT_COMMAND_CAST_SPELL for script id {}",
6118 tableName, tmp.CastSpell.CreatureEntry, tmp.id);
6119 continue;
6120 }
6121 break;
6122 }
6123
6125 {
6127 {
6128 LOG_ERROR("sql.sql", "Table `{}` has nonexistent item (entry: {}) in SCRIPT_COMMAND_CREATE_ITEM for script id {}",
6129 tableName, tmp.CreateItem.ItemEntry, tmp.id);
6130 continue;
6131 }
6132 if (!tmp.CreateItem.Amount)
6133 {
6134 LOG_ERROR("sql.sql", "Table `{}` SCRIPT_COMMAND_CREATE_ITEM but amount is {} for script id {}",
6135 tableName, tmp.CreateItem.Amount, tmp.id);
6136 continue;
6137 }
6138 break;
6139 }
6140 default:
6141 break;
6142 }
6143
6144 if (scripts->find(tmp.id) == scripts->end())
6145 {
6146 ScriptMap emptyMap;
6147 (*scripts)[tmp.id] = emptyMap;
6148 }
6149 (*scripts)[tmp.id].insert(std::pair<uint32, ScriptInfo>(tmp.delay, tmp));
6150
6151 ++count;
6152 } while (result->NextRow());
6153
6154 LOG_INFO("server.loading", ">> Loaded {} script definitions in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
6155 LOG_INFO("server.loading", " ");
6156}
@ CHAT_TYPE_WHISPER
Definition CreatureData.h:416
#define DEFAULT_VISIBILITY_DISTANCE
Definition ObjectDefines.h:39
#define INTERACTION_DISTANCE
Definition ObjectDefines.h:24
std::multimap< uint32, ScriptInfo > ScriptMap
Definition ObjectMgr.h:386
ScriptMapMap * GetScriptsMapByType(ScriptsType type)
Definition ObjectMgr.cpp:84
ScriptCommands
Definition ObjectMgr.h:92
@ SCRIPT_COMMAND_EMOTE
Definition ObjectMgr.h:94
@ SCRIPT_COMMAND_CREATE_ITEM
Definition ObjectMgr.h:110
@ SCRIPT_COMMAND_CLOSE_DOOR
Definition ObjectMgr.h:105
@ SCRIPT_COMMAND_CAST_SPELL
Definition ObjectMgr.h:108
@ SCRIPT_COMMAND_RESPAWN_GAMEOBJECT
Definition ObjectMgr.h:102
@ SCRIPT_COMMAND_QUEST_EXPLORED
Definition ObjectMgr.h:100
@ SCRIPT_COMMAND_TALK
Definition ObjectMgr.h:93
@ SCRIPT_COMMAND_OPEN_DOOR
Definition ObjectMgr.h:104
@ SCRIPT_COMMAND_TELEPORT_TO
Definition ObjectMgr.h:99
@ SCRIPT_COMMAND_TEMP_SUMMON_CREATURE
Definition ObjectMgr.h:103
@ SCRIPT_COMMAND_KILL_CREDIT
Definition ObjectMgr.h:101
@ SCRIPT_COMMAND_REMOVE_AURA
Definition ObjectMgr.h:107
std::string GetScriptCommandName(ScriptCommands command)
Definition ObjectMgr.cpp:104
std::map< uint32, ScriptMap > ScriptMapMap
Definition ObjectMgr.h:387
std::string GetScriptsTableNameByType(ScriptsType type)
Definition ObjectMgr.cpp:64
@ SCRIPTS_SPELL
Definition ObjectMgr.h:149
@ GAMEOBJECT_TYPE_FISHINGNODE
Definition SharedDefines.h:1583
@ CHAT_MSG_RAID_BOSS_WHISPER
Definition SharedDefines.h:3429
Definition ObjectMgr.h:191
float Orientation
Definition ObjectMgr.h:251
uint32 Flags
Definition ObjectMgr.h:208
ScriptsType type
Definition ObjectMgr.h:192
struct ScriptInfo::@269::@279 KillCredit
uint32 QuestID
Definition ObjectMgr.h:256
struct ScriptInfo::@269::@282 ToggleDoor
int32 TextID
Definition ObjectMgr.h:209
struct ScriptInfo::@269::@271 Raw
struct ScriptInfo::@269::@277 TeleportTo
float DestX
Definition ObjectMgr.h:230
uint32 ItemEntry
Definition ObjectMgr.h:317
uint32 ChatType
Definition ObjectMgr.h:207
struct ScriptInfo::@269::@283 RemoveAura
uint32 id
Definition ObjectMgr.h:193
uint32 delay
Definition ObjectMgr.h:194
float fData[4]
Definition ObjectMgr.h:202
float PosY
Definition ObjectMgr.h:279
ScriptCommands command
Definition ObjectMgr.h:195
float DestY
Definition ObjectMgr.h:231
uint32 MapID
Definition ObjectMgr.h:244
uint32 nData[3]
Definition ObjectMgr.h:201
struct ScriptInfo::@269::@273 Emote
float PosZ
Definition ObjectMgr.h:280
struct ScriptInfo::@269::@280 RespawnGameobject
struct ScriptInfo::@269::@281 TempSummonCreature
struct ScriptInfo::@269::@278 QuestExplored
float PosX
Definition ObjectMgr.h:278
struct ScriptInfo::@269::@286 CreateItem
uint32 Distance
Definition ObjectMgr.h:257
uint32 SpellID
Definition ObjectMgr.h:295
struct ScriptInfo::@269::@284 CastSpell
float DestZ
Definition ObjectMgr.h:232
uint32 GOGuid
Definition ObjectMgr.h:268
uint32 CreatureEntry
Definition ObjectMgr.h:262
uint32 Amount
Definition ObjectMgr.h:318
struct ScriptInfo::@269::@272 Talk
uint32 EmoteID
Definition ObjectMgr.h:214

References ScriptInfo::Amount, ScriptInfo::CastSpell, CHAT_MSG_RAID_BOSS_WHISPER, CHAT_TYPE_WHISPER, ScriptInfo::ChatType, ScriptInfo::command, ScriptInfo::CreateItem, ScriptInfo::CreatureEntry, DEFAULT_VISIBILITY_DISTANCE, ScriptInfo::delay, ScriptInfo::DestX, ScriptInfo::DestY, ScriptInfo::DestZ, ScriptInfo::Distance, ScriptInfo::Emote, ScriptInfo::EmoteID, GameObjectTemplate::entry, ScriptInfo::fData, ScriptInfo::Flags, GAMEOBJECT_TYPE_BUTTON, GAMEOBJECT_TYPE_DOOR, GAMEOBJECT_TYPE_FISHINGHOLE, GAMEOBJECT_TYPE_FISHINGNODE, GAMEOBJECT_TYPE_TRAP, Field::Get(), GetBroadcastText(), GetCreatureTemplate(), GetGameObjectData(), GetGameObjectTemplate(), GetItemTemplate(), getMSTime(), GetMSTimeDiffToNow(), GetQuestTemplate(), GetScriptCommandName(), GetScriptsMapByType(), GetScriptsTableNameByType(), ScriptInfo::GOGuid, Quest::HasSpecialFlag(), GameObjectData::id, ScriptInfo::id, INTERACTION_DISTANCE, Acore::IsValidMapCoord(), ScriptInfo::ItemEntry, ScriptInfo::KillCredit, LOG_ERROR, LOG_INFO, LOG_WARN, ScriptInfo::MapID, ScriptInfo::nData, ScriptInfo::Orientation, ScriptInfo::PosX, ScriptInfo::PosY, ScriptInfo::PosZ, QUEST_SPECIAL_FLAGS_EXPLORATION_OR_EVENT, ScriptInfo::QuestExplored, ScriptInfo::QuestID, ScriptInfo::Raw, ScriptInfo::RemoveAura, ScriptInfo::RespawnGameobject, SCRIPT_COMMAND_CAST_SPELL, SCRIPT_COMMAND_CLOSE_DOOR, SCRIPT_COMMAND_CREATE_ITEM, SCRIPT_COMMAND_EMOTE, SCRIPT_COMMAND_KILL_CREDIT, SCRIPT_COMMAND_OPEN_DOOR, SCRIPT_COMMAND_QUEST_EXPLORED, SCRIPT_COMMAND_REMOVE_AURA, SCRIPT_COMMAND_RESPAWN_GAMEOBJECT, SCRIPT_COMMAND_TALK, SCRIPT_COMMAND_TELEPORT_TO, SCRIPT_COMMAND_TEMP_SUMMON_CREATURE, SCRIPTS_SPELL, sEmotesStore, sMapStore, ScriptInfo::SpellID, sScriptMgr, sSpellMgr, ScriptInfo::Talk, ScriptInfo::TeleportTo, ScriptInfo::TempSummonCreature, ScriptInfo::TextID, ScriptInfo::ToggleDoor, GameObjectTemplate::type, ScriptInfo::type, and WorldDatabase.

Referenced by LoadEventScripts(), LoadSpellScripts(), and LoadWaypointScripts().

◆ LoadSpellScriptNames()

void ObjectMgr::LoadSpellScriptNames ( )
6258{
6259 uint32 oldMSTime = getMSTime();
6260
6261 _spellScriptsStore.clear(); // need for reload case
6262
6263 QueryResult result = WorldDatabase.Query("SELECT spell_id, ScriptName FROM spell_script_names");
6264
6265 if (!result)
6266 {
6267 LOG_WARN("server.loading", ">> Loaded 0 spell script names. DB table `spell_script_names` is empty!");
6268 LOG_INFO("server.loading", " ");
6269 return;
6270 }
6271
6272 uint32 count = 0;
6273
6274 do
6275 {
6276 Field* fields = result->Fetch();
6277
6278 int32 spellId = fields[0].Get<int32>();
6279 std::string scriptName = fields[1].Get<std::string>();
6280
6281 bool allRanks = false;
6282 if (spellId <= 0)
6283 {
6284 allRanks = true;
6285 spellId = -spellId;
6286 }
6287
6288 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spellId);
6289 if (!spellInfo)
6290 {
6291 LOG_ERROR("sql.sql", "Scriptname: `{}` spell (spell_id:{}) does not exist in `Spell.dbc`.", scriptName, fields[0].Get<int32>());
6292 continue;
6293 }
6294
6295 if (allRanks)
6296 {
6297 if (sSpellMgr->GetFirstSpellInChain(spellId) != uint32(spellId))
6298 {
6299 LOG_ERROR("sql.sql", "Scriptname: `{}` spell (spell_id:{}) is not first rank of spell.", scriptName, fields[0].Get<int32>());
6300 continue;
6301 }
6302 while (spellInfo)
6303 {
6304 _spellScriptsStore.insert(SpellScriptsContainer::value_type(spellInfo->Id, GetScriptId(scriptName)));
6305 spellInfo = spellInfo->GetNextRankSpell();
6306 }
6307 }
6308 else
6309 _spellScriptsStore.insert(SpellScriptsContainer::value_type(spellInfo->Id, GetScriptId(scriptName)));
6310 ++count;
6311 } while (result->NextRow());
6312
6313 LOG_INFO("server.loading", ">> Loaded {} spell script names in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
6314 LOG_INFO("server.loading", " ");
6315}
SpellInfo const * GetNextRankSpell() const
Definition SpellInfo.cpp:2915

References _spellScriptsStore, Field::Get(), getMSTime(), GetMSTimeDiffToNow(), SpellInfo::GetNextRankSpell(), GetScriptId(), SpellInfo::Id, LOG_ERROR, LOG_INFO, LOG_WARN, sSpellMgr, and WorldDatabase.

◆ LoadSpellScripts()

void ObjectMgr::LoadSpellScripts ( )
6159{
6161
6162 // check ids
6163 for (ScriptMapMap::const_iterator itr = sSpellScripts.begin(); itr != sSpellScripts.end(); ++itr)
6164 {
6165 uint32 spellId = uint32(itr->first) & 0x00FFFFFF;
6166 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spellId);
6167
6168 if (!spellInfo)
6169 {
6170 LOG_ERROR("sql.sql", "Table `spell_scripts` has not existing spell (Id: {}) as script id", spellId);
6171 continue;
6172 }
6173
6174 SpellEffIndex i = SpellEffIndex((uint32(itr->first) >> 24) & 0x000000FF);
6175 if (uint32(i) >= MAX_SPELL_EFFECTS)
6176 {
6177 LOG_ERROR("sql.sql", "Table `spell_scripts` has too high effect index {} for spell (Id: {}) as script id", uint32(i), spellId);
6178 }
6179
6180 //check for correct spellEffect
6181 if (!spellInfo->Effects[i].Effect || (spellInfo->Effects[i].Effect != SPELL_EFFECT_SCRIPT_EFFECT && spellInfo->Effects[i].Effect != SPELL_EFFECT_DUMMY))
6182 LOG_ERROR("sql.sql", "Table `spell_scripts` - spell {} effect {} is not SPELL_EFFECT_SCRIPT_EFFECT or SPELL_EFFECT_DUMMY", spellId, uint32(i));
6183 }
6184}
ScriptMapMap sSpellScripts
Definition ObjectMgr.cpp:60
SpellEffIndex
Definition SharedDefines.h:30
@ SPELL_EFFECT_DUMMY
Definition SharedDefines.h:769
@ SPELL_EFFECT_SCRIPT_EFFECT
Definition SharedDefines.h:843

References SpellInfo::Effects, LoadScripts(), LOG_ERROR, MAX_SPELL_EFFECTS, SCRIPTS_SPELL, SPELL_EFFECT_DUMMY, SPELL_EFFECT_SCRIPT_EFFECT, sSpellMgr, and sSpellScripts.

◆ LoadTavernAreaTriggers()

void ObjectMgr::LoadTavernAreaTriggers ( )
7098{
7099 uint32 oldMSTime = getMSTime();
7100
7101 _tavernAreaTriggerStore.clear(); // need for reload case
7102
7103 QueryResult result = WorldDatabase.Query("SELECT id, faction FROM areatrigger_tavern");
7104
7105 if (!result)
7106 {
7107 LOG_WARN("server.loading", ">> Loaded 0 tavern triggers. DB table `areatrigger_tavern` is empty.");
7108 LOG_INFO("server.loading", " ");
7109 return;
7110 }
7111
7112 uint32 count = 0;
7113
7114 do
7115 {
7116 ++count;
7117
7118 Field* fields = result->Fetch();
7119
7120 uint32 Trigger_ID = fields[0].Get<uint32>();
7121
7122 AreaTrigger const* atEntry = GetAreaTrigger(Trigger_ID);
7123 if (!atEntry)
7124 {
7125 LOG_ERROR("sql.sql", "Area trigger (ID:{}) does not exist in `AreaTrigger.dbc`.", Trigger_ID);
7126 continue;
7127 }
7128
7129 uint32 faction = fields[1].Get<uint32>();
7130
7131 _tavernAreaTriggerStore.emplace(Trigger_ID, faction);
7132 } while (result->NextRow());
7133
7134 LOG_INFO("server.loading", ">> Loaded {} Tavern Triggers in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
7135 LOG_INFO("server.loading", " ");
7136}

References _tavernAreaTriggerStore, Field::Get(), GetAreaTrigger(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadTempSummons()

void ObjectMgr::LoadTempSummons ( )
2150{
2151 uint32 oldMSTime = getMSTime();
2152
2153 // 0 1 2 3 4 5 6 7 8 9
2154 QueryResult result = WorldDatabase.Query("SELECT summonerId, summonerType, groupId, entry, position_x, position_y, position_z, orientation, summonType, summonTime FROM creature_summon_groups");
2155
2156 if (!result)
2157 {
2158 LOG_WARN("server.loading", ">> Loaded 0 temp summons. DB table `creature_summon_groups` is empty.");
2159 return;
2160 }
2161
2162 uint32 count = 0;
2163 do
2164 {
2165 Field* fields = result->Fetch();
2166
2167 uint32 summonerId = fields[0].Get<uint32>();
2168 SummonerType summonerType = SummonerType(fields[1].Get<uint8>());
2169 uint8 group = fields[2].Get<uint8>();
2170
2171 switch (summonerType)
2172 {
2174 if (!GetCreatureTemplate(summonerId))
2175 {
2176 LOG_ERROR("sql.sql", "Table `creature_summon_groups` has summoner with non existing entry {} for creature summoner type, skipped.", summonerId);
2177 continue;
2178 }
2179 break;
2181 if (!GetGameObjectTemplate(summonerId))
2182 {
2183 LOG_ERROR("sql.sql", "Table `creature_summon_groups` has summoner with non existing entry {} for gameobject summoner type, skipped.", summonerId);
2184 continue;
2185 }
2186 break;
2187 case SUMMONER_TYPE_MAP:
2188 if (!sMapStore.LookupEntry(summonerId))
2189 {
2190 LOG_ERROR("sql.sql", "Table `creature_summon_groups` has summoner with non existing entry {} for map summoner type, skipped.", summonerId);
2191 continue;
2192 }
2193 break;
2194 default:
2195 LOG_ERROR("sql.sql", "Table `creature_summon_groups` has unhandled summoner type {} for summoner {}, skipped.", summonerType, summonerId);
2196 continue;
2197 }
2198
2199 TempSummonData data;
2200 data.entry = fields[3].Get<uint32>();
2201
2202 if (!GetCreatureTemplate(data.entry))
2203 {
2204 LOG_ERROR("sql.sql", "Table `creature_summon_groups` has creature in group [Summoner ID: {}, Summoner Type: {}, Group ID: {}] with non existing creature entry {}, skipped.", summonerId, summonerType, group, data.entry);
2205 continue;
2206 }
2207
2208 float posX = fields[4].Get<float>();
2209 float posY = fields[5].Get<float>();
2210 float posZ = fields[6].Get<float>();
2211 float orientation = fields[7].Get<float>();
2212
2213 data.pos.Relocate(posX, posY, posZ, orientation);
2214
2215 data.type = TempSummonType(fields[8].Get<uint8>());
2216
2218 {
2219 LOG_ERROR("sql.sql", "Table `creature_summon_groups` has unhandled temp summon type {} in group [Summoner ID: {}, Summoner Type: {}, Group ID: {}] for creature entry {}, skipped.", data.type, summonerId, summonerType, group, data.entry);
2220 continue;
2221 }
2222
2223 data.time = fields[9].Get<uint32>();
2224
2225 TempSummonGroupKey key(summonerId, summonerType, group);
2226 _tempSummonDataStore[key].push_back(data);
2227
2228 ++count;
2229 } while (result->NextRow());
2230
2231 LOG_INFO("server.loading", ">> Loaded {} Temporary Summons in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2232 LOG_INFO("server.loading", " ");
2233}
TempSummonType
Definition Object.h:48
@ TEMPSUMMON_MANUAL_DESPAWN
Definition Object.h:56
Stores data for temp summons.
Definition TemporarySummon.h:33
TempSummonType type
Summon type, see TempSummonType for available types.
Definition TemporarySummon.h:36
uint32 time
Despawn time, usable only with certain temp summon types.
Definition TemporarySummon.h:37
uint32 entry
Entry of summoned creature.
Definition TemporarySummon.h:34
Position pos
Position, where should be creature spawned.
Definition TemporarySummon.h:35

References _tempSummonDataStore, TempSummonData::entry, Field::Get(), GetCreatureTemplate(), GetGameObjectTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, TempSummonData::pos, Position::Relocate(), sMapStore, SUMMONER_TYPE_CREATURE, SUMMONER_TYPE_GAMEOBJECT, SUMMONER_TYPE_MAP, TEMPSUMMON_MANUAL_DESPAWN, TempSummonData::time, TempSummonData::type, and WorldDatabase.

◆ LoadTrainers()

void ObjectMgr::LoadTrainers ( )
9748{
9749 uint32 oldMSTime = getMSTime();
9750
9751 // For reload case
9752 _trainers.clear();
9753 _classTrainers.clear();
9754
9755 std::unordered_map<int32, std::vector<Trainer::Spell>> spellsByTrainer;
9756 if (QueryResult trainerSpellsResult = WorldDatabase.Query("SELECT TrainerId, SpellId, MoneyCost, ReqSkillLine, ReqSkillRank, ReqAbility1, ReqAbility2, ReqAbility3, ReqLevel FROM trainer_spell"))
9757 {
9758 do
9759 {
9760 Field* fields = trainerSpellsResult->Fetch();
9761
9762 Trainer::Spell spell;
9763 uint32 trainerId = fields[0].Get<uint32>();
9764 spell.SpellId = fields[1].Get<uint32>();
9765 spell.MoneyCost = fields[2].Get<uint32>();
9766 spell.ReqSkillLine = fields[3].Get<uint32>();
9767 spell.ReqSkillRank = fields[4].Get<uint32>();
9768 spell.ReqAbility[0] = fields[5].Get<uint32>();
9769 spell.ReqAbility[1] = fields[6].Get<uint32>();
9770 spell.ReqAbility[2] = fields[7].Get<uint32>();
9771 spell.ReqLevel = fields[8].Get<uint8>();
9772
9773 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spell.SpellId);
9774 if (!spellInfo)
9775 {
9776 LOG_ERROR("sql.sql", "Table `trainer_spell` references non-existing spell (SpellId: {}) for TrainerId {}, ignoring", spell.SpellId, trainerId);
9777 continue;
9778 }
9779
9780 if (GetTalentSpellCost(spell.SpellId))
9781 {
9782 LOG_ERROR("sql.sql", "Table `trainer_spell` references non-existing spell (SpellId: {}) which is a talent, for TrainerId {}, ignoring", spell.SpellId, trainerId);
9783 continue;
9784 }
9785
9786 if (spell.ReqSkillLine && !sSkillLineStore.LookupEntry(spell.ReqSkillLine))
9787 {
9788 LOG_ERROR("sql.sql", "Table `trainer_spell` references non-existing skill (ReqSkillLine: {}) for TrainerId {} and SpellId {}, ignoring",
9789 spell.ReqSkillLine, spell.SpellId, trainerId);
9790 continue;
9791 }
9792
9793 bool allReqValid = true;
9794 for (std::size_t i = 0; i < spell.ReqAbility.size(); ++i)
9795 {
9796 uint32 requiredSpell = spell.ReqAbility[i];
9797 if (requiredSpell && !sSpellMgr->GetSpellInfo(requiredSpell))
9798 {
9799 LOG_ERROR("sql.sql", "Table `trainer_spell` references non-existing spell (ReqAbility {} : {}) for TrainerId {} and SpellId {}, ignoring",
9800 i + 1, requiredSpell, trainerId, spell.SpellId);
9801 allReqValid = false;
9802 }
9803 }
9804
9805 if (!allReqValid)
9806 continue;
9807
9808 spellsByTrainer[trainerId].push_back(spell);
9809 } while (trainerSpellsResult->NextRow());
9810 }
9811
9812 if (QueryResult trainersResult = WorldDatabase.Query("SELECT Id, Type, Requirement, Greeting FROM trainer"))
9813 {
9814 do
9815 {
9816 Field* fields = trainersResult->Fetch();
9817
9818 uint32 trainerId = fields[0].Get<uint32>();
9819 Trainer::Type trainerType = Trainer::Type(fields[1].Get<uint8>());
9820 uint32 requirement = fields[2].Get<uint32>();
9821 std::string greeting = fields[3].Get<std::string>();
9822 std::vector<Trainer::Spell> spells;
9823 auto spellsItr = spellsByTrainer.find(trainerId);
9824 if (spellsItr != spellsByTrainer.end())
9825 {
9826 spells = std::move(spellsItr->second);
9827 spellsByTrainer.erase(spellsItr);
9828 }
9829
9830 auto [it, isNew] = _trainers.emplace(std::piecewise_construct, std::forward_as_tuple(trainerId), std::forward_as_tuple(trainerId, trainerType, requirement, std::move(greeting), std::move(spells)));
9831 ASSERT(isNew);
9832 if (trainerType == Trainer::Type::Class)
9833 {
9834 if (!requirement || requirement >= MAX_CLASSES)
9835 LOG_ERROR("sql.sql", "Table `trainer` has invalid class requirement for trainer {}, ignoring");
9836 else
9837 {
9838 uint8 classId = static_cast<uint8>(requirement);
9839 _classTrainers[classId].push_back(&it->second);
9840 }
9841 }
9842 } while (trainersResult->NextRow());
9843 }
9844
9845 for (auto const& unusedSpells : spellsByTrainer)
9846 {
9847 for (Trainer::Spell const& unusedSpell : unusedSpells.second)
9848 {
9849 LOG_ERROR("sql.sql", "Table `trainer_spell` references non-existing trainer (TrainerId: {}) for SpellId {}, ignoring", unusedSpells.first, unusedSpell.SpellId);
9850 }
9851 }
9852
9853 if (QueryResult trainerLocalesResult = WorldDatabase.Query("SELECT Id, locale, Greeting_lang FROM trainer_locale"))
9854 {
9855 do
9856 {
9857 Field* fields = trainerLocalesResult->Fetch();
9858 uint32 trainerId = fields[0].Get<uint32>();
9859 std::string localeName = fields[1].Get<std::string>();
9860
9861 LocaleConstant locale = GetLocaleByName(localeName);
9862 if (locale == LOCALE_enUS)
9863 continue;
9864
9866 trainer->AddGreetingLocale(locale, fields[2].Get<std::string>());
9867 else
9868 LOG_ERROR("sql.sql", "Table `trainer_locale` references non-existing trainer (TrainerId: {}) for locale %s, ignoring",
9869 trainerId, localeName.c_str());
9870 } while (trainerLocalesResult->NextRow());
9871 }
9872
9873 LOG_INFO("server.loading", ">> Loaded {} Trainers in {} ms", _trainers.size(), GetMSTimeDiffToNow(oldMSTime));
9874}
#define ASSERT
Definition Errors.h:68
Definition Trainer.h:66
Type
Definition Trainer.h:32
Definition Trainer.h:54
uint32 ReqSkillLine
Definition Trainer.h:57
std::array< uint32, 3 > ReqAbility
Definition Trainer.h:59
uint8 ReqLevel
Definition Trainer.h:60
uint32 ReqSkillRank
Definition Trainer.h:58
uint32 SpellId
Definition Trainer.h:55
uint32 MoneyCost
Definition Trainer.h:56

References _classTrainers, _trainers, ASSERT, Trainer::Class, Field::Get(), GetLocaleByName(), getMSTime(), GetMSTimeDiffToNow(), GetTalentSpellCost(), LOCALE_enUS, LOG_ERROR, LOG_INFO, Acore::Containers::MapGetValuePtr(), MAX_CLASSES, Trainer::Spell::MoneyCost, Trainer::Spell::ReqAbility, Trainer::Spell::ReqLevel, Trainer::Spell::ReqSkillLine, Trainer::Spell::ReqSkillRank, Trainer::Spell::SpellId, sSkillLineStore, sSpellMgr, and WorldDatabase.

◆ LoadVehicleAccessories()

void ObjectMgr::LoadVehicleAccessories ( )
4025{
4026 uint32 oldMSTime = getMSTime();
4027
4028 _vehicleAccessoryStore.clear(); // needed for reload case
4029
4030 uint32 count = 0;
4031
4032 // 0 1 2 3 4 5
4033 QueryResult result = WorldDatabase.Query("SELECT `guid`, `accessory_entry`, `seat_id`, `minion`, `summontype`, `summontimer` FROM `vehicle_accessory`");
4034
4035 if (!result)
4036 {
4037 LOG_WARN("server.loading", ">> Loaded 0 Vehicle Accessories in {} ms", GetMSTimeDiffToNow(oldMSTime));
4038 LOG_INFO("server.loading", " ");
4039 return;
4040 }
4041
4042 do
4043 {
4044 Field* fields = result->Fetch();
4045
4046 uint32 uiGUID = fields[0].Get<uint32>();
4047 uint32 uiAccessory = fields[1].Get<uint32>();
4048 int8 uiSeat = int8(fields[2].Get<int16>());
4049 bool bMinion = fields[3].Get<bool>();
4050 uint8 uiSummonType = fields[4].Get<uint8>();
4051 uint32 uiSummonTimer = fields[5].Get<uint32>();
4052
4053 if (!GetCreatureTemplate(uiAccessory))
4054 {
4055 LOG_ERROR("sql.sql", "Table `vehicle_accessory`: Accessory {} does not exist.", uiAccessory);
4056 continue;
4057 }
4058
4059 _vehicleAccessoryStore[uiGUID].push_back(VehicleAccessory(uiAccessory, uiSeat, bMinion, uiSummonType, uiSummonTimer));
4060
4061 ++count;
4062 } while (result->NextRow());
4063
4064 LOG_INFO("server.loading", ">> Loaded {} Vehicle Accessories in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4065 LOG_INFO("server.loading", " ");
4066}
Definition VehicleDefines.h:115

References _vehicleAccessoryStore, Field::Get(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadVehicleSeatAddon()

void ObjectMgr::LoadVehicleSeatAddon ( )
4069{
4070 uint32 oldMSTime = getMSTime();
4071
4072 _vehicleSeatAddonStore.clear(); // needed for reload case
4073
4074 uint32 count = 0;
4075
4076 // 0 1 2 3 4 5 6
4077 QueryResult result = WorldDatabase.Query("SELECT `SeatEntry`, `SeatOrientation`, `ExitParamX`, `ExitParamY`, `ExitParamZ`, `ExitParamO`, `ExitParamValue` FROM `vehicle_seat_addon`");
4078
4079 if (!result)
4080 {
4081 LOG_ERROR("server.loading", ">> Loaded 0 vehicle seat addons. DB table `vehicle_seat_addon` is empty.");
4082 return;
4083 }
4084
4085 do
4086 {
4087 Field* fields = result->Fetch();
4088
4089 uint32 seatID = fields[0].Get<uint32>();
4090 float orientation = fields[1].Get<float>();
4091 float exitX = fields[2].Get<float>();
4092 float exitY = fields[3].Get<float>();
4093 float exitZ = fields[4].Get<float>();
4094 float exitO = fields[5].Get<float>();
4095 uint8 exitParam = fields[6].Get<uint8>();
4096
4097 if (!sVehicleSeatStore.LookupEntry(seatID))
4098 {
4099 LOG_ERROR("sql.sql", "Table `vehicle_seat_addon`: SeatID: {} does not exist in VehicleSeat.dbc. Skipping entry.", seatID);
4100 continue;
4101 }
4102
4103 // Sanitizing values
4104 if (orientation > float(M_PI * 2))
4105 {
4106 LOG_ERROR("sql.sql", "Table `vehicle_seat_addon`: SeatID: {} is using invalid angle offset value ({}). Set Value to 0.", seatID, orientation);
4107 orientation = 0.0f;
4108 }
4109
4111 {
4112 LOG_ERROR("sql.sql", "Table `vehicle_seat_addon`: SeatID: {} is using invalid exit parameter value ({}). Setting to 0 (none).", seatID, exitParam);
4113 continue;
4114 }
4115
4116 _vehicleSeatAddonStore[seatID] = VehicleSeatAddon(orientation, exitX, exitY, exitZ, exitO, exitParam);
4117
4118 ++count;
4119 } while (result->NextRow());
4120
4121 LOG_INFO("server.loading", ">> Loaded {} Vehicle Seat Addon entries in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4122}
DBCStorage< VehicleSeatEntry > sVehicleSeatStore(VehicleSeatEntryfmt)
Definition VehicleDefines.h:86

References _vehicleSeatAddonStore, AsUnderlyingType(), Field::Get(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, sVehicleSeatStore, VehicleExitParamMax, and WorldDatabase.

◆ LoadVehicleTemplateAccessories()

void ObjectMgr::LoadVehicleTemplateAccessories ( )
3969{
3970 uint32 oldMSTime = getMSTime();
3971
3972 _vehicleTemplateAccessoryStore.clear(); // needed for reload case
3973
3974 uint32 count = 0;
3975
3976 // 0 1 2 3 4 5
3977 QueryResult result = WorldDatabase.Query("SELECT `entry`, `accessory_entry`, `seat_id`, `minion`, `summontype`, `summontimer` FROM `vehicle_template_accessory`");
3978
3979 if (!result)
3980 {
3981 LOG_WARN("server.loading", ">> Loaded 0 vehicle template accessories. DB table `vehicle_template_accessory` is empty.");
3982 LOG_INFO("server.loading", " ");
3983 return;
3984 }
3985
3986 do
3987 {
3988 Field* fields = result->Fetch();
3989
3990 uint32 uiEntry = fields[0].Get<uint32>();
3991 uint32 uiAccessory = fields[1].Get<uint32>();
3992 int8 uiSeat = int8(fields[2].Get<int8>());
3993 bool bMinion = fields[3].Get<bool>();
3994 uint8 uiSummonType = fields[4].Get<uint8>();
3995 uint32 uiSummonTimer = fields[5].Get<uint32>();
3996
3997 if (!GetCreatureTemplate(uiEntry))
3998 {
3999 LOG_ERROR("sql.sql", "Table `vehicle_template_accessory`: creature template entry {} does not exist.", uiEntry);
4000 continue;
4001 }
4002
4003 if (!GetCreatureTemplate(uiAccessory))
4004 {
4005 LOG_ERROR("sql.sql", "Table `vehicle_template_accessory`: Accessory {} does not exist.", uiAccessory);
4006 continue;
4007 }
4008
4009 if (_spellClickInfoStore.find(uiEntry) == _spellClickInfoStore.end())
4010 {
4011 LOG_ERROR("sql.sql", "Table `vehicle_template_accessory`: creature template entry {} has no data in npc_spellclick_spells", uiEntry);
4012 continue;
4013 }
4014
4015 _vehicleTemplateAccessoryStore[uiEntry].push_back(VehicleAccessory(uiAccessory, uiSeat, bMinion, uiSummonType, uiSummonTimer));
4016
4017 ++count;
4018 } while (result->NextRow());
4019
4020 LOG_INFO("server.loading", ">> Loaded {} Vehicle Template Accessories in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
4021 LOG_INFO("server.loading", " ");
4022}

References _spellClickInfoStore, _vehicleTemplateAccessoryStore, Field::Get(), GetCreatureTemplate(), getMSTime(), GetMSTimeDiffToNow(), LOG_ERROR, LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadVendors()

void ObjectMgr::LoadVendors ( )
9953{
9954 uint32 oldMSTime = getMSTime();
9955
9956 // For reload case
9957 for (CacheVendorItemContainer::iterator itr = _cacheVendorItemStore.begin(); itr != _cacheVendorItemStore.end(); ++itr)
9958 itr->second.Clear();
9959 _cacheVendorItemStore.clear();
9960
9961 std::set<uint32> skip_vendors;
9962
9963 QueryResult result = WorldDatabase.Query("SELECT entry, item, maxcount, incrtime, ExtendedCost FROM npc_vendor ORDER BY entry, slot ASC, item, ExtendedCost");
9964 if (!result)
9965 {
9966 LOG_INFO("server.loading", " ");
9967 LOG_WARN("server.loading", ">> Loaded 0 Vendors. DB table `npc_vendor` is empty!");
9968 return;
9969 }
9970
9971 uint32 count = 0;
9972
9973 do
9974 {
9975 Field* fields = result->Fetch();
9976
9977 uint32 entry = fields[0].Get<uint32>();
9978 int32 item_id = fields[1].Get<int32>();
9979
9980 // if item is a negative, its a reference
9981 if (item_id < 0)
9982 count += LoadReferenceVendor(entry, -item_id, &skip_vendors);
9983 else
9984 {
9985 uint32 maxcount = fields[2].Get<uint32>();
9986 uint32 incrtime = fields[3].Get<uint32>();
9987 uint32 ExtendedCost = fields[4].Get<uint32>();
9988
9989 if (!IsVendorItemValid(entry, item_id, maxcount, incrtime, ExtendedCost, nullptr, &skip_vendors))
9990 continue;
9991
9992 VendorItemData& vList = _cacheVendorItemStore[entry];
9993
9994 vList.AddItem(item_id, maxcount, incrtime, ExtendedCost);
9995 ++count;
9996 }
9997 } while (result->NextRow());
9998
9999 LOG_INFO("server.loading", ">> Loaded {} Vendors in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
10000 LOG_INFO("server.loading", " ");
10001}

References _cacheVendorItemStore, VendorItemData::AddItem(), Field::Get(), getMSTime(), GetMSTimeDiffToNow(), IsVendorItemValid(), LoadReferenceVendor(), LOG_INFO, LOG_WARN, and WorldDatabase.

◆ LoadWaypointScripts()

void ObjectMgr::LoadWaypointScripts ( )
6231{
6233
6234 std::set<uint32> actionSet;
6235
6236 for (ScriptMapMap::const_iterator itr = sWaypointScripts.begin(); itr != sWaypointScripts.end(); ++itr)
6237 actionSet.insert(itr->first);
6238
6240 PreparedQueryResult result = WorldDatabase.Query(stmt);
6241
6242 if (result)
6243 {
6244 do
6245 {
6246 Field* fields = result->Fetch();
6247 uint32 action = fields[0].Get<uint32>();
6248
6249 actionSet.erase(action);
6250 } while (result->NextRow());
6251 }
6252
6253 for (std::set<uint32>::iterator itr = actionSet.begin(); itr != actionSet.end(); ++itr)
6254 LOG_ERROR("sql.sql", "There is no waypoint which links to the waypoint script {}", *itr);
6255}
ScriptMapMap sWaypointScripts
Definition ObjectMgr.cpp:62
@ SCRIPTS_WAYPOINT
Definition ObjectMgr.h:151
@ WORLD_SEL_WAYPOINT_DATA_ACTION
Definition WorldDatabase.h:69

References Field::Get(), LoadScripts(), LOG_ERROR, SCRIPTS_WAYPOINT, sWaypointScripts, WORLD_SEL_WAYPOINT_DATA_ACTION, and WorldDatabase.

◆ NewGOData()

GameObjectData & ObjectMgr::NewGOData ( ObjectGuid::LowType  guid)
inline
1349{ return _gameObjectDataStore[guid]; }

References _gameObjectDataStore.

Referenced by AddGOData().

◆ NewOrExistCreatureData()

CreatureData & ObjectMgr::NewOrExistCreatureData ( ObjectGuid::LowType  spawnId)
inline
1241{ return _creatureDataStore[spawnId]; }

References _creatureDataStore.

Referenced by AddCreData().

◆ PlayerCreateInfoAddItemHelper()

void ObjectMgr::PlayerCreateInfoAddItemHelper ( uint32  race_,
uint32  class_,
uint32  itemId,
int32  count 
)
private
4230{
4231 if (!_playerInfo[race_][class_])
4232 return;
4233
4234 if (count > 0)
4235 _playerInfo[race_][class_]->item.push_back(PlayerCreateInfoItem(itemId, count));
4236 else
4237 {
4238 if (count < -1)
4239 LOG_ERROR("sql.sql", "Invalid count {} specified on item {} be removed from original player create info (use -1)!", count, itemId);
4240
4241 for (uint32 gender = 0; gender < GENDER_NONE; ++gender)
4242 {
4243 if (CharStartOutfitEntry const* entry = GetCharStartOutfitEntry(race_, class_, gender))
4244 {
4245 bool found = false;
4246 for (uint8 x = 0; x < MAX_OUTFIT_ITEMS; ++x)
4247 {
4248 if (entry->ItemId[x] > 0 && uint32(entry->ItemId[x]) == itemId)
4249 {
4250 found = true;
4251 const_cast<CharStartOutfitEntry*>(entry)->ItemId[x] = 0;
4252 break;
4253 }
4254 }
4255
4256 if (!found)
4257 LOG_ERROR("sql.sql", "Item {} specified to be removed from original create info not found in dbc!", itemId);
4258 }
4259 }
4260 }
4261}
CharStartOutfitEntry const * GetCharStartOutfitEntry(uint8 race, uint8 class_, uint8 gender)
Definition DBCStores.cpp:842
Definition Player.h:266

References _playerInfo, GENDER_NONE, GetCharStartOutfitEntry(), LOG_ERROR, and MAX_OUTFIT_ITEMS.

Referenced by LoadPlayerInfo().

◆ RemoveCreatureFromGrid()

void ObjectMgr::RemoveCreatureFromGrid ( ObjectGuid::LowType  guid,
CreatureData const *  data 
)
2725{
2726 uint8 mask = data->spawnMask;
2727 for (uint8 i = 0; mask != 0; i++, mask >>= 1)
2728 {
2729 if (mask & 1)
2730 {
2731 GridCoord gridCoord = Acore::ComputeGridCoord(data->posX, data->posY);
2732 CellObjectGuids& cell_guids = _mapObjectGuidsStore[MAKE_PAIR32(data->mapid, i)][gridCoord.GetId()];
2733 cell_guids.creatures.erase(guid);
2734 }
2735 }
2736}

References _mapObjectGuidsStore, Acore::ComputeGridCoord(), CellObjectGuids::creatures, CoordPair< LIMIT >::GetId(), MAKE_PAIR32(), SpawnData::mapid, SpawnData::posX, SpawnData::posY, and SpawnData::spawnMask.

Referenced by DeleteCreatureData().

◆ RemoveGameobjectFromGrid()

void ObjectMgr::RemoveGameobjectFromGrid ( ObjectGuid::LowType  guid,
GameObjectData const *  data 
)
3169{
3170 uint8 mask = data->spawnMask;
3171 for (uint8 i = 0; mask != 0; i++, mask >>= 1)
3172 {
3173 if (mask & 1)
3174 {
3175 GridCoord gridCoord = Acore::ComputeGridCoord(data->posX, data->posY);
3176 CellObjectGuids& cell_guids = _mapObjectGuidsStore[MAKE_PAIR32(data->mapid, i)][gridCoord.GetId()];
3177 cell_guids.gameobjects.erase(guid);
3178 }
3179 }
3180}

References _mapObjectGuidsStore, Acore::ComputeGridCoord(), CellObjectGuids::gameobjects, CoordPair< LIMIT >::GetId(), MAKE_PAIR32(), SpawnData::mapid, SpawnData::posX, SpawnData::posY, and SpawnData::spawnMask.

Referenced by DeleteGOData().

◆ RemoveVendorItem()

bool ObjectMgr::RemoveVendorItem ( uint32  entry,
uint32  item,
bool  persist = true 
)
10154{
10155 CacheVendorItemContainer::iterator iter = _cacheVendorItemStore.find(entry);
10156 if (iter == _cacheVendorItemStore.end())
10157 return false;
10158
10159 if (!iter->second.RemoveItem(item))
10160 return false;
10161
10162 if (persist)
10163 {
10165
10166 stmt->SetData(0, entry);
10167 stmt->SetData(1, item);
10168
10169 WorldDatabase.Execute(stmt);
10170 }
10171
10172 return true;
10173}
@ WORLD_DEL_NPC_VENDOR
Definition WorldDatabase.h:44

References _cacheVendorItemStore, PreparedStatementBase::SetData(), WORLD_DEL_NPC_VENDOR, and WorldDatabase.

◆ ReturnOrDeleteOldMails()

void ObjectMgr::ReturnOrDeleteOldMails ( bool  serverUp)
6726{
6727 uint32 oldMSTime = getMSTime();
6728
6729 time_t curTime = GameTime::GetGameTime().count();
6730
6732 stmt->SetData(0, uint32(curTime));
6733 PreparedQueryResult result = CharacterDatabase.Query(stmt);
6734 if (!result)
6735 return;
6736
6737 std::map<uint32 /*messageId*/, MailItemInfoVec> itemsCache;
6738 stmt = CharacterDatabase.GetPreparedStatement(CHAR_SEL_EXPIRED_MAIL_ITEMS);
6739 stmt->SetData(0, uint32(curTime));
6740 if (PreparedQueryResult items = CharacterDatabase.Query(stmt))
6741 {
6742 MailItemInfo item;
6743 do
6744 {
6745 Field* fields = items->Fetch();
6746 item.item_guid = fields[0].Get<uint32>();
6747 item.item_template = fields[1].Get<uint32>();
6748 uint32 mailId = fields[2].Get<uint32>();
6749 itemsCache[mailId].push_back(item);
6750 } while (items->NextRow());
6751 }
6752
6753 uint32 deletedCount = 0;
6754 uint32 returnedCount = 0;
6755 do
6756 {
6757 Field* fields = result->Fetch();
6758 Mail* m = new Mail;
6759 m->messageID = fields[0].Get<uint32>();
6760 m->messageType = fields[1].Get<uint8>();
6761 m->sender = fields[2].Get<uint32>();
6762 m->receiver = fields[3].Get<uint32>();
6763 bool has_items = fields[4].Get<bool>();
6764 m->expire_time = time_t(fields[5].Get<uint32>());
6765 m->deliver_time = time_t(0);
6766 m->stationery = fields[6].Get<uint8>();
6767 m->checked = fields[7].Get<uint8>();
6768 m->mailTemplateId = fields[8].Get<int16>();
6769
6770 Player* player = nullptr;
6771 if (serverUp)
6773
6774 if (player) // don't modify mails of a logged in player
6775 {
6776 delete m;
6777 continue;
6778 }
6779
6780 // Delete or return mail
6781 if (has_items)
6782 {
6783 // read items from cache
6784 m->items.swap(itemsCache[m->messageID]);
6785
6786 // If it is mail from non-player, or if it's already return mail, it shouldn't be returned, but deleted
6787 if (!m->IsSentByPlayer() || m->IsSentByGM() || (m->IsCODPayment() || m->IsReturnedMail()))
6788 {
6789 for (auto const& mailedItem : m->items)
6790 {
6791 stmt = CharacterDatabase.GetPreparedStatement(CHAR_DEL_ITEM_INSTANCE);
6792 stmt->SetData(0, mailedItem.item_guid);
6793 CharacterDatabase.Execute(stmt);
6794 }
6795
6796 stmt = CharacterDatabase.GetPreparedStatement(CHAR_DEL_MAIL_ITEM_BY_ID);
6797 stmt->SetData(0, m->messageID);
6798 CharacterDatabase.Execute(stmt);
6799 }
6800 else
6801 {
6802 // Mail will be returned
6803 stmt = CharacterDatabase.GetPreparedStatement(CHAR_UPD_MAIL_RETURNED);
6804 stmt->SetData(0, m->receiver);
6805 stmt->SetData(1, m->sender);
6806 stmt->SetData(2, uint32(curTime + 30 * DAY));
6807 stmt->SetData(3, uint32(curTime));
6809 stmt->SetData(5, m->messageID);
6810 CharacterDatabase.Execute(stmt);
6811 for (auto const& mailedItem : m->items)
6812 {
6813 // Update receiver in mail items for its proper delivery, and in instance_item for avoid lost item at sender delete
6814 stmt = CharacterDatabase.GetPreparedStatement(CHAR_UPD_MAIL_ITEM_RECEIVER);
6815 stmt->SetData(0, m->sender);
6816 stmt->SetData(1, mailedItem.item_guid);
6817 CharacterDatabase.Execute(stmt);
6818
6819 stmt = CharacterDatabase.GetPreparedStatement(CHAR_UPD_ITEM_OWNER);
6820 stmt->SetData(0, m->sender);
6821 stmt->SetData(1, mailedItem.item_guid);
6822 CharacterDatabase.Execute(stmt);
6823 }
6824
6825 // xinef: update global data
6826 sCharacterCache->IncreaseCharacterMailCount(ObjectGuid(HighGuid::Player, m->sender));
6827 sCharacterCache->DecreaseCharacterMailCount(ObjectGuid(HighGuid::Player, m->receiver));
6828
6829 delete m;
6830 ++returnedCount;
6831 continue;
6832 }
6833 }
6834
6835 sCharacterCache->DecreaseCharacterMailCount(ObjectGuid(HighGuid::Player, m->receiver));
6836
6837 stmt = CharacterDatabase.GetPreparedStatement(CHAR_DEL_MAIL_BY_ID);
6838 stmt->SetData(0, m->messageID);
6839 CharacterDatabase.Execute(stmt);
6840 delete m;
6841 ++deletedCount;
6842 } while (result->NextRow());
6843
6844 LOG_INFO("server.loading", ">> Processed {} expired mails: {} deleted and {} returned in {} ms", deletedCount + returnedCount, deletedCount, returnedCount, GetMSTimeDiffToNow(oldMSTime));
6845 LOG_INFO("server.loading", " ");
6846}
#define sCharacterCache
Definition CharacterCache.h:83
@ CHAR_UPD_ITEM_OWNER
Definition CharacterDatabase.h:118
@ CHAR_DEL_ITEM_INSTANCE
Definition CharacterDatabase.h:127
@ CHAR_UPD_MAIL_RETURNED
Definition CharacterDatabase.h:116
@ CHAR_SEL_EXPIRED_MAIL
Definition CharacterDatabase.h:114
@ CHAR_SEL_EXPIRED_MAIL_ITEMS
Definition CharacterDatabase.h:115
@ CHAR_DEL_MAIL_BY_ID
Definition CharacterDatabase.h:110
@ CHAR_DEL_MAIL_ITEM_BY_ID
Definition CharacterDatabase.h:382
@ CHAR_UPD_MAIL_ITEM_RECEIVER
Definition CharacterDatabase.h:117
std::vector< MailItemInfo > MailItemInfoVec
Definition Mail.h:164
@ MAIL_CHECK_MASK_RETURNED
Definition Mail.h:48
Definition Player.h:1084
Seconds GetGameTime()
Definition GameTime.cpp:38
Player * FindPlayerByLowGUID(ObjectGuid::LowType lowguid)
Definition ObjectAccessor.cpp:251
Definition Mail.h:160
ObjectGuid::LowType item_guid
Definition Mail.h:161
uint32 item_template
Definition Mail.h:162
Definition Mail.h:167
bool IsSentByGM() const
Definition Mail.h:208
bool IsCODPayment() const
Definition Mail.h:209
ObjectGuid::LowType receiver
Definition Mail.h:173
uint8 messageType
Definition Mail.h:169
bool IsSentByPlayer() const
Definition Mail.h:207
uint32 messageID
Definition Mail.h:168
time_t expire_time
Definition Mail.h:178
uint32 sender
Definition Mail.h:172
uint8 stationery
Definition Mail.h:170
std::vector< MailItemInfo > items
Definition Mail.h:176
time_t deliver_time
Definition Mail.h:179
bool IsReturnedMail() const
Definition Mail.h:210
uint32 checked
Definition Mail.h:182
uint16 mailTemplateId
Definition Mail.h:171

References CHAR_DEL_ITEM_INSTANCE, CHAR_DEL_MAIL_BY_ID, CHAR_DEL_MAIL_ITEM_BY_ID, CHAR_SEL_EXPIRED_MAIL, CHAR_SEL_EXPIRED_MAIL_ITEMS, CHAR_UPD_ITEM_OWNER, CHAR_UPD_MAIL_ITEM_RECEIVER, CHAR_UPD_MAIL_RETURNED, CharacterDatabase, Mail::checked, DAY, Mail::deliver_time, Mail::expire_time, ObjectAccessor::FindPlayerByLowGUID(), Field::Get(), GameTime::GetGameTime(), getMSTime(), GetMSTimeDiffToNow(), Mail::IsCODPayment(), Mail::IsReturnedMail(), Mail::IsSentByGM(), Mail::IsSentByPlayer(), MailItemInfo::item_guid, MailItemInfo::item_template, Mail::items, LOG_INFO, MAIL_CHECK_MASK_RETURNED, Mail::mailTemplateId, Mail::messageID, Mail::messageType, Player, Mail::receiver, sCharacterCache, Mail::sender, PreparedStatementBase::SetData(), and Mail::stationery.

◆ SetCreatureLinkedRespawn()

bool ObjectMgr::SetCreatureLinkedRespawn ( ObjectGuid::LowType  guid,
ObjectGuid::LowType  linkedGuid 
)
2103{
2104 if (!guidLow)
2105 return false;
2106
2107 CreatureData const* master = GetCreatureData(guidLow);
2108 ObjectGuid guid = ObjectGuid::Create<HighGuid::Unit>(master->id1, guidLow);
2109
2110 if (!linkedGuidLow) // we're removing the linking
2111 {
2112 _linkedRespawnStore.erase(guid);
2114 stmt->SetData(0, guidLow);
2115 WorldDatabase.Execute(stmt);
2116 return true;
2117 }
2118
2119 CreatureData const* slave = GetCreatureData(linkedGuidLow);
2120 if (!slave)
2121 {
2122 LOG_ERROR("sql.sql", "Creature '{}' linking to non-existent creature '{}'.", guidLow, linkedGuidLow);
2123 return false;
2124 }
2125
2126 MapEntry const* map = sMapStore.LookupEntry(master->mapid);
2127 if (!map || !map->Instanceable() || (master->mapid != slave->mapid))
2128 {
2129 LOG_ERROR("sql.sql", "Creature '{}' linking to '{}' on an unpermitted map.", guidLow, linkedGuidLow);
2130 return false;
2131 }
2132
2133 if (!(master->spawnMask & slave->spawnMask)) // they must have a possibility to meet (normal/heroic difficulty)
2134 {
2135 LOG_ERROR("sql.sql", "LinkedRespawn: Creature '{}' linking to '{}' with not corresponding spawnMask", guidLow, linkedGuidLow);
2136 return false;
2137 }
2138
2139 ObjectGuid linkedGuid = ObjectGuid::Create<HighGuid::Unit>(slave->id1, linkedGuidLow);
2140
2141 _linkedRespawnStore[guid] = linkedGuid;
2143 stmt->SetData(0, guidLow);
2144 stmt->SetData(1, linkedGuidLow);
2145 WorldDatabase.Execute(stmt);
2146 return true;
2147}
@ WORLD_REP_CREATURE_LINKED_RESPAWN
Definition WorldDatabase.h:33
@ WORLD_DEL_CRELINKED_RESPAWN
Definition WorldDatabase.h:32

References _linkedRespawnStore, GetCreatureData(), CreatureData::id1, MapEntry::Instanceable(), LOG_ERROR, SpawnData::mapid, PreparedStatementBase::SetData(), sMapStore, SpawnData::spawnMask, WORLD_DEL_CRELINKED_RESPAWN, WORLD_REP_CREATURE_LINKED_RESPAWN, and WorldDatabase.

◆ SetDBCLocaleIndex()

void ObjectMgr::SetDBCLocaleIndex ( LocaleConstant  locale)
inline
1389{ DBCLocaleIndex = locale; }

References DBCLocaleIndex.

◆ SetHighestGuids()

void ObjectMgr::SetHighestGuids ( )
7613{
7614 QueryResult result = CharacterDatabase.Query("SELECT MAX(guid) FROM characters");
7615 if (result)
7616 GetGuidSequenceGenerator<HighGuid::Player>().Set((*result)[0].Get<uint32>() + 1);
7617
7618 result = CharacterDatabase.Query("SELECT MAX(guid) FROM item_instance");
7619 if (result)
7620 GetGuidSequenceGenerator<HighGuid::Item>().Set((*result)[0].Get<uint32>() + 1);
7621
7622 // Cleanup other tables from not existed guids ( >= _hiItemGuid)
7623 CharacterDatabase.Execute("DELETE FROM character_inventory WHERE item >= '{}'", GetGuidSequenceGenerator<HighGuid::Item>().GetNextAfterMaxUsed()); // One-time query
7624 CharacterDatabase.Execute("DELETE FROM mail_items WHERE item_guid >= '{}'", GetGuidSequenceGenerator<HighGuid::Item>().GetNextAfterMaxUsed()); // One-time query
7625 CharacterDatabase.Execute("DELETE FROM auctionhouse WHERE itemguid >= '{}'", GetGuidSequenceGenerator<HighGuid::Item>().GetNextAfterMaxUsed()); // One-time query
7626 CharacterDatabase.Execute("DELETE FROM guild_bank_item WHERE item_guid >= '{}'", GetGuidSequenceGenerator<HighGuid::Item>().GetNextAfterMaxUsed()); // One-time query
7627
7628 result = WorldDatabase.Query("SELECT MAX(guid) FROM transports");
7629 if (result)
7630 GetGuidSequenceGenerator<HighGuid::Mo_Transport>().Set((*result)[0].Get<uint32>() + 1);
7631
7632 result = CharacterDatabase.Query("SELECT MAX(id) FROM auctionhouse");
7633 if (result)
7634 _auctionId = (*result)[0].Get<uint32>() + 1;
7635
7636 result = CharacterDatabase.Query("SELECT MAX(id) FROM mail");
7637 if (result)
7638 _mailId = (*result)[0].Get<uint32>() + 1;
7639
7640 result = CharacterDatabase.Query("SELECT MAX(arenateamid) FROM arena_team");
7641 if (result)
7642 sArenaTeamMgr->SetNextArenaTeamId((*result)[0].Get<uint32>() + 1);
7643
7644 result = CharacterDatabase.Query("SELECT MAX(fight_id) FROM log_arena_fights");
7645 if (result)
7646 sArenaTeamMgr->SetLastArenaLogId((*result)[0].Get<uint32>());
7647
7648 result = CharacterDatabase.Query("SELECT MAX(setguid) FROM character_equipmentsets");
7649 if (result)
7650 _equipmentSetGuid = (*result)[0].Get<uint64>() + 1;
7651
7652 result = CharacterDatabase.Query("SELECT MAX(guildId) FROM guild");
7653 if (result)
7654 sGuildMgr->SetNextGuildId((*result)[0].Get<uint32>() + 1);
7655
7656 result = WorldDatabase.Query("SELECT MAX(guid) FROM creature");
7657 if (result)
7658 _creatureSpawnId = (*result)[0].Get<uint32>() + 1;
7659
7660 result = WorldDatabase.Query("SELECT MAX(guid) FROM gameobject");
7661 if (result)
7662 _gameObjectSpawnId = (*result)[0].Get<uint32>() + 1;
7663}
#define sArenaTeamMgr
Definition ArenaTeamMgr.h:69
#define sGuildMgr
Definition GuildMgr.h:51

References _auctionId, _creatureSpawnId, _equipmentSetGuid, _gameObjectSpawnId, _mailId, CharacterDatabase, sArenaTeamMgr, sGuildMgr, and WorldDatabase.

◆ ValidateSpellScripts()

void ObjectMgr::ValidateSpellScripts ( )
6318{
6319 uint32 oldMSTime = getMSTime();
6320
6321 if (_spellScriptsStore.empty())
6322 {
6323 LOG_INFO("server.loading", ">> Validated 0 scripts.");
6324 LOG_INFO("server.loading", " ");
6325 return;
6326 }
6327
6328 uint32 count = 0;
6329
6330 for (SpellScriptsContainer::iterator itr = _spellScriptsStore.begin(); itr != _spellScriptsStore.end();)
6331 {
6332 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(itr->first);
6333 std::vector<std::pair<SpellScriptLoader*, SpellScriptsContainer::iterator> > SpellScriptLoaders;
6334 sScriptMgr->CreateSpellScriptLoaders(itr->first, SpellScriptLoaders);
6335 itr = _spellScriptsStore.upper_bound(itr->first);
6336
6337 for (std::vector<std::pair<SpellScriptLoader*, SpellScriptsContainer::iterator> >::iterator sitr = SpellScriptLoaders.begin(); sitr != SpellScriptLoaders.end(); ++sitr)
6338 {
6339 SpellScript* spellScript = sitr->first->GetSpellScript();
6340 AuraScript* auraScript = sitr->first->GetAuraScript();
6341 bool valid = true;
6342 if (!spellScript && !auraScript)
6343 {
6344 LOG_ERROR("sql.sql", "Functions GetSpellScript() and GetAuraScript() of script `{}` do not return objects - script skipped", GetScriptName(sitr->second->second));
6345 valid = false;
6346 }
6347 if (spellScript)
6348 {
6349 spellScript->_Init(&sitr->first->GetName(), spellInfo->Id);
6350 spellScript->_Register();
6351 if (!spellScript->_Validate(spellInfo))
6352 valid = false;
6353 delete spellScript;
6354 }
6355 if (auraScript)
6356 {
6357 auraScript->_Init(&sitr->first->GetName(), spellInfo->Id);
6358 auraScript->_Register();
6359 if (!auraScript->_Validate(spellInfo))
6360 valid = false;
6361 delete auraScript;
6362 }
6363 if (!valid)
6364 {
6365 _spellScriptsStore.erase(sitr->second);
6366 }
6367 }
6368 ++count;
6369 }
6370
6371 LOG_INFO("server.loading", ">> Validated {} scripts in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
6372 LOG_INFO("server.loading", " ");
6373}
Definition SpellScript.h:518
bool _Validate(SpellInfo const *entry) override
Definition SpellScript.cpp:662
std::string const & GetScriptName(uint32 id) const
Definition ObjectMgr.cpp:10311
Definition SpellScript.h:182
bool _Validate(SpellInfo const *entry) override
Definition SpellScript.cpp:316
virtual void _Register()
Definition SpellScript.cpp:45
virtual void _Init(std::string const *scriptname, uint32 spellId)
Definition SpellScript.cpp:59

References _SpellScript::_Init(), _SpellScript::_Register(), _spellScriptsStore, SpellScript::_Validate(), AuraScript::_Validate(), getMSTime(), GetMSTimeDiffToNow(), GetScriptName(), SpellInfo::Id, LOG_ERROR, LOG_INFO, sScriptMgr, and sSpellMgr.

Friends And Related Symbol Documentation

◆ PlayerDumpReader

friend class PlayerDumpReader
friend

Member Data Documentation

◆ _accessRequirementStore

DungeonProgressionRequirementsContainer ObjectMgr::_accessRequirementStore
private

◆ _acoreStringStore

AcoreStringContainer ObjectMgr::_acoreStringStore
private

Referenced by GetAcoreString(), and LoadAcoreStrings().

◆ _areaTriggerScriptStore

AreaTriggerScriptContainer ObjectMgr::_areaTriggerScriptStore
private

◆ _areaTriggerStore

AreaTriggerContainer ObjectMgr::_areaTriggerStore
private

Referenced by GetAreaTrigger(), and LoadAreaTriggers().

◆ _areaTriggerTeleportStore

◆ _auctionId

uint32 ObjectMgr::_auctionId
private

◆ _baseXPTable

BaseXPContainer ObjectMgr::_baseXPTable
private

Referenced by GetBaseXP(), and LoadExplorationBaseXP().

◆ _breadcrumbsForQuest

BreadcrumbQuestMap ObjectMgr::_breadcrumbsForQuest

◆ _broadcastTextStore

BroadcastTextContainer ObjectMgr::_broadcastTextStore
private

◆ _cacheVendorItemStore

◆ _classTrainers

std::unordered_map<uint8, std::vector<Trainer::Trainer const*> > ObjectMgr::_classTrainers
private

Referenced by GetClassTrainers(), and LoadTrainers().

◆ _creatureAddonStore

CreatureAddonContainer ObjectMgr::_creatureAddonStore
private

◆ _creatureBaseStatsStore

CreatureBaseStatsContainer ObjectMgr::_creatureBaseStatsStore
private

◆ _creatureCustomIDsStore

CreatureCustomIDsContainer ObjectMgr::_creatureCustomIDsStore
private

◆ _creatureDataStore

◆ _creatureDefaultTrainers

std::unordered_map<uint32, uint32> ObjectMgr::_creatureDefaultTrainers
private

◆ _creatureLocaleStore

CreatureLocaleContainer ObjectMgr::_creatureLocaleStore
private

◆ _creatureModelStore

CreatureModelContainer ObjectMgr::_creatureModelStore
private

◆ _creatureMovementOverrides

std::unordered_map<ObjectGuid::LowType, CreatureMovementData> ObjectMgr::_creatureMovementOverrides
private

◆ _creatureQuestInvolvedRelations

◆ _creatureQuestItemStore

CreatureQuestItemMap ObjectMgr::_creatureQuestItemStore
private

◆ _creatureQuestRelations

QuestRelations ObjectMgr::_creatureQuestRelations
private

◆ _creatureSparringStore

CreatureSparringContainer ObjectMgr::_creatureSparringStore
private

◆ _creatureSpawnId

ObjectGuid::LowType ObjectMgr::_creatureSpawnId
private

◆ _creatureTemplateAddonStore

CreatureAddonContainer ObjectMgr::_creatureTemplateAddonStore
private

◆ _creatureTemplateStore

◆ _creatureTemplateStoreFast

std::vector<CreatureTemplate*> ObjectMgr::_creatureTemplateStoreFast
private

◆ _difficultyEntries

std::set<uint32> ObjectMgr::_difficultyEntries[MAX_DIFFICULTY - 1]
private

◆ _dungeonEncounterStore

DungeonEncounterContainer ObjectMgr::_dungeonEncounterStore
private

◆ _emptyCellObjectGuids

CellObjectGuids ObjectMgr::_emptyCellObjectGuids
private

Referenced by GetGridObjectGuids().

◆ _emptyCellObjectGuidsMap

CellObjectGuidsMap ObjectMgr::_emptyCellObjectGuidsMap
private

Referenced by GetMapObjectGuids().

◆ _equipmentInfoStore

EquipmentInfoContainer ObjectMgr::_equipmentInfoStore
private

◆ _equipmentSetGuid

uint64 ObjectMgr::_equipmentSetGuid
private

◆ _fishingBaseForAreaStore

◆ _gameObjectAddonStore

GameObjectAddonContainer ObjectMgr::_gameObjectAddonStore
private

◆ _gameObjectDataStore

◆ _gameObjectLocaleStore

GameObjectLocaleContainer ObjectMgr::_gameObjectLocaleStore
private

◆ _gameObjectQuestItemStore

GameObjectQuestItemMap ObjectMgr::_gameObjectQuestItemStore
private

◆ _gameObjectSpawnId

ObjectGuid::LowType ObjectMgr::_gameObjectSpawnId
private

◆ _gameObjectTemplateAddonStore

GameObjectTemplateAddonContainer ObjectMgr::_gameObjectTemplateAddonStore
private

◆ _gameObjectTemplateStore

GameObjectTemplateContainer ObjectMgr::_gameObjectTemplateStore
private

◆ _gameTeleStore

◆ _goQuestInvolvedRelations

QuestRelations ObjectMgr::_goQuestInvolvedRelations
private

◆ _goQuestRelations

QuestRelations ObjectMgr::_goQuestRelations
private

◆ _gossipMenuItemsLocaleStore

GossipMenuItemsLocaleContainer ObjectMgr::_gossipMenuItemsLocaleStore
private

◆ _gossipMenuItemsStore

◆ _gossipMenusStore

GossipMenusContainer ObjectMgr::_gossipMenusStore
private

◆ _gossipTextStore

GossipTextContainer ObjectMgr::_gossipTextStore
private

Referenced by GetGossipText(), and LoadGossipText().

◆ _goSummonDataStore

GameObjectSummonDataContainer ObjectMgr::_goSummonDataStore
private

Stores gameobject summon data grouped by summoner's entry, summoner's type and group id.

Referenced by GetGameObjectSummonGroup(), and LoadGameObjectSummons().

◆ _guidGenerators

std::map<HighGuid, std::unique_ptr<ObjectGuidGeneratorBase> > ObjectMgr::_guidGenerators
private

◆ _hasDifficultyEntries

std::set<uint32> ObjectMgr::_hasDifficultyEntries[MAX_DIFFICULTY - 1]
private

Referenced by CheckCreatureTemplate().

◆ _hiPetNumber

uint32 ObjectMgr::_hiPetNumber
private

Referenced by GeneratePetNumber(), and LoadPetNumber().

◆ _hiPetNumberMutex

std::mutex ObjectMgr::_hiPetNumberMutex
private

Referenced by GeneratePetNumber().

◆ _instanceTemplateStore

InstanceTemplateContainer ObjectMgr::_instanceTemplateStore
private

◆ _itemLocaleStore

ItemLocaleContainer ObjectMgr::_itemLocaleStore
private

Referenced by GetItemLocale(), and LoadItemLocales().

◆ _itemSetNameLocaleStore

ItemSetNameLocaleContainer ObjectMgr::_itemSetNameLocaleStore
private

◆ _itemSetNameStore

ItemSetNameContainer ObjectMgr::_itemSetNameStore
private

◆ _itemTemplateStore

ItemTemplateContainer ObjectMgr::_itemTemplateStore
private

◆ _itemTemplateStoreFast

std::vector<ItemTemplate*> ObjectMgr::_itemTemplateStoreFast
private

◆ _linkedRespawnStore

LinkedRespawnContainer ObjectMgr::_linkedRespawnStore
private

◆ _mailId

uint32 ObjectMgr::_mailId
private

Referenced by GenerateMailID(), and SetHighestGuids().

◆ _mailIdMutex

std::mutex ObjectMgr::_mailIdMutex
private

Referenced by GenerateMailID().

◆ _mailLevelRewardStore

MailLevelRewardContainer ObjectMgr::_mailLevelRewardStore
private

◆ _mapObjectGuidsStore

◆ _moduleStringStore

ModuleStringContainer ObjectMgr::_moduleStringStore
private

◆ _npcTextLocaleStore

NpcTextLocaleContainer ObjectMgr::_npcTextLocaleStore
private

◆ _pageTextLocaleStore

PageTextLocaleContainer ObjectMgr::_pageTextLocaleStore
private

◆ _pageTextStore

PageTextContainer ObjectMgr::_pageTextStore
private

Referenced by GetPageText(), and LoadPageTexts().

◆ _petHalfLocaleName0

HalfNameContainerLocale ObjectMgr::_petHalfLocaleName0
private

◆ _petHalfLocaleName1

HalfNameContainerLocale ObjectMgr::_petHalfLocaleName1
private

◆ _petHalfName0

HalfNameContainer ObjectMgr::_petHalfName0
private

Referenced by GeneratePetName(), and LoadPetNames().

◆ _petHalfName1

HalfNameContainer ObjectMgr::_petHalfName1
private

Referenced by GeneratePetName(), and LoadPetNames().

◆ _petInfoStore

PetLevelInfoContainer ObjectMgr::_petInfoStore
private

◆ _playerClassInfo

◆ _playerInfo

std::vector<std::vector<PlayerInfo*> > ObjectMgr::_playerInfo
private

◆ _playerShapeshiftModel

PlayerShapeshiftModelMap ObjectMgr::_playerShapeshiftModel
private

◆ _playerTotemModel

PlayerTotemModelMap ObjectMgr::_playerTotemModel
private

◆ _playerXPperLevel

PlayerXPperLevel ObjectMgr::_playerXPperLevel
private

Referenced by GetXPForLevel(), and LoadPlayerInfo().

◆ _pointOfInterestLocaleStore

PointOfInterestLocaleContainer ObjectMgr::_pointOfInterestLocaleStore
private

◆ _pointsOfInterestStore

PointOfInterestContainer ObjectMgr::_pointsOfInterestStore
private

◆ _profanityNamesStore

◆ _questAreaTriggerStore

QuestAreaTriggerContainer ObjectMgr::_questAreaTriggerStore
private

◆ _questGreetingStore

QuestGreetingContainer ObjectMgr::_questGreetingStore
private

◆ _questLocaleStore

QuestLocaleContainer ObjectMgr::_questLocaleStore
private

Referenced by GetQuestLocale(), and LoadQuestLocales().

◆ _questMoneyRewards

QuestMoneyRewardStore ObjectMgr::_questMoneyRewards
private

◆ _questOfferRewardLocaleStore

QuestOfferRewardLocaleContainer ObjectMgr::_questOfferRewardLocaleStore
private

◆ _questPOIStore

QuestPOIContainer ObjectMgr::_questPOIStore
private

Referenced by GetQuestPOIVector(), and LoadQuestPOI().

◆ _questRequestItemsLocaleStore

QuestRequestItemsLocaleContainer ObjectMgr::_questRequestItemsLocaleStore
private

◆ _questTemplates

QuestMap ObjectMgr::_questTemplates
private

◆ _questTemplatesFast

std::vector<Quest*> ObjectMgr::_questTemplatesFast
private

Referenced by GetQuestTemplate(), and LoadQuests().

◆ _repOnKillStore

RepOnKillContainer ObjectMgr::_repOnKillStore
private

◆ _repRewardRateStore

RepRewardRateContainer ObjectMgr::_repRewardRateStore
private

◆ _repSpilloverTemplateStore

RepSpilloverTemplateContainer ObjectMgr::_repSpilloverTemplateStore
private

◆ _reservedNamesStore

◆ _scriptNamesStore

ScriptNameContainer ObjectMgr::_scriptNamesStore
private

◆ _spawnGroupDataStore

SpawnGroupDataContainer ObjectMgr::_spawnGroupDataStore
private

Referenced by GetSpawnGroupData(), and ObjectMgr().

◆ _spellClickInfoStore

◆ _spellScriptsStore

SpellScriptsContainer ObjectMgr::_spellScriptsStore
private

◆ _tavernAreaTriggerStore

TavernAreaTriggerContainer ObjectMgr::_tavernAreaTriggerStore
private

◆ _tempSummonDataStore

TempSummonDataContainer ObjectMgr::_tempSummonDataStore
private

Stores temp summon data grouped by summoner's entry, summoner's type and group id.

Referenced by GetSummonGroup(), and LoadTempSummons().

◆ _trainers

std::unordered_map<uint32, Trainer::Trainer> ObjectMgr::_trainers
private

Referenced by GetTrainer(), and LoadTrainers().

◆ _transportMaps

std::set<uint32> ObjectMgr::_transportMaps
private

◆ _vehicleAccessoryStore

VehicleAccessoryContainer ObjectMgr::_vehicleAccessoryStore
private

◆ _vehicleSeatAddonStore

VehicleSeatAddonContainer ObjectMgr::_vehicleSeatAddonStore
private

◆ _vehicleTemplateAccessoryStore

VehicleAccessoryContainer ObjectMgr::_vehicleTemplateAccessoryStore
private

◆ DBCLocaleIndex

LocaleConstant ObjectMgr::DBCLocaleIndex
private

◆ FactionChangeAchievements

CharacterConversionMap ObjectMgr::FactionChangeAchievements

◆ FactionChangeItems

CharacterConversionMap ObjectMgr::FactionChangeItems

Referenced by LoadFactionChangeItems().

◆ FactionChangeQuests

CharacterConversionMap ObjectMgr::FactionChangeQuests

Referenced by LoadFactionChangeQuests().

◆ FactionChangeReputation

CharacterConversionMap ObjectMgr::FactionChangeReputation

◆ FactionChangeSpells

CharacterConversionMap ObjectMgr::FactionChangeSpells

Referenced by LoadFactionChangeSpells().

◆ FactionChangeTitles

CharacterConversionMap ObjectMgr::FactionChangeTitles

Referenced by LoadFactionChangeTitles().

◆ GameobjectInstanceSavedStateList

std::vector<GameobjectInstanceSavedState> ObjectMgr::GameobjectInstanceSavedStateList
private

◆ mExclusiveQuestGroups

ExclusiveQuestGroups ObjectMgr::mExclusiveQuestGroups

Referenced by LoadQuests().


The documentation for this class was generated from the following files: