[7146] Trailing whitespace code cleanup
[getmangos.git] / src / shared / Database / DBCStores.cpp
blob02db49af9f0472f7c4c9cc85a21b0ea77a4a58c8
1 /*
2 * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/>
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 #include "DBCStores.h"
20 //#include "DataStore.h"
21 #include "Policies/SingletonImp.h"
22 #include "Log.h"
23 #include "ProgressBar.h"
25 #include "DBCfmt.cpp"
27 #include <map>
29 typedef std::map<uint16,uint32> AreaFlagByAreaID;
30 typedef std::map<uint32,uint32> AreaFlagByMapID;
32 DBCStorage <AreaTableEntry> sAreaStore(AreaTableEntryfmt);
33 DBCStorage <AreaGroupEntry> sAreaGroupStore(AreaGroupEntryfmt);
34 static AreaFlagByAreaID sAreaFlagByAreaID;
35 static AreaFlagByMapID sAreaFlagByMapID; // for instances without generated *.map files
37 DBCStorage <AchievementEntry> sAchievementStore(Achievementfmt);
38 DBCStorage <AchievementCriteriaEntry> sAchievementCriteriaStore(AchievementCriteriafmt);
39 DBCStorage <AreaTriggerEntry> sAreaTriggerStore(AreaTriggerEntryfmt);
40 DBCStorage <BankBagSlotPricesEntry> sBankBagSlotPricesStore(BankBagSlotPricesEntryfmt);
41 DBCStorage <BattlemasterListEntry> sBattlemasterListStore(BattlemasterListEntryfmt);
42 DBCStorage <BarberShopStyleEntry> sBarberShopStyleStore(BarberShopStyleEntryfmt);
43 DBCStorage <CharStartOutfitEntry> sCharStartOutfitStore(CharStartOutfitEntryfmt);
44 DBCStorage <CharTitlesEntry> sCharTitlesStore(CharTitlesEntryfmt);
45 DBCStorage <ChatChannelsEntry> sChatChannelsStore(ChatChannelsEntryfmt);
46 DBCStorage <ChrClassesEntry> sChrClassesStore(ChrClassesEntryfmt);
47 DBCStorage <ChrRacesEntry> sChrRacesStore(ChrRacesEntryfmt);
48 DBCStorage <CreatureDisplayInfoEntry> sCreatureDisplayInfoStore(CreatureDisplayInfofmt);
49 DBCStorage <CreatureFamilyEntry> sCreatureFamilyStore(CreatureFamilyfmt);
50 DBCStorage <CreatureSpellDataEntry> sCreatureSpellDataStore(CreatureSpellDatafmt);
52 DBCStorage <DurabilityQualityEntry> sDurabilityQualityStore(DurabilityQualityfmt);
53 DBCStorage <DurabilityCostsEntry> sDurabilityCostsStore(DurabilityCostsfmt);
55 DBCStorage <EmotesTextEntry> sEmotesTextStore(EmoteEntryfmt);
57 typedef std::map<uint32,SimpleFactionsList> FactionTeamMap;
58 static FactionTeamMap sFactionTeamMap;
59 DBCStorage <FactionEntry> sFactionStore(FactionEntryfmt);
60 DBCStorage <FactionTemplateEntry> sFactionTemplateStore(FactionTemplateEntryfmt);
62 DBCStorage <GemPropertiesEntry> sGemPropertiesStore(GemPropertiesEntryfmt);
63 DBCStorage <GlyphPropertiesEntry> sGlyphPropertiesStore(GlyphPropertiesfmt);
64 DBCStorage <GlyphSlotEntry> sGlyphSlotStore(GlyphSlotfmt);
66 DBCStorage <GtBarberShopCostBaseEntry> sGtBarberShopCostBaseStore(GtBarberShopCostBasefmt);
67 DBCStorage <GtCombatRatingsEntry> sGtCombatRatingsStore(GtCombatRatingsfmt);
68 DBCStorage <GtChanceToMeleeCritBaseEntry> sGtChanceToMeleeCritBaseStore(GtChanceToMeleeCritBasefmt);
69 DBCStorage <GtChanceToMeleeCritEntry> sGtChanceToMeleeCritStore(GtChanceToMeleeCritfmt);
70 DBCStorage <GtChanceToSpellCritBaseEntry> sGtChanceToSpellCritBaseStore(GtChanceToSpellCritBasefmt);
71 DBCStorage <GtChanceToSpellCritEntry> sGtChanceToSpellCritStore(GtChanceToSpellCritfmt);
72 DBCStorage <GtOCTRegenHPEntry> sGtOCTRegenHPStore(GtOCTRegenHPfmt);
73 //DBCStorage <GtOCTRegenMPEntry> sGtOCTRegenMPStore(GtOCTRegenMPfmt); -- not used currently
74 DBCStorage <GtRegenHPPerSptEntry> sGtRegenHPPerSptStore(GtRegenHPPerSptfmt);
75 DBCStorage <GtRegenMPPerSptEntry> sGtRegenMPPerSptStore(GtRegenMPPerSptfmt);
76 DBCStorage <ItemEntry> sItemStore(Itemfmt);
77 //DBCStorage <ItemCondExtCostsEntry> sItemCondExtCostsStore(ItemCondExtCostsEntryfmt);
78 //DBCStorage <ItemDisplayInfoEntry> sItemDisplayInfoStore(ItemDisplayTemplateEntryfmt); -- not used currently
79 DBCStorage <ItemExtendedCostEntry> sItemExtendedCostStore(ItemExtendedCostEntryfmt);
80 DBCStorage <ItemRandomPropertiesEntry> sItemRandomPropertiesStore(ItemRandomPropertiesfmt);
81 DBCStorage <ItemRandomSuffixEntry> sItemRandomSuffixStore(ItemRandomSuffixfmt);
82 DBCStorage <ItemSetEntry> sItemSetStore(ItemSetEntryfmt);
84 DBCStorage <LockEntry> sLockStore(LockEntryfmt);
86 DBCStorage <MailTemplateEntry> sMailTemplateStore(MailTemplateEntryfmt);
87 DBCStorage <MapEntry> sMapStore(MapEntryfmt);
89 DBCStorage <QuestSortEntry> sQuestSortStore(QuestSortEntryfmt);
91 DBCStorage <RandomPropertiesPointsEntry> sRandomPropertiesPointsStore(RandomPropertiesPointsfmt);
92 DBCStorage <ScalingStatDistributionEntry> sScalingStatDistributionStore(ScalingStatDistributionfmt);
93 DBCStorage <ScalingStatValuesEntry> sScalingStatValuesStore(ScalingStatValuesfmt);
95 DBCStorage <SkillLineEntry> sSkillLineStore(SkillLinefmt);
96 DBCStorage <SkillLineAbilityEntry> sSkillLineAbilityStore(SkillLineAbilityfmt);
98 DBCStorage <SoundEntriesEntry> sSoundEntriesStore(SoundEntriesfmt);
100 DBCStorage <SpellItemEnchantmentEntry> sSpellItemEnchantmentStore(SpellItemEnchantmentfmt);
101 DBCStorage <SpellItemEnchantmentConditionEntry> sSpellItemEnchantmentConditionStore(SpellItemEnchantmentConditionfmt);
102 DBCStorage <SpellEntry> sSpellStore(SpellEntryfmt);
103 SpellCategoryStore sSpellCategoryStore;
104 PetFamilySpellsStore sPetFamilySpellsStore;
106 DBCStorage <SpellCastTimesEntry> sSpellCastTimesStore(SpellCastTimefmt);
107 DBCStorage <SpellDurationEntry> sSpellDurationStore(SpellDurationfmt);
108 DBCStorage <SpellFocusObjectEntry> sSpellFocusObjectStore(SpellFocusObjectfmt);
109 DBCStorage <SpellRadiusEntry> sSpellRadiusStore(SpellRadiusfmt);
110 DBCStorage <SpellRangeEntry> sSpellRangeStore(SpellRangefmt);
111 DBCStorage <SpellRuneCostEntry> sSpellRuneCostStore(SpellRuneCostfmt);
112 DBCStorage <SpellShapeshiftEntry> sSpellShapeshiftStore(SpellShapeshiftfmt);
113 DBCStorage <StableSlotPricesEntry> sStableSlotPricesStore(StableSlotPricesfmt);
114 //DBCStorage <SummonPropertiesEntry> sSummonPropertiesStore(SummonPropertiesfmt);
115 DBCStorage <TalentEntry> sTalentStore(TalentEntryfmt);
116 TalentSpellPosMap sTalentSpellPosMap;
117 DBCStorage <TalentTabEntry> sTalentTabStore(TalentTabEntryfmt);
119 // store absolute bit position for first rank for talent inspect
120 typedef std::map<uint32,uint32> TalentInspectMap;
121 static TalentInspectMap sTalentPosInInspect;
122 static TalentInspectMap sTalentTabSizeInInspect;
123 static uint32 sTalentTabPages[12/*MAX_CLASSES*/][3];
125 DBCStorage <TaxiNodesEntry> sTaxiNodesStore(TaxiNodesEntryfmt);
126 TaxiMask sTaxiNodesMask;
128 // DBC used only for initialization sTaxiPathSetBySource at startup.
129 TaxiPathSetBySource sTaxiPathSetBySource;
130 DBCStorage <TaxiPathEntry> sTaxiPathStore(TaxiPathEntryfmt);
132 // DBC used only for initialization sTaxiPathSetBySource at startup.
133 TaxiPathNodesByPath sTaxiPathNodesByPath;
135 static DBCStorage <TaxiPathNodeEntry> sTaxiPathNodeStore(TaxiPathNodeEntryfmt);
136 DBCStorage <TotemCategoryEntry> sTotemCategoryStore(TotemCategoryEntryfmt);
137 DBCStorage <VehicleEntry> sVehicleStore(VehicleEntryfmt);
138 DBCStorage <VehicleSeatEntry> sVehicleSeatStore(VehicleSeatEntryfmt);
139 DBCStorage <WorldMapAreaEntry> sWorldMapAreaStore(WorldMapAreaEntryfmt);
140 DBCStorage <WorldSafeLocsEntry> sWorldSafeLocsStore(WorldSafeLocsEntryfmt);
141 DBCStorage <WorldMapOverlayEntry> sWorldMapOverlayStore(WorldMapOverlayEntryfmt);
143 typedef std::list<std::string> StoreProblemList;
145 static bool LoadDBC_assert_print(uint32 fsize,uint32 rsize, const std::string& filename)
147 sLog.outError("ERROR: Size of '%s' setted by format string (%u) not equal size of C++ structure (%u).",filename.c_str(),fsize,rsize);
149 // assert must fail after function call
150 return false;
153 template<class T>
154 inline void LoadDBC(uint32& availableDbcLocales,barGoLink& bar, StoreProblemList& errlist, DBCStorage<T>& storage, const std::string& dbc_path, const std::string& filename)
156 // compatibility format and C++ structure sizes
157 assert(DBCFile::GetFormatRecordSize(storage.GetFormat()) == sizeof(T) || LoadDBC_assert_print(DBCFile::GetFormatRecordSize(storage.GetFormat()),sizeof(T),filename));
159 std::string dbc_filename = dbc_path + filename;
160 if(storage.Load(dbc_filename.c_str()))
162 bar.step();
163 for(uint8 i = 0; i < MAX_LOCALE; ++i)
165 if(!(availableDbcLocales & (1 << i)))
166 continue;
168 std::string dbc_filename_loc = dbc_path + localeNames[i] + "/" + filename;
169 if(!storage.LoadStringsFrom(dbc_filename_loc.c_str()))
170 availableDbcLocales &= ~(1<<i); // mark as not available for speedup next checks
173 else
175 // sort problematic dbc to (1) non compatible and (2) non-existed
176 FILE * f=fopen(dbc_filename.c_str(),"rb");
177 if(f)
179 char buf[100];
180 snprintf(buf,100," (exist, but have %d fields instead %d) Wrong client version DBC file?",storage.GetFieldCount(),strlen(storage.GetFormat()));
181 errlist.push_back(dbc_filename + buf);
182 fclose(f);
184 else
185 errlist.push_back(dbc_filename);
189 void LoadDBCStores(const std::string& dataPath)
191 std::string dbcPath = dataPath+"dbc/";
193 const uint32 DBCFilesCount = 69;
195 barGoLink bar( DBCFilesCount );
197 StoreProblemList bad_dbc_files;
198 uint32 availableDbcLocales = 0xFFFFFFFF;
200 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sAreaStore, dbcPath,"AreaTable.dbc");
202 // must be after sAreaStore loading
203 for(uint32 i = 0; i < sAreaStore.GetNumRows(); ++i) // areaflag numbered from 0
205 if(AreaTableEntry const* area = sAreaStore.LookupEntry(i))
207 // fill AreaId->DBC records
208 sAreaFlagByAreaID.insert(AreaFlagByAreaID::value_type(uint16(area->ID),area->exploreFlag));
210 // fill MapId->DBC records ( skip sub zones and continents )
211 if(area->zone==0 && area->mapid != 0 && area->mapid != 1 && area->mapid != 530 && area->mapid != 571 )
212 sAreaFlagByMapID.insert(AreaFlagByMapID::value_type(area->mapid,area->exploreFlag));
216 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sAchievementStore, dbcPath,"Achievement.dbc");
217 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sAchievementCriteriaStore, dbcPath,"Achievement_Criteria.dbc");
218 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sAreaTriggerStore, dbcPath,"AreaTrigger.dbc");
219 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sAreaGroupStore, dbcPath,"AreaGroup.dbc");
220 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sBankBagSlotPricesStore, dbcPath,"BankBagSlotPrices.dbc");
221 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sBattlemasterListStore, dbcPath,"BattlemasterList.dbc");
222 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sBarberShopStyleStore, dbcPath,"BarberShopStyle.dbc");
223 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sCharStartOutfitStore, dbcPath,"CharStartOutfit.dbc");
225 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sCharTitlesStore, dbcPath,"CharTitles.dbc");
226 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sChatChannelsStore, dbcPath,"ChatChannels.dbc");
227 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sChrClassesStore, dbcPath,"ChrClasses.dbc");
228 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sChrRacesStore, dbcPath,"ChrRaces.dbc");
229 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sCreatureDisplayInfoStore, dbcPath,"CreatureDisplayInfo.dbc");
230 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sCreatureFamilyStore, dbcPath,"CreatureFamily.dbc");
231 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sCreatureSpellDataStore, dbcPath,"CreatureSpellData.dbc");
232 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sDurabilityCostsStore, dbcPath,"DurabilityCosts.dbc");
233 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sDurabilityQualityStore, dbcPath,"DurabilityQuality.dbc");
234 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sEmotesTextStore, dbcPath,"EmotesText.dbc");
235 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sFactionStore, dbcPath,"Faction.dbc");
236 for (uint32 i=0;i<sFactionStore.GetNumRows(); ++i)
238 FactionEntry const * faction = sFactionStore.LookupEntry(i);
239 if (faction && faction->team)
241 SimpleFactionsList &flist = sFactionTeamMap[faction->team];
242 flist.push_back(i);
246 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sFactionTemplateStore, dbcPath,"FactionTemplate.dbc");
247 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGemPropertiesStore, dbcPath,"GemProperties.dbc");
248 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGlyphPropertiesStore, dbcPath,"GlyphProperties.dbc");
249 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGlyphSlotStore, dbcPath,"GlyphSlot.dbc");
251 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtBarberShopCostBaseStore,dbcPath,"gtBarberShopCostBase.dbc");
252 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtCombatRatingsStore, dbcPath,"gtCombatRatings.dbc");
254 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtChanceToMeleeCritBaseStore, dbcPath,"gtChanceToMeleeCritBase.dbc");
255 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtChanceToMeleeCritStore, dbcPath,"gtChanceToMeleeCrit.dbc");
257 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtChanceToSpellCritBaseStore, dbcPath,"gtChanceToSpellCritBase.dbc");
258 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtChanceToSpellCritStore, dbcPath,"gtChanceToSpellCrit.dbc");
260 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtOCTRegenHPStore, dbcPath,"gtOCTRegenHP.dbc");
261 //LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtOCTRegenMPStore, dbcPath,"gtOCTRegenMP.dbc"); -- not used currently
262 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtRegenHPPerSptStore, dbcPath,"gtRegenHPPerSpt.dbc");
263 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sGtRegenMPPerSptStore, dbcPath,"gtRegenMPPerSpt.dbc");
264 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sItemStore, dbcPath,"Item.dbc");
265 //LoadDBC(availableDbcLocales,bar,bad_dbc_files,sItemDisplayInfoStore, dbcPath,"ItemDisplayInfo.dbc"); -- not used currently
266 //LoadDBC(availableDbcLocales,bar,bad_dbc_files,sItemCondExtCostsStore, dbcPath,"ItemCondExtCosts.dbc");
267 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sItemExtendedCostStore, dbcPath,"ItemExtendedCost.dbc");
268 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sItemRandomPropertiesStore,dbcPath,"ItemRandomProperties.dbc");
269 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sItemRandomSuffixStore, dbcPath,"ItemRandomSuffix.dbc");
270 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sItemSetStore, dbcPath,"ItemSet.dbc");
271 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sLockStore, dbcPath,"Lock.dbc");
272 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sMailTemplateStore, dbcPath,"MailTemplate.dbc");
273 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sMapStore, dbcPath,"Map.dbc");
274 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sQuestSortStore, dbcPath,"QuestSort.dbc");
275 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sRandomPropertiesPointsStore, dbcPath,"RandPropPoints.dbc");
276 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sScalingStatDistributionStore, dbcPath,"ScalingStatDistribution.dbc");
277 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sScalingStatValuesStore, dbcPath,"ScalingStatValues.dbc");
278 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSkillLineStore, dbcPath,"SkillLine.dbc");
279 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSkillLineAbilityStore, dbcPath,"SkillLineAbility.dbc");
280 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSoundEntriesStore, dbcPath,"SoundEntries.dbc");
281 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellStore, dbcPath,"Spell.dbc");
282 for(uint32 i = 1; i < sSpellStore.GetNumRows(); ++i)
284 SpellEntry const * spell = sSpellStore.LookupEntry(i);
285 if(spell && spell->Category)
286 sSpellCategoryStore[spell->Category].insert(i);
288 // DBC not support uint64 fields but SpellEntry have SpellFamilyFlags mapped at 2 uint32 fields
289 // uint32 field already converted to bigendian if need, but must be swapped for correct uint64 bigendian view
290 #if MANGOS_ENDIAN == MANGOS_BIGENDIAN
291 std::swap(*((uint32*)(&spell->SpellFamilyFlags)),*(((uint32*)(&spell->SpellFamilyFlags))+1));
292 #endif
295 for (uint32 j = 0; j < sSkillLineAbilityStore.GetNumRows(); ++j)
297 SkillLineAbilityEntry const *skillLine = sSkillLineAbilityStore.LookupEntry(j);
299 if(!skillLine)
300 continue;
302 SpellEntry const* spellInfo = sSpellStore.LookupEntry(skillLine->spellId);
304 if(spellInfo && (spellInfo->Attributes & 0x1D0) == 0x1D0)
306 for (unsigned int i = 1; i < sCreatureFamilyStore.GetNumRows(); ++i)
308 CreatureFamilyEntry const* cFamily = sCreatureFamilyStore.LookupEntry(i);
309 if(!cFamily)
310 continue;
312 if(skillLine->skillId != cFamily->skillLine[0] && skillLine->skillId != cFamily->skillLine[1])
313 continue;
315 sPetFamilySpellsStore[i].insert(spellInfo->Id);
320 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellCastTimesStore, dbcPath,"SpellCastTimes.dbc");
321 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellDurationStore, dbcPath,"SpellDuration.dbc");
322 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellFocusObjectStore, dbcPath,"SpellFocusObject.dbc");
323 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellItemEnchantmentStore,dbcPath,"SpellItemEnchantment.dbc");
324 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellItemEnchantmentConditionStore,dbcPath,"SpellItemEnchantmentCondition.dbc");
325 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellRadiusStore, dbcPath,"SpellRadius.dbc");
326 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellRangeStore, dbcPath,"SpellRange.dbc");
327 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellRuneCostStore, dbcPath,"SpellRuneCost.dbc");
328 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSpellShapeshiftStore, dbcPath,"SpellShapeshiftForm.dbc");
329 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sStableSlotPricesStore, dbcPath,"StableSlotPrices.dbc");
330 //LoadDBC(availableDbcLocales,bar,bad_dbc_files,sSummonPropertiesStore, dbcPath,"SummonProperties.dbc");
331 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sTalentStore, dbcPath,"Talent.dbc");
333 // create talent spells set
334 for (unsigned int i = 0; i < sTalentStore.GetNumRows(); ++i)
336 TalentEntry const *talentInfo = sTalentStore.LookupEntry(i);
337 if (!talentInfo) continue;
338 for (int j = 0; j < 5; j++)
339 if(talentInfo->RankID[j])
340 sTalentSpellPosMap[talentInfo->RankID[j]] = TalentSpellPos(i,j);
343 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sTalentTabStore, dbcPath,"TalentTab.dbc");
345 // prepare fast data access to bit pos of talent ranks for use at inspecting
347 // fill table by amount of talent ranks and fill sTalentTabBitSizeInInspect
348 // store in with (row,col,talent)->size key for correct sorting by (row,col)
349 typedef std::map<uint32,uint32> TalentBitSize;
350 TalentBitSize sTalentBitSize;
351 for(uint32 i = 1; i < sTalentStore.GetNumRows(); ++i)
353 TalentEntry const *talentInfo = sTalentStore.LookupEntry(i);
354 if (!talentInfo) continue;
356 TalentTabEntry const *talentTabInfo = sTalentTabStore.LookupEntry( talentInfo->TalentTab );
357 if(!talentTabInfo)
358 continue;
360 // find talent rank
361 uint32 curtalent_maxrank = 0;
362 for(uint32 k = 5; k > 0; --k)
364 if(talentInfo->RankID[k-1])
366 curtalent_maxrank = k;
367 break;
371 sTalentBitSize[(talentInfo->Row<<24) + (talentInfo->Col<<16)+talentInfo->TalentID] = curtalent_maxrank;
372 sTalentTabSizeInInspect[talentInfo->TalentTab] += curtalent_maxrank;
375 // now have all max ranks (and then bit amount used for store talent ranks in inspect)
376 for(uint32 talentTabId = 1; talentTabId < sTalentTabStore.GetNumRows(); ++talentTabId)
378 TalentTabEntry const *talentTabInfo = sTalentTabStore.LookupEntry( talentTabId );
379 if(!talentTabInfo)
380 continue;
382 // store class talent tab pages
383 uint32 cls = 1;
384 for(uint32 m=1;!(m & talentTabInfo->ClassMask) && cls < 12 /*MAX_CLASSES*/;m <<=1, ++cls) {}
386 sTalentTabPages[cls][talentTabInfo->tabpage]=talentTabId;
388 // add total amount bits for first rank starting from talent tab first talent rank pos.
389 uint32 pos = 0;
390 for(TalentBitSize::iterator itr = sTalentBitSize.begin(); itr != sTalentBitSize.end(); ++itr)
392 uint32 talentId = itr->first & 0xFFFF;
393 TalentEntry const *talentInfo = sTalentStore.LookupEntry( talentId );
394 if(!talentInfo)
395 continue;
397 if(talentInfo->TalentTab != talentTabId)
398 continue;
400 sTalentPosInInspect[talentId] = pos;
401 pos+= itr->second;
406 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sTaxiNodesStore, dbcPath,"TaxiNodes.dbc");
408 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sTaxiPathStore, dbcPath,"TaxiPath.dbc");
409 for(uint32 i = 1; i < sTaxiPathStore.GetNumRows(); ++i)
410 if(TaxiPathEntry const* entry = sTaxiPathStore.LookupEntry(i))
411 sTaxiPathSetBySource[entry->from][entry->to] = TaxiPathBySourceAndDestination(entry->ID,entry->price);
412 uint32 pathCount = sTaxiPathStore.GetNumRows();
414 //## TaxiPathNode.dbc ## Loaded only for initialization different structures
415 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sTaxiPathNodeStore, dbcPath,"TaxiPathNode.dbc");
416 // Calculate path nodes count
417 std::vector<uint32> pathLength;
418 pathLength.resize(pathCount); // 0 and some other indexes not used
419 for(uint32 i = 1; i < sTaxiPathNodeStore.GetNumRows(); ++i)
420 if(TaxiPathNodeEntry const* entry = sTaxiPathNodeStore.LookupEntry(i))
422 if (pathLength[entry->path] < entry->index + 1)
423 pathLength[entry->path] = entry->index + 1;
425 // Set path length
426 sTaxiPathNodesByPath.resize(pathCount); // 0 and some other indexes not used
427 for(uint32 i = 1; i < sTaxiPathNodesByPath.size(); ++i)
428 sTaxiPathNodesByPath[i].resize(pathLength[i]);
429 // fill data
430 for(uint32 i = 1; i < sTaxiPathNodeStore.GetNumRows(); ++i)
431 if(TaxiPathNodeEntry const* entry = sTaxiPathNodeStore.LookupEntry(i))
432 sTaxiPathNodesByPath[entry->path][entry->index] = TaxiPathNode(entry->mapid,entry->x,entry->y,entry->z,entry->actionFlag,entry->delay);
433 sTaxiPathNodeStore.Clear();
435 // Initialize global taxinodes mask
436 // include existed nodes that have at least single not spell base (scripted) path
438 std::set<uint32> spellPaths;
439 for(uint32 i = 1; i < sSpellStore.GetNumRows (); ++i)
440 if(SpellEntry const* sInfo = sSpellStore.LookupEntry (i))
441 for(int j=0; j < 3; ++j)
442 if(sInfo->Effect[j]==123 /*SPELL_EFFECT_SEND_TAXI*/)
443 spellPaths.insert(sInfo->EffectMiscValue[j]);
445 memset(sTaxiNodesMask,0,sizeof(sTaxiNodesMask));
446 for(uint32 i = 1; i < sTaxiNodesStore.GetNumRows(); ++i)
448 if(!sTaxiNodesStore.LookupEntry(i))
449 continue;
451 TaxiPathSetBySource::const_iterator src_i = sTaxiPathSetBySource.find(i);
452 if(src_i!=sTaxiPathSetBySource.end() && !src_i->second.empty())
454 bool ok = false;
455 for(TaxiPathSetForSource::const_iterator dest_i = src_i->second.begin();dest_i != src_i->second.end(); ++dest_i)
457 // not spell path
458 if(spellPaths.find(dest_i->second.ID)==spellPaths.end())
460 ok = true;
461 break;
465 if(!ok)
466 continue;
469 // valid taxi netowrk node
470 uint8 field = (uint8)((i - 1) / 32);
471 uint32 submask = 1<<((i-1)%32);
472 sTaxiNodesMask[field] |= submask;
476 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sTotemCategoryStore, dbcPath,"TotemCategory.dbc");
477 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sVehicleStore, dbcPath,"Vehicle.dbc");
478 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sVehicleSeatStore, dbcPath,"VehicleSeat.dbc");
479 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sWorldMapAreaStore, dbcPath,"WorldMapArea.dbc");
480 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sWorldSafeLocsStore, dbcPath,"WorldSafeLocs.dbc");
481 LoadDBC(availableDbcLocales,bar,bad_dbc_files,sWorldMapOverlayStore, dbcPath,"WorldMapOverlay.dbc");
483 // error checks
484 if(bad_dbc_files.size() >= DBCFilesCount )
486 sLog.outError("\nIncorrect DataDir value in mangosd.conf or ALL required *.dbc files (%d) not found by path: %sdbc",DBCFilesCount,dataPath.c_str());
487 exit(1);
489 else if(!bad_dbc_files.empty() )
491 std::string str;
492 for(std::list<std::string>::iterator i = bad_dbc_files.begin(); i != bad_dbc_files.end(); ++i)
493 str += *i + "\n";
495 sLog.outError("\nSome required *.dbc files (%u from %d) not found or not compatible:\n%s",bad_dbc_files.size(),DBCFilesCount,str.c_str());
496 exit(1);
499 // check at up-to-date DBC files (54909 is last added spell in 3.0.1)
500 // check at up-to-date DBC files (19162 is last added spell in abilities in 3.0.1)
501 // check at up-to-date DBC files (619 is last map added in 3.0.1)
502 // check at up-to-date DBC files (1361 is last gem property added in 3.0.1)
503 // check at up-to-date DBC files (2425 is last item extended cost added in 3.0.1)
504 // check at up-to-date DBC files (76 is last char title added in 3.0.1)
505 // check at up-to-date DBC files (2311 is last area added in 3.0.1)
506 if( !sSpellStore.LookupEntry(54909) ||
507 !sSkillLineAbilityStore.LookupEntry(19162) ||
508 !sMapStore.LookupEntry(619) ||
509 !sGemPropertiesStore.LookupEntry(1361) ||
510 !sItemExtendedCostStore.LookupEntry(2425) ||
511 !sCharTitlesStore.LookupEntry(76) ||
512 !sAreaStore.LookupEntry(2311) )
514 sLog.outError("\nYou have _outdated_ DBC files. Please extract correct versions from current using client.");
515 exit(1);
518 sLog.outString();
519 sLog.outString( ">> Loaded %d data stores", DBCFilesCount );
520 sLog.outString();
523 SimpleFactionsList const* GetFactionTeamList(uint32 faction)
525 FactionTeamMap::const_iterator itr = sFactionTeamMap.find(faction);
526 if(itr==sFactionTeamMap.end())
527 return NULL;
528 return &itr->second;
531 char* GetPetName(uint32 petfamily, uint32 dbclang)
533 if(!petfamily)
534 return NULL;
535 CreatureFamilyEntry const *pet_family = sCreatureFamilyStore.LookupEntry(petfamily);
536 if(!pet_family)
537 return NULL;
538 return pet_family->Name[dbclang]?pet_family->Name[dbclang]:NULL;
541 TalentSpellPos const* GetTalentSpellPos(uint32 spellId)
543 TalentSpellPosMap::const_iterator itr = sTalentSpellPosMap.find(spellId);
544 if(itr==sTalentSpellPosMap.end())
545 return NULL;
547 return &itr->second;
550 uint32 GetTalentSpellCost(uint32 spellId)
552 if(TalentSpellPos const* pos = GetTalentSpellPos(spellId))
553 return pos->rank+1;
555 return 0;
558 int32 GetAreaFlagByAreaID(uint32 area_id)
560 AreaFlagByAreaID::iterator i = sAreaFlagByAreaID.find(area_id);
561 if(i == sAreaFlagByAreaID.end())
562 return -1;
564 return i->second;
567 AreaTableEntry const* GetAreaEntryByAreaID(uint32 area_id)
569 int32 areaflag = GetAreaFlagByAreaID(area_id);
570 if(areaflag < 0)
571 return NULL;
573 return sAreaStore.LookupEntry(areaflag );
576 AreaTableEntry const* GetAreaEntryByAreaFlagAndMap(uint32 area_flag,uint32 map_id)
578 if(area_flag)
579 return sAreaStore.LookupEntry(area_flag);
581 if(MapEntry const* mapEntry = sMapStore.LookupEntry(map_id))
582 return GetAreaEntryByAreaID(mapEntry->linked_zone);
584 return NULL;
587 uint32 GetAreaFlagByMapId(uint32 mapid)
589 AreaFlagByMapID::iterator i = sAreaFlagByMapID.find(mapid);
590 if(i == sAreaFlagByMapID.end())
591 return 0;
592 else
593 return i->second;
596 uint32 GetVirtualMapForMapAndZone(uint32 mapid, uint32 zoneId)
598 if(mapid != 530 && mapid != 571) // speed for most cases
599 return mapid;
601 if(WorldMapAreaEntry const* wma = sWorldMapAreaStore.LookupEntry(zoneId))
602 return wma->virtual_map_id >= 0 ? wma->virtual_map_id : wma->map_id;
604 return mapid;
607 ContentLevels GetContentLevelsForMapAndZone(uint32 mapid, uint32 zoneId)
609 mapid = GetVirtualMapForMapAndZone(mapid,zoneId);
610 if(mapid < 2)
611 return CONTENT_1_60;
613 MapEntry const* mapEntry = sMapStore.LookupEntry(mapid);
614 if(!mapEntry)
615 return CONTENT_1_60;
617 switch(mapEntry->Expansion())
619 default: return CONTENT_1_60;
620 case 1: return CONTENT_61_70;
621 case 2: return CONTENT_71_80;
625 ChatChannelsEntry const* GetChannelEntryFor(uint32 channel_id)
627 // not sorted, numbering index from 0
628 for(uint32 i = 0; i < sChatChannelsStore.GetNumRows(); ++i)
630 ChatChannelsEntry const* ch = sChatChannelsStore.LookupEntry(i);
631 if(ch && ch->ChannelID == channel_id)
632 return ch;
634 return NULL;
637 bool IsTotemCategoryCompatiableWith(uint32 itemTotemCategoryId, uint32 requiredTotemCategoryId)
639 if(requiredTotemCategoryId==0)
640 return true;
641 if(itemTotemCategoryId==0)
642 return false;
644 TotemCategoryEntry const* itemEntry = sTotemCategoryStore.LookupEntry(itemTotemCategoryId);
645 if(!itemEntry)
646 return false;
647 TotemCategoryEntry const* reqEntry = sTotemCategoryStore.LookupEntry(requiredTotemCategoryId);
648 if(!reqEntry)
649 return false;
651 if(itemEntry->categoryType!=reqEntry->categoryType)
652 return false;
654 return (itemEntry->categoryMask & reqEntry->categoryMask)==reqEntry->categoryMask;
657 void Zone2MapCoordinates(float& x,float& y,uint32 zone)
659 WorldMapAreaEntry const* maEntry = sWorldMapAreaStore.LookupEntry(zone);
661 // if not listed then map coordinates (instance)
662 if(!maEntry)
663 return;
665 std::swap(x,y); // at client map coords swapped
666 x = x*((maEntry->x2-maEntry->x1)/100)+maEntry->x1;
667 y = y*((maEntry->y2-maEntry->y1)/100)+maEntry->y1; // client y coord from top to down
670 void Map2ZoneCoordinates(float& x,float& y,uint32 zone)
672 WorldMapAreaEntry const* maEntry = sWorldMapAreaStore.LookupEntry(zone);
674 // if not listed then map coordinates (instance)
675 if(!maEntry)
676 return;
678 x = (x-maEntry->x1)/((maEntry->x2-maEntry->x1)/100);
679 y = (y-maEntry->y1)/((maEntry->y2-maEntry->y1)/100); // client y coord from top to down
680 std::swap(x,y); // client have map coords swapped
683 uint32 GetTalentInspectBitPosInTab(uint32 talentId)
685 TalentInspectMap::const_iterator itr = sTalentPosInInspect.find(talentId);
686 if(itr == sTalentPosInInspect.end())
687 return 0;
689 return itr->second;
692 uint32 GetTalentTabInspectBitSize(uint32 talentTabId)
694 TalentInspectMap::const_iterator itr = sTalentTabSizeInInspect.find(talentTabId);
695 if(itr == sTalentTabSizeInInspect.end())
696 return 0;
698 return itr->second;
701 uint32 const* GetTalentTabPages(uint32 cls)
703 return sTalentTabPages[cls];
706 // script support functions
707 MANGOS_DLL_SPEC DBCStorage <SoundEntriesEntry> const* GetSoundEntriesStore() { return &sSoundEntriesStore; }
708 MANGOS_DLL_SPEC DBCStorage <SpellEntry> const* GetSpellStore() { return &sSpellStore; }
709 MANGOS_DLL_SPEC DBCStorage <SpellRangeEntry> const* GetSpellRangeStore() { return &sSpellRangeStore; }