AzerothCore 3.3.5a
OpenSource WoW Emulator
Loading...
Searching...
No Matches
LootMgr.cpp File Reference
#include "LootMgr.h"
#include "Containers.h"
#include "DisableMgr.h"
#include "Group.h"
#include "Log.h"
#include "ObjectMgr.h"
#include "Player.h"
#include "ScriptMgr.h"
#include "SharedDefines.h"
#include "SpellInfo.h"
#include "SpellMgr.h"
#include "Util.h"
#include "World.h"

Go to the source code of this file.

Classes

struct  LootGroupInvalidSelector
 
class  LootTemplate::LootGroup
 

Functions

ByteBufferoperator<< (ByteBuffer &b, LootItem const &li)
 
ByteBufferoperator<< (ByteBuffer &b, LootView const &lv)
 
void LoadLootTemplates_Creature ()
 
void LoadLootTemplates_Disenchant ()
 
void LoadLootTemplates_Fishing ()
 
void LoadLootTemplates_Gameobject ()
 
void LoadLootTemplates_Item ()
 
void LoadLootTemplates_Milling ()
 
void LoadLootTemplates_Pickpocketing ()
 
void LoadLootTemplates_Prospecting ()
 
void LoadLootTemplates_Mail ()
 
void LoadLootTemplates_Skinning ()
 
void LoadLootTemplates_Spell ()
 
void LoadLootTemplates_Player ()
 
void LoadLootTemplates_Reference ()
 

Variables

static Rates const qualityToRate [MAX_ITEM_QUALITY]
 
LootStore LootTemplates_Creature ("creature_loot_template", "creature entry", true)
 
LootStore LootTemplates_Disenchant ("disenchant_loot_template", "item disenchant id", true)
 
LootStore LootTemplates_Fishing ("fishing_loot_template", "area id", true)
 
LootStore LootTemplates_Gameobject ("gameobject_loot_template", "gameobject entry", true)
 
LootStore LootTemplates_Item ("item_loot_template", "item entry", true)
 
LootStore LootTemplates_Mail ("mail_loot_template", "mail template id", false)
 
LootStore LootTemplates_Milling ("milling_loot_template", "item entry (herb)", true)
 
LootStore LootTemplates_Pickpocketing ("pickpocketing_loot_template", "creature pickpocket lootid", true)
 
LootStore LootTemplates_Prospecting ("prospecting_loot_template", "item entry (ore)", true)
 
LootStore LootTemplates_Reference ("reference_loot_template", "reference id", false)
 
LootStore LootTemplates_Skinning ("skinning_loot_template", "creature skinning id", true)
 
LootStore LootTemplates_Spell ("spell_loot_template", "spell id (random item creating)", false)
 
LootStore LootTemplates_Player ("player_loot_template", "team id", true)
 

Function Documentation

◆ LoadLootTemplates_Creature()

