BodyComponent.h 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160
  1. // Copyright (C) 2009-present, Panagiotis Christopoulos Charitos and contributors.
  2. // All rights reserved.
  3. // Code licensed under the BSD License.
  4. // http://www.anki3d.org/LICENSE
  5. #pragma once
  6. #include <AnKi/Scene/Components/SceneComponent.h>
  7. #include <AnKi/Physics/PhysicsBody.h>
  8. #include <AnKi/Resource/Forward.h>
  9. namespace anki {
  10. enum class BodyComponentCollisionShapeType : U8
  11. {
  12. kFromMeshComponent, // Set the collision shape by looking at the MeshComponent's mesh.
  13. kAabb,
  14. kSphere,
  15. kCount,
  16. kFirst = 0
  17. };
  18. ANKI_ENUM_ALLOW_NUMERIC_OPERATIONS(BodyComponentCollisionShapeType)
  19. inline constexpr Array<const Char*, U32(BodyComponentCollisionShapeType::kCount)> kBodyComponentCollisionShapeTypeNames = {"Mesh Component", "AABB",
  20. "Sphere"};
  21. // Rigid body component.
  22. class BodyComponent : public SceneComponent
  23. {
  24. ANKI_SCENE_COMPONENT(BodyComponent)
  25. public:
  26. BodyComponent(SceneNode* node);
  27. ~BodyComponent();
  28. void setCollisionShapeType(BodyComponentCollisionShapeType type)
  29. {
  30. if(ANKI_EXPECT(type <= BodyComponentCollisionShapeType::kCount) && m_shapeType != type)
  31. {
  32. m_shapeType = type;
  33. cleanup(); // Force recreate
  34. }
  35. }
  36. BodyComponentCollisionShapeType getCollisionShapeType() const
  37. {
  38. return m_shapeType;
  39. }
  40. void setBoxExtend(Vec3 extend)
  41. {
  42. if(ANKI_EXPECT(extend > 0.01f) && extend != m_box.m_extend)
  43. {
  44. m_box.m_extend = extend;
  45. if(m_shapeType == BodyComponentCollisionShapeType::kAabb)
  46. {
  47. cleanup(); // Force recreate
  48. }
  49. }
  50. }
  51. const Vec3& getBoxExtend() const
  52. {
  53. return m_box.m_extend;
  54. }
  55. void setSphereRadius(F32 radius)
  56. {
  57. if(ANKI_EXPECT(radius > 0.01f) && radius != m_sphere.m_radius)
  58. {
  59. m_sphere.m_radius = radius;
  60. if(m_shapeType == BodyComponentCollisionShapeType::kSphere)
  61. {
  62. cleanup(); // Force recreate
  63. }
  64. }
  65. }
  66. F32 getSphereRadius() const
  67. {
  68. return m_sphere.m_radius;
  69. }
  70. void setMass(F32 mass)
  71. {
  72. if(ANKI_EXPECT(mass >= 0.0f) && m_mass != mass)
  73. {
  74. m_mass = mass;
  75. cleanup(); // Force recreate
  76. }
  77. }
  78. F32 getMass() const
  79. {
  80. return m_mass;
  81. }
  82. const PhysicsBodyPtr& getPhysicsBody() const
  83. {
  84. return m_body;
  85. }
  86. void applyForce(Vec3 force, Vec3 relativePosition)
  87. {
  88. m_force = force;
  89. m_forcePosition = relativePosition;
  90. }
  91. SceneNode& getSceneNode()
  92. {
  93. return *m_node;
  94. }
  95. Bool isValid() const;
  96. private:
  97. SceneNode* m_node = nullptr;
  98. PhysicsBodyPtr m_body;
  99. Vec3 m_creationScale = Vec3(0.0f); // Track the scale the body was created with
  100. PhysicsCollisionShapePtr m_collisionShape;
  101. class
  102. {
  103. public:
  104. MeshComponent* m_meshc = nullptr;
  105. U32 m_meshResourceUuid = 0;
  106. } m_mesh;
  107. class
  108. {
  109. public:
  110. Vec3 m_extend = Vec3(1.0f);
  111. } m_box;
  112. class
  113. {
  114. public:
  115. F32 m_radius = 1.0f;
  116. } m_sphere;
  117. F32 m_mass = 0.0f;
  118. Vec3 m_force = Vec3(0.0f);
  119. Vec3 m_forcePosition = Vec3(0.0f);
  120. U32 m_transformVersion = 0;
  121. BodyComponentCollisionShapeType m_shapeType = BodyComponentCollisionShapeType::kAabb;
  122. void update(SceneComponentUpdateInfo& info, Bool& updated) override;
  123. void onOtherComponentRemovedOrAdded(SceneComponent* other, Bool added) override;
  124. void cleanup();
  125. };
  126. } // end namespace anki