vertex.cpp 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491
  1. /**
  2. * Copyright (c) 2006-2023 LOVE Development Team
  3. *
  4. * This software is provided 'as-is', without any express or implied
  5. * warranty. In no event will the authors be held liable for any damages
  6. * arising from the use of this software.
  7. *
  8. * Permission is granted to anyone to use this software for any purpose,
  9. * including commercial applications, and to alter it and redistribute it
  10. * freely, subject to the following restrictions:
  11. *
  12. * 1. The origin of this software must not be misrepresented; you must not
  13. * claim that you wrote the original software. If you use this software
  14. * in a product, an acknowledgment in the product documentation would be
  15. * appreciated but is not required.
  16. * 2. Altered source versions must be plainly marked as such, and must not be
  17. * misrepresented as being the original software.
  18. * 3. This notice may not be removed or altered from any source distribution.
  19. **/
  20. #include "vertex.h"
  21. #include "common/StringMap.h"
  22. namespace love
  23. {
  24. namespace graphics
  25. {
  26. static_assert(sizeof(Color32) == 4, "sizeof(Color32) incorrect!");
  27. static_assert(sizeof(STf_RGBAub) == sizeof(float)*2 + sizeof(Color32), "sizeof(STf_RGBAub) incorrect!");
  28. static_assert(sizeof(STPf_RGBAub) == sizeof(float)*3 + sizeof(Color32), "sizeof(STPf_RGBAub) incorrect!");
  29. static_assert(sizeof(XYf_STf) == sizeof(float)*2 + sizeof(float)*2, "sizeof(XYf_STf) incorrect!");
  30. static_assert(sizeof(XYf_STPf) == sizeof(float)*2 + sizeof(float)*3, "sizeof(XYf_STPf) incorrect!");
  31. static_assert(sizeof(XYf_STf_RGBAub) == sizeof(float)*2 + sizeof(float)*2 + sizeof(Color32), "sizeof(XYf_STf_RGBAub) incorrect!");
  32. static_assert(sizeof(XYf_STus_RGBAub) == sizeof(float)*2 + sizeof(uint16)*2 + sizeof(Color32), "sizeof(XYf_STus_RGBAub) incorrect!");
  33. static_assert(sizeof(XYf_STPf_RGBAub) == sizeof(float)*2 + sizeof(float)*3 + sizeof(Color32), "sizeof(XYf_STPf_RGBAub) incorrect!");
  34. size_t getFormatStride(CommonFormat format)
  35. {
  36. switch (format)
  37. {
  38. case CommonFormat::NONE: return 0;
  39. case CommonFormat::XYf: return sizeof(float) * 2;
  40. case CommonFormat::XYZf: return sizeof(float) * 3;
  41. case CommonFormat::RGBAub: return sizeof(uint8) * 4;
  42. case CommonFormat::STf_RGBAub: return sizeof(STf_RGBAub);
  43. case CommonFormat::STPf_RGBAub: return sizeof(STPf_RGBAub);
  44. case CommonFormat::XYf_STf: return sizeof(XYf_STf);
  45. case CommonFormat::XYf_STPf: return sizeof(XYf_STPf);
  46. case CommonFormat::XYf_STf_RGBAub: return sizeof(XYf_STf_RGBAub);
  47. case CommonFormat::XYf_STus_RGBAub: return sizeof(XYf_STus_RGBAub);
  48. case CommonFormat::XYf_STPf_RGBAub: return sizeof(XYf_STPf_RGBAub);
  49. }
  50. return 0;
  51. }
  52. uint32 getFormatFlags(CommonFormat format)
  53. {
  54. switch (format)
  55. {
  56. case CommonFormat::NONE:
  57. return 0;
  58. case CommonFormat::XYf:
  59. case CommonFormat::XYZf:
  60. return ATTRIBFLAG_POS;
  61. case CommonFormat::RGBAub:
  62. return ATTRIBFLAG_COLOR;
  63. case CommonFormat::STf_RGBAub:
  64. case CommonFormat::STPf_RGBAub:
  65. return ATTRIBFLAG_TEXCOORD | ATTRIBFLAG_COLOR;
  66. case CommonFormat::XYf_STf:
  67. case CommonFormat::XYf_STPf:
  68. return ATTRIBFLAG_POS | ATTRIBFLAG_TEXCOORD;
  69. case CommonFormat::XYf_STf_RGBAub:
  70. case CommonFormat::XYf_STus_RGBAub:
  71. case CommonFormat::XYf_STPf_RGBAub:
  72. return ATTRIBFLAG_POS | ATTRIBFLAG_TEXCOORD | ATTRIBFLAG_COLOR;
  73. }
  74. return 0;
  75. }
  76. int getFormatPositionComponents(CommonFormat format)
  77. {
  78. switch (format)
  79. {
  80. case CommonFormat::NONE:
  81. case CommonFormat::RGBAub:
  82. case CommonFormat::STf_RGBAub:
  83. case CommonFormat::STPf_RGBAub:
  84. return 0;
  85. case CommonFormat::XYf:
  86. case CommonFormat::XYf_STf:
  87. case CommonFormat::XYf_STPf:
  88. case CommonFormat::XYf_STf_RGBAub:
  89. case CommonFormat::XYf_STus_RGBAub:
  90. case CommonFormat::XYf_STPf_RGBAub:
  91. return 2;
  92. case CommonFormat::XYZf:
  93. return 3;
  94. }
  95. return 0;
  96. }
  97. // Order here relies on order of DataFormat enum.
  98. static const DataFormatInfo dataFormatInfo[]
  99. {
  100. // baseType, isMatrix, components, rows, columns, componentSize, size
  101. { DATA_BASETYPE_FLOAT, false, 1, 0, 0, 4, 4 }, // DATAFORMAT_FLOAT
  102. { DATA_BASETYPE_FLOAT, false, 2, 0, 0, 4, 8 }, // DATAFORMAT_FLOAT_VEC2
  103. { DATA_BASETYPE_FLOAT, false, 3, 0, 0, 4, 12 }, // DATAFORMAT_FLOAT_VEC3
  104. { DATA_BASETYPE_FLOAT, false, 4, 0, 0, 4, 16 }, // DATAFORMAT_FLOAT_VEC4
  105. { DATA_BASETYPE_FLOAT, true, 0, 2, 2, 4, 16 }, // DATAFORMAT_FLOAT_MAT2X2
  106. { DATA_BASETYPE_FLOAT, true, 0, 2, 3, 4, 24 }, // DATAFORMAT_FLOAT_MAT2X3
  107. { DATA_BASETYPE_FLOAT, true, 0, 2, 4, 4, 32 }, // DATAFORMAT_FLOAT_MAT2X4
  108. { DATA_BASETYPE_FLOAT, true, 0, 3, 2, 4, 24 }, // DATAFORMAT_FLOAT_MAT3X2
  109. { DATA_BASETYPE_FLOAT, true, 0, 3, 3, 4, 36 }, // DATAFORMAT_FLOAT_MAT3X3
  110. { DATA_BASETYPE_FLOAT, true, 0, 3, 4, 4, 48 }, // DATAFORMAT_FLOAT_MAT3X4
  111. { DATA_BASETYPE_FLOAT, true, 0, 4, 2, 4, 32 }, // DATAFORMAT_FLOAT_MAT4X2
  112. { DATA_BASETYPE_FLOAT, true, 0, 4, 3, 4, 48 }, // DATAFORMAT_FLOAT_MAT4X3
  113. { DATA_BASETYPE_FLOAT, true, 0, 4, 4, 4, 64 }, // DATAFORMAT_FLOAT_MAT4X4
  114. { DATA_BASETYPE_INT, false, 1, 0, 0, 4, 4 }, // DATAFORMAT_INT32
  115. { DATA_BASETYPE_INT, false, 2, 0, 0, 4, 8 }, // DATAFORMAT_INT32_VEC2
  116. { DATA_BASETYPE_INT, false, 3, 0, 0, 4, 12 }, // DATAFORMAT_INT32_VEC3
  117. { DATA_BASETYPE_INT, false, 4, 0, 0, 4, 16 }, // DATAFORMAT_INT32_VEC4
  118. { DATA_BASETYPE_UINT, false, 1, 0, 0, 4, 4 }, // DATAFORMAT_UINT32
  119. { DATA_BASETYPE_UINT, false, 2, 0, 0, 4, 8 }, // DATAFORMAT_UINT32_VEC2
  120. { DATA_BASETYPE_UINT, false, 3, 0, 0, 4, 12 }, // DATAFORMAT_UINT32_VEC3
  121. { DATA_BASETYPE_UINT, false, 4, 0, 0, 4, 16 }, // DATAFORMAT_UINT32_VEC4
  122. { DATA_BASETYPE_SNORM, false, 4, 0, 0, 1, 4 }, // DATAFORMAT_SNORM8_VEC4
  123. { DATA_BASETYPE_UNORM, false, 4, 0, 0, 1, 4 }, // DATAFORMAT_UNORM8_VEC4
  124. { DATA_BASETYPE_INT, false, 4, 0, 0, 1, 4 }, // DATAFORMAT_INT8_VEC4
  125. { DATA_BASETYPE_UINT, false, 4, 0, 0, 1, 4 }, // DATAFORMAT_UINT8_VEC4
  126. { DATA_BASETYPE_SNORM, false, 2, 0, 0, 2, 4 }, // DATAFORMAT_SNORM16_VEC2
  127. { DATA_BASETYPE_SNORM, false, 4, 0, 0, 2, 8 }, // DATAFORMAT_SNORM16_VEC4
  128. { DATA_BASETYPE_UNORM, false, 2, 0, 0, 2, 4 }, // DATAFORMAT_UNORM16_VEC2
  129. { DATA_BASETYPE_UNORM, false, 4, 0, 0, 2, 8 }, // DATAFORMAT_UNORM16_VEC4
  130. { DATA_BASETYPE_INT, false, 2, 0, 0, 2, 4 }, // DATAFORMAT_INT16_VEC2
  131. { DATA_BASETYPE_INT, false, 4, 0, 0, 2, 8 }, // DATAFORMAT_INT16_VEC4
  132. { DATA_BASETYPE_UINT, false, 1, 0, 0, 2, 2 }, // DATAFORMAT_UINT16
  133. { DATA_BASETYPE_UINT, false, 2, 0, 0, 2, 4 }, // DATAFORMAT_UINT16_VEC2
  134. { DATA_BASETYPE_UINT, false, 4, 0, 0, 2, 8 }, // DATAFORMAT_UINT16_VEC4
  135. { DATA_BASETYPE_BOOL, false, 1, 0, 0, 4, 4 }, // DATAFORMAT_BOOL
  136. { DATA_BASETYPE_BOOL, false, 2, 0, 0, 4, 8 }, // DATAFORMAT_BOOL_VEC2
  137. { DATA_BASETYPE_BOOL, false, 3, 0, 0, 4, 12 }, // DATAFORMAT_BOOL_VEC3
  138. { DATA_BASETYPE_BOOL, false, 4, 0, 0, 4, 16 }, // DATAFORMAT_BOOL_VEC4
  139. };
  140. static_assert((sizeof(dataFormatInfo) / sizeof(DataFormatInfo)) == DATAFORMAT_MAX_ENUM, "dataFormatInfo array size must match number of DataFormat enum values.");
  141. const DataFormatInfo &getDataFormatInfo(DataFormat format)
  142. {
  143. return dataFormatInfo[format];
  144. }
  145. size_t getIndexDataSize(IndexDataType type)
  146. {
  147. switch (type)
  148. {
  149. case INDEX_UINT16: return sizeof(uint16);
  150. case INDEX_UINT32: return sizeof(uint32);
  151. default: return 0;
  152. }
  153. }
  154. IndexDataType getIndexDataTypeFromMax(size_t maxvalue)
  155. {
  156. return maxvalue > LOVE_UINT16_MAX ? INDEX_UINT32 : INDEX_UINT16;
  157. }
  158. DataFormat getIndexDataFormat(IndexDataType type)
  159. {
  160. return type == INDEX_UINT32 ? DATAFORMAT_UINT32 : DATAFORMAT_UINT16;
  161. }
  162. IndexDataType getIndexDataType(DataFormat format)
  163. {
  164. switch (format)
  165. {
  166. case DATAFORMAT_UINT16: return INDEX_UINT16;
  167. case DATAFORMAT_UINT32: return INDEX_UINT32;
  168. default: return INDEX_MAX_ENUM;
  169. }
  170. }
  171. int getIndexCount(TriangleIndexMode mode, int vertexCount)
  172. {
  173. switch (mode)
  174. {
  175. case TRIANGLEINDEX_NONE:
  176. return 0;
  177. case TRIANGLEINDEX_STRIP:
  178. case TRIANGLEINDEX_FAN:
  179. return 3 * (vertexCount - 2);
  180. case TRIANGLEINDEX_QUADS:
  181. return vertexCount * 6 / 4;
  182. }
  183. return 0;
  184. }
  185. template <typename T>
  186. static void fillIndicesT(TriangleIndexMode mode, T vertexStart, T vertexCount, T *indices)
  187. {
  188. switch (mode)
  189. {
  190. case TRIANGLEINDEX_NONE:
  191. break;
  192. case TRIANGLEINDEX_STRIP:
  193. {
  194. int i = 0;
  195. for (T index = 0; index < vertexCount - 2; index++)
  196. {
  197. indices[i++] = vertexStart + index;
  198. indices[i++] = vertexStart + index + 1 + (index & 1);
  199. indices[i++] = vertexStart + index + 2 - (index & 1);
  200. }
  201. }
  202. break;
  203. case TRIANGLEINDEX_FAN:
  204. {
  205. int i = 0;
  206. for (T index = 2; index < vertexCount; index++)
  207. {
  208. indices[i++] = vertexStart;
  209. indices[i++] = vertexStart + index - 1;
  210. indices[i++] = vertexStart + index;
  211. }
  212. }
  213. break;
  214. case TRIANGLEINDEX_QUADS:
  215. {
  216. // 0---2
  217. // | / |
  218. // 1---3
  219. int count = vertexCount / 4;
  220. for (int i = 0; i < count; i++)
  221. {
  222. int ii = i * 6;
  223. T vi = T(vertexStart + i * 4);
  224. indices[ii + 0] = vi + 0;
  225. indices[ii + 1] = vi + 1;
  226. indices[ii + 2] = vi + 2;
  227. indices[ii + 3] = vi + 2;
  228. indices[ii + 4] = vi + 1;
  229. indices[ii + 5] = vi + 3;
  230. }
  231. }
  232. break;
  233. }
  234. }
  235. void fillIndices(TriangleIndexMode mode, uint16 vertexStart, uint16 vertexCount, uint16 *indices)
  236. {
  237. fillIndicesT(mode, vertexStart, vertexCount, indices);
  238. }
  239. void fillIndices(TriangleIndexMode mode, uint32 vertexStart, uint32 vertexCount, uint32 *indices)
  240. {
  241. fillIndicesT(mode, vertexStart, vertexCount, indices);
  242. }
  243. void VertexAttributes::setCommonFormat(CommonFormat format, uint8 bufferindex)
  244. {
  245. setBufferLayout(bufferindex, (uint16) getFormatStride(format));
  246. switch (format)
  247. {
  248. case CommonFormat::NONE:
  249. break;
  250. case CommonFormat::XYf:
  251. set(ATTRIB_POS, DATAFORMAT_FLOAT_VEC2, 0, bufferindex);
  252. break;
  253. case CommonFormat::XYZf:
  254. set(ATTRIB_POS, DATAFORMAT_FLOAT_VEC3, 0, bufferindex);
  255. break;
  256. case CommonFormat::RGBAub:
  257. set(ATTRIB_COLOR, DATAFORMAT_UNORM8_VEC4, 0, bufferindex);
  258. break;
  259. case CommonFormat::STf_RGBAub:
  260. set(ATTRIB_TEXCOORD, DATAFORMAT_FLOAT_VEC2, 0, bufferindex);
  261. set(ATTRIB_COLOR, DATAFORMAT_UNORM8_VEC4, uint16(sizeof(float) * 2), bufferindex);
  262. break;
  263. case CommonFormat::STPf_RGBAub:
  264. set(ATTRIB_TEXCOORD, DATAFORMAT_FLOAT_VEC3, 0, bufferindex);
  265. set(ATTRIB_COLOR, DATAFORMAT_UNORM8_VEC4, uint16(sizeof(float) * 3), bufferindex);
  266. break;
  267. case CommonFormat::XYf_STf:
  268. set(ATTRIB_POS, DATAFORMAT_FLOAT_VEC2, 0, bufferindex);
  269. set(ATTRIB_TEXCOORD, DATAFORMAT_FLOAT_VEC2, uint16(sizeof(float) * 2), bufferindex);
  270. break;
  271. case CommonFormat::XYf_STPf:
  272. set(ATTRIB_POS, DATAFORMAT_FLOAT_VEC2, 0, bufferindex);
  273. set(ATTRIB_TEXCOORD, DATAFORMAT_FLOAT_VEC3, uint16(sizeof(float) * 2), bufferindex);
  274. break;
  275. case CommonFormat::XYf_STf_RGBAub:
  276. set(ATTRIB_POS, DATAFORMAT_FLOAT_VEC2, 0, bufferindex);
  277. set(ATTRIB_TEXCOORD, DATAFORMAT_FLOAT_VEC2, uint16(sizeof(float) * 2), bufferindex);
  278. set(ATTRIB_COLOR, DATAFORMAT_UNORM8_VEC4, uint16(sizeof(float) * 4), bufferindex);
  279. break;
  280. case CommonFormat::XYf_STus_RGBAub:
  281. set(ATTRIB_POS, DATAFORMAT_FLOAT_VEC2, 0, bufferindex);
  282. set(ATTRIB_TEXCOORD, DATAFORMAT_UNORM16_VEC2, uint16(sizeof(float) * 2), bufferindex);
  283. set(ATTRIB_COLOR, DATAFORMAT_UNORM8_VEC4, uint16(sizeof(float) * 2 + sizeof(uint16) * 2), bufferindex);
  284. break;
  285. case CommonFormat::XYf_STPf_RGBAub:
  286. set(ATTRIB_POS, DATAFORMAT_FLOAT_VEC2, 0, bufferindex);
  287. set(ATTRIB_TEXCOORD, DATAFORMAT_FLOAT_VEC3, uint16(sizeof(float) * 2), bufferindex);
  288. set(ATTRIB_COLOR, DATAFORMAT_UNORM8_VEC4, uint16(sizeof(float) * 5), bufferindex);
  289. break;
  290. }
  291. }
  292. bool VertexAttributes::operator == (const VertexAttributes &other) const
  293. {
  294. if (enableBits != other.enableBits || instanceBits != other.instanceBits)
  295. return false;
  296. uint32 allbits = enableBits;
  297. uint32 i = 0;
  298. while (allbits)
  299. {
  300. if (isEnabled(i))
  301. {
  302. const auto &a = attribs[i];
  303. const auto &b = other.attribs[i];
  304. if (a.bufferIndex != b.bufferIndex || a.format != b.format || a.offsetFromVertex != b.offsetFromVertex)
  305. return false;
  306. if (bufferLayouts[a.bufferIndex].stride != other.bufferLayouts[a.bufferIndex].stride)
  307. return false;
  308. }
  309. i++;
  310. allbits >>= 1;
  311. }
  312. return true;
  313. }
  314. STRINGMAP_BEGIN(BuiltinVertexAttribute, ATTRIB_MAX_ENUM, attribName)
  315. {
  316. { "VertexPosition", ATTRIB_POS },
  317. { "VertexTexCoord", ATTRIB_TEXCOORD },
  318. { "VertexColor", ATTRIB_COLOR },
  319. }
  320. STRINGMAP_END(BuiltinVertexAttribute, ATTRIB_MAX_ENUM, attribName)
  321. const char *getConstant(BuiltinVertexAttribute attrib)
  322. {
  323. const char *name = nullptr;
  324. getConstant(attrib, name);
  325. return name;
  326. }
  327. STRINGMAP_BEGIN(BufferUsage, BUFFERUSAGE_MAX_ENUM, bufferUsageName)
  328. {
  329. { "vertex", BUFFERUSAGE_VERTEX },
  330. { "index", BUFFERUSAGE_INDEX },
  331. { "texel", BUFFERUSAGE_TEXEL },
  332. { "shaderstorage", BUFFERUSAGE_SHADER_STORAGE },
  333. { "indirectarguments", BUFFERUSAGE_INDIRECT_ARGUMENTS },
  334. }
  335. STRINGMAP_END(BufferUsage, BUFFERUSAGE_MAX_ENUM, bufferUsageName)
  336. STRINGMAP_BEGIN(IndexDataType, INDEX_MAX_ENUM, indexType)
  337. {
  338. { "uint16", INDEX_UINT16 },
  339. { "uint32", INDEX_UINT32 },
  340. }
  341. STRINGMAP_END(IndexDataType, INDEX_MAX_ENUM, indexType)
  342. STRINGMAP_BEGIN(BufferDataUsage, BUFFERDATAUSAGE_MAX_ENUM, bufferDataUsage)
  343. {
  344. { "stream", BUFFERDATAUSAGE_STREAM },
  345. { "dynamic", BUFFERDATAUSAGE_DYNAMIC },
  346. { "static", BUFFERDATAUSAGE_STATIC },
  347. { "readback", BUFFERDATAUSAGE_READBACK },
  348. }
  349. STRINGMAP_END(BufferDataUsage, BUFFERDATAUSAGE_MAX_ENUM, bufferDataUsage)
  350. STRINGMAP_BEGIN(PrimitiveType, PRIMITIVE_MAX_ENUM, primitiveType)
  351. {
  352. { "fan", PRIMITIVE_TRIANGLE_FAN },
  353. { "strip", PRIMITIVE_TRIANGLE_STRIP },
  354. { "triangles", PRIMITIVE_TRIANGLES },
  355. { "points", PRIMITIVE_POINTS },
  356. }
  357. STRINGMAP_END(PrimitiveType, PRIMITIVE_MAX_ENUM, primitiveType)
  358. STRINGMAP_BEGIN(AttributeStep, STEP_MAX_ENUM, attributeStep)
  359. {
  360. { "pervertex", STEP_PER_VERTEX },
  361. { "perinstance", STEP_PER_INSTANCE },
  362. }
  363. STRINGMAP_END(AttributeStep, STEP_MAX_ENUM, attributeStep)
  364. STRINGMAP_BEGIN(DataFormat, DATAFORMAT_MAX_ENUM, dataFormat)
  365. {
  366. { "float", DATAFORMAT_FLOAT },
  367. { "floatvec2", DATAFORMAT_FLOAT_VEC2 },
  368. { "floatvec3", DATAFORMAT_FLOAT_VEC3 },
  369. { "floatvec4", DATAFORMAT_FLOAT_VEC4 },
  370. { "floatmat2x2", DATAFORMAT_FLOAT_MAT2X2 },
  371. { "floatmat2x3", DATAFORMAT_FLOAT_MAT2X3 },
  372. { "floatmat2x4", DATAFORMAT_FLOAT_MAT2X4 },
  373. { "floatmat3x2", DATAFORMAT_FLOAT_MAT3X2 },
  374. { "floatmat3x3", DATAFORMAT_FLOAT_MAT3X3 },
  375. { "floatmat3x4", DATAFORMAT_FLOAT_MAT3X4 },
  376. { "floatmat4x2", DATAFORMAT_FLOAT_MAT4X2 },
  377. { "floatmat4x3", DATAFORMAT_FLOAT_MAT4X3 },
  378. { "floatmat4x4", DATAFORMAT_FLOAT_MAT4X4 },
  379. { "int32", DATAFORMAT_INT32 },
  380. { "int32vec2", DATAFORMAT_INT32_VEC2 },
  381. { "int32vec3", DATAFORMAT_INT32_VEC3 },
  382. { "int32vec4", DATAFORMAT_INT32_VEC4 },
  383. { "uint32", DATAFORMAT_UINT32 },
  384. { "uint32vec2", DATAFORMAT_UINT32_VEC2 },
  385. { "uint32vec3", DATAFORMAT_UINT32_VEC3 },
  386. { "uint32vec4", DATAFORMAT_UINT32_VEC4 },
  387. { "snorm8vec4", DATAFORMAT_SNORM8_VEC4 },
  388. { "unorm8vec4", DATAFORMAT_UNORM8_VEC4 },
  389. { "int8vec4", DATAFORMAT_INT8_VEC4 },
  390. { "uint8vec4", DATAFORMAT_UINT8_VEC4 },
  391. { "snorm16vec2", DATAFORMAT_SNORM16_VEC2 },
  392. { "snorm16vec4", DATAFORMAT_SNORM16_VEC4 },
  393. { "unorm16vec2", DATAFORMAT_UNORM16_VEC2 },
  394. { "unorm16vec4", DATAFORMAT_UNORM16_VEC4 },
  395. { "int16vec2", DATAFORMAT_INT16_VEC2 },
  396. { "int16vec4", DATAFORMAT_INT16_VEC4 },
  397. { "uint16", DATAFORMAT_UINT16 },
  398. { "uint16vec2", DATAFORMAT_UINT16_VEC2 },
  399. { "uint16vec4", DATAFORMAT_UINT16_VEC4 },
  400. { "bool", DATAFORMAT_BOOL },
  401. { "boolvec2", DATAFORMAT_BOOL_VEC2 },
  402. { "boolvec3", DATAFORMAT_BOOL_VEC3 },
  403. { "boolvec4", DATAFORMAT_BOOL_VEC4 },
  404. }
  405. STRINGMAP_END(DataFormat, DATAFORMAT_MAX_ENUM, dataFormat)
  406. STRINGMAP_BEGIN(DataBaseType, DATA_BASETYPE_MAX_ENUM, dataBaseType)
  407. {
  408. { "float", DATA_BASETYPE_FLOAT },
  409. { "int", DATA_BASETYPE_INT },
  410. { "uint", DATA_BASETYPE_UINT },
  411. { "snorm", DATA_BASETYPE_SNORM },
  412. { "unorm", DATA_BASETYPE_UNORM },
  413. { "bool", DATA_BASETYPE_BOOL },
  414. }
  415. STRINGMAP_END(DataBaseType, DATA_BASETYPE_MAX_ENUM, dataBaseType)
  416. STRINGMAP_BEGIN(CullMode, CULL_MAX_ENUM, cullMode)
  417. {
  418. { "none", CULL_NONE },
  419. { "back", CULL_BACK },
  420. { "front", CULL_FRONT },
  421. }
  422. STRINGMAP_END(CullMode, CULL_MAX_ENUM, cullMode)
  423. STRINGMAP_BEGIN(Winding, WINDING_MAX_ENUM, winding)
  424. {
  425. { "cw", WINDING_CW },
  426. { "ccw", WINDING_CCW },
  427. }
  428. STRINGMAP_END(Winding, WINDING_MAX_ENUM, winding)
  429. } // graphics
  430. } // love