SceneGraph.cpp 8.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381
  1. #include "anki/scene/SceneGraph.h"
  2. #include "anki/scene/Camera.h"
  3. #include "anki/scene/ModelNode.h"
  4. #include "anki/util/Exception.h"
  5. #include "anki/core/ThreadPool.h"
  6. #include "anki/core/Counters.h"
  7. #include "anki/renderer/Renderer.h"
  8. #include "anki/misc/Xml.h"
  9. namespace anki {
  10. //==============================================================================
  11. // Misc =
  12. //==============================================================================
  13. //==============================================================================
  14. struct UpdateMovablesJob: ThreadJob
  15. {
  16. SceneGraph* scene = nullptr;
  17. U32 movablesCount;
  18. void operator()(U threadId, U threadsCount)
  19. {
  20. U64 start, end;
  21. ANKI_ASSERT(scene);
  22. choseStartEnd(
  23. threadId, threadsCount, scene->getSceneNodesCount(), start, end);
  24. scene->iterateSceneNodes(start, end, [](SceneNode& sn)
  25. {
  26. Movable* m = sn.getMovable();
  27. if(m)
  28. {
  29. m->update();
  30. }
  31. });
  32. }
  33. };
  34. //==============================================================================
  35. static void updateSceneNode(SceneNode& sn, F32 prevUpdateTime,
  36. F32 crntTime, SectorGroup& sectorGroup)
  37. {
  38. sn.frameUpdate(prevUpdateTime, crntTime, getGlobTimestamp());
  39. // Do some spatial stuff
  40. Spatial* sp = sn.getSpatial();
  41. if(sp)
  42. {
  43. if(sp->getSpatialTimestamp() >= getGlobTimestamp())
  44. {
  45. sp->update();
  46. //sectorGroup.placeSceneNode(&sn);
  47. }
  48. sp->resetFrame();
  49. }
  50. // Do some frustumable stuff
  51. Frustumable* fr = sn.getFrustumable();
  52. if(fr)
  53. {
  54. fr->resetFrame();
  55. }
  56. // Do some renderable stuff
  57. Renderable* r = sn.getRenderable();
  58. if(r)
  59. {
  60. r->resetFrame();
  61. }
  62. }
  63. //==============================================================================
  64. struct UpdateSceneNodesJob: ThreadJob
  65. {
  66. SceneGraph* scene = nullptr;
  67. F32 prevUpdateTime;
  68. F32 crntTime;
  69. SectorGroup* sectorGroup;
  70. void operator()(U threadId, U threadsCount)
  71. {
  72. ANKI_ASSERT(scene);
  73. U64 start, end;
  74. choseStartEnd(
  75. threadId, threadsCount, scene->getSceneNodesCount(), start, end);
  76. scene->iterateSceneNodes(start, end, [&](SceneNode& sn)
  77. {
  78. updateSceneNode(sn, prevUpdateTime, crntTime, *sectorGroup);
  79. });
  80. }
  81. };
  82. //==============================================================================
  83. // Scene =
  84. //==============================================================================
  85. //==============================================================================
  86. SceneGraph::SceneGraph()
  87. : alloc(ANKI_SCENE_ALLOCATOR_SIZE),
  88. frameAlloc(ANKI_SCENE_FRAME_ALLOCATOR_SIZE),
  89. nodes(alloc),
  90. dict(10, DictionaryHasher(), DictionaryEqual(), alloc),
  91. sectorGroup(this),
  92. events(this)
  93. {
  94. nodes.reserve(ANKI_SCENE_OPTIMAL_SCENE_NODES_COUNT);
  95. ambientCol = Vec3(0.0);
  96. }
  97. //==============================================================================
  98. SceneGraph::~SceneGraph()
  99. {}
  100. //==============================================================================
  101. void SceneGraph::registerNode(SceneNode* node)
  102. {
  103. ANKI_ASSERT(node);
  104. // Add to dict if it has name
  105. if(node->getName())
  106. {
  107. if(dict.find(node->getName()) != dict.end())
  108. {
  109. throw ANKI_EXCEPTION("Node with the same name already exists: "
  110. + node->getName());
  111. }
  112. dict[node->getName()] = node;
  113. }
  114. // Add to vector
  115. ANKI_ASSERT(std::find(nodes.begin(), nodes.end(), node) == nodes.end());
  116. nodes.push_back(node);
  117. }
  118. //==============================================================================
  119. void SceneGraph::unregisterNode(SceneNode* node)
  120. {
  121. // Remove from vector
  122. auto it = nodes.begin();
  123. for(; it != nodes.end(); it++)
  124. {
  125. if((*it) == node)
  126. {
  127. break;
  128. }
  129. }
  130. ANKI_ASSERT(it != nodes.end());
  131. nodes.erase(it);
  132. // Remove from dict
  133. if(node->getName())
  134. {
  135. auto it = dict.find(node->getName());
  136. ANKI_ASSERT(it != dict.end());
  137. dict.erase(it);
  138. }
  139. }
  140. //==============================================================================
  141. SceneNode& SceneGraph::findSceneNode(const char* name)
  142. {
  143. ANKI_ASSERT(dict.find(name) != dict.end());
  144. return *(dict.find(name))->second;
  145. }
  146. //==============================================================================
  147. SceneNode* SceneGraph::tryFindSceneNode(const char* name)
  148. {
  149. auto it = dict.find(name);
  150. return (it == dict.end()) ? nullptr : it->second;
  151. }
  152. //==============================================================================
  153. void SceneGraph::deleteNodesMarkedForDeletion()
  154. {
  155. /// Delete all nodes pending deletion. At this point all scene threads
  156. /// should have finished their tasks
  157. while(nodesMarkedForDeletionCount > 0)
  158. {
  159. // First gather the nodes that will be de
  160. SceneFrameVector<decltype(nodes)::iterator> forDeletion;
  161. for(auto it = nodes.begin(); it != nodes.end(); it++)
  162. {
  163. if((*it)->isMarkedForDeletion())
  164. {
  165. forDeletion.push_back(it);
  166. }
  167. }
  168. // Now delete
  169. for(auto& it : forDeletion)
  170. {
  171. // Disable events for that node
  172. events.iterateEvents([&](Event& e)
  173. {
  174. if(e.getSceneNode() == *it)
  175. {
  176. e.markForDeletion();
  177. }
  178. });
  179. // Remove it
  180. unregisterNode(*it);
  181. SceneAllocator<SceneNode> al = alloc;
  182. alloc.destroy(*it);
  183. alloc.deallocate(*it, 1);
  184. ++nodesMarkedForDeletionCount;
  185. }
  186. }
  187. }
  188. //==============================================================================
  189. void SceneGraph::update(F32 prevUpdateTime, F32 crntTime, Renderer& renderer)
  190. {
  191. ANKI_ASSERT(mainCam);
  192. ANKI_COUNTER_START_TIMER(C_SCENE_UPDATE_TIME);
  193. //
  194. // Sync point. Here we wait for all scene's threads
  195. //
  196. // XXX
  197. //
  198. // Reset the frame mem pool
  199. //
  200. frameAlloc.reset();
  201. deleteNodesMarkedForDeletion();
  202. ThreadPool& threadPool = ThreadPoolSingleton::get();
  203. (void)threadPool;
  204. // XXX Do that in parallel
  205. physics.update(prevUpdateTime, crntTime);
  206. renderer.getTiler().updateTiles(*mainCam);
  207. events.updateAllEvents(prevUpdateTime, crntTime);
  208. #if 0
  209. // First do the movable updates
  210. for(SceneNode* n : nodes)
  211. {
  212. Movable* m = n->getMovable();
  213. if(m)
  214. {
  215. m->update();
  216. }
  217. }
  218. #else
  219. UpdateMovablesJob jobs[ThreadPool::MAX_THREADS];
  220. for(U i = 0; i < threadPool.getThreadsCount(); i++)
  221. {
  222. jobs[i].scene = this;
  223. threadPool.assignNewJob(i, &jobs[i]);
  224. }
  225. threadPool.waitForAllJobsToFinish();
  226. #endif
  227. // Then the rest
  228. #if 0
  229. for(SceneNode* n : nodes)
  230. {
  231. updateSceneNode(*n, prevUpdateTime, crntTime, sectorGroup);
  232. }
  233. #else
  234. Array<UpdateSceneNodesJob, ThreadPool::MAX_THREADS> jobs2;
  235. for(U i = 0; i < threadPool.getThreadsCount(); i++)
  236. {
  237. UpdateSceneNodesJob& job = jobs2[i];
  238. job.scene = this;
  239. job.prevUpdateTime = prevUpdateTime;
  240. job.crntTime = crntTime;
  241. job.sectorGroup = &sectorGroup;
  242. threadPool.assignNewJob(i, &job);
  243. }
  244. threadPool.waitForAllJobsToFinish();
  245. #endif
  246. doVisibilityTests(*mainCam, *this, renderer);
  247. /*sectorGroup.doVisibilityTests(*mainCam,
  248. VisibilityTest(VT_RENDERABLES | VT_LIGHTS), &r);*/
  249. ANKI_COUNTER_STOP_TIMER_INC(C_SCENE_UPDATE_TIME);
  250. }
  251. //==============================================================================
  252. void SceneGraph::load(const char* filename)
  253. {
  254. try
  255. {
  256. XmlDocument doc;
  257. doc.loadFile(ANKI_R(filename));
  258. XmlElement rootEl = doc.getChildElement("scene");
  259. // Model nodes
  260. //
  261. XmlElement mdlNodeEl = rootEl.getChildElement("modelNode");
  262. do
  263. {
  264. XmlElement el, el1;
  265. // <name>
  266. el = mdlNodeEl.getChildElement("name");
  267. std::string name = el.getText();
  268. // <model>
  269. el = mdlNodeEl.getChildElement("model");
  270. // <instancesCount>
  271. el1 = mdlNodeEl.getChildElementOptional("instancesCount");
  272. U32 instancesCount = (el1) ? el1.getInt() : 1;
  273. if(instancesCount > ANKI_MAX_INSTANCES)
  274. {
  275. throw ANKI_EXCEPTION("Too many instances");
  276. }
  277. ModelNode* node;
  278. newSceneNode(node, name.c_str(), nullptr,
  279. Movable::MF_NONE, el.getText(), instancesCount);
  280. // <transform>
  281. el = mdlNodeEl.getChildElement("transform");
  282. U i = 0;
  283. do
  284. {
  285. if(i == 0)
  286. {
  287. node->setLocalTransform(Transform(el.getMat4()));
  288. node->setInstanceLocalTransform(
  289. i, Transform(el.getMat4()));
  290. }
  291. else
  292. {
  293. node->setInstanceLocalTransform(i, Transform(el.getMat4()));
  294. }
  295. // Advance
  296. el = el.getNextSiblingElement("transform");
  297. ++i;
  298. }
  299. while(el && i < instancesCount);
  300. if(i != instancesCount)
  301. {
  302. throw ANKI_EXCEPTION("instancesCount does not match "
  303. "with transform");
  304. }
  305. // Advance
  306. mdlNodeEl = mdlNodeEl.getNextSiblingElement("modelNode");
  307. } while(mdlNodeEl);
  308. }
  309. catch(const std::exception& e)
  310. {
  311. throw ANKI_EXCEPTION("Scene loading failed") << e;
  312. }
  313. }
  314. } // end namespace anki