ResourceID.cpp 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204
  1. /*
  2. * ResourceID.cpp, part of VCMI engine
  3. *
  4. * Authors: listed in file AUTHORS in main folder
  5. *
  6. * License: GNU General Public License v2.0 or later
  7. * Full text of license available in license.txt file, in main folder
  8. *
  9. */
  10. #include "StdInc.h"
  11. #include "ResourceID.h"
  12. #include "FileInfo.h"
  13. // trivial to_upper that completely ignores localization and only work with ASCII
  14. // Technically not a problem since
  15. // 1) Right now VCMI does not supports unicode in filenames on Win
  16. // 2) Filesystem case-sensivity is only problem for H3 data which uses ASCII-only symbols
  17. // for me (Ivan) this define gives notable decrease in loading times
  18. // #define ENABLE_TRIVIAL_TOUPPER
  19. #ifdef ENABLE_TRIVIAL_TOUPPER
  20. static inline void toUpper(char & symbol)
  21. {
  22. static const int diff = 'a' - 'A';
  23. if (symbol >= 'a' && symbol <= 'z')
  24. symbol -= diff;
  25. }
  26. static inline void toUpper(std::string & string)
  27. {
  28. for (char & symbol : string)
  29. toUpper(symbol);
  30. }
  31. #else
  32. static inline void toUpper(std::string & string)
  33. {
  34. boost::to_upper(string);
  35. }
  36. #endif
  37. static inline EResType::Type readType(const std::string& name)
  38. {
  39. return EResTypeHelper::getTypeFromExtension(FileInfo::GetExtension(name).to_string());
  40. }
  41. static inline std::string readName(std::string name)
  42. {
  43. const auto dotPos = name.find_last_of('.');
  44. //do not cut "extension" of directory name
  45. auto delimPos = name.find_last_of('/');
  46. if(delimPos == std::string::npos)
  47. delimPos = name.find_last_of('\\');
  48. if((delimPos == std::string::npos || delimPos < dotPos) && dotPos != std::string::npos)
  49. {
  50. auto type = EResTypeHelper::getTypeFromExtension(name.substr(dotPos));
  51. if(type != EResType::OTHER)
  52. name.resize(dotPos);
  53. }
  54. toUpper(name);
  55. return name;
  56. }
  57. #if 0
  58. ResourceID::ResourceID()
  59. :type(EResType::OTHER)
  60. {
  61. }
  62. #endif
  63. ResourceID::ResourceID(std::string name_):
  64. type{readType(name_)},
  65. name{readName(std::move(name_))}
  66. {}
  67. ResourceID::ResourceID(std::string name_, EResType::Type type_):
  68. type{type_},
  69. name{readName(std::move(name_))}
  70. {}
  71. #if 0
  72. std::string ResourceID::getName() const
  73. {
  74. return name;
  75. }
  76. EResType::Type ResourceID::getType() const
  77. {
  78. return type;
  79. }
  80. void ResourceID::setName(std::string name)
  81. {
  82. // setName shouldn't be used if type is UNDEFINED
  83. assert(type != EResType::UNDEFINED);
  84. this->name = std::move(name);
  85. size_t dotPos = this->name.find_last_of("/.");
  86. if(dotPos != std::string::npos && this->name[dotPos] == '.'
  87. && this->type == EResTypeHelper::getTypeFromExtension(this->name.substr(dotPos)))
  88. {
  89. this->name.erase(dotPos);
  90. }
  91. toUpper(this->name);
  92. }
  93. void ResourceID::setType(EResType::Type type)
  94. {
  95. this->type = type;
  96. }
  97. #endif
  98. EResType::Type EResTypeHelper::getTypeFromExtension(std::string extension)
  99. {
  100. toUpper(extension);
  101. static const std::map<std::string, EResType::Type> stringToRes =
  102. {
  103. {".TXT", EResType::TEXT},
  104. {".JSON", EResType::TEXT},
  105. {".DEF", EResType::ANIMATION},
  106. {".MSK", EResType::MASK},
  107. {".MSG", EResType::MASK},
  108. {".H3C", EResType::CAMPAIGN},
  109. {".H3M", EResType::MAP},
  110. {".FNT", EResType::BMP_FONT},
  111. {".TTF", EResType::TTF_FONT},
  112. {".BMP", EResType::IMAGE},
  113. {".JPG", EResType::IMAGE},
  114. {".PCX", EResType::IMAGE},
  115. {".PNG", EResType::IMAGE},
  116. {".TGA", EResType::IMAGE},
  117. {".WAV", EResType::SOUND},
  118. {".82M", EResType::SOUND},
  119. {".SMK", EResType::VIDEO},
  120. {".BIK", EResType::VIDEO},
  121. {".MJPG", EResType::VIDEO},
  122. {".MPG", EResType::VIDEO},
  123. {".AVI", EResType::VIDEO},
  124. {".MP3", EResType::MUSIC},
  125. {".OGG", EResType::MUSIC},
  126. {".FLAC", EResType::MUSIC},
  127. {".ZIP", EResType::ARCHIVE_ZIP},
  128. {".LOD", EResType::ARCHIVE_LOD},
  129. {".PAC", EResType::ARCHIVE_LOD},
  130. {".VID", EResType::ARCHIVE_VID},
  131. {".SND", EResType::ARCHIVE_SND},
  132. {".PAL", EResType::PALETTE},
  133. {".VCGM1", EResType::CLIENT_SAVEGAME},
  134. {".VSGM1", EResType::SERVER_SAVEGAME},
  135. {".ERM", EResType::ERM},
  136. {".ERT", EResType::ERT},
  137. {".ERS", EResType::ERS},
  138. {".VMAP", EResType::MAP}
  139. };
  140. auto iter = stringToRes.find(extension);
  141. if (iter == stringToRes.end())
  142. return EResType::OTHER;
  143. return iter->second;
  144. }
  145. std::string EResTypeHelper::getEResTypeAsString(EResType::Type type)
  146. {
  147. #define MAP_ENUM(value) {EResType::value, #value},
  148. static const std::map<EResType::Type, std::string> stringToRes =
  149. {
  150. MAP_ENUM(TEXT)
  151. MAP_ENUM(ANIMATION)
  152. MAP_ENUM(MASK)
  153. MAP_ENUM(CAMPAIGN)
  154. MAP_ENUM(MAP)
  155. MAP_ENUM(BMP_FONT)
  156. MAP_ENUM(TTF_FONT)
  157. MAP_ENUM(IMAGE)
  158. MAP_ENUM(VIDEO)
  159. MAP_ENUM(SOUND)
  160. MAP_ENUM(MUSIC)
  161. MAP_ENUM(ARCHIVE_ZIP)
  162. MAP_ENUM(ARCHIVE_LOD)
  163. MAP_ENUM(ARCHIVE_SND)
  164. MAP_ENUM(ARCHIVE_VID)
  165. MAP_ENUM(PALETTE)
  166. MAP_ENUM(CLIENT_SAVEGAME)
  167. MAP_ENUM(SERVER_SAVEGAME)
  168. MAP_ENUM(DIRECTORY)
  169. MAP_ENUM(ERM)
  170. MAP_ENUM(ERT)
  171. MAP_ENUM(ERS)
  172. MAP_ENUM(OTHER)
  173. };
  174. #undef MAP_ENUM
  175. auto iter = stringToRes.find(type);
  176. assert(iter != stringToRes.end());
  177. return iter->second;
  178. }