Node.cpp 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637
  1. //
  2. // Urho3D Engine
  3. // Copyright (c) 2008-2011 Lasse Öörni
  4. //
  5. // Permission is hereby granted, free of charge, to any person obtaining a copy
  6. // of this software and associated documentation files (the "Software"), to deal
  7. // in the Software without restriction, including without limitation the rights
  8. // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  9. // copies of the Software, and to permit persons to whom the Software is
  10. // furnished to do so, subject to the following conditions:
  11. //
  12. // The above copyright notice and this permission notice shall be included in
  13. // all copies or substantial portions of the Software.
  14. //
  15. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  16. // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  17. // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  18. // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  19. // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  20. // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  21. // THE SOFTWARE.
  22. //
  23. #include "Precompiled.h"
  24. #include "Node.h"
  25. #include "ReplicationUtils.h"
  26. #include "Scene.h"
  27. #include "StringUtils.h"
  28. #include "DebugNew.h"
  29. // Normalize rotation quaternion after this many incremental updates to prevent distortion
  30. static const unsigned NORMALIZE_ROTATION_EVERY = 32;
  31. Node::Node(const std::string& name) :
  32. Component(name),
  33. mParent(0),
  34. mInterpolationFlags(INTERP_NONE),
  35. mNodeFlags(NODE_NODE),
  36. mDirty(false),
  37. mWorldTransformDirty(false),
  38. mPosition(Vector3::sZero),
  39. mRotation(Quaternion::sIdentity),
  40. mScale(Vector3::sUnity),
  41. mWorldPosition(Vector3::sZero),
  42. mWorldRotation(Quaternion::sIdentity),
  43. mWorldScale(Vector3::sUnity),
  44. mWorldTransform(Matrix4x3::sIdentity),
  45. mRotateCount(0)
  46. {
  47. }
  48. Node::Node(unsigned flags, const std::string& name) :
  49. Component(name),
  50. mParent(0),
  51. mNodeFlags(flags),
  52. mDirty(true),
  53. mWorldTransformDirty(true),
  54. mPosition(Vector3::sZero),
  55. mRotation(Quaternion::sIdentity),
  56. mScale(Vector3::sUnity),
  57. mRotateCount(0),
  58. mInterpolationFlags(0)
  59. {
  60. }
  61. Node::~Node()
  62. {
  63. // Remove all children, and set world transform if they are refcounted elsewhere
  64. while (mChildren.size())
  65. {
  66. std::vector<SharedPtr<Node> >::iterator i = mChildren.end() - 1;
  67. if (i->getRefCount() > 1)
  68. removeChild(i, true);
  69. else
  70. removeChild(i, false);
  71. }
  72. }
  73. void Node::save(Serializer& dest)
  74. {
  75. // Write Component properties
  76. Component::save(dest);
  77. // Write transform (interpolation transform & flags for network proxies)
  78. if (!isProxy())
  79. {
  80. dest.writeVector3(mPosition);
  81. dest.writeQuaternion(mRotation);
  82. dest.writeVector3(mScale);
  83. }
  84. else
  85. {
  86. dest.writeVector3(mInterpolationPosition);
  87. dest.writeQuaternion(mInterpolationRotation);
  88. dest.writeVector3(mInterpolationScale);
  89. dest.writeUByte(mInterpolationFlags);
  90. }
  91. // Write parent node reference
  92. ComponentRef parentRef(mParent);
  93. parentRef.write(dest);
  94. }
  95. void Node::load(Deserializer& source, ResourceCache* cache)
  96. {
  97. // Read Component properties
  98. Component::load(source, cache);
  99. // Read transform (interpolation transform & flags for network proxies)
  100. if (!isProxy())
  101. {
  102. mPosition = source.readVector3();
  103. mRotation = source.readQuaternion();
  104. mScale = source.readVector3();
  105. }
  106. else
  107. {
  108. mInterpolationPosition = source.readVector3();
  109. mInterpolationRotation = source.readQuaternion();
  110. mInterpolationScale = source.readVector3();
  111. mInterpolationFlags = source.readUByte();
  112. }
  113. // Read parent node reference
  114. mParentRef.read(source);
  115. markDirty();
  116. }
  117. void Node::saveXML(XMLElement& dest)
  118. {
  119. // Write Component properties
  120. Component::saveXML(dest);
  121. // Write transform
  122. XMLElement transformElem = dest.createChildElement("transform");
  123. transformElem.setVector3("pos", mPosition);
  124. transformElem.setVector3("rot", mRotation.getEulerAngles());
  125. transformElem.setVector3("scale", mScale);
  126. // Write parent node reference
  127. ComponentRef parentRef(mParent, true);
  128. XMLElement parentElem = dest.createChildElement("parent");
  129. parentRef.writeXML(parentElem);
  130. }
  131. void Node::loadXML(const XMLElement& source, ResourceCache* cache)
  132. {
  133. // Read Component properties
  134. Component::loadXML(source, cache);
  135. // Read transform
  136. XMLElement transformElem = source.getChildElement("transform");
  137. mPosition = transformElem.getVector3("pos");
  138. mRotation = transformElem.getQuaternion("rot");
  139. mScale = transformElem.getVector3("scale");
  140. // Read parent node reference
  141. if (source.hasChildElement("parent"))
  142. {
  143. XMLElement parentElem = source.getChildElement("parent");
  144. mParentRef.readXML(parentElem);
  145. }
  146. else
  147. mParentRef = ComponentRef();
  148. markDirty();
  149. }
  150. void Node::postLoad(ResourceCache* cache)
  151. {
  152. if (mParentRef.mDirty)
  153. {
  154. Node* parent = static_cast<Node*>(mEntity->getScene()->getComponent(mParentRef));
  155. if (parent)
  156. parent->addChild(this);
  157. mParentRef.mDirty = false;
  158. }
  159. }
  160. bool Node::writeNetUpdate(Serializer& dest, Serializer& destRevision, Deserializer& baseRevision, const NetUpdateInfo& info)
  161. {
  162. // Use possibly modified transform in case the parent component is not to be replicated
  163. Vector3 position;
  164. Quaternion rotation;
  165. Vector3 scale;
  166. ComponentRef parentRef;
  167. getNetTransform(position, rotation, scale, parentRef, info);
  168. // Build bitmask of changed properties
  169. unsigned char bits = 0;
  170. checkVector3(position, Vector3::sZero, baseRevision, bits, 1);
  171. checkQuaternion(rotation, Quaternion::sIdentity, baseRevision, bits, 2);
  172. checkVector3(scale, Vector3::sUnity, baseRevision, bits, 4);
  173. checkComponentRef(parentRef, ComponentRef(), baseRevision, bits, 8);
  174. // Update replication state fully, and network stream by delta
  175. dest.writeUByte(bits);
  176. writeVector3Delta(position, dest, destRevision, bits & 1);
  177. writePackedQuaternionDelta(rotation, dest, destRevision, bits & 2);
  178. writeVector3Delta(scale, dest, destRevision, bits & 4);
  179. writeComponentRefDelta(parentRef, dest, destRevision, bits & 8);
  180. return bits != 0;
  181. }
  182. void Node::readNetUpdate(Deserializer& source, ResourceCache* cache, const NetUpdateInfo& info)
  183. {
  184. unsigned char bits = source.readUByte();
  185. // Interpolate if just position/rotation/scale changes, snap if parent changes
  186. bool interpolate = (bits & 7) && (!(bits & 8));
  187. if (!interpolate)
  188. {
  189. if (bits & 1)
  190. setPosition(source.readVector3());
  191. if (bits & 2)
  192. setRotation(source.readPackedQuaternion());
  193. if (bits & 4)
  194. setScale(source.readVector3());
  195. }
  196. else
  197. {
  198. if (bits & 1)
  199. {
  200. mInterpolationPosition = source.readVector3();
  201. mInterpolationFlags |= INTERP_POS;
  202. }
  203. if (bits & 2)
  204. {
  205. mInterpolationRotation = source.readPackedQuaternion();
  206. mInterpolationFlags |= INTERP_ROT;
  207. }
  208. if (bits & 4)
  209. {
  210. mInterpolationScale = source.readVector3();
  211. mInterpolationFlags |= INTERP_SCALE;
  212. }
  213. }
  214. readComponentRefDelta(mParentRef, source, bits & 8);
  215. if (bits & 7)
  216. markDirty();
  217. }
  218. void Node::postNetUpdate(ResourceCache* cache)
  219. {
  220. // This is the same as in file deserialization: update parent if the ref is dirty
  221. postLoad(cache);
  222. }
  223. void Node::interpolate(bool snapToEnd)
  224. {
  225. if (!mInterpolationFlags)
  226. return;
  227. if (!snapToEnd)
  228. {
  229. Scene* scene = mEntity->getScene();
  230. float t = scene->getInterpolationLerpFactor();
  231. if (mInterpolationFlags & INTERP_POS)
  232. {
  233. // If position snaps, snap everything to the end
  234. float delta = (mPosition - mInterpolationPosition).getLengthSquared();
  235. if (delta > scene->getInterpolationSnapThresholdSquared())
  236. t = 1.0f;
  237. if (delta < M_EPSILON)
  238. {
  239. mPosition = mInterpolationPosition;
  240. mInterpolationFlags &= ~INTERP_POS;
  241. }
  242. else
  243. mPosition = mPosition.lerp(mInterpolationPosition, t);
  244. }
  245. if (mInterpolationFlags & INTERP_ROT)
  246. {
  247. float delta = (mRotation - mInterpolationRotation).getLengthSquared();
  248. if (delta < M_EPSILON)
  249. {
  250. mRotation = mInterpolationRotation;
  251. mInterpolationFlags &= ~INTERP_ROT;
  252. }
  253. else
  254. mRotation = mRotation.slerp(mInterpolationRotation, t);
  255. }
  256. if (mInterpolationFlags & INTERP_SCALE)
  257. {
  258. float delta = (mScale - mInterpolationScale).getLengthSquared();
  259. if (delta < M_EPSILON)
  260. {
  261. mScale = mInterpolationScale;
  262. mInterpolationFlags &= ~INTERP_SCALE;
  263. }
  264. else
  265. mScale = mScale.lerp(mInterpolationScale, t);
  266. }
  267. }
  268. else
  269. {
  270. if (mInterpolationFlags & INTERP_POS)
  271. mPosition = mInterpolationPosition;
  272. if (mInterpolationFlags & INTERP_ROT)
  273. mRotation = mInterpolationRotation;
  274. if (mInterpolationFlags & INTERP_SCALE)
  275. mScale = mInterpolationScale;
  276. mInterpolationFlags = INTERP_NONE;
  277. }
  278. markDirty();
  279. }
  280. void Node::getComponentRefs(std::vector<ComponentRef>& dest)
  281. {
  282. if (mParent)
  283. dest.push_back(ComponentRef(mParent));
  284. }
  285. void Node::setPosition(const Vector3& position)
  286. {
  287. mPosition = position;
  288. mInterpolationFlags &= ~INTERP_POS;
  289. if (!mDirty)
  290. markDirty();
  291. }
  292. void Node::setRotation(const Quaternion& rotation)
  293. {
  294. mRotation = rotation;
  295. mRotateCount = 0;
  296. mInterpolationFlags &= ~INTERP_ROT;
  297. if (!mDirty)
  298. markDirty();
  299. }
  300. void Node::setDirection(const Vector3& direction)
  301. {
  302. setRotation(Quaternion(Vector3::sForward, direction));
  303. }
  304. void Node::setScale(float scale)
  305. {
  306. mScale = Vector3(scale, scale, scale);
  307. mInterpolationFlags &= ~INTERP_SCALE;
  308. if (!mDirty)
  309. markDirty();
  310. }
  311. void Node::setScale(const Vector3& scale)
  312. {
  313. mScale = scale;
  314. mInterpolationFlags &= ~INTERP_SCALE;
  315. if (!mDirty)
  316. markDirty();
  317. }
  318. void Node::setTransform(const Vector3& position, const Quaternion& rotation)
  319. {
  320. mPosition = position;
  321. mRotation = rotation;
  322. mRotateCount = 0;
  323. mInterpolationFlags &= ~(INTERP_POS | INTERP_ROT);
  324. if (!mDirty)
  325. markDirty();
  326. }
  327. void Node::setTransform(const Vector3& position, const Quaternion& rotation, float scale)
  328. {
  329. mPosition = position;
  330. mRotation = rotation;
  331. mScale = Vector3(scale, scale, scale);
  332. mRotateCount = 0;
  333. mInterpolationFlags &= ~(INTERP_POS | INTERP_ROT | INTERP_SCALE);
  334. if (!mDirty)
  335. markDirty();
  336. }
  337. void Node::setTransform(const Vector3& position, const Quaternion& rotation, const Vector3& scale)
  338. {
  339. mPosition = position;
  340. mRotation = rotation;
  341. mScale = scale;
  342. mRotateCount = 0;
  343. mInterpolationFlags &= ~(INTERP_POS | INTERP_ROT | INTERP_SCALE);
  344. if (!mDirty)
  345. markDirty();
  346. }
  347. void Node::translate(const Vector3& delta)
  348. {
  349. mPosition += delta;
  350. mInterpolationFlags &= ~INTERP_POS;
  351. if (!mDirty)
  352. markDirty();
  353. }
  354. void Node::translateRelative(const Vector3& delta)
  355. {
  356. mPosition += mRotation * delta;
  357. mInterpolationFlags &= ~INTERP_POS;
  358. if (!mDirty)
  359. markDirty();
  360. }
  361. void Node::rotate(const Quaternion& delta, bool fixedAxis)
  362. {
  363. if (!fixedAxis)
  364. mRotation = mRotation * delta;
  365. else
  366. mRotation = delta * mRotation;
  367. mRotateCount++;
  368. if (mRotateCount >= NORMALIZE_ROTATION_EVERY)
  369. {
  370. mRotation.normalize();
  371. mRotateCount = 0;
  372. }
  373. mInterpolationFlags &= ~INTERP_ROT;
  374. if (!mDirty)
  375. markDirty();
  376. }
  377. void Node::yaw(float angle, bool fixedAxis)
  378. {
  379. rotate(Quaternion(angle, Vector3::sUp), fixedAxis);
  380. }
  381. void Node::pitch(float angle, bool fixedAxis)
  382. {
  383. rotate(Quaternion(angle, Vector3::sRight), fixedAxis);
  384. }
  385. void Node::roll(float angle, bool fixedAxis)
  386. {
  387. rotate(Quaternion(angle, Vector3::sForward), fixedAxis);
  388. }
  389. void Node::scale(float scale)
  390. {
  391. mScale *= scale;
  392. mInterpolationFlags &= ~INTERP_SCALE;
  393. if (!mDirty)
  394. markDirty();
  395. }
  396. void Node::scale(const Vector3& scale)
  397. {
  398. mScale *= scale;
  399. mInterpolationFlags &= ~INTERP_SCALE;
  400. if (!mDirty)
  401. markDirty();
  402. }
  403. void Node::addChild(Node* node)
  404. {
  405. if ((!node) || (node == this) || (node->mParent == this) || (mParent == node))
  406. return;
  407. // Add first, then remove from old parent, to ensure the node does not get deleted
  408. mChildren.push_back(SharedPtr<Node>(node));
  409. if (node->mParent)
  410. node->mParent->removeChild(node);
  411. node->mParent = this;
  412. node->markDirty();
  413. }
  414. void Node::removeChild(Node* node, bool setWorldTransform)
  415. {
  416. for (std::vector<SharedPtr<Node> >::iterator i = mChildren.begin(); i != mChildren.end(); ++i)
  417. {
  418. if ((*i) == node)
  419. {
  420. removeChild(i, setWorldTransform);
  421. return;
  422. }
  423. }
  424. }
  425. void Node::removeAllChildren(bool setWorldPosition)
  426. {
  427. while (mChildren.size())
  428. removeChild(mChildren.end() - 1, setWorldPosition);
  429. }
  430. std::vector<Node*> Node::getChildren(unsigned nodeFlags, bool recursive) const
  431. {
  432. if (!recursive)
  433. {
  434. std::vector<Node*> children;
  435. for (std::vector<SharedPtr<Node> >::const_iterator i = mChildren.begin(); i != mChildren.end(); ++i)
  436. {
  437. if ((*i)->mNodeFlags & nodeFlags)
  438. children.push_back(*i);
  439. }
  440. return children;
  441. }
  442. else
  443. {
  444. std::vector<Node*> allChildren;
  445. getChildrenRecursive(nodeFlags, allChildren);
  446. return allChildren;
  447. }
  448. }
  449. unsigned Node::getNumChildren(bool recursive) const
  450. {
  451. if (!recursive)
  452. return mChildren.size();
  453. else
  454. {
  455. unsigned allChildren = mChildren.size();
  456. for (std::vector<SharedPtr<Node> >::const_iterator i = mChildren.begin(); i != mChildren.end(); ++i)
  457. allChildren += (*i)->getNumChildren(true);
  458. return allChildren;
  459. }
  460. }
  461. Node* Node::getChild(unsigned index) const
  462. {
  463. return index < mChildren.size() ? mChildren[index] : (Node*)0;
  464. }
  465. Node* Node::getChild(const std::string& name, bool recursive) const
  466. {
  467. return getChild(StringHash(name), recursive);
  468. }
  469. Node* Node::getChild(StringHash nameHash, bool recursive) const
  470. {
  471. for (std::vector<SharedPtr<Node> >::const_iterator i = mChildren.begin(); i != mChildren.end(); ++i)
  472. {
  473. if ((*i)->getNameHash() == nameHash)
  474. return *i;
  475. if (recursive)
  476. {
  477. Node* node = (*i)->getChild(nameHash, true);
  478. if (node)
  479. return node;
  480. }
  481. }
  482. return 0;
  483. }
  484. void Node::markDirty()
  485. {
  486. mDirty = true;
  487. onMarkedDirty();
  488. for (std::vector<SharedPtr<Node> >::iterator i = mChildren.begin(); i != mChildren.end(); ++i)
  489. (*i)->markDirty();
  490. }
  491. void Node::getNetTransform(Vector3& position, Quaternion& rotation, Vector3& scale, ComponentRef& parentRef, const NetUpdateInfo& info)
  492. {
  493. // Use the parent node only if it will be synced
  494. bool useParent = (!mParent) || (mParent->checkSync(info.mConnection));
  495. if (useParent)
  496. {
  497. position = mPosition;
  498. rotation = mRotation;
  499. scale = mScale;
  500. parentRef = ComponentRef(mParent);
  501. }
  502. else
  503. {
  504. position = getWorldPosition();
  505. rotation = getWorldRotation();
  506. scale = getWorldScale();
  507. parentRef = ComponentRef();
  508. }
  509. }
  510. void Node::updateWorldPosition()
  511. {
  512. if (mParent)
  513. {
  514. const Quaternion& parentRotation = mParent->getWorldRotation();
  515. const Vector3& parentScale = mParent->getWorldScale();
  516. mWorldPosition = mParent->getWorldPosition() + (parentRotation * (parentScale * mPosition));
  517. mWorldRotation = parentRotation * mRotation;
  518. mWorldScale = parentScale * mScale;
  519. }
  520. else
  521. {
  522. mWorldPosition = mPosition;
  523. mWorldRotation = mRotation;
  524. mWorldScale = mScale;
  525. }
  526. mDirty = false;
  527. mWorldTransformDirty = true;
  528. }
  529. void Node::removeChild(std::vector<SharedPtr<Node> >::iterator i, bool setWorldTransform)
  530. {
  531. Node* node = (*i);
  532. if (setWorldTransform)
  533. node->setTransform(node->getWorldPosition(), node->getWorldRotation(), node->getWorldScale());
  534. node->mParent = 0;
  535. node->markDirty();
  536. mChildren.erase(i);
  537. }
  538. void Node::getChildrenRecursive(unsigned nodeFlags, std::vector<Node*>& dest) const
  539. {
  540. for (std::vector<SharedPtr<Node> >::const_iterator i = mChildren.begin(); i != mChildren.end(); ++i)
  541. {
  542. if ((*i)->mNodeFlags & nodeFlags)
  543. dest.push_back(*i);
  544. (*i)->getChildrenRecursive(nodeFlags, dest);
  545. }
  546. }