Merge branch 'fixes' into main/rendor-staging
[ryzomcore.git] / nel / src / misc / sheet_id.cpp
blobab7d0d254bbd5bdd0a0b520e7bb6fd56e2002588
1 // NeL - MMORPG Framework <http://dev.ryzom.com/projects/nel/>
2 // Copyright (C) 2010 Winch Gate Property Limited
3 //
4 // This source file has been modified by the following contributors:
5 // Copyright (C) 2012-2020 Jan BOON (Kaetemi) <jan.boon@kaetemi.be>
6 //
7 // This program is free software: you can redistribute it and/or modify
8 // it under the terms of the GNU Affero General Public License as
9 // published by the Free Software Foundation, either version 3 of the
10 // License, or (at your option) any later version.
12 // This program is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 // GNU Affero General Public License for more details.
17 // You should have received a copy of the GNU Affero General Public License
18 // along with this program. If not, see <http://www.gnu.org/licenses/>.
20 /* This class is case unsensitive. It means that you can call build() and
21 * buildIdVector() with string with anycase, it'll work.
24 #include "stdmisc.h"
26 #include "nel/misc/file.h"
27 #include "nel/misc/path.h"
29 #include "nel/misc/sheet_id.h"
30 #include "nel/misc/common.h"
31 #include "nel/misc/hierarchical_timer.h"
33 using namespace std;
35 #ifdef DEBUG_NEW
36 #define new DEBUG_NEW
37 #endif
39 namespace NLMISC
42 CSheetId::CChar CSheetId::_AllStrings;
43 CStaticMap<uint32, CSheetId::CChar> CSheetId::_SheetIdToName;
44 CStaticMap<CSheetId::CChar, uint32, CSheetId::CCharComp> CSheetId::_SheetNameToId;
45 //map<uint32,std::string> CSheetId::_SheetIdToName;
46 //map<std::string,uint32> CSheetId::_SheetNameToId;
47 vector<std::string> CSheetId::_FileExtensions;
48 bool CSheetId::_Initialised = false;
49 bool CSheetId::_RemoveUnknownSheet = true;
50 bool CSheetId::_DontHaveSheetKnowledge = false;
51 std::map<std::string, uint32> CSheetId::_DevTypeNameToId;
52 std::vector<std::vector<std::string>> CSheetId::_DevSheetIdToName;
53 std::map<std::string, uint32> CSheetId::_DevSheetNameToId;
55 const CSheetId CSheetId::Unknown((uint32)0);
57 void CSheetId::cbFileChange(const std::string &filename)
59 nlinfo("SHEETID: %s changed, reload it", filename.c_str());
61 loadSheetId();
64 //-----------------------------------------------
65 // CSheetId
67 //-----------------------------------------------
68 CSheetId::CSheetId(uint32 sheetRef)
70 _Id.Id = sheetRef;
72 #ifdef NL_DEBUG_SHEET_ID
73 // Yoyo: don't access the static map, because of order of static ctor call.
74 // For now, all static CSheetId are 0 (eg: CSheetId::Unknown)
75 if (sheetRef)
77 TSheetIdToNameMap::iterator it(_SheetIdToName.find(sheetRef));
78 if (it != _SheetIdToName.end())
80 _DebugSheetName = it->second.Ptr;
82 else
83 _DebugSheetName = NULL;
85 else
87 _DebugSheetName = NULL;
89 #endif
92 //-----------------------------------------------
93 // CSheetId
95 //-----------------------------------------------
96 CSheetId::CSheetId(int sheetRef)
98 _Id.Id = (uint32)sheetRef;
100 #ifdef NL_DEBUG_SHEET_ID
101 // Yoyo: don't access the static map, because of order of static ctor call.
102 // For now, all static CSheetId are 0 (eg: CSheetId::Unknown)
103 if (sheetRef)
105 TSheetIdToNameMap::iterator it(_SheetIdToName.find(sheetRef));
106 if (it != _SheetIdToName.end())
108 _DebugSheetName = it->second.Ptr;
110 else
111 _DebugSheetName = NULL;
113 else
115 _DebugSheetName = NULL;
117 #endif
120 //-----------------------------------------------
121 // CSheetId
123 //-----------------------------------------------
124 CSheetId::CSheetId(const string &sheetName)
126 if (!buildSheetId(sheetName.c_str(), sheetName.size()))
128 if (sheetName.empty())
129 nlwarning("SHEETID: Try to create an CSheetId with empty name. TODO: check why.");
130 else
131 nlwarning("SHEETID: The sheet '%s' is not in sheet_id.bin, setting it to Unknown", sheetName.c_str());
132 //std::string stack;
133 //NLMISC::getCallStack(stack);
134 //std::vector<std::string> contexts;
135 //NLMISC::explode(stack, string("\n"), contexts);
136 //nldebug("Dumping callstack :");
137 //for (uint i=0; i<contexts.size(); ++i)
138 // nldebug(" %3u : %s", i, contexts[i].c_str());
139 *this = Unknown;
142 // nldebug("LIST_SHEET_ID: %s (%s)", toString().c_str(), sheetName.c_str());
144 } // CSheetId //
146 //-----------------------------------------------
147 // CSheetId
149 //-----------------------------------------------
150 CSheetId::CSheetId(const char *sheetName)
152 if (!buildSheetId(sheetName, strlen(sheetName)))
154 if (!sheetName[0])
155 nlwarning("SHEETID: Try to create an CSheetId with empty name. TODO: check why.");
156 else
157 nlwarning("SHEETID: The sheet '%s' is not in sheet_id.bin, setting it to Unknown", sheetName);
158 *this = Unknown;
161 // nldebug("LIST_SHEET_ID: %s (%s)", toString().c_str(), sheetName.c_str());
163 } // CSheetId //
165 CSheetId::CSheetId(const std::string &sheetName, const std::string &defaultType)
167 // Don't use this function without defaultType, use the one above.
168 nlassert(defaultType.size() != 0);
170 if (sheetName.rfind('.') == std::string::npos)
172 std::string withType = sheetName + "." + defaultType;
173 *this = CSheetId(withType);
174 // nldebug("SHEETID: Constructing CSheetId from name '%s' without explicit type, defaulting as '%s' to '%s'", sheetName.c_str(), defaultType.c_str(), withType.c_str());
176 else
178 *this = CSheetId(sheetName);
182 static std::string s_Dot = ".";
184 CSheetId::CSheetId(const std::string &sheetName, const char *defaultType)
186 // Don't use this function without defaultType, use the one above.
187 nlassert(defaultType[0]);
189 if (sheetName.rfind('.') == std::string::npos)
191 std::string withType = sheetName + s_Dot + defaultType;
192 *this = CSheetId(withType);
193 // nldebug("SHEETID: Constructing CSheetId from name '%s' without explicit type, defaulting as '%s' to '%s'", sheetName.c_str(), defaultType.c_str(), withType.c_str());
195 else
197 *this = CSheetId(sheetName);
201 CSheetId::CSheetId(const char *sheetName, const char *defaultType)
203 // Don't use this function without defaultType, use the one above.
204 nlassert(defaultType[0]);
206 if (!strchr(sheetName, '.'))
208 std::string withType = sheetName + s_Dot + defaultType;
209 *this = CSheetId(withType);
210 // nldebug("SHEETID: Constructing CSheetId from name '%s' without explicit type, defaulting as '%s' to '%s'", sheetName.c_str(), defaultType.c_str(), withType.c_str());
212 else
214 *this = CSheetId(sheetName);
218 //-----------------------------------------------
219 // Build
221 //-----------------------------------------------
222 bool CSheetId::buildSheetId(const char *sheetName, size_t sheetNameLen)
224 nlassert(_Initialised);
226 // When no sheet_id.bin is loaded, use dynamically assigned IDs.
227 if (_DontHaveSheetKnowledge)
229 std::string sheetNameLc = toLowerAscii(sheetName);
230 std::map<std::string, uint32>::iterator it = _DevSheetNameToId.find(sheetNameLc);
231 if (it == _DevSheetNameToId.end())
233 // Create a new dynamic sheet ID.
234 // nldebug("SHEETID: Creating a dynamic sheet id for '%s'", sheetName.c_str());
235 std::string sheetType = CFile::getExtension(sheetNameLc);
236 std::string sheetName = CFile::getFilenameWithoutExtension(sheetNameLc);
237 std::map<std::string, uint32>::iterator tit = _DevTypeNameToId.find(sheetType);
238 uint32 typeId;
239 if (tit == _DevTypeNameToId.end())
241 _FileExtensions.push_back(sheetType);
242 _DevSheetIdToName.push_back(std::vector<std::string>());
243 typeId = (uint32)_FileExtensions.size() - 1;
244 _DevTypeNameToId[sheetType] = typeId;
245 std::string unknownNewType = std::string("unknown." + sheetType);
246 _DevSheetIdToName[typeId].push_back(unknownNewType);
247 _Id.IdInfos.Type = typeId;
248 _Id.IdInfos.Id = _DevSheetIdToName[typeId].size() - 1;
249 _DevSheetNameToId[unknownNewType] = _Id.Id;
250 if (sheetName == "unknown")
251 return true; // Return with the unknown sheet id of this type
253 else
255 typeId = tit->second;
256 _Id.IdInfos.Type = typeId;
258 // Add a new sheet name to the type
259 _DevSheetIdToName[typeId].push_back(sheetNameLc);
260 _Id.IdInfos.Id = _DevSheetIdToName[typeId].size() - 1;
261 // nldebug("SHEETID: Type %i, id %i, sheetid %i", _Id.IdInfos.Type, _Id.IdInfos.Id, _Id.Id);
262 _DevSheetNameToId[sheetNameLc] = _Id.Id;
263 return true;
265 _Id.Id = it->second;
266 return true;
269 // try looking up the sheet name in _SheetNameToId
270 TSheetNameToIdMap::const_iterator itId;
271 CChar c;
272 #ifdef alloca
273 #pragma warning(push)
274 #pragma warning(disable : 6255)
275 c.Ptr = (char *)alloca(sheetNameLen + 1);
276 #pragma warning(pop)
277 #else
278 c.Ptr = new char[sheetName.size() + 1];
279 #endif
280 strcpy(c.Ptr, sheetName);
281 toLowerAscii(c.Ptr);
283 itId = _SheetNameToId.find(c);
284 #ifndef alloca
285 delete[] c.Ptr; // Don't delete alloca
286 #endif
287 if (itId != _SheetNameToId.end())
289 _Id.Id = itId->second;
290 #ifdef NL_DEBUG_SHEET_ID
291 // store debug info
292 _DebugSheetName = itId->first.Ptr;
293 #endif
294 return true;
297 // we failed to find the sheet name in the sheetname map so see if the string is numeric
298 if (sheetName[0] == '#' && sheetName[1])
300 uint32 numericId;
301 if (NLMISC::fromString((const char *)(sheetName + 1), numericId))
303 _Id.Id = numericId;
304 return true;
308 return false;
311 void CSheetId::loadSheetId()
313 H_AUTO(CSheetIdInit);
314 //nldebug("Loading sheet_id.bin");
316 // Open the sheet id to sheet file name association
317 CIFile file;
318 std::string path = CPath::lookup("sheet_id.bin", false, false);
319 if (!path.empty() && file.open(path))
321 // clear entries
322 _FileExtensions.clear();
323 _SheetIdToName.clear();
324 _SheetNameToId.clear();
326 // reserve space for the vector of file extensions
327 _FileExtensions.resize(1 << (NL_SHEET_ID_TYPE_BITS));
329 // Get the map from the file
330 map<uint32, string> tempMap;
331 contReset(tempMap);
332 file.serialCont(tempMap);
333 file.close();
335 if (_RemoveUnknownSheet)
337 uint32 removednbfiles = 0;
338 uint32 nbfiles = (uint32)tempMap.size();
340 // now we remove all files that not available
341 map<uint32, string>::iterator itStr2;
342 for (itStr2 = tempMap.begin(); itStr2 != tempMap.end();)
344 if (CPath::exists((*itStr2).second))
346 ++itStr2;
348 else
350 map<uint32, string>::iterator olditStr = itStr2;
351 //nldebug ("Removing file '%s' from CSheetId because the file not exists", (*olditStr).second.c_str ());
352 itStr2++;
353 tempMap.erase(olditStr);
354 removednbfiles++;
357 nlinfo("SHEETID: Removed %d files on %d from CSheetId because these files don't exist", removednbfiles, nbfiles);
360 // Convert the map to one big string and 1 static map (id to name)
362 // Get the number and size of all strings
363 vector<CChar> tempVec; // Used to initialise the first map
364 uint32 nNb = 0;
365 uint32 nSize = 0;
366 map<uint32, string>::const_iterator it = tempMap.begin();
367 while (it != tempMap.end())
369 nSize += (uint32)it->second.size() + 1;
370 nNb++;
371 it++;
374 // Make the big string (composed of all strings) and a vector referencing each string
375 tempVec.resize(nNb);
376 _AllStrings.Ptr = new char[nSize];
377 it = tempMap.begin();
378 nSize = 0;
379 nNb = 0;
380 while (it != tempMap.end())
382 tempVec[nNb].Ptr = _AllStrings.Ptr + nSize;
383 strcpy(_AllStrings.Ptr + nSize, it->second.c_str());
384 toLowerAscii(_AllStrings.Ptr + nSize);
385 nSize += (uint32)it->second.size() + 1;
386 nNb++;
387 it++;
390 // Finally build the static map (id to name)
391 _SheetIdToName.reserve(tempVec.size());
392 it = tempMap.begin();
393 nNb = 0;
394 while (it != tempMap.end())
396 _SheetIdToName.add(pair<uint32, CChar>(it->first, CChar(tempVec[nNb])));
398 nNb++;
399 it++;
402 // The vector of all small string is not needed anymore we have all the info in
403 // the static map and with the pointer AllStrings referencing the beginning.
406 // Build the invert map (Name to Id) & file extension vector
408 uint32 nSize = (uint32)_SheetIdToName.size();
409 _SheetNameToId.reserve(nSize);
410 TSheetIdToNameMap::iterator itStr;
411 for (itStr = _SheetIdToName.begin(); itStr != _SheetIdToName.end(); ++itStr)
413 // add entry to the inverse map
414 _SheetNameToId.add(make_pair((*itStr).second, (*itStr).first));
416 // work out the type value for this entry in the map
417 TSheetId sheetId;
418 sheetId.Id = (*itStr).first;
419 uint32 type = sheetId.IdInfos.Type;
421 // check whether we need to add an entry to the file extensions vector
422 if (_FileExtensions[type].empty())
424 // find the file extension part of the given file name
425 _FileExtensions[type] = toLowerAscii(CFile::getExtension((*itStr).second.Ptr));
427 nSize--;
429 _SheetNameToId.endAdd();
432 else
434 nlerror("<CSheetId::init> Can't open the file sheet_id.bin");
436 nldebug("Finished loading sheet_id.bin: %u entries read", _SheetIdToName.size());
439 //-----------------------------------------------
440 // init
442 //-----------------------------------------------
443 void CSheetId::init(bool removeUnknownSheet)
445 // allow multiple calls to init in case libraries depending on sheetid call this init from their own
446 if (_Initialised)
448 if (_DontHaveSheetKnowledge)
449 nlinfo("SHEETID: CSheetId is already initialized without sheet_id.bin");
450 return;
453 // CFile::addFileChangeCallback ("sheet_id.bin", cbFileChange);
455 _RemoveUnknownSheet = removeUnknownSheet;
457 loadSheetId();
458 _Initialised = true;
460 } // init //
462 void CSheetId::initWithoutSheet()
464 if (_Initialised)
466 nlassert(_DontHaveSheetKnowledge);
467 return;
470 _Initialised = true;
471 _DontHaveSheetKnowledge = true;
473 // Initialize id 0,0 as unknown.unknown
474 CSheetId unknownUnknown = CSheetId("unknown.unknown");
475 nlassert(unknownUnknown == CSheetId::Unknown);
478 //-----------------------------------------------
479 // uninit
481 //-----------------------------------------------
482 void CSheetId::uninit()
484 delete[] _AllStrings.Ptr;
485 _FileExtensions.clear();
486 _DevTypeNameToId.clear();
487 _DevSheetIdToName.clear();
488 _DevSheetNameToId.clear();
489 } // uninit //
491 //-----------------------------------------------
492 // operator=
494 //-----------------------------------------------
495 CSheetId &CSheetId::operator=(const CSheetId &sheetId)
497 if (!_Initialised)
498 init(false);
500 if (this == &sheetId)
502 return *this;
505 _Id.Id = sheetId.asInt();
507 #ifdef NL_DEBUG_SHEET_ID
508 _DebugSheetName = sheetId._DebugSheetName;
509 #endif
511 return *this;
513 } // operator= //
515 //-----------------------------------------------
516 // operator=
518 //-----------------------------------------------
519 CSheetId &CSheetId::operator=(const string &sheetName)
522 if (!buildSheetId(sheetName.c_str(), sheetName.size()))
523 *this = Unknown;
525 // nldebug("LIST_SHEET_ID: %s (%s)", toString().c_str(), sheetName.c_str());
527 return *this;
529 } // operator= //
531 //-----------------------------------------------
532 // operator=
534 //-----------------------------------------------
535 CSheetId &CSheetId::operator=(const char *sheetName)
538 if (!buildSheetId(sheetName, strlen(sheetName)))
539 *this = Unknown;
541 // nldebug("LIST_SHEET_ID: %s (%s)", toString().c_str(), sheetName);
543 return *this;
545 } // operator= //
547 //-----------------------------------------------
548 // operator=
550 //-----------------------------------------------
551 CSheetId &CSheetId::operator=(uint32 sheetRef)
553 if (!_Initialised)
554 init(false);
556 _Id.Id = sheetRef;
558 return *this;
560 } // operator= //
562 //-----------------------------------------------
563 // operator=
565 //-----------------------------------------------
566 CSheetId &CSheetId::operator=(int sheetRef)
568 if (!_Initialised)
569 init(false);
571 _Id.Id = (uint32)sheetRef;
573 return *this;
575 } // operator= //
577 //-----------------------------------------------
578 // operator<
580 //-----------------------------------------------
581 bool CSheetId::operator<(const CSheetId &sheetRef) const
583 if (!_Initialised)
584 init(false);
586 if (_Id.Id < sheetRef.asInt())
588 return true;
591 return false;
593 } // operator< //
595 //-----------------------------------------------
596 // toString
598 //-----------------------------------------------
599 string CSheetId::toString(bool ifNotFoundUseNumericId) const
601 if (!_Initialised)
602 init(false);
604 if (_DontHaveSheetKnowledge)
606 if (_Id.IdInfos.Type < _DevSheetIdToName.size()
607 && _Id.IdInfos.Id < _DevSheetIdToName[_Id.IdInfos.Type].size())
609 return _DevSheetIdToName[_Id.IdInfos.Type][_Id.IdInfos.Id];
611 else
613 if (ifNotFoundUseNumericId)
615 return NLMISC::toString("#%u", _Id.Id);
617 else
619 return NLMISC::toString("<Sheet %u not found in loaded sheets>", _Id.Id);
624 TSheetIdToNameMap::const_iterator itStr = _SheetIdToName.find(_Id.Id);
625 if (itStr != _SheetIdToName.end())
627 return string((*itStr).second.Ptr);
629 else
631 // This nlwarning is commented out because the loggers are mutexed, therefore
632 // you couldn't use toString() within a nlwarning().
633 //nlwarning("<CSheetId::toString> The sheet %08x is not in sheet_id.bin",_Id.Id);
634 if (ifNotFoundUseNumericId)
636 return NLMISC::toString("#%u", _Id.Id);
638 else
640 return NLMISC::toString("<Sheet %u not found in sheet_id.bin>", _Id.Id);
644 } // toString //
646 void CSheetId::serial(NLMISC::IStream &f)
648 nlassert(!_DontHaveSheetKnowledge);
650 f.serial(_Id.Id);
652 #ifdef NL_DEBUG_SHEET_ID
653 TSheetIdToNameMap::iterator it(_SheetIdToName.find(_Id.Id));
654 if (it != _SheetIdToName.end())
655 _DebugSheetName = it->second.Ptr;
656 else
657 _DebugSheetName = NULL;
658 #endif
661 void CSheetId::serialString(NLMISC::IStream &f, const std::string &defaultType)
663 nlassert(_Initialised);
665 if (f.isReading())
667 std::string sheetName;
668 f.serial(sheetName);
669 *this = CSheetId(sheetName, defaultType);
671 else
673 // if this assert fails, you may be using an outdated id bin
674 nlassert(*this != CSheetId::Unknown);
675 std::string sheetName = toString();
676 f.serial(sheetName);
680 //-----------------------------------------------
681 // display
683 //-----------------------------------------------
684 void CSheetId::display()
686 if (!_Initialised)
687 init(false);
689 TSheetIdToNameMap::const_iterator itStr;
690 for (itStr = _SheetIdToName.begin(); itStr != _SheetIdToName.end(); ++itStr)
692 //nlinfo("%d %s",(*itStr).first,(*itStr).second.c_str());
693 nlinfo("SHEETID: (%08x %d) %s", (*itStr).first, (*itStr).first, (*itStr).second.Ptr);
696 } // display //
698 //-----------------------------------------------
699 // display
701 //-----------------------------------------------
702 void CSheetId::display(uint32 type)
704 if (!_Initialised)
705 init(false);
707 TSheetIdToNameMap::const_iterator itStr;
708 for (itStr = _SheetIdToName.begin(); itStr != _SheetIdToName.end(); ++itStr)
710 // work out the type value for this entry in the map
711 TSheetId sheetId;
712 sheetId.Id = (*itStr).first;
714 // decide whether or not to display the entry
715 if (type == sheetId.IdInfos.Type)
717 //nlinfo("%d %s",(*itStr).first,(*itStr).second.c_str());
718 nlinfo("SHEETID: (%08x %d) %s", (*itStr).first, (*itStr).first, (*itStr).second.Ptr);
722 } // display //
724 //-----------------------------------------------
725 // buildIdVector
727 //-----------------------------------------------
728 void CSheetId::buildIdVector(std::vector<CSheetId> &result)
730 if (!_Initialised)
731 init(false);
733 TSheetIdToNameMap::const_iterator itStr;
734 for (itStr = _SheetIdToName.begin(); itStr != _SheetIdToName.end(); ++itStr)
736 result.push_back((CSheetId)(*itStr).first);
739 } // buildIdVector //
741 //-----------------------------------------------
742 // buildIdVector
744 //-----------------------------------------------
745 void CSheetId::buildIdVector(std::vector<CSheetId> &result, uint32 type)
747 if (!_Initialised)
748 init(false);
749 nlassert(type < (1 << (NL_SHEET_ID_TYPE_BITS)));
751 TSheetIdToNameMap::const_iterator itStr;
752 for (itStr = _SheetIdToName.begin(); itStr != _SheetIdToName.end(); ++itStr)
754 // work out the type value for this entry in the map
755 TSheetId sheetId;
756 sheetId.Id = (*itStr).first;
758 // decide whether or not to use the entry
759 if (type == sheetId.IdInfos.Type)
761 result.push_back((CSheetId)sheetId.Id);
765 } // buildIdVector //
767 //-----------------------------------------------
768 // buildIdVector
770 //-----------------------------------------------
771 void CSheetId::buildIdVector(std::vector<CSheetId> &result, std::vector<std::string> &resultFilenames, uint32 type)
773 if (!_Initialised)
774 init(false);
775 nlassert(type < (1 << (NL_SHEET_ID_TYPE_BITS)));
777 TSheetIdToNameMap::const_iterator itStr;
778 for (itStr = _SheetIdToName.begin(); itStr != _SheetIdToName.end(); ++itStr)
780 // work out the type value for this entry in the map
781 TSheetId sheetId;
782 sheetId.Id = (*itStr).first;
784 // decide whether or not to use the entry
785 if (type == sheetId.IdInfos.Type)
787 result.push_back((CSheetId)sheetId.Id);
788 resultFilenames.push_back((*itStr).second.Ptr);
792 } // buildIdVector //
794 //-----------------------------------------------
795 // buildIdVector
797 //-----------------------------------------------
798 void CSheetId::buildIdVector(std::vector<CSheetId> &result, const std::string &fileExtension)
800 uint32 type = typeFromFileExtension(fileExtension);
801 if (type != std::numeric_limits<uint32>::max())
802 buildIdVector(result, type);
804 } // buildIdVector //
806 //-----------------------------------------------
807 // buildIdVector
809 //-----------------------------------------------
810 void CSheetId::buildIdVector(std::vector<CSheetId> &result, std::vector<std::string> &resultFilenames, const std::string &fileExtension)
812 uint32 type = typeFromFileExtension(fileExtension);
813 if (type != std::numeric_limits<uint32>::max())
814 buildIdVector(result, resultFilenames, type);
816 } // buildIdVector //
818 //-----------------------------------------------
819 // typeFromFileExtension
821 //-----------------------------------------------
822 uint32 CSheetId::typeFromFileExtension(const std::string &fileExtension)
824 if (!_Initialised)
825 init(false);
827 uint i;
828 for (i = 0; i < _FileExtensions.size(); i++)
829 if (toLowerAscii(fileExtension) == _FileExtensions[i])
830 return i;
832 return std::numeric_limits<uint32>::max();
833 } // typeFromFileExtension //
835 //-----------------------------------------------
836 // fileExtensionFromType
838 //-----------------------------------------------
839 const std::string &CSheetId::fileExtensionFromType(uint32 type)
841 if (!_Initialised)
842 init(false);
843 nlassert(type < (1 << (NL_SHEET_ID_TYPE_BITS)));
845 return _FileExtensions[type];
847 } // fileExtensionFromType //
849 //-----------------------------------------------
850 // build
852 //-----------------------------------------------
853 void CSheetId::buildSheetId(uint32 shortId, uint32 type)
855 nlassert(shortId < (1 << NL_SHEET_ID_ID_BITS));
856 nlassert(type < (1 << (NL_SHEET_ID_TYPE_BITS)));
858 _Id.IdInfos.Id = shortId;
859 _Id.IdInfos.Type = type;
861 #ifdef NL_DEBUG_SHEET_ID
862 TSheetIdToNameMap::iterator it(_SheetIdToName.find(_Id.Id));
863 if (it != _SheetIdToName.end())
865 _DebugSheetName = it->second.Ptr;
867 else
868 _DebugSheetName = NULL;
869 #endif
872 } // NLMISC