void LoadLootTemplates_Creature ( )
1948{
1949 LOG_INFO("server.loading", "Loading Creature Loot Templates...");
1950
1951 uint32 oldMSTime = getMSTime();
1952
1953 LootIdSet lootIdSet, lootIdSetUsed;
1955
1956 // Remove real entries and check loot existence
1957 CreatureTemplateContainer const* ctc = sObjectMgr->GetCreatureTemplates();
1958 for (CreatureTemplateContainer::const_iterator itr = ctc->begin(); itr != ctc->end(); ++itr)
1959 {
1960 if (uint32 lootid = itr->second.lootid)
1961 {
1962 if (lootIdSet.find(lootid) == lootIdSet.end())
1963 LootTemplates_Creature.ReportNonExistingId(lootid, "Creature", itr->second.Entry);
1964 else
1965 lootIdSetUsed.insert(lootid);
1966 }
1967 }
1968
1969 for (LootIdSet::const_iterator itr = lootIdSetUsed.begin(); itr != lootIdSetUsed.end(); ++itr)
1970 lootIdSet.erase(*itr);
1971
1972 // output error for any still listed (not referenced from appropriate table) ids
1974
1975 if (count)
1976 LOG_INFO("server.loading", ">> Loaded {} Creature Loot Templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
1977 else
1978 LOG_WARN("server.loading", ">> Loaded 0 creature loot templates. DB table `creature_loot_template` is empty");
1979
1980 LOG_INFO("server.loading", " ");
1981}
std::uint32_t uint32
Definition: Define.h:108
#define LOG_INFO(filterType__,...)
Definition: Log.h:165
#define LOG_WARN(filterType__,...)
Definition: Log.h:161
uint32 GetMSTimeDiffToNow(uint32 oldMSTime)
Definition: Timer.h:131
uint32 getMSTime()
Definition: Timer.h:103
std::unordered_map< uint32, CreatureTemplate > CreatureTemplateContainer
Definition: CreatureData.h:281
#define sObjectMgr
Definition: ObjectMgr.h:1640
LootStore LootTemplates_Creature("creature_loot_template", "creature entry", true)
std::set< uint32 > LootIdSet
Definition: LootMgr.h:205
uint32 LoadAndCollectLootIds(LootIdSet &ids_set)
Definition: LootMgr.cpp:266
void ReportNonExistingId(uint32 lootId) const
Definition: LootMgr.cpp:289
void ReportUnusedIds(LootIdSet const &ids_set) const
Definition: LootMgr.cpp:282

References getMSTime(), GetMSTimeDiffToNow(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Creature, LootStore::ReportNonExistingId(), LootStore::ReportUnusedIds(), and sObjectMgr.

Referenced by reload_commandscript::HandleReloadLootTemplatesCreatureCommand(), and LoadLootTables().

◆ LoadLootTemplates_Disenchant()

void LoadLootTemplates_Disenchant ( )
1984{
1985 LOG_INFO("server.loading", "Loading Disenchanting Loot Templates...");
1986
1987 uint32 oldMSTime = getMSTime();
1988
1989 LootIdSet lootIdSet, lootIdSetUsed;
1991
1992 ItemTemplateContainer const* its = sObjectMgr->GetItemTemplateStore();
1993 for (ItemTemplateContainer::const_iterator itr = its->begin(); itr != its->end(); ++itr)
1994 {
1995 if (uint32 lootid = itr->second.DisenchantID)
1996 {
1997 if (lootIdSet.find(lootid) == lootIdSet.end())
1999 else
2000 lootIdSetUsed.insert(lootid);
2001 }
2002 }
2003
2004 for (LootIdSet::const_iterator itr = lootIdSetUsed.begin(); itr != lootIdSetUsed.end(); ++itr)
2005 lootIdSet.erase(*itr);
2006
2007 // output error for any still listed (not referenced from appropriate table) ids
2009
2010 if (count)
2011 LOG_INFO("server.loading", ">> Loaded {} disenchanting loot templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2012 else
2013 LOG_WARN("server.loading", ">> Loaded 0 disenchanting loot templates. DB table `disenchant_loot_template` is empty");
2014 LOG_INFO("server.loading", " ");
2015}
std::unordered_map< uint32, ItemTemplate > ItemTemplateContainer
Definition: ItemTemplate.h:840
LootStore LootTemplates_Disenchant("disenchant_loot_template", "item disenchant id", true)

References getMSTime(), GetMSTimeDiffToNow(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Disenchant, LootStore::ReportNonExistingId(), LootStore::ReportUnusedIds(), and sObjectMgr.

Referenced by reload_commandscript::HandleReloadLootTemplatesDisenchantCommand(), and LoadLootTables().

◆ LoadLootTemplates_Fishing()

void LoadLootTemplates_Fishing ( )
2018{
2019 LOG_INFO("server.loading", "Loading Fishing Loot Templates...");
2020
2021 uint32 oldMSTime = getMSTime();
2022
2023 LootIdSet lootIdSet;
2025
2026 // remove real entries and check existence loot
2027 for (uint32 i = 1; i < sAreaTableStore.GetNumRows(); ++i)
2028 if (AreaTableEntry const* areaEntry = sAreaTableStore.LookupEntry(i))
2029 if (lootIdSet.find(areaEntry->ID) != lootIdSet.end())
2030 lootIdSet.erase(areaEntry->ID);
2031
2032 // output error for any still listed (not referenced from appropriate table) ids
2034
2035 if (count)
2036 LOG_INFO("server.loading", ">> Loaded {} Fishing Loot Templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2037 else
2038 LOG_WARN("server.loading", ">> Loaded 0 fishing loot templates. DB table `fishing_loot_template` is empty");
2039
2040 LOG_INFO("server.loading", " ");
2041}
DBCStorage< AreaTableEntry > sAreaTableStore(AreaTableEntryfmt)
LootStore LootTemplates_Fishing("fishing_loot_template", "area id", true)
Definition: DBCStructure.h:519

References getMSTime(), GetMSTimeDiffToNow(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Fishing, LootStore::ReportUnusedIds(), and sAreaTableStore.

Referenced by reload_commandscript::HandleReloadLootTemplatesFishingCommand(), and LoadLootTables().

◆ LoadLootTemplates_Gameobject()

void LoadLootTemplates_Gameobject ( )
2044{
2045 LOG_INFO("server.loading", "Loading Gameobject Loot Templates...");
2046
2047 uint32 oldMSTime = getMSTime();
2048
2049 LootIdSet lootIdSet, lootIdSetUsed;
2051
2052 // remove real entries and check existence loot
2053 GameObjectTemplateContainer const* gotc = sObjectMgr->GetGameObjectTemplates();
2054 for (GameObjectTemplateContainer::const_iterator itr = gotc->begin(); itr != gotc->end(); ++itr)
2055 {
2056 if (uint32 lootid = itr->second.GetLootId())
2057 {
2058 if (lootIdSet.find(lootid) == lootIdSet.end())
2059 LootTemplates_Gameobject.ReportNonExistingId(lootid, "Gameobject", itr->second.entry);
2060 else
2061 lootIdSetUsed.insert(lootid);
2062 }
2063 }
2064
2065 for (LootIdSet::const_iterator itr = lootIdSetUsed.begin(); itr != lootIdSetUsed.end(); ++itr)
2066 lootIdSet.erase(*itr);
2067
2068 // output error for any still listed (not referenced from appropriate table) ids
2070
2071 if (count)
2072 LOG_INFO("server.loading", ">> Loaded {} Gameobject Loot Templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2073 else
2074 LOG_WARN("server.loading", ">> Loaded 0 gameobject loot templates. DB table `gameobject_loot_template` is empty");
2075
2076 LOG_INFO("server.loading", " ");
2077}
std::unordered_map< uint32, GameObjectTemplate > GameObjectTemplateContainer
Definition: GameObject.h:44
LootStore LootTemplates_Gameobject("gameobject_loot_template", "gameobject entry", true)

References getMSTime(), GetMSTimeDiffToNow(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Gameobject, LootStore::ReportNonExistingId(), LootStore::ReportUnusedIds(), and sObjectMgr.

Referenced by reload_commandscript::HandleReloadLootTemplatesGameobjectCommand(), and LoadLootTables().

◆ LoadLootTemplates_Item()

void LoadLootTemplates_Item ( )
2080{
2081 LOG_INFO("server.loading", "Loading Item Loot Templates...");
2082
2083 uint32 oldMSTime = getMSTime();
2084
2085 LootIdSet lootIdSet;
2087
2088 // remove real entries and check existence loot
2089 ItemTemplateContainer const* its = sObjectMgr->GetItemTemplateStore();
2090 for (ItemTemplateContainer::const_iterator itr = its->begin(); itr != its->end(); ++itr)
2091 if (lootIdSet.find(itr->second.ItemId) != lootIdSet.end() && itr->second.Flags & ITEM_FLAG_HAS_LOOT)
2092 lootIdSet.erase(itr->second.ItemId);
2093
2094 // output error for any still listed (not referenced from appropriate table) ids
2096
2097 if (count)
2098 LOG_INFO("server.loading", ">> Loaded {} item loot templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2099 else
2100 LOG_WARN("server.loading", ">> Loaded 0 item loot templates. DB table `item_loot_template` is empty");
2101
2102 LOG_INFO("server.loading", " ");
2103}
@ ITEM_FLAG_HAS_LOOT
Definition: ItemTemplate.h:150
LootStore LootTemplates_Item("item_loot_template", "item entry", true)

References getMSTime(), GetMSTimeDiffToNow(), ITEM_FLAG_HAS_LOOT, LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Item, LootStore::ReportUnusedIds(), and sObjectMgr.

Referenced by reload_commandscript::HandleReloadLootTemplatesItemCommand(), and LoadLootTables().

◆ LoadLootTemplates_Mail()

void LoadLootTemplates_Mail ( )
2204{
2205 LOG_INFO("server.loading", "Loading Mail Loot Templates...");
2206
2207 uint32 oldMSTime = getMSTime();
2208
2209 LootIdSet lootIdSet;
2211
2212 // remove real entries and check existence loot
2213 for (uint32 i = 1; i < sMailTemplateStore.GetNumRows(); ++i)
2214 if (sMailTemplateStore.LookupEntry(i))
2215 if (lootIdSet.find(i) != lootIdSet.end())
2216 lootIdSet.erase(i);
2217
2218 // output error for any still listed (not referenced from appropriate table) ids
2220
2221 if (count)
2222 LOG_INFO("server.loading", ">> Loaded {} mail loot templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2223 else
2224 LOG_WARN("server.loading", ">> Loaded 0 mail loot templates. DB table `mail_loot_template` is empty");
2225
2226 LOG_INFO("server.loading", " ");
2227}
DBCStorage< MailTemplateEntry > sMailTemplateStore(MailTemplateEntryfmt)
LootStore LootTemplates_Mail("mail_loot_template", "mail template id", false)

References getMSTime(), GetMSTimeDiffToNow(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Mail, LootStore::ReportUnusedIds(), and sMailTemplateStore.

Referenced by reload_commandscript::HandleReloadLootTemplatesMailCommand(), and LoadLootTables().

◆ LoadLootTemplates_Milling()

void LoadLootTemplates_Milling ( )
2106{
2107 LOG_INFO("server.loading", "Loading Milling Loot Templates...");
2108
2109 uint32 oldMSTime = getMSTime();
2110
2111 LootIdSet lootIdSet;
2113
2114 // remove real entries and check existence loot
2115 ItemTemplateContainer const* its = sObjectMgr->GetItemTemplateStore();
2116 for (ItemTemplateContainer::const_iterator itr = its->begin(); itr != its->end(); ++itr)
2117 {
2118 if (!(itr->second.Flags & ITEM_FLAG_IS_MILLABLE))
2119 continue;
2120
2121 if (lootIdSet.find(itr->second.ItemId) != lootIdSet.end())
2122 lootIdSet.erase(itr->second.ItemId);
2123 }
2124
2125 // output error for any still listed (not referenced from appropriate table) ids
2127
2128 if (count)
2129 LOG_INFO("server.loading", ">> Loaded {} milling loot templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2130 else
2131 LOG_WARN("server.loading", ">> Loaded 0 milling loot templates. DB table `milling_loot_template` is empty");
2132
2133 LOG_INFO("server.loading", " ");
2134}
@ ITEM_FLAG_IS_MILLABLE
Definition: ItemTemplate.h:177
LootStore LootTemplates_Milling("milling_loot_template", "item entry (herb)", true)

References getMSTime(), GetMSTimeDiffToNow(), ITEM_FLAG_IS_MILLABLE, LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Milling, LootStore::ReportUnusedIds(), and sObjectMgr.

Referenced by reload_commandscript::HandleReloadLootTemplatesMillingCommand(), and LoadLootTables().

◆ LoadLootTemplates_Pickpocketing()

void LoadLootTemplates_Pickpocketing ( )
2137{
2138 LOG_INFO("server.loading", "Loading Pickpocketing Loot Templates...");
2139
2140 uint32 oldMSTime = getMSTime();
2141
2142 LootIdSet lootIdSet, lootIdSetUsed;
2144
2145 // Remove real entries and check loot existence
2146 CreatureTemplateContainer const* ctc = sObjectMgr->GetCreatureTemplates();
2147 for (CreatureTemplateContainer::const_iterator itr = ctc->begin(); itr != ctc->end(); ++itr)
2148 {
2149 if (uint32 lootid = itr->second.pickpocketLootId)
2150 {
2151 if (lootIdSet.find(lootid) == lootIdSet.end())
2152 LootTemplates_Pickpocketing.ReportNonExistingId(lootid, "Creature", itr->second.Entry);
2153 else
2154 lootIdSetUsed.insert(lootid);
2155 }
2156 }
2157
2158 for (LootIdSet::const_iterator itr = lootIdSetUsed.begin(); itr != lootIdSetUsed.end(); ++itr)
2159 lootIdSet.erase(*itr);
2160
2161 // output error for any still listed (not referenced from appropriate table) ids
2163
2164 if (count)
2165 LOG_INFO("server.loading", ">> Loaded {} pickpocketing loot templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2166 else
2167 LOG_WARN("server.loading", ">> Loaded 0 pickpocketing loot templates. DB table `pickpocketing_loot_template` is empty");
2168
2169 LOG_INFO("server.loading", " ");
2170}
LootStore LootTemplates_Pickpocketing("pickpocketing_loot_template", "creature pickpocket lootid", true)

References getMSTime(), GetMSTimeDiffToNow(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Pickpocketing, LootStore::ReportNonExistingId(), LootStore::ReportUnusedIds(), and sObjectMgr.

Referenced by reload_commandscript::HandleReloadLootTemplatesPickpocketingCommand(), and LoadLootTables().

◆ LoadLootTemplates_Player()

void LoadLootTemplates_Player ( )
2309{
2310 LOG_INFO("server.loading", "Loading Player Loot Templates...");
2311
2312 uint32 oldMSTime = getMSTime();
2313
2314 LootIdSet lootIdSet;
2316
2317 if (count)
2318 {
2319 LOG_INFO("server.loading", ">> Loaded {} player loot templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2320 }
2321 else
2322 {
2323 LOG_WARN("server.loading", ">> Loaded 0 player loot templates. DB table `player_loot_template` is empty");
2324 }
2325
2326 LOG_INFO("server.loading", " ");
2327}
LootStore LootTemplates_Player("player_loot_template", "team id", true)

References getMSTime(), GetMSTimeDiffToNow(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, and LootTemplates_Player.

Referenced by reload_commandscript::HandleReloadLootTemplatesPlayerCommand(), and LoadLootTables().

◆ LoadLootTemplates_Prospecting()

void LoadLootTemplates_Prospecting ( )
2173{
2174 LOG_INFO("server.loading", "Loading Prospecting Loot Templates...");
2175
2176 uint32 oldMSTime = getMSTime();
2177
2178 LootIdSet lootIdSet;
2180
2181 // remove real entries and check existence loot
2182 ItemTemplateContainer const* its = sObjectMgr->GetItemTemplateStore();
2183 for (ItemTemplateContainer::const_iterator itr = its->begin(); itr != its->end(); ++itr)
2184 {
2185 if (!(itr->second.Flags & ITEM_FLAG_IS_PROSPECTABLE))
2186 continue;
2187
2188 if (lootIdSet.find(itr->second.ItemId) != lootIdSet.end())
2189 lootIdSet.erase(itr->second.ItemId);
2190 }
2191
2192 // output error for any still listed (not referenced from appropriate table) ids
2194
2195 if (count)
2196 LOG_INFO("server.loading", ">> Loaded {} prospecting loot templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2197 else
2198 LOG_WARN("server.loading", ">> Loaded 0 prospecting loot templates. DB table `prospecting_loot_template` is empty");
2199
2200 LOG_INFO("server.loading", " ");
2201}
@ ITEM_FLAG_IS_PROSPECTABLE
Definition: ItemTemplate.h:166
LootStore LootTemplates_Prospecting("prospecting_loot_template", "item entry (ore)", true)

References getMSTime(), GetMSTimeDiffToNow(), ITEM_FLAG_IS_PROSPECTABLE, LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Prospecting, LootStore::ReportUnusedIds(), and sObjectMgr.

Referenced by reload_commandscript::HandleReloadLootTemplatesProspectingCommand(), and LoadLootTables().

◆ LoadLootTemplates_Reference()

void LoadLootTemplates_Reference ( )
2330{
2331 LOG_INFO("server.loading", "Loading Reference Loot Templates...");
2332
2333 uint32 oldMSTime = getMSTime();
2334
2335 LootIdSet lootIdSet;
2337
2338 // check references and remove used
2350
2351 // output error for any still listed ids (not referenced from any loot table)
2353
2354 LOG_INFO("server.loading", ">> Loaded refence loot templates in {} ms", GetMSTimeDiffToNow(oldMSTime));
2355 LOG_INFO("server.loading", " ");
2356}
LootStore LootTemplates_Skinning("skinning_loot_template", "creature skinning id", true)
LootStore LootTemplates_Reference("reference_loot_template", "reference id", false)
void CheckLootRefs(LootIdSet *ref_set=nullptr) const
Definition: LootMgr.cpp:276

References LootStore::CheckLootRefs(), getMSTime(), GetMSTimeDiffToNow(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LootTemplates_Creature, LootTemplates_Disenchant, LootTemplates_Fishing, LootTemplates_Gameobject, LootTemplates_Item, LootTemplates_Mail, LootTemplates_Milling, LootTemplates_Pickpocketing, LootTemplates_Prospecting, LootTemplates_Reference, LootTemplates_Skinning, and LootStore::ReportUnusedIds().

Referenced by reload_commandscript::HandleReloadLootTemplatesReferenceCommand(), and LoadLootTables().

◆ LoadLootTemplates_Skinning()

void LoadLootTemplates_Skinning ( )
2230{
2231 LOG_INFO("server.loading", "Loading Skinning Loot Templates...");
2232
2233 uint32 oldMSTime = getMSTime();
2234
2235 LootIdSet lootIdSet, lootIdSetUsed;
2237
2238 // remove real entries and check existence loot
2239 CreatureTemplateContainer const* ctc = sObjectMgr->GetCreatureTemplates();
2240 for (CreatureTemplateContainer::const_iterator itr = ctc->begin(); itr != ctc->end(); ++itr)
2241 {
2242 if (uint32 lootid = itr->second.SkinLootId)
2243 {
2244 if (lootIdSet.find(lootid) == lootIdSet.end())
2245 LootTemplates_Skinning.ReportNonExistingId(lootid, "Creature", itr->second.Entry);
2246 else
2247 lootIdSetUsed.insert(lootid);
2248 }
2249 }
2250
2251 for (LootIdSet::const_iterator itr = lootIdSetUsed.begin(); itr != lootIdSetUsed.end(); ++itr)
2252 lootIdSet.erase(*itr);
2253
2254 // output error for any still listed (not referenced from appropriate table) ids
2256
2257 if (count)
2258 LOG_INFO("server.loading", ">> Loaded {} skinning loot templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2259 else
2260 LOG_WARN("server.loading", ">> Loaded 0 skinning loot templates. DB table `skinning_loot_template` is empty");
2261
2262 LOG_INFO("server.loading", " ");
2263}

References getMSTime(), GetMSTimeDiffToNow(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Skinning, LootStore::ReportNonExistingId(), LootStore::ReportUnusedIds(), and sObjectMgr.

Referenced by reload_commandscript::HandleReloadLootTemplatesSkinningCommand(), and LoadLootTables().

◆ LoadLootTemplates_Spell()

void LoadLootTemplates_Spell ( )
2266{
2267 LOG_INFO("server.loading", "Loading Spell Loot Templates...");
2268
2269 uint32 oldMSTime = getMSTime();
2270
2271 LootIdSet lootIdSet;
2273
2274 // remove real entries and check existence loot
2275 for (uint32 spell_id = 1; spell_id < sSpellMgr->GetSpellInfoStoreSize(); ++spell_id)
2276 {
2277 SpellInfo const* spellInfo = sSpellMgr->GetSpellInfo(spell_id);
2278 if (!spellInfo)
2279 continue;
2280
2281 // possible cases
2282 if (!spellInfo->IsLootCrafting())
2283 continue;
2284
2285 if (lootIdSet.find(spell_id) == lootIdSet.end())
2286 {
2287 // not report about not trainable spells (optionally supported by DB)
2288 // ignore 61756 (Northrend Inscription Research (FAST QA VERSION) for example
2290 {
2291 LootTemplates_Spell.ReportNonExistingId(spell_id, "Spell", spellInfo->Id);
2292 }
2293 }
2294 else
2295 lootIdSet.erase(spell_id);
2296 }
2297
2298 // output error for any still listed (not referenced from appropriate table) ids
2300
2301 if (count)
2302 LOG_INFO("server.loading", ">> Loaded {} spell loot templates in {} ms", count, GetMSTimeDiffToNow(oldMSTime));
2303 else
2304 LOG_WARN("server.loading", ">> Loaded 0 spell loot templates. DB table `spell_loot_template` is empty");
2305 LOG_INFO("server.loading", " ");
2306}
LootStore LootTemplates_Spell("spell_loot_template", "spell id (random item creating)", false)
#define sSpellMgr
Definition: SpellMgr.h:825
@ SPELL_ATTR0_IS_TRADESKILL
Definition: SharedDefines.h:387
@ SPELL_ATTR0_NOT_SHAPESHIFTED
Definition: SharedDefines.h:398
Definition: SpellInfo.h:314
uint32 Id
Definition: SpellInfo.h:318
bool IsLootCrafting() const
Definition: SpellInfo.cpp:912
bool HasAttribute(SpellAttr0 attribute) const
Definition: SpellInfo.h:412

References getMSTime(), GetMSTimeDiffToNow(), SpellInfo::HasAttribute(), SpellInfo::Id, SpellInfo::IsLootCrafting(), LootStore::LoadAndCollectLootIds(), LOG_INFO, LOG_WARN, LootTemplates_Spell, LootStore::ReportNonExistingId(), LootStore::ReportUnusedIds(), SPELL_ATTR0_IS_TRADESKILL, SPELL_ATTR0_NOT_SHAPESHIFTED, and sSpellMgr.

Referenced by reload_commandscript::HandleReloadLootTemplatesSpellCommand(), and LoadLootTables().

◆ operator<<() [1/2]

ByteBuffer & operator<< ( ByteBuffer b,
LootItem const &  li 
)
974{
975 b << uint32(li.itemid);
976 b << uint32(li.count); // nr of items of this type
977 b << uint32(sObjectMgr->GetItemTemplate(li.itemid)->DisplayInfoID);
978 b << uint32(li.randomSuffix);
979 b << uint32(li.randomPropertyId);
980 //b << uint8(0); // slot type - will send after this function call
981 return b;
982}

References LootItem::count, LootItem::itemid, LootItem::randomPropertyId, LootItem::randomSuffix, and sObjectMgr.

◆ operator<<() [2/2]

ByteBuffer & operator<< ( ByteBuffer b,
LootView const &  lv 
)
985{
986 if (lv.permission == NONE_PERMISSION)
987 {
988 b << uint32(0); //gold
989 b << uint8(0); // item count
990 return b; // nothing output more
991 }
992
993 Loot& l = lv.loot;
994
995 uint8 itemsShown = 0;
996
997 b << uint32(l.gold); //gold
998
999 size_t count_pos = b.wpos(); // pos of item count byte
1000 b << uint8(0); // item count placeholder
1001
1002 switch (lv.permission)
1003 {
1004 case GROUP_PERMISSION:
1005 case MASTER_PERMISSION:
1007 {
1008 bool isMasterLooter = lv.viewer->GetGroup() && lv.viewer->GetGroup()->GetMasterLooterGuid() == lv.viewer->GetGUID();
1009
1010 // if you are not the round-robin group looter, you can only see
1011 // blocked rolled items and quest items, and !ffa items
1012 for (uint8 i = 0; i < l.items.size(); ++i)
1013 {
1014 if (!l.items[i].is_looted && !l.items[i].freeforall && (l.items[i].conditions.empty() || isMasterLooter) && l.items[i].AllowedForPlayer(lv.viewer, l.sourceWorldObjectGUID))
1015 {
1016 uint8 slot_type = 0;
1017
1018 if (l.items[i].is_blocked) // for ML & restricted is_blocked = !is_underthreshold
1019 {
1020 switch (lv.permission)
1021 {
1022 case GROUP_PERMISSION:
1023 slot_type = LOOT_SLOT_TYPE_ROLL_ONGOING;
1024 break;
1025 case MASTER_PERMISSION:
1026 {
1027 if (lv.viewer->GetGroup())
1028 {
1029 if (lv.viewer->GetGroup()->GetMasterLooterGuid() == lv.viewer->GetGUID())
1030 slot_type = LOOT_SLOT_TYPE_MASTER;
1031 else
1032 slot_type = LOOT_SLOT_TYPE_LOCKED;
1033 }
1034 break;
1035 }
1037 slot_type = LOOT_SLOT_TYPE_LOCKED;
1038 break;
1039 default:
1040 continue;
1041 }
1042 }
1043 else if (l.items[i].rollWinnerGUID)
1044 {
1045 if (l.items[i].rollWinnerGUID == lv.viewer->GetGUID())
1046 slot_type = LOOT_SLOT_TYPE_OWNER;
1047 else
1048 continue;
1049 }
1050 else if (!l.roundRobinPlayer || lv.viewer->GetGUID() == l.roundRobinPlayer || !l.items[i].is_underthreshold)
1051 {
1052 // no round robin owner or he has released the loot
1053 // or it IS the round robin group owner
1054 // => item is lootable
1055 slot_type = LOOT_SLOT_TYPE_ALLOW_LOOT;
1056 }
1057 else
1058 // item shall not be displayed.
1059 continue;
1060
1061 b << uint8(i) << l.items[i];
1062 b << uint8(slot_type);
1063 ++itemsShown;
1064 }
1065 }
1066 break;
1067 }
1069 {
1070 for (uint8 i = 0; i < l.items.size(); ++i)
1071 {
1072 if (!l.items[i].is_looted && !l.items[i].freeforall && l.items[i].conditions.empty() && l.items[i].AllowedForPlayer(lv.viewer, l.sourceWorldObjectGUID))
1073 {
1074 if (l.roundRobinPlayer && lv.viewer->GetGUID() != l.roundRobinPlayer)
1075 // item shall not be displayed.
1076 continue;
1077
1078 b << uint8(i) << l.items[i];
1080 ++itemsShown;
1081 }
1082 }
1083 break;
1084 }
1085 case ALL_PERMISSION:
1086 case OWNER_PERMISSION:
1087 {
1089 for (uint8 i = 0; i < l.items.size(); ++i)
1090 {
1091 if (!l.items[i].is_looted && !l.items[i].freeforall && l.items[i].conditions.empty() && l.items[i].AllowedForPlayer(lv.viewer, l.sourceWorldObjectGUID))
1092 {
1093 b << uint8(i) << l.items[i];
1094 b << uint8(slot_type);
1095 ++itemsShown;
1096 }
1097 }
1098 break;
1099 }
1100 default:
1101 return b;
1102 }
1103
1105
1106 // Xinef: items that do not follow loot rules need this
1107 LootSlotType partySlotType = lv.permission == MASTER_PERMISSION ? LOOT_SLOT_TYPE_MASTER : slotType;
1108
1109 QuestItemMap const& lootPlayerQuestItems = l.GetPlayerQuestItems();
1110 QuestItemMap::const_iterator q_itr = lootPlayerQuestItems.find(lv.viewer->GetGUID());
1111 if (q_itr != lootPlayerQuestItems.end())
1112 {
1113 QuestItemList* q_list = q_itr->second;
1114 for (QuestItemList::const_iterator qi = q_list->begin(); qi != q_list->end(); ++qi)
1115 {
1116 LootItem& item = l.quest_items[qi->index];
1117 if (!qi->is_looted && !item.is_looted)
1118 {
1119 bool showInLoot = true;
1120 bool hasQuestForItem = lv.viewer->HasQuestForItem(item.itemid, 0, false, &showInLoot);
1121 if (!hasQuestForItem)
1122 {
1123 if (!showInLoot)
1124 {
1125 const_cast<QuestItem*>(&(*qi))->is_looted = true;
1126 if (!item.freeforall)
1127 {
1128 item.is_looted = true;
1129 }
1130 continue;
1131 }
1132
1133 b << uint8(l.items.size() + (qi - q_list->begin()));
1134 b << item;
1136 }
1137 else
1138 {
1139 b << uint8(l.items.size() + (qi - q_list->begin()));
1140 b << item;
1141
1142 if (item.follow_loot_rules)
1143 {
1144 switch (lv.permission)
1145 {
1146 case MASTER_PERMISSION:
1148 break;
1150 b << (item.is_blocked ? uint8(LOOT_SLOT_TYPE_LOCKED) : uint8(slotType));
1151 break;
1152 case GROUP_PERMISSION:
1154 if (!item.is_blocked)
1156 else
1158 break;
1159 default:
1160 b << uint8(slotType);
1161 break;
1162 }
1163 }
1164 else if (!item.freeforall)
1165 b << uint8(partySlotType);
1166 else
1167 b << uint8(slotType);
1168 }
1169
1170 ++itemsShown;
1171 }
1172 }
1173 }
1174
1175 QuestItemMap const& lootPlayerFFAItems = l.GetPlayerFFAItems();
1176 QuestItemMap::const_iterator ffa_itr = lootPlayerFFAItems.find(lv.viewer->GetGUID());
1177 if (ffa_itr != lootPlayerFFAItems.end())
1178 {
1179 QuestItemList* ffa_list = ffa_itr->second;
1180 for (QuestItemList::const_iterator fi = ffa_list->begin(); fi != ffa_list->end(); ++fi)
1181 {
1182 LootItem& item = l.items[fi->index];
1183 if (!fi->is_looted && !item.is_looted)
1184 {
1185 b << uint8(fi->index);
1186 b << item;
1187 // Xinef: Here are FFA items, so dont use owner permision
1188 b << uint8(LOOT_SLOT_TYPE_ALLOW_LOOT /*slotType*/);
1189 ++itemsShown;
1190 }
1191 }
1192 }
1193
1194 QuestItemMap const& lootPlayerNonQuestNonFFAConditionalItems = l.GetPlayerNonQuestNonFFAConditionalItems();
1195 QuestItemMap::const_iterator nn_itr = lootPlayerNonQuestNonFFAConditionalItems.find(lv.viewer->GetGUID());
1196 if (nn_itr != lootPlayerNonQuestNonFFAConditionalItems.end())
1197 {
1198 QuestItemList* conditional_list = nn_itr->second;
1199 for (QuestItemList::const_iterator ci = conditional_list->begin(); ci != conditional_list->end(); ++ci)
1200 {
1201 LootItem& item = l.items[ci->index];
1202 if (!ci->is_looted && !item.is_looted)
1203 {
1204 b << uint8(ci->index);
1205 b << item;
1206 if (item.follow_loot_rules)
1207 {
1208 switch (lv.permission)
1209 {
1210 case MASTER_PERMISSION:
1212 break;
1214 b << (item.is_blocked ? uint8(LOOT_SLOT_TYPE_LOCKED) : uint8(slotType));
1215 break;
1216 case GROUP_PERMISSION:
1218 if (!item.is_blocked)
1220 else
1222 break;
1223 default:
1224 b << uint8(slotType);
1225 break;
1226 }
1227 }
1228 else if (!item.freeforall)
1229 b << uint8(partySlotType);
1230 else
1231 b << uint8(slotType);
1232 ++itemsShown;
1233 }
1234 }
1235 }
1236
1237 //update number of items shown
1238 b.put<uint8>(count_pos, itemsShown);
1239
1240 return b;
1241}
std::uint8_t uint8
Definition: Define.h:110
@ OWNER_PERMISSION
Definition: LootMgr.h:73
@ ALL_PERMISSION
Definition: LootMgr.h:68
@ RESTRICTED_PERMISSION
Definition: LootMgr.h:71
@ NONE_PERMISSION
Definition: LootMgr.h:74
@ ROUND_ROBIN_PERMISSION
Definition: LootMgr.h:72
@ MASTER_PERMISSION
Definition: LootMgr.h:70
@ GROUP_PERMISSION
Definition: LootMgr.h:69
std::map< ObjectGuid, QuestItemList * > QuestItemMap
Definition: LootMgr.h:201
LootSlotType
Definition: LootMgr.h:114
@ LOOT_SLOT_TYPE_MASTER
Definition: LootMgr.h:117
@ LOOT_SLOT_TYPE_ROLL_ONGOING
Definition: LootMgr.h:116
@ LOOT_SLOT_TYPE_ALLOW_LOOT
Definition: LootMgr.h:115
@ LOOT_SLOT_TYPE_OWNER
Definition: LootMgr.h:119
@ LOOT_SLOT_TYPE_LOCKED
Definition: LootMgr.h:118
std::vector< QuestItem > QuestItemList
Definition: LootMgr.h:199
Definition: LootMgr.h:155
uint32 itemid
Definition: LootMgr.h:156
bool is_looted
Definition: LootMgr.h:164
bool freeforall
Definition: LootMgr.h:166
Definition: LootMgr.h:186
Definition: LootMgr.h:313
ObjectGuid sourceWorldObjectGUID
Definition: LootMgr.h:330
ObjectGuid roundRobinPlayer
Definition: LootMgr.h:324
uint32 gold
Definition: LootMgr.h:322
QuestItemMap const & GetPlayerQuestItems() const
Definition: LootMgr.h:316
std::vector< LootItem > items
Definition: LootMgr.h:320
QuestItemMap const & GetPlayerFFAItems() const
Definition: LootMgr.h:317
QuestItemMap const & GetPlayerNonQuestNonFFAConditionalItems() const
Definition: LootMgr.h:318
std::vector< LootItem > quest_items
Definition: LootMgr.h:321
size_t wpos() const
Definition: ByteBuffer.h:330
void put(std::size_t pos, T value)
Definition: ByteBuffer.h:137

Variable Documentation

◆ LootTemplates_Creature

◆ LootTemplates_Disenchant

LootStore LootTemplates_Disenchant("disenchant_loot_template", "item disenchant id", true) ( "disenchant_loot_template"  ,
"item disenchant id"  ,
true   
)

◆ LootTemplates_Fishing

LootStore LootTemplates_Fishing("fishing_loot_template", "area id", true) ( "fishing_loot_template"  ,
"area id"  ,
true   
)

◆ LootTemplates_Gameobject

LootStore LootTemplates_Gameobject("gameobject_loot_template", "gameobject entry", true) ( "gameobject_loot_template"  ,
"gameobject entry"  ,
true   
)

◆ LootTemplates_Item

LootStore LootTemplates_Item("item_loot_template", "item entry", true) ( "item_loot_template"  ,
"item entry"  ,
true   
)

◆ LootTemplates_Mail

LootStore LootTemplates_Mail("mail_loot_template", "mail template id", false) ( "mail_loot_template"  ,
"mail template id"  ,
false   
)

◆ LootTemplates_Milling

LootStore LootTemplates_Milling("milling_loot_template", "item entry (herb)", true) ( "milling_loot_template"  ,
"item entry (herb)"  ,
true   
)

◆ LootTemplates_Pickpocketing

LootStore LootTemplates_Pickpocketing("pickpocketing_loot_template", "creature pickpocket lootid", true) ( "pickpocketing_loot_template"  ,
"creature pickpocket lootid"  ,
true   
)

◆ LootTemplates_Player

LootStore LootTemplates_Player("player_loot_template", "team id", true) ( "player_loot_template"  ,
"team id"  ,
true   
)

◆ LootTemplates_Prospecting

LootStore LootTemplates_Prospecting("prospecting_loot_template", "item entry (ore)", true) ( "prospecting_loot_template"  ,
"item entry (ore)"  ,
true   
)

◆ LootTemplates_Reference

LootStore LootTemplates_Reference("reference_loot_template", "reference id", false) ( "reference_loot_template"  ,
"reference id"  ,
false   
)

◆ LootTemplates_Skinning

LootStore LootTemplates_Skinning("skinning_loot_template", "creature skinning id", true) ( "skinning_loot_template"  ,
"creature skinning id"  ,
true   
)

◆ LootTemplates_Spell

LootStore LootTemplates_Spell("spell_loot_template", "spell id (random item creating)", false) ( "spell_loot_template"  ,
"spell id (random item creating)"  ,
false   
)

◆ qualityToRate

Rates const qualityToRate[MAX_ITEM_QUALITY]
static
Initial value:
=
{
}
@ RATE_DROP_ITEM_RARE
Definition: IWorld.h:439
@ RATE_DROP_ITEM_LEGENDARY
Definition: IWorld.h:441
@ RATE_DROP_ITEM_POOR
Definition: IWorld.h:436
@ RATE_DROP_ITEM_UNCOMMON
Definition: IWorld.h:438
@ RATE_DROP_ITEM_EPIC
Definition: IWorld.h:440
@ RATE_DROP_ITEM_ARTIFACT
Definition: IWorld.h:442
@ RATE_DROP_ITEM_NORMAL
Definition: IWorld.h:437