Model.h 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205
  1. #ifndef ANKI_RESOURCE_MODEL_H
  2. #define ANKI_RESOURCE_MODEL_H
  3. #include "anki/resource/Resource.h"
  4. #include "anki/gl/Vao.h"
  5. #include "anki/collision/Obb.h"
  6. #include "anki/resource/PassLodKey.h"
  7. #include "anki/resource/Mesh.h"
  8. #include "anki/resource/Material.h"
  9. #include "anki/resource/Skeleton.h"
  10. #include "anki/resource/Animation.h"
  11. #include "anki/util/Vector.h"
  12. namespace anki {
  13. /// Model patch interface class. Its very important class and it binds the
  14. /// material with the mesh
  15. class ModelPatchBase
  16. {
  17. public:
  18. /// VAOs container
  19. typedef Vector<Vao> VaosContainer;
  20. virtual ~ModelPatchBase()
  21. {}
  22. const Material& getMaterial() const
  23. {
  24. ANKI_ASSERT(modelPatchProtected.mtl);
  25. return *modelPatchProtected.mtl;
  26. }
  27. const Mesh& getMesh(const PassLodKey& key) const
  28. {
  29. ANKI_ASSERT(key.level < modelPatchProtected.meshes.size());
  30. return *modelPatchProtected.meshes[key.level];
  31. }
  32. U32 getMeshesCount() const
  33. {
  34. return modelPatchProtected.meshes.size();
  35. }
  36. const Obb& getBoundingShape() const
  37. {
  38. PassLodKey key(COLOR_PASS, 0);
  39. return getMesh(key).getBoundingShape();
  40. }
  41. const Obb& getBoundingShapeSub(U32 subMeshId) const
  42. {
  43. PassLodKey key(COLOR_PASS, 0);
  44. return getMesh(key).getBoundingShapeSub(subMeshId);
  45. }
  46. U32 getSubMeshesCount() const
  47. {
  48. PassLodKey key(COLOR_PASS, 0);
  49. return getMesh(key).getSubMeshesCount();
  50. }
  51. /// Given a pass lod key retrieve variables useful for rendering
  52. void getRenderingData(const PassLodKey& key, const Vao*& vao,
  53. const ShaderProgram*& prog, U32& indicesCount) const;
  54. /// Get information for multiDraw rendering.
  55. /// Given an array of submeshes that are visible return the correct indices
  56. /// offsets and counts
  57. void getRenderingDataSub(
  58. const PassLodKey& key,
  59. const Vao*& vao,
  60. const ShaderProgram*& prog,
  61. const U32* subMeshIndicesArray, U subMeshIndicesCount,
  62. Array<U32, ANKI_MAX_MULTIDRAW_PRIMITIVES>& indicesCountArray,
  63. Array<const void*, ANKI_MAX_MULTIDRAW_PRIMITIVES>& indicesOffsetArray,
  64. U32& drawcallCount) const;
  65. protected:
  66. struct
  67. {
  68. /// Array [lod][pass]
  69. VaosContainer vaos;
  70. Material* mtl = nullptr;
  71. Vector<Mesh*> meshes;
  72. } modelPatchProtected;
  73. /// Create VAOs using a material and a mesh. It writes a VaosContainer and
  74. /// a hash map
  75. void create();
  76. private:
  77. /// Called by @a createVaos multiple times to create and populate a single
  78. /// VAO
  79. static void createVao(
  80. const ShaderProgram &prog,
  81. const Mesh& mesh,
  82. Vao& vao);
  83. };
  84. /// Its a chunk of a model. Its very important class and it binds the material
  85. /// with the mesh
  86. template<typename MeshResourcePointerType>
  87. class ModelPatch: public ModelPatchBase
  88. {
  89. public:
  90. ModelPatch(const char* meshFNames[], U32 meshesCount,
  91. const char* mtlFName)
  92. {
  93. // Load
  94. ANKI_ASSERT(meshesCount > 0);
  95. meshes.resize(meshesCount);
  96. modelPatchProtected.meshes.resize(meshesCount);
  97. for(U32 i = 0; i < meshesCount; i++)
  98. {
  99. meshes[i].load(meshFNames[i]);
  100. modelPatchProtected.meshes[i] = meshes[i].get();
  101. if(i > 0 && !meshes[i]->isCompatible(*meshes[i - 1]))
  102. {
  103. throw ANKI_EXCEPTION("Meshes not compatible");
  104. }
  105. }
  106. mtl.load(mtlFName);
  107. modelPatchProtected.mtl = mtl.get();
  108. /// Create VAOs
  109. create();
  110. }
  111. ~ModelPatch()
  112. {}
  113. private:
  114. Vector<MeshResourcePointerType> meshes; ///< The geometries
  115. MaterialResourcePointer mtl; ///< Material
  116. };
  117. /// Model is an entity that acts as a container for other resources. Models are
  118. /// all the non static objects in a map.
  119. ///
  120. /// XML file format:
  121. /// @code
  122. /// <model>
  123. /// <modelPatches>
  124. /// <modelPatch>
  125. /// [<mesh>path/to/mesh.mesh</mesh>
  126. /// [<mesh1>path/to/mesh_lod_1.mesh</mesh1>]
  127. /// [<mesh2>path/to/mesh_lod_2.mesh</mesh2>]] |
  128. /// [<bucketMesh>path/to/mesh.bmesh</bucketMesh>
  129. /// [<bucketMesh1>path/to/mesh_lod_1.bmesh</bucketMesh1>]
  130. /// [<bucketMesh2>path/to/mesh_lod_2.bmesh</bucketMesh2>]]
  131. /// <material>path/to/material.mtl</material>
  132. /// </modelPatch>
  133. /// ...
  134. /// <modelPatch>...</modelPatch>
  135. /// </modelPatches>
  136. /// [<skeleton>path/to/skeleton.skel</skeleton>]
  137. /// [<skeletonAnimations>
  138. /// <animation>path/to/animation.anim</animation>
  139. /// ...
  140. /// </skeletonAnimations>]
  141. /// </model>
  142. /// @endcode
  143. ///
  144. /// Requirements:
  145. /// - If the materials need texture coords then mesh should have them
  146. /// - The skeleton and skelAnims are optional
  147. /// - Its an error to have skelAnims without skeleton
  148. class Model
  149. {
  150. public:
  151. typedef Vector<ModelPatchBase*> ModelPatchesContainer;
  152. Model()
  153. {}
  154. ~Model();
  155. /// @name Accessors
  156. /// @{
  157. const ModelPatchesContainer& getModelPatches() const
  158. {
  159. return modelPatches;
  160. }
  161. const Obb& getVisibilityShape() const
  162. {
  163. return visibilityShape;
  164. }
  165. /// @}
  166. void load(const char* filename);
  167. private:
  168. /// The vector of ModelPatch
  169. ModelPatchesContainer modelPatches;
  170. Obb visibilityShape;
  171. SkeletonResourcePointer skeleton;
  172. Vector<AnimationResourcePointer> animations;
  173. };
  174. } // end namespace anki
  175. #endif