PhysicsController.cpp 49 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375
  1. #include "Base.h"
  2. #include "PhysicsController.h"
  3. #include "PhysicsRigidBody.h"
  4. #include "PhysicsCharacter.h"
  5. #include "PhysicsMotionState.h"
  6. #include "Game.h"
  7. #include "MeshPart.h"
  8. #include "Bundle.h"
  9. #include "BulletCollision/CollisionShapes/btHeightfieldTerrainShape.h"
  10. // The initial capacity of the Bullet debug drawer's vertex batch.
  11. #define INITIAL_CAPACITY 280
  12. namespace gameplay
  13. {
  14. const int PhysicsController::DIRTY = 0x01;
  15. const int PhysicsController::COLLISION = 0x02;
  16. const int PhysicsController::REGISTERED = 0x04;
  17. const int PhysicsController::REMOVE = 0x08;
  18. PhysicsController::PhysicsController()
  19. : _collisionConfiguration(NULL), _dispatcher(NULL),
  20. _overlappingPairCache(NULL), _solver(NULL), _world(NULL), _ghostPairCallback(NULL),
  21. _debugDrawer(NULL), _status(PhysicsController::Listener::DEACTIVATED), _listeners(NULL),
  22. _gravity(btScalar(0.0), btScalar(-9.8), btScalar(0.0))
  23. {
  24. // Default gravity is 9.8 along the negative Y axis.
  25. }
  26. PhysicsController::~PhysicsController()
  27. {
  28. SAFE_DELETE(_ghostPairCallback);
  29. SAFE_DELETE(_debugDrawer);
  30. SAFE_DELETE(_listeners);
  31. }
  32. void PhysicsController::addStatusListener(Listener* listener)
  33. {
  34. GP_ASSERT(listener);
  35. if (!_listeners)
  36. _listeners = new std::vector<Listener*>();
  37. _listeners->push_back(listener);
  38. }
  39. void PhysicsController::removeStatusListener(Listener* listener)
  40. {
  41. GP_ASSERT(listener);
  42. if (!_listeners)
  43. return;
  44. for (std::vector<Listener*>::iterator iter = _listeners->begin(); iter != _listeners->end(); iter++)
  45. {
  46. if (*iter == listener)
  47. {
  48. _listeners->erase(iter);
  49. return;
  50. }
  51. }
  52. }
  53. PhysicsFixedConstraint* PhysicsController::createFixedConstraint(PhysicsRigidBody* a, PhysicsRigidBody* b)
  54. {
  55. checkConstraintRigidBodies(a, b);
  56. PhysicsFixedConstraint* constraint = new PhysicsFixedConstraint(a, b);
  57. addConstraint(a, b, constraint);
  58. return constraint;
  59. }
  60. PhysicsGenericConstraint* PhysicsController::createGenericConstraint(PhysicsRigidBody* a, PhysicsRigidBody* b)
  61. {
  62. checkConstraintRigidBodies(a, b);
  63. PhysicsGenericConstraint* constraint = new PhysicsGenericConstraint(a, b);
  64. addConstraint(a, b, constraint);
  65. return constraint;
  66. }
  67. PhysicsGenericConstraint* PhysicsController::createGenericConstraint(PhysicsRigidBody* a,
  68. const Quaternion& rotationOffsetA, const Vector3& translationOffsetA, PhysicsRigidBody* b,
  69. const Quaternion& rotationOffsetB, const Vector3& translationOffsetB)
  70. {
  71. checkConstraintRigidBodies(a, b);
  72. PhysicsGenericConstraint* constraint = new PhysicsGenericConstraint(a, rotationOffsetA, translationOffsetA, b, rotationOffsetB, translationOffsetB);
  73. addConstraint(a, b, constraint);
  74. return constraint;
  75. }
  76. PhysicsHingeConstraint* PhysicsController::createHingeConstraint(PhysicsRigidBody* a,
  77. const Quaternion& rotationOffsetA, const Vector3& translationOffsetA, PhysicsRigidBody* b,
  78. const Quaternion& rotationOffsetB, const Vector3& translationOffsetB)
  79. {
  80. checkConstraintRigidBodies(a, b);
  81. PhysicsHingeConstraint* constraint = new PhysicsHingeConstraint(a, rotationOffsetA, translationOffsetA, b, rotationOffsetB, translationOffsetB);
  82. addConstraint(a, b, constraint);
  83. return constraint;
  84. }
  85. PhysicsSocketConstraint* PhysicsController::createSocketConstraint(PhysicsRigidBody* a, PhysicsRigidBody* b)
  86. {
  87. checkConstraintRigidBodies(a, b);
  88. PhysicsSocketConstraint* constraint = new PhysicsSocketConstraint(a, b);
  89. addConstraint(a, b, constraint);
  90. return constraint;
  91. }
  92. PhysicsSocketConstraint* PhysicsController::createSocketConstraint(PhysicsRigidBody* a,
  93. const Vector3& translationOffsetA, PhysicsRigidBody* b, const Vector3& translationOffsetB)
  94. {
  95. checkConstraintRigidBodies(a, b);
  96. PhysicsSocketConstraint* constraint = new PhysicsSocketConstraint(a,translationOffsetA, b, translationOffsetB);
  97. addConstraint(a, b, constraint);
  98. return constraint;
  99. }
  100. PhysicsSpringConstraint* PhysicsController::createSpringConstraint(PhysicsRigidBody* a, PhysicsRigidBody* b)
  101. {
  102. checkConstraintRigidBodies(a, b);
  103. PhysicsSpringConstraint* constraint = new PhysicsSpringConstraint(a, b);
  104. addConstraint(a, b, constraint);
  105. return constraint;
  106. }
  107. PhysicsSpringConstraint* PhysicsController::createSpringConstraint(PhysicsRigidBody* a, const Quaternion& rotationOffsetA, const Vector3& translationOffsetA,
  108. PhysicsRigidBody* b, const Quaternion& rotationOffsetB, const Vector3& translationOffsetB)
  109. {
  110. checkConstraintRigidBodies(a, b);
  111. PhysicsSpringConstraint* constraint = new PhysicsSpringConstraint(a, rotationOffsetA, translationOffsetA, b, rotationOffsetB, translationOffsetB);
  112. addConstraint(a, b, constraint);
  113. return constraint;
  114. }
  115. const Vector3& PhysicsController::getGravity() const
  116. {
  117. return _gravity;
  118. }
  119. void PhysicsController::setGravity(const Vector3& gravity)
  120. {
  121. _gravity = gravity;
  122. if (_world)
  123. _world->setGravity(BV(_gravity));
  124. }
  125. void PhysicsController::drawDebug(const Matrix& viewProjection)
  126. {
  127. GP_ASSERT(_debugDrawer);
  128. GP_ASSERT(_world);
  129. _debugDrawer->begin(viewProjection);
  130. _world->debugDrawWorld();
  131. _debugDrawer->end();
  132. }
  133. bool PhysicsController::rayTest(const Ray& ray, float distance, PhysicsController::HitResult* result)
  134. {
  135. GP_ASSERT(_world);
  136. btCollisionWorld::ClosestRayResultCallback callback(BV(ray.getOrigin()), BV(distance * ray.getDirection()));
  137. _world->rayTest(BV(ray.getOrigin()), BV(distance * ray.getDirection()), callback);
  138. if (callback.hasHit())
  139. {
  140. if (result)
  141. {
  142. result->object = getCollisionObject(callback.m_collisionObject);
  143. result->point.set(callback.m_hitPointWorld.x(), callback.m_hitPointWorld.y(), callback.m_hitPointWorld.z());
  144. result->fraction = callback.m_closestHitFraction;
  145. result->normal.set(callback.m_hitNormalWorld.x(), callback.m_hitNormalWorld.y(), callback.m_hitNormalWorld.z());
  146. }
  147. return true;
  148. }
  149. return false;
  150. }
  151. bool PhysicsController::sweepTest(PhysicsCollisionObject* object, const Vector3& endPosition, PhysicsController::HitResult* result)
  152. {
  153. class SweepTestCallback : public btCollisionWorld::ClosestConvexResultCallback
  154. {
  155. public:
  156. SweepTestCallback(PhysicsCollisionObject* me)
  157. : btCollisionWorld::ClosestConvexResultCallback(btVector3(0.0, 0.0, 0.0), btVector3(0.0, 0.0, 0.0)), me(me)
  158. {
  159. }
  160. btScalar addSingleResult(btCollisionWorld::LocalConvexResult& convexResult, bool normalInWorldSpace)
  161. {
  162. GP_ASSERT(convexResult.m_hitCollisionObject);
  163. PhysicsCollisionObject* object = reinterpret_cast<PhysicsCollisionObject*>(convexResult.m_hitCollisionObject->getUserPointer());
  164. if (object == me)
  165. return 1.0f;
  166. return ClosestConvexResultCallback::addSingleResult(convexResult, normalInWorldSpace);
  167. }
  168. PhysicsCollisionObject* me;
  169. };
  170. GP_ASSERT(object && object->getCollisionShape());
  171. PhysicsCollisionShape* shape = object->getCollisionShape();
  172. PhysicsCollisionShape::Type type = shape->getType();
  173. if (type != PhysicsCollisionShape::SHAPE_BOX && type != PhysicsCollisionShape::SHAPE_SPHERE && type != PhysicsCollisionShape::SHAPE_CAPSULE)
  174. return false; // unsupported type
  175. // Define the start transform.
  176. btTransform start;
  177. start.setIdentity();
  178. if (object->getNode())
  179. {
  180. Vector3 translation;
  181. Quaternion rotation;
  182. const Matrix& m = object->getNode()->getWorldMatrix();
  183. m.getTranslation(&translation);
  184. m.getRotation(&rotation);
  185. start.setIdentity();
  186. start.setOrigin(BV(translation));
  187. start.setRotation(BQ(rotation));
  188. }
  189. // Define the end transform.
  190. btTransform end(start);
  191. end.setOrigin(BV(endPosition));
  192. // Perform bullet convex sweep test.
  193. SweepTestCallback callback(object);
  194. // If the object is represented by a ghost object, use the ghost object's convex sweep test
  195. // since it is much faster than the world's version.
  196. // NOTE: Unfortunately the ghost object sweep test does not seem reliable here currently, so using world's version instead.
  197. /*switch (object->getType())
  198. {
  199. case PhysicsCollisionObject::GHOST_OBJECT:
  200. case PhysicsCollisionObject::CHARACTER:
  201. static_cast<PhysicsGhostObject*>(object)->_ghostObject->convexSweepTest(static_cast<btConvexShape*>(shape->getShape()), start, end, callback, _world->getDispatchInfo().m_allowedCcdPenetration);
  202. break;
  203. default:
  204. _world->convexSweepTest(static_cast<btConvexShape*>(shape->getShape()), start, end, callback, _world->getDispatchInfo().m_allowedCcdPenetration);
  205. break;
  206. }*/
  207. GP_ASSERT(_world);
  208. _world->convexSweepTest(static_cast<btConvexShape*>(shape->getShape()), start, end, callback, _world->getDispatchInfo().m_allowedCcdPenetration);
  209. // Check for hits and store results.
  210. if (callback.hasHit())
  211. {
  212. if (result)
  213. {
  214. result->object = getCollisionObject(callback.m_hitCollisionObject);
  215. result->point.set(callback.m_hitPointWorld.x(), callback.m_hitPointWorld.y(), callback.m_hitPointWorld.z());
  216. result->fraction = callback.m_closestHitFraction;
  217. result->normal.set(callback.m_hitNormalWorld.x(), callback.m_hitNormalWorld.y(), callback.m_hitNormalWorld.z());
  218. }
  219. return true;
  220. }
  221. return false;
  222. }
  223. btScalar PhysicsController::addSingleResult(btManifoldPoint& cp, const btCollisionObject* a, int partIdA, int indexA,
  224. const btCollisionObject* b, int partIdB, int indexB)
  225. {
  226. GP_ASSERT(Game::getInstance()->getPhysicsController());
  227. // Get pointers to the PhysicsCollisionObject objects.
  228. PhysicsCollisionObject* objectA = Game::getInstance()->getPhysicsController()->getCollisionObject(a);
  229. PhysicsCollisionObject* objectB = Game::getInstance()->getPhysicsController()->getCollisionObject(b);
  230. // If the given collision object pair has collided in the past, then
  231. // we notify the listeners only if the pair was not colliding
  232. // during the previous frame. Otherwise, it's a new pair, so add a
  233. // new entry to the cache with the appropriate listeners and notify them.
  234. PhysicsCollisionObject::CollisionPair pair(objectA, objectB);
  235. CollisionInfo* collisionInfo;
  236. if (_collisionStatus.count(pair) > 0)
  237. {
  238. collisionInfo = &_collisionStatus[pair];
  239. }
  240. else
  241. {
  242. // Add a new collision pair for these objects.
  243. collisionInfo = &_collisionStatus[pair];
  244. // Add the appropriate listeners.
  245. PhysicsCollisionObject::CollisionPair p1(pair.objectA, NULL);
  246. if (_collisionStatus.count(p1) > 0)
  247. {
  248. const CollisionInfo& ci = _collisionStatus[p1];
  249. std::vector<PhysicsCollisionObject::CollisionListener*>::const_iterator iter = ci._listeners.begin();
  250. for (; iter != ci._listeners.end(); iter++)
  251. {
  252. GP_ASSERT(*iter);
  253. collisionInfo->_listeners.push_back(*iter);
  254. }
  255. }
  256. PhysicsCollisionObject::CollisionPair p2(pair.objectB, NULL);
  257. if (_collisionStatus.count(p2) > 0)
  258. {
  259. const CollisionInfo& ci = _collisionStatus[p2];
  260. std::vector<PhysicsCollisionObject::CollisionListener*>::const_iterator iter = ci._listeners.begin();
  261. for (; iter != ci._listeners.end(); iter++)
  262. {
  263. GP_ASSERT(*iter);
  264. collisionInfo->_listeners.push_back(*iter);
  265. }
  266. }
  267. }
  268. // Fire collision event.
  269. if ((collisionInfo->_status & COLLISION) == 0)
  270. {
  271. std::vector<PhysicsCollisionObject::CollisionListener*>::const_iterator iter = collisionInfo->_listeners.begin();
  272. for (; iter != collisionInfo->_listeners.end(); iter++)
  273. {
  274. GP_ASSERT(*iter);
  275. if ((collisionInfo->_status & REMOVE) == 0)
  276. {
  277. (*iter)->collisionEvent(PhysicsCollisionObject::CollisionListener::COLLIDING, pair, Vector3(cp.getPositionWorldOnA().x(), cp.getPositionWorldOnA().y(), cp.getPositionWorldOnA().z()),
  278. Vector3(cp.getPositionWorldOnB().x(), cp.getPositionWorldOnB().y(), cp.getPositionWorldOnB().z()));
  279. }
  280. }
  281. }
  282. // Update the collision status cache (we remove the dirty bit
  283. // set in the controller's update so that this particular collision pair's
  284. // status is not reset to 'no collision' when the controller's update completes).
  285. collisionInfo->_status &= ~DIRTY;
  286. collisionInfo->_status |= COLLISION;
  287. return 0.0f;
  288. }
  289. void PhysicsController::initialize()
  290. {
  291. _collisionConfiguration = new btDefaultCollisionConfiguration();
  292. _dispatcher = new btCollisionDispatcher(_collisionConfiguration);
  293. _overlappingPairCache = new btDbvtBroadphase();
  294. _solver = new btSequentialImpulseConstraintSolver();
  295. // Create the world.
  296. _world = new btDiscreteDynamicsWorld(_dispatcher, _overlappingPairCache, _solver, _collisionConfiguration);
  297. _world->setGravity(BV(_gravity));
  298. // Register ghost pair callback so bullet detects collisions with ghost objects (used for character collisions).
  299. GP_ASSERT(_world->getPairCache());
  300. _ghostPairCallback = bullet_new<btGhostPairCallback>();
  301. _world->getPairCache()->setInternalGhostPairCallback(_ghostPairCallback);
  302. _world->getDispatchInfo().m_allowedCcdPenetration = 0.0001f;
  303. // Set up debug drawing.
  304. _debugDrawer = new DebugDrawer();
  305. _world->setDebugDrawer(_debugDrawer);
  306. }
  307. void PhysicsController::finalize()
  308. {
  309. // Clean up the world and its various components.
  310. SAFE_DELETE(_world);
  311. SAFE_DELETE(_ghostPairCallback);
  312. SAFE_DELETE(_solver);
  313. SAFE_DELETE(_overlappingPairCache);
  314. SAFE_DELETE(_dispatcher);
  315. SAFE_DELETE(_collisionConfiguration);
  316. }
  317. void PhysicsController::pause()
  318. {
  319. // Unused
  320. }
  321. void PhysicsController::resume()
  322. {
  323. // Unused
  324. }
  325. void PhysicsController::update(long elapsedTime)
  326. {
  327. GP_ASSERT(_world);
  328. // Update the physics simulation, with a maximum
  329. // of 10 simulation steps being performed in a given frame.
  330. //
  331. // Note that stepSimulation takes elapsed time in seconds
  332. // so we divide by 1000 to convert from milliseconds.
  333. _world->stepSimulation((float)elapsedTime * 0.001, 10);
  334. // If we have status listeners, then check if our status has changed.
  335. if (_listeners)
  336. {
  337. Listener::EventType oldStatus = _status;
  338. if (_status == Listener::DEACTIVATED)
  339. {
  340. for (int i = 0; i < _world->getNumCollisionObjects(); i++)
  341. {
  342. GP_ASSERT(_world->getCollisionObjectArray()[i]);
  343. if (_world->getCollisionObjectArray()[i]->isActive())
  344. {
  345. _status = Listener::ACTIVATED;
  346. break;
  347. }
  348. }
  349. }
  350. else
  351. {
  352. bool allInactive = true;
  353. for (int i = 0; i < _world->getNumCollisionObjects(); i++)
  354. {
  355. GP_ASSERT(_world->getCollisionObjectArray()[i]);
  356. if (_world->getCollisionObjectArray()[i]->isActive())
  357. {
  358. allInactive = false;
  359. break;
  360. }
  361. }
  362. if (allInactive)
  363. _status = Listener::DEACTIVATED;
  364. }
  365. // If the status has changed, notify our listeners.
  366. if (oldStatus != _status)
  367. {
  368. for (unsigned int k = 0; k < _listeners->size(); k++)
  369. {
  370. GP_ASSERT((*_listeners)[k]);
  371. (*_listeners)[k]->statusEvent(_status);
  372. }
  373. }
  374. }
  375. // All statuses are set with the DIRTY bit before collision processing occurs.
  376. // During collision processing, if a collision occurs, the status is
  377. // set to COLLISION and the DIRTY bit is cleared. Then, after collision processing
  378. // is finished, if a given status is still dirty, the COLLISION bit is cleared.
  379. //
  380. // If an entry was marked for removal in the last frame, remove it now.
  381. // Dirty the collision status cache entries.
  382. std::map<PhysicsCollisionObject::CollisionPair, CollisionInfo>::iterator iter = _collisionStatus.begin();
  383. for (; iter != _collisionStatus.end();)
  384. {
  385. if ((iter->second._status & REMOVE) != 0)
  386. {
  387. std::map<PhysicsCollisionObject::CollisionPair, CollisionInfo>::iterator eraseIter = iter;
  388. iter++;
  389. _collisionStatus.erase(eraseIter);
  390. }
  391. else
  392. {
  393. iter->second._status |= DIRTY;
  394. iter++;
  395. }
  396. }
  397. // Go through the collision status cache and perform all registered collision tests.
  398. iter = _collisionStatus.begin();
  399. for (; iter != _collisionStatus.end(); iter++)
  400. {
  401. // If this collision pair was one that was registered for listening, then perform the collision test.
  402. // (In the case where we register for all collisions with a rigid body, there will be a lot
  403. // of collision pairs in the status cache that we did not explicitly register for.)
  404. if ((iter->second._status & REGISTERED) != 0 && (iter->second._status & REMOVE) == 0)
  405. {
  406. if (iter->first.objectB)
  407. _world->contactPairTest(iter->first.objectA->getCollisionObject(), iter->first.objectB->getCollisionObject(), *this);
  408. else
  409. _world->contactTest(iter->first.objectA->getCollisionObject(), *this);
  410. }
  411. }
  412. // Update all the collision status cache entries.
  413. iter = _collisionStatus.begin();
  414. for (; iter != _collisionStatus.end(); iter++)
  415. {
  416. if ((iter->second._status & DIRTY) != 0)
  417. {
  418. if ((iter->second._status & COLLISION) != 0 && iter->first.objectB)
  419. {
  420. unsigned int size = iter->second._listeners.size();
  421. for (unsigned int i = 0; i < size; i++)
  422. {
  423. iter->second._listeners[i]->collisionEvent(PhysicsCollisionObject::CollisionListener::NOT_COLLIDING, iter->first);
  424. }
  425. }
  426. iter->second._status &= ~COLLISION;
  427. }
  428. }
  429. }
  430. void PhysicsController::addCollisionListener(PhysicsCollisionObject::CollisionListener* listener, PhysicsCollisionObject* objectA, PhysicsCollisionObject* objectB)
  431. {
  432. GP_ASSERT(listener);
  433. // One of the collision objects in the pair must be non-null.
  434. GP_ASSERT(objectA || objectB);
  435. PhysicsCollisionObject::CollisionPair pair(objectA, objectB);
  436. // Add the listener and ensure the status includes that this collision pair is registered.
  437. CollisionInfo& info = _collisionStatus[pair];
  438. info._listeners.push_back(listener);
  439. info._status |= PhysicsController::REGISTERED;
  440. }
  441. void PhysicsController::removeCollisionListener(PhysicsCollisionObject::CollisionListener* listener, PhysicsCollisionObject* objectA, PhysicsCollisionObject* objectB)
  442. {
  443. // One of the collision objects in the pair must be non-null.
  444. GP_ASSERT(objectA || objectB);
  445. PhysicsCollisionObject::CollisionPair pair(objectA, objectB);
  446. // Mark the collision pair for these objects for removal.
  447. if (_collisionStatus.count(pair) > 0)
  448. {
  449. _collisionStatus[pair]._status |= REMOVE;
  450. }
  451. }
  452. void PhysicsController::addCollisionObject(PhysicsCollisionObject* object)
  453. {
  454. GP_ASSERT(object && object->getCollisionObject());
  455. GP_ASSERT(_world);
  456. // Assign user pointer for the bullet collision object to allow efficient
  457. // lookups of bullet objects -> gameplay objects.
  458. object->getCollisionObject()->setUserPointer(object);
  459. // Add the object to the physics world.
  460. switch (object->getType())
  461. {
  462. case PhysicsCollisionObject::RIGID_BODY:
  463. _world->addRigidBody(static_cast<btRigidBody*>(object->getCollisionObject()), btBroadphaseProxy::DefaultFilter, btBroadphaseProxy::DefaultFilter | btBroadphaseProxy::StaticFilter | btBroadphaseProxy::CharacterFilter | btBroadphaseProxy::AllFilter);
  464. break;
  465. case PhysicsCollisionObject::CHARACTER:
  466. _world->addCollisionObject(object->getCollisionObject(), btBroadphaseProxy::CharacterFilter, btBroadphaseProxy::DefaultFilter | btBroadphaseProxy::StaticFilter | btBroadphaseProxy::CharacterFilter | btBroadphaseProxy::AllFilter);
  467. break;
  468. case PhysicsCollisionObject::GHOST_OBJECT:
  469. _world->addCollisionObject(object->getCollisionObject(), btBroadphaseProxy::DefaultFilter, btBroadphaseProxy::DefaultFilter | btBroadphaseProxy::StaticFilter | btBroadphaseProxy::CharacterFilter | btBroadphaseProxy::AllFilter);
  470. break;
  471. default:
  472. GP_ERROR("Unsupported collision object type (%d).", object->getType());
  473. break;
  474. }
  475. }
  476. void PhysicsController::removeCollisionObject(PhysicsCollisionObject* object)
  477. {
  478. GP_ASSERT(object);
  479. GP_ASSERT(_world);
  480. // Remove the collision object from the world.
  481. if (object->getCollisionObject())
  482. {
  483. switch (object->getType())
  484. {
  485. case PhysicsCollisionObject::RIGID_BODY:
  486. _world->removeRigidBody(static_cast<btRigidBody*>(object->getCollisionObject()));
  487. break;
  488. case PhysicsCollisionObject::CHARACTER:
  489. case PhysicsCollisionObject::GHOST_OBJECT:
  490. _world->removeCollisionObject(object->getCollisionObject());
  491. break;
  492. default:
  493. GP_ERROR("Unsupported collision object type (%d).", object->getType());
  494. break;
  495. }
  496. }
  497. // Find all references to the object in the collision status cache and mark them for removal.
  498. std::map<PhysicsCollisionObject::CollisionPair, CollisionInfo>::iterator iter = _collisionStatus.begin();
  499. for (; iter != _collisionStatus.end(); iter++)
  500. {
  501. if (iter->first.objectA == object || iter->first.objectB == object)
  502. iter->second._status |= REMOVE;
  503. }
  504. }
  505. PhysicsCollisionObject* PhysicsController::getCollisionObject(const btCollisionObject* collisionObject) const
  506. {
  507. // Gameplay collision objects are stored in the userPointer data of Bullet collision objects.
  508. GP_ASSERT(collisionObject);
  509. return reinterpret_cast<PhysicsCollisionObject*>(collisionObject->getUserPointer());
  510. }
  511. void getBoundingBox(Node* node, BoundingBox* out, bool merge = false)
  512. {
  513. GP_ASSERT(node);
  514. GP_ASSERT(out);
  515. if (node->getModel())
  516. {
  517. GP_ASSERT(node->getModel()->getMesh());
  518. if (merge)
  519. out->merge(node->getModel()->getMesh()->getBoundingBox());
  520. else
  521. {
  522. out->set(node->getModel()->getMesh()->getBoundingBox());
  523. merge = true;
  524. }
  525. }
  526. Node* child = node->getFirstChild();
  527. while (child)
  528. {
  529. getBoundingBox(child, out, merge);
  530. child = child->getNextSibling();
  531. }
  532. }
  533. void getBoundingSphere(Node* node, BoundingSphere* out, bool merge = false)
  534. {
  535. GP_ASSERT(node);
  536. GP_ASSERT(out);
  537. if (node->getModel())
  538. {
  539. GP_ASSERT(node->getModel()->getMesh());
  540. if (merge)
  541. out->merge(node->getModel()->getMesh()->getBoundingSphere());
  542. else
  543. {
  544. out->set(node->getModel()->getMesh()->getBoundingSphere());
  545. merge = true;
  546. }
  547. }
  548. Node* child = node->getFirstChild();
  549. while (child)
  550. {
  551. getBoundingSphere(child, out, merge);
  552. child = child->getNextSibling();
  553. }
  554. }
  555. void computeCenterOfMass(const Vector3& center, const Vector3& scale, Vector3* centerOfMassOffset)
  556. {
  557. GP_ASSERT(centerOfMassOffset);
  558. // Update center of mass offset.
  559. *centerOfMassOffset = center;
  560. centerOfMassOffset->x *= scale.x;
  561. centerOfMassOffset->y *= scale.y;
  562. centerOfMassOffset->z *= scale.z;
  563. centerOfMassOffset->negate();
  564. }
  565. PhysicsCollisionShape* PhysicsController::createShape(Node* node, const PhysicsCollisionShape::Definition& shape, Vector3* centerOfMassOffset)
  566. {
  567. GP_ASSERT(node);
  568. PhysicsCollisionShape* collisionShape = NULL;
  569. // Get the node's world scale (we need to apply this during creation since rigid bodies don't scale dynamically).
  570. Vector3 scale;
  571. node->getWorldMatrix().getScale(&scale);
  572. switch (shape.type)
  573. {
  574. case PhysicsCollisionShape::SHAPE_BOX:
  575. {
  576. if (shape.isExplicit)
  577. {
  578. // Use the passed in box information.
  579. collisionShape = createBox(Vector3(shape.data.box.extents), Vector3::one());
  580. if (shape.centerAbsolute)
  581. {
  582. computeCenterOfMass(Vector3(shape.data.box.center), Vector3::one(), centerOfMassOffset);
  583. }
  584. else
  585. {
  586. BoundingBox box;
  587. getBoundingBox(node, &box);
  588. computeCenterOfMass(box.getCenter() + Vector3(shape.data.box.center), scale, centerOfMassOffset);
  589. }
  590. }
  591. else
  592. {
  593. // Automatically compute bounding box from mesh's bounding box.
  594. BoundingBox box;
  595. getBoundingBox(node, &box);
  596. collisionShape = createBox(Vector3(std::abs(box.max.x - box.min.x), std::abs(box.max.y - box.min.y), std::abs(box.max.z - box.min.z)), scale);
  597. computeCenterOfMass(box.getCenter(), scale, centerOfMassOffset);
  598. }
  599. }
  600. break;
  601. case PhysicsCollisionShape::SHAPE_SPHERE:
  602. {
  603. if (shape.isExplicit)
  604. {
  605. // Use the passed in sphere information.
  606. collisionShape = createSphere(shape.data.sphere.radius, Vector3::one());
  607. if (shape.centerAbsolute)
  608. {
  609. computeCenterOfMass(Vector3(shape.data.sphere.center), Vector3::one(), centerOfMassOffset);
  610. }
  611. else
  612. {
  613. BoundingSphere sphere;
  614. getBoundingSphere(node, &sphere);
  615. computeCenterOfMass(sphere.center + Vector3(shape.data.sphere.center), scale, centerOfMassOffset);
  616. }
  617. }
  618. else
  619. {
  620. // Automatically compute bounding sphere from mesh's bounding sphere.
  621. BoundingSphere sphere;
  622. getBoundingSphere(node, &sphere);
  623. collisionShape = createSphere(sphere.radius, scale);
  624. computeCenterOfMass(sphere.center, scale, centerOfMassOffset);
  625. }
  626. }
  627. break;
  628. case PhysicsCollisionShape::SHAPE_CAPSULE:
  629. {
  630. if (shape.isExplicit)
  631. {
  632. // Use the passed in capsule information.
  633. collisionShape = createCapsule(shape.data.capsule.radius, shape.data.capsule.height, Vector3::one());
  634. if (shape.centerAbsolute)
  635. {
  636. computeCenterOfMass(Vector3(shape.data.capsule.center), Vector3::one(), centerOfMassOffset);
  637. }
  638. else
  639. {
  640. BoundingBox box;
  641. getBoundingBox(node, &box);
  642. computeCenterOfMass(box.getCenter() + Vector3(shape.data.capsule.center), scale, centerOfMassOffset);
  643. }
  644. }
  645. else
  646. {
  647. // Compute a capsule shape that roughly matches the bounding box of the mesh.
  648. BoundingBox box;
  649. getBoundingBox(node, &box);
  650. float radius = std::max((box.max.x - box.min.x) * 0.5f, (box.max.z - box.min.z) * 0.5f);
  651. float height = box.max.y - box.min.y;
  652. collisionShape = createCapsule(radius, height, scale);
  653. computeCenterOfMass(box.getCenter(), scale, centerOfMassOffset);
  654. }
  655. }
  656. break;
  657. case PhysicsCollisionShape::SHAPE_HEIGHTFIELD:
  658. {
  659. // Build heightfield rigid body from the passed in shape.
  660. collisionShape = createHeightfield(node, shape.data.heightfield, centerOfMassOffset);
  661. }
  662. break;
  663. case PhysicsCollisionShape::SHAPE_MESH:
  664. {
  665. // Build mesh from passed in shape.
  666. collisionShape = createMesh(shape.data.mesh, scale);
  667. }
  668. break;
  669. default:
  670. GP_ERROR("Unsupported collision shape type (%d).", shape.type);
  671. break;
  672. }
  673. return collisionShape;
  674. }
  675. PhysicsCollisionShape* PhysicsController::createBox(const Vector3& extents, const Vector3& scale)
  676. {
  677. btVector3 halfExtents(scale.x * 0.5 * extents.x, scale.y * 0.5 * extents.y, scale.z * 0.5 * extents.z);
  678. PhysicsCollisionShape* shape;
  679. // Return the box shape from the cache if it already exists.
  680. for (unsigned int i = 0; i < _shapes.size(); ++i)
  681. {
  682. shape = _shapes[i];
  683. GP_ASSERT(shape);
  684. if (shape->getType() == PhysicsCollisionShape::SHAPE_BOX)
  685. {
  686. btBoxShape* box = static_cast<btBoxShape*>(shape->_shape);
  687. if (box && box->getHalfExtentsWithMargin() == halfExtents)
  688. {
  689. shape->addRef();
  690. return shape;
  691. }
  692. }
  693. }
  694. // Create the box shape and add it to the cache.
  695. shape = new PhysicsCollisionShape(PhysicsCollisionShape::SHAPE_BOX, bullet_new<btBoxShape>(halfExtents));
  696. _shapes.push_back(shape);
  697. return shape;
  698. }
  699. PhysicsCollisionShape* PhysicsController::createSphere(float radius, const Vector3& scale)
  700. {
  701. // Since sphere shapes depend only on the radius, the best we can do is take
  702. // the largest dimension and apply that as the uniform scale to the rigid body.
  703. float uniformScale = scale.x;
  704. if (uniformScale < scale.y)
  705. uniformScale = scale.y;
  706. if (uniformScale < scale.z)
  707. uniformScale = scale.z;
  708. float scaledRadius = radius * uniformScale;
  709. PhysicsCollisionShape* shape;
  710. // Return the sphere shape from the cache if it already exists.
  711. for (unsigned int i = 0; i < _shapes.size(); ++i)
  712. {
  713. shape = _shapes[i];
  714. GP_ASSERT(shape);
  715. if (shape->getType() == PhysicsCollisionShape::SHAPE_SPHERE)
  716. {
  717. btSphereShape* sphere = static_cast<btSphereShape*>(shape->_shape);
  718. if (sphere && sphere->getRadius() == scaledRadius)
  719. {
  720. shape->addRef();
  721. return shape;
  722. }
  723. }
  724. }
  725. // Create the sphere shape and add it to the cache.
  726. shape = new PhysicsCollisionShape(PhysicsCollisionShape::SHAPE_SPHERE, bullet_new<btSphereShape>(scaledRadius));
  727. _shapes.push_back(shape);
  728. return shape;
  729. }
  730. PhysicsCollisionShape* PhysicsController::createCapsule(float radius, float height, const Vector3& scale)
  731. {
  732. float girthScale = scale.x;
  733. if (girthScale < scale.z)
  734. girthScale = scale.z;
  735. float scaledRadius = radius * girthScale;
  736. float scaledHeight = height * scale.y - radius * 2;
  737. PhysicsCollisionShape* shape;
  738. // Return the capsule shape from the cache if it already exists.
  739. for (unsigned int i = 0; i < _shapes.size(); i++)
  740. {
  741. shape = _shapes[i];
  742. GP_ASSERT(shape);
  743. if (shape->getType() == PhysicsCollisionShape::SHAPE_CAPSULE)
  744. {
  745. btCapsuleShape* capsule = static_cast<btCapsuleShape*>(shape->_shape);
  746. if (capsule && capsule->getRadius() == scaledRadius && capsule->getHalfHeight() == 0.5f * scaledHeight)
  747. {
  748. shape->addRef();
  749. return shape;
  750. }
  751. }
  752. }
  753. // Create the capsule shape and add it to the cache.
  754. shape = new PhysicsCollisionShape(PhysicsCollisionShape::SHAPE_CAPSULE, bullet_new<btCapsuleShape>(scaledRadius, scaledHeight));
  755. _shapes.push_back(shape);
  756. return shape;
  757. }
  758. PhysicsCollisionShape* PhysicsController::createHeightfield(Node* node, Image* image, Vector3* centerOfMassOffset)
  759. {
  760. GP_ASSERT(node);
  761. GP_ASSERT(image);
  762. GP_ASSERT(centerOfMassOffset);
  763. // Get the dimensions of the heightfield.
  764. // If the node has a mesh defined, use the dimensions of the bounding box for the mesh.
  765. // Otherwise simply use the image dimensions (with a max height of 255).
  766. float width, length, minHeight, maxHeight;
  767. if (node->getModel() && node->getModel()->getMesh())
  768. {
  769. const BoundingBox& box = node->getModel()->getMesh()->getBoundingBox();
  770. width = box.max.x - box.min.x;
  771. length = box.max.z - box.min.z;
  772. minHeight = box.min.y;
  773. maxHeight = box.max.y;
  774. }
  775. else
  776. {
  777. width = image->getWidth();
  778. length = image->getHeight();
  779. minHeight = 0.0f;
  780. maxHeight = 255.0f;
  781. }
  782. // Get the size in bytes of a pixel (we ensure that the image's
  783. // pixel format is actually supported before calling this constructor).
  784. unsigned int pixelSize = 0;
  785. switch (image->getFormat())
  786. {
  787. case Image::RGB:
  788. pixelSize = 3;
  789. break;
  790. case Image::RGBA:
  791. pixelSize = 4;
  792. break;
  793. default:
  794. GP_ERROR("Unsupported pixel format for heightmap image (%d).", image->getFormat());
  795. return NULL;
  796. }
  797. // Calculate the heights for each pixel.
  798. float* heights = new float[image->getWidth() * image->getHeight()];
  799. unsigned char* data = image->getData();
  800. for (unsigned int x = 0, w = image->getWidth(); x < w; ++x)
  801. {
  802. for (unsigned int y = 0, h = image->getHeight(); y < h; ++y)
  803. {
  804. heights[x + y * w] = ((((float)data[(x + y * h) * pixelSize + 0]) +
  805. ((float)data[(x + y * h) * pixelSize + 1]) +
  806. ((float)data[(x + y * h) * pixelSize + 2])) / 768.0f) * (maxHeight - minHeight) + minHeight;
  807. }
  808. }
  809. PhysicsCollisionShape::HeightfieldData* heightfieldData = new PhysicsCollisionShape::HeightfieldData();
  810. heightfieldData->heightData = NULL;
  811. heightfieldData->inverseIsDirty = true;
  812. unsigned int sizeWidth = width;
  813. unsigned int sizeHeight = length;
  814. GP_ASSERT(sizeWidth);
  815. GP_ASSERT(sizeHeight);
  816. // Generate the heightmap data needed for physics (one height per world unit).
  817. heightfieldData->width = sizeWidth + 1;
  818. heightfieldData->height = sizeHeight + 1;
  819. heightfieldData->heightData = new float[heightfieldData->width * heightfieldData->height];
  820. unsigned int heightIndex = 0;
  821. float widthImageFactor = (float)(image->getWidth() - 1) / sizeWidth;
  822. float heightImageFactor = (float)(image->getHeight() - 1) / sizeHeight;
  823. float x = 0.0f;
  824. float z = 0.0f;
  825. for (unsigned int row = 0, z = 0.0f; row <= sizeHeight; row++, z += 1.0f)
  826. {
  827. for (unsigned int col = 0, x = 0.0f; col <= sizeWidth; col++, x += 1.0f)
  828. {
  829. heightIndex = row * heightfieldData->width + col;
  830. heightfieldData->heightData[heightIndex] = calculateHeight(heights, image->getWidth(), image->getHeight(), x * widthImageFactor, (sizeHeight - z) * heightImageFactor);
  831. }
  832. }
  833. SAFE_DELETE_ARRAY(heights);
  834. // Offset the heightmap's center of mass according to the way that Bullet calculates the origin
  835. // of its heightfield collision shape; see documentation for the btHeightfieldTerrainShape for more info.
  836. Vector3 s;
  837. node->getWorldMatrix().getScale(&s);
  838. GP_ASSERT(s.y);
  839. centerOfMassOffset->set(0.0f, -(maxHeight - (0.5f * (maxHeight - minHeight))) / s.y, 0.0f);
  840. // Create the bullet terrain shape.
  841. btHeightfieldTerrainShape* terrainShape = bullet_new<btHeightfieldTerrainShape>(
  842. heightfieldData->width, heightfieldData->height, heightfieldData->heightData, 1.0f, minHeight, maxHeight, 1, PHY_FLOAT, false);
  843. // Create our collision shape object and store heightfieldData in it.
  844. PhysicsCollisionShape* shape = new PhysicsCollisionShape(PhysicsCollisionShape::SHAPE_HEIGHTFIELD, terrainShape);
  845. shape->_shapeData.heightfieldData = heightfieldData;
  846. _shapes.push_back(shape);
  847. return shape;
  848. }
  849. PhysicsCollisionShape* PhysicsController::createMesh(Mesh* mesh, const Vector3& scale)
  850. {
  851. GP_ASSERT(mesh);
  852. // Only support meshes with triangle list primitive types.
  853. bool triMesh = true;
  854. if (mesh->getPartCount() > 0)
  855. {
  856. for (unsigned int i = 0; i < mesh->getPartCount(); ++i)
  857. {
  858. if (mesh->getPart(i)->getPrimitiveType() != Mesh::TRIANGLES)
  859. {
  860. triMesh = false;
  861. break;
  862. }
  863. }
  864. }
  865. else
  866. {
  867. triMesh = mesh->getPrimitiveType() == Mesh::TRIANGLES;
  868. }
  869. if (!triMesh)
  870. {
  871. GP_ERROR("Mesh rigid bodies are currently only supported on meshes with TRIANGLES primitive type.");
  872. return NULL;
  873. }
  874. // The mesh must have a valid URL (i.e. it must have been loaded from a Bundle)
  875. // in order to fetch mesh data for computing mesh rigid body.
  876. if (strlen(mesh->getUrl()) == 0)
  877. {
  878. GP_ERROR("Cannot create mesh rigid body for mesh without valid URL.");
  879. return NULL;
  880. }
  881. Bundle::MeshData* data = Bundle::readMeshData(mesh->getUrl());
  882. if (data == NULL)
  883. {
  884. GP_ERROR("Failed to load mesh data from url '%s'.", mesh->getUrl());
  885. return NULL;
  886. }
  887. // Create mesh data to be populated and store in returned collision shape.
  888. PhysicsCollisionShape::MeshData* shapeMeshData = new PhysicsCollisionShape::MeshData();
  889. shapeMeshData->vertexData = NULL;
  890. // Copy the scaled vertex position data to the rigid body's local buffer.
  891. Matrix m;
  892. Matrix::createScale(scale, &m);
  893. unsigned int vertexCount = data->vertexCount;
  894. shapeMeshData->vertexData = new float[vertexCount * 3];
  895. Vector3 v;
  896. int vertexStride = data->vertexFormat.getVertexSize();
  897. for (unsigned int i = 0; i < data->vertexCount; i++)
  898. {
  899. v.set(*((float*)&data->vertexData[i * vertexStride + 0 * sizeof(float)]),
  900. *((float*)&data->vertexData[i * vertexStride + 1 * sizeof(float)]),
  901. *((float*)&data->vertexData[i * vertexStride + 2 * sizeof(float)]));
  902. v *= m;
  903. memcpy(&(shapeMeshData->vertexData[i * 3]), &v, sizeof(float) * 3);
  904. }
  905. btTriangleIndexVertexArray* meshInterface = bullet_new<btTriangleIndexVertexArray>();
  906. unsigned int partCount = data->parts.size();
  907. if (partCount > 0)
  908. {
  909. PHY_ScalarType indexType = PHY_UCHAR;
  910. int indexStride = 0;
  911. Bundle::MeshPartData* meshPart = NULL;
  912. for (unsigned int i = 0; i < partCount; i++)
  913. {
  914. meshPart = data->parts[i];
  915. GP_ASSERT(meshPart);
  916. switch (meshPart->indexFormat)
  917. {
  918. case Mesh::INDEX8:
  919. indexType = PHY_UCHAR;
  920. indexStride = 1;
  921. break;
  922. case Mesh::INDEX16:
  923. indexType = PHY_SHORT;
  924. indexStride = 2;
  925. break;
  926. case Mesh::INDEX32:
  927. indexType = PHY_INTEGER;
  928. indexStride = 4;
  929. break;
  930. default:
  931. GP_ERROR("Unsupported index format (%d).", meshPart->indexFormat);
  932. SAFE_DELETE(meshInterface);
  933. SAFE_DELETE_ARRAY(shapeMeshData->vertexData);
  934. SAFE_DELETE(shapeMeshData);
  935. SAFE_DELETE(data);
  936. return NULL;
  937. }
  938. // Move the index data into the rigid body's local buffer.
  939. // Set it to NULL in the MeshPartData so it is not released when the data is freed.
  940. shapeMeshData->indexData.push_back(meshPart->indexData);
  941. meshPart->indexData = NULL;
  942. // Create a btIndexedMesh object for the current mesh part.
  943. btIndexedMesh indexedMesh;
  944. indexedMesh.m_indexType = indexType;
  945. indexedMesh.m_numTriangles = meshPart->indexCount / 3; // assume TRIANGLES primitive type
  946. indexedMesh.m_numVertices = meshPart->indexCount;
  947. indexedMesh.m_triangleIndexBase = (const unsigned char*)shapeMeshData->indexData[i];
  948. indexedMesh.m_triangleIndexStride = indexStride*3;
  949. indexedMesh.m_vertexBase = (const unsigned char*)shapeMeshData->vertexData;
  950. indexedMesh.m_vertexStride = sizeof(float)*3;
  951. indexedMesh.m_vertexType = PHY_FLOAT;
  952. // Add the indexed mesh data to the mesh interface.
  953. meshInterface->addIndexedMesh(indexedMesh, indexType);
  954. }
  955. }
  956. else
  957. {
  958. // Generate index data for the mesh locally in the rigid body.
  959. unsigned int* indexData = new unsigned int[data->vertexCount];
  960. for (unsigned int i = 0; i < data->vertexCount; i++)
  961. {
  962. indexData[i] = i;
  963. }
  964. shapeMeshData->indexData.push_back((unsigned char*)indexData);
  965. // Create a single btIndexedMesh object for the mesh interface.
  966. btIndexedMesh indexedMesh;
  967. indexedMesh.m_indexType = PHY_INTEGER;
  968. indexedMesh.m_numTriangles = data->vertexCount / 3; // assume TRIANGLES primitive type
  969. indexedMesh.m_numVertices = data->vertexCount;
  970. indexedMesh.m_triangleIndexBase = shapeMeshData->indexData[0];
  971. indexedMesh.m_triangleIndexStride = sizeof(unsigned int);
  972. indexedMesh.m_vertexBase = (const unsigned char*)shapeMeshData->vertexData;
  973. indexedMesh.m_vertexStride = sizeof(float)*3;
  974. indexedMesh.m_vertexType = PHY_FLOAT;
  975. // Set the data in the mesh interface.
  976. meshInterface->addIndexedMesh(indexedMesh, indexedMesh.m_indexType);
  977. }
  978. // Create our collision shape object and store shapeMeshData in it.
  979. PhysicsCollisionShape* shape = new PhysicsCollisionShape(PhysicsCollisionShape::SHAPE_MESH, bullet_new<btBvhTriangleMeshShape>(meshInterface, true));
  980. shape->_shapeData.meshData = shapeMeshData;
  981. _shapes.push_back(shape);
  982. // Free the temporary mesh data now that it's stored in physics system.
  983. SAFE_DELETE(data);
  984. return shape;
  985. }
  986. void PhysicsController::destroyShape(PhysicsCollisionShape* shape)
  987. {
  988. if (shape)
  989. {
  990. if (shape->getRefCount() == 1)
  991. {
  992. // Remove shape from shape cache.
  993. std::vector<PhysicsCollisionShape*>::iterator shapeItr = std::find(_shapes.begin(), _shapes.end(), shape);
  994. if (shapeItr != _shapes.end())
  995. _shapes.erase(shapeItr);
  996. }
  997. // Release the shape.
  998. shape->release();
  999. }
  1000. }
  1001. float PhysicsController::calculateHeight(float* data, unsigned int width, unsigned int height, float x, float y)
  1002. {
  1003. GP_ASSERT(data);
  1004. unsigned int x1 = x;
  1005. unsigned int y1 = y;
  1006. unsigned int x2 = x1 + 1;
  1007. unsigned int y2 = y1 + 1;
  1008. float tmp;
  1009. float xFactor = modf(x, &tmp);
  1010. float yFactor = modf(y, &tmp);
  1011. float xFactorI = 1.0f - xFactor;
  1012. float yFactorI = 1.0f - yFactor;
  1013. if (x2 >= width && y2 >= height)
  1014. {
  1015. return data[x1 + y1 * width];
  1016. }
  1017. else if (x2 >= width)
  1018. {
  1019. return data[x1 + y1 * width] * yFactorI + data[x1 + y2 * width] * yFactor;
  1020. }
  1021. else if (y2 >= height)
  1022. {
  1023. return data[x1 + y1 * width] * xFactorI + data[x2 + y1 * width] * xFactor;
  1024. }
  1025. else
  1026. {
  1027. return data[x1 + y1 * width] * xFactorI * yFactorI + data[x1 + y2 * width] * xFactorI * yFactor +
  1028. data[x2 + y2 * width] * xFactor * yFactor + data[x2 + y1 * width] * xFactor * yFactorI;
  1029. }
  1030. }
  1031. void PhysicsController::addConstraint(PhysicsRigidBody* a, PhysicsRigidBody* b, PhysicsConstraint* constraint)
  1032. {
  1033. GP_ASSERT(a);
  1034. GP_ASSERT(constraint);
  1035. GP_ASSERT(_world);
  1036. a->addConstraint(constraint);
  1037. if (b)
  1038. {
  1039. b->addConstraint(constraint);
  1040. }
  1041. _world->addConstraint(constraint->_constraint);
  1042. }
  1043. bool PhysicsController::checkConstraintRigidBodies(PhysicsRigidBody* a, PhysicsRigidBody* b)
  1044. {
  1045. GP_ASSERT(a);
  1046. if (!a->supportsConstraints())
  1047. {
  1048. GP_ASSERT(a->_node);
  1049. GP_ERROR("Rigid body '%s' does not support constraints; unexpected behavior may occur.", a->_node->getId());
  1050. return false;
  1051. }
  1052. if (b && !b->supportsConstraints())
  1053. {
  1054. GP_ASSERT(b->_node);
  1055. GP_ERROR("Rigid body '%s' does not support constraints; unexpected behavior may occur.", b->_node->getId());
  1056. return false;
  1057. }
  1058. return true;
  1059. }
  1060. void PhysicsController::removeConstraint(PhysicsConstraint* constraint)
  1061. {
  1062. GP_ASSERT(constraint);
  1063. GP_ASSERT(_world);
  1064. // Find the constraint and remove it from the physics world.
  1065. for (int i = _world->getNumConstraints() - 1; i >= 0; i--)
  1066. {
  1067. btTypedConstraint* currentConstraint = _world->getConstraint(i);
  1068. if (constraint->_constraint == currentConstraint)
  1069. {
  1070. _world->removeConstraint(currentConstraint);
  1071. break;
  1072. }
  1073. }
  1074. }
  1075. PhysicsController::DebugDrawer::DebugDrawer()
  1076. : _mode(btIDebugDraw::DBG_DrawAabb | btIDebugDraw::DBG_DrawConstraintLimits | btIDebugDraw::DBG_DrawConstraints |
  1077. btIDebugDraw::DBG_DrawContactPoints | btIDebugDraw::DBG_DrawWireframe), _viewProjection(NULL), _meshBatch(NULL)
  1078. {
  1079. // Vertex shader for drawing colored lines.
  1080. const char* vs_str =
  1081. {
  1082. "uniform mat4 u_viewProjectionMatrix;\n"
  1083. "attribute vec4 a_position;\n"
  1084. "attribute vec4 a_color;\n"
  1085. "varying vec4 v_color;\n"
  1086. "void main(void) {\n"
  1087. " v_color = a_color;\n"
  1088. " gl_Position = u_viewProjectionMatrix * a_position;\n"
  1089. "}"
  1090. };
  1091. // Fragment shader for drawing colored lines.
  1092. const char* fs_str =
  1093. {
  1094. #ifdef OPENGL_ES
  1095. "precision highp float;\n"
  1096. #endif
  1097. "varying vec4 v_color;\n"
  1098. "void main(void) {\n"
  1099. " gl_FragColor = v_color;\n"
  1100. "}"
  1101. };
  1102. Effect* effect = Effect::createFromSource(vs_str, fs_str);
  1103. Material* material = Material::create(effect);
  1104. GP_ASSERT(material && material->getStateBlock());
  1105. material->getStateBlock()->setDepthTest(true);
  1106. VertexFormat::Element elements[] =
  1107. {
  1108. VertexFormat::Element(VertexFormat::POSITION, 3),
  1109. VertexFormat::Element(VertexFormat::COLOR, 4),
  1110. };
  1111. _meshBatch = MeshBatch::create(VertexFormat(elements, 2), Mesh::LINES, material, false);
  1112. SAFE_RELEASE(material);
  1113. SAFE_RELEASE(effect);
  1114. }
  1115. PhysicsController::DebugDrawer::~DebugDrawer()
  1116. {
  1117. SAFE_DELETE(_meshBatch);
  1118. }
  1119. void PhysicsController::DebugDrawer::begin(const Matrix& viewProjection)
  1120. {
  1121. GP_ASSERT(_meshBatch);
  1122. _viewProjection = &viewProjection;
  1123. _meshBatch->begin();
  1124. }
  1125. void PhysicsController::DebugDrawer::end()
  1126. {
  1127. GP_ASSERT(_meshBatch && _meshBatch->getMaterial() && _meshBatch->getMaterial()->getParameter("u_viewProjectionMatrix"));
  1128. _meshBatch->end();
  1129. _meshBatch->getMaterial()->getParameter("u_viewProjectionMatrix")->setValue(_viewProjection);
  1130. _meshBatch->draw();
  1131. }
  1132. void PhysicsController::DebugDrawer::drawLine(const btVector3& from, const btVector3& to, const btVector3& fromColor, const btVector3& toColor)
  1133. {
  1134. GP_ASSERT(_meshBatch);
  1135. static DebugDrawer::DebugVertex fromVertex, toVertex;
  1136. fromVertex.x = from.getX();
  1137. fromVertex.y = from.getY();
  1138. fromVertex.z = from.getZ();
  1139. fromVertex.r = fromColor.getX();
  1140. fromVertex.g = fromColor.getY();
  1141. fromVertex.b = fromColor.getZ();
  1142. fromVertex.a = 1.0f;
  1143. toVertex.x = to.getX();
  1144. toVertex.y = to.getY();
  1145. toVertex.z = to.getZ();
  1146. toVertex.r = toColor.getX();
  1147. toVertex.g = toColor.getY();
  1148. toVertex.b = toColor.getZ();
  1149. toVertex.a = 1.0f;
  1150. _meshBatch->add(&fromVertex, 1);
  1151. _meshBatch->add(&toVertex, 1);
  1152. }
  1153. void PhysicsController::DebugDrawer::drawLine(const btVector3& from, const btVector3& to, const btVector3& color)
  1154. {
  1155. drawLine(from, to, color, color);
  1156. }
  1157. void PhysicsController::DebugDrawer::drawContactPoint(const btVector3& pointOnB, const btVector3& normalOnB, btScalar distance, int lifeTime, const btVector3& color)
  1158. {
  1159. drawLine(pointOnB, pointOnB + normalOnB, color);
  1160. }
  1161. void PhysicsController::DebugDrawer::reportErrorWarning(const char* warningString)
  1162. {
  1163. GP_WARN(warningString);
  1164. }
  1165. void PhysicsController::DebugDrawer::draw3dText(const btVector3& location, const char* textString)
  1166. {
  1167. GP_WARN("Physics debug drawing: 3D text is not supported.");
  1168. }
  1169. void PhysicsController::DebugDrawer::setDebugMode(int mode)
  1170. {
  1171. _mode = mode;
  1172. }
  1173. int PhysicsController::DebugDrawer::getDebugMode() const
  1174. {
  1175. return _mode;
  1176. }
  1177. PhysicsController::Listener::~Listener()
  1178. {
  1179. GP_ASSERT(Game::getInstance()->getPhysicsController());
  1180. Game::getInstance()->getPhysicsController()->removeStatusListener(this);
  1181. }
  1182. }