SceneNode.cpp 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155
  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. #include <AnKi/Scene/SceneNode.h>
  6. #include <AnKi/Scene/SceneGraph.h>
  7. #include <AnKi/Scene/Components/SceneComponent.h>
  8. #include <AnKi/Scene/Components/MoveComponent.h>
  9. #include <AnKi/Scene/Components/BodyComponent.h>
  10. #include <AnKi/Scene/Components/CameraComponent.h>
  11. #include <AnKi/Scene/Components/DecalComponent.h>
  12. #include <AnKi/Scene/Components/FogDensityComponent.h>
  13. #include <AnKi/Scene/Components/GlobalIlluminationProbeComponent.h>
  14. #include <AnKi/Scene/Components/JointComponent.h>
  15. #include <AnKi/Scene/Components/LensFlareComponent.h>
  16. #include <AnKi/Scene/Components/LightComponent.h>
  17. #include <AnKi/Scene/Components/ModelComponent.h>
  18. #include <AnKi/Scene/Components/MoveComponent.h>
  19. #include <AnKi/Scene/Components/ParticleEmitterComponent.h>
  20. #include <AnKi/Scene/Components/PlayerControllerComponent.h>
  21. #include <AnKi/Scene/Components/ReflectionProbeComponent.h>
  22. #include <AnKi/Scene/Components/ScriptComponent.h>
  23. #include <AnKi/Scene/Components/SkinComponent.h>
  24. #include <AnKi/Scene/Components/SkyboxComponent.h>
  25. #include <AnKi/Scene/Components/TriggerComponent.h>
  26. #include <AnKi/Scene/Components/UiComponent.h>
  27. namespace anki {
  28. // Specialize newComponent(). Do that first
  29. #define ANKI_DEFINE_SCENE_COMPONENT(name, weight) \
  30. template<> \
  31. name##Component* SceneNode::newComponent<name##Component>() \
  32. { \
  33. auto it = SceneGraph::getSingleton().getComponentArrays().get##name##s().emplace(this); \
  34. it->setArrayIndex(it.getArrayIndex()); \
  35. newComponentInternal(&(*it)); \
  36. return &(*it); \
  37. }
  38. #include <AnKi/Scene/Components/SceneComponentClasses.def.h>
  39. SceneNode::SceneNode(CString name)
  40. : m_uuid(SceneGraph::getSingleton().getNewUuid())
  41. {
  42. if(name)
  43. {
  44. m_name = name;
  45. }
  46. // Add the implicit MoveComponent
  47. newComponent<MoveComponent>();
  48. }
  49. SceneNode::~SceneNode()
  50. {
  51. for(SceneComponent* comp : m_components)
  52. {
  53. comp->onDestroy(*this);
  54. switch(comp->getType())
  55. {
  56. #define ANKI_DEFINE_SCENE_COMPONENT(name, weight) \
  57. case SceneComponentType::k##name: \
  58. SceneGraph::getSingleton().getComponentArrays().get##name##s().erase(comp->getArrayIndex()); \
  59. break;
  60. #include <AnKi/Scene/Components/SceneComponentClasses.def.h>
  61. default:
  62. ANKI_ASSERT(0);
  63. }
  64. }
  65. }
  66. void SceneNode::markForDeletion()
  67. {
  68. visitThisAndChildren([](SceneNode& obj) {
  69. obj.m_markedForDeletion = true;
  70. return true;
  71. });
  72. }
  73. void SceneNode::newComponentInternal(SceneComponent* newc)
  74. {
  75. m_componentTypeMask |= 1 << SceneComponentTypeMask(newc->getType());
  76. // Inform all other components that some component was added
  77. for(SceneComponent* other : m_components)
  78. {
  79. other->onOtherComponentRemovedOrAdded(newc, true);
  80. }
  81. // Inform the current component about others
  82. for(SceneComponent* other : m_components)
  83. {
  84. newc->onOtherComponentRemovedOrAdded(other, true);
  85. }
  86. m_components.emplaceBack(newc);
  87. // Sort based on update weight
  88. std::sort(m_components.getBegin(), m_components.getEnd(), [](const SceneComponent* a, const SceneComponent* b) {
  89. const F32 weightA = SceneComponent::getUpdateOrderWeight(a->getType());
  90. const F32 weightB = SceneComponent::getUpdateOrderWeight(b->getType());
  91. if(weightA != weightB)
  92. {
  93. return weightA < weightB;
  94. }
  95. else
  96. {
  97. return a->getType() < b->getType();
  98. }
  99. });
  100. }
  101. Bool SceneNode::updateTransform()
  102. {
  103. const Bool needsUpdate = m_localTransformDirty;
  104. m_localTransformDirty = false;
  105. const Bool updatedLastFrame = m_transformUpdatedThisFrame;
  106. m_transformUpdatedThisFrame = needsUpdate;
  107. if(needsUpdate || updatedLastFrame)
  108. {
  109. m_prevWTrf = m_wtrf;
  110. }
  111. // Update world transform
  112. if(needsUpdate)
  113. {
  114. const SceneNode* parent = getParent();
  115. if(parent == nullptr || m_ignoreParentNodeTransform)
  116. {
  117. m_wtrf = m_ltrf;
  118. }
  119. else
  120. {
  121. m_wtrf = parent->getWorldTransform().combineTransformations(m_ltrf);
  122. }
  123. // Make children dirty as well. Don't walk the whole tree because you will re-walk it later
  124. visitChildrenMaxDepth(1, [](SceneNode& childNode) {
  125. if(!childNode.m_ignoreParentNodeTransform)
  126. {
  127. childNode.m_localTransformDirty = true;
  128. }
  129. return true;
  130. });
  131. }
  132. return needsUpdate;
  133. }
  134. } // end namespace anki