diff --git a/src/collision/broadphase/DynamicAABBTree.h b/src/collision/broadphase/DynamicAABBTree.h index 3cbf2daa..0316395b 100644 --- a/src/collision/broadphase/DynamicAABBTree.h +++ b/src/collision/broadphase/DynamicAABBTree.h @@ -130,8 +130,7 @@ class DynamicAABBTreeRaycastCallback { // Class DynamicAABBTree /** * This class implements a dynamic AABB tree that is used for broad-phase - * collision detection. This data structure is inspired by Nathanael Presson's - * dynamic tree implementation in BulletPhysics. The following implementation is + * collision detection. The following implementation is * based on the one from Erin Catto in Box2D as described in the book * "Introduction to Game Physics with Box2D" by Ian Parberry. */ diff --git a/src/collision/narrowphase/SAT/SATAlgorithm.cpp b/src/collision/narrowphase/SAT/SATAlgorithm.cpp index d8d18876..ff16e0b7 100644 --- a/src/collision/narrowphase/SAT/SATAlgorithm.cpp +++ b/src/collision/narrowphase/SAT/SATAlgorithm.cpp @@ -536,7 +536,7 @@ bool SATAlgorithm::testCollisionConvexPolyhedronVsConvexPolyhedron(NarrowPhaseIn // Compute the contact points between two faces of two convex polyhedra. if(computePolyhedronVsPolyhedronFaceContactPoints(isMinPenetrationFaceNormalPolyhedron1, polyhedron1, polyhedron2, polyhedron1ToPolyhedron2, polyhedron2ToPolyhedron1, minFaceIndex, - narrowPhaseInfoBatch, batchIndex, minPenetrationDepth)) { + narrowPhaseInfoBatch, batchIndex)) { lastFrameCollisionInfo->satIsAxisFacePolyhedron1 = isMinPenetrationFaceNormalPolyhedron1; lastFrameCollisionInfo->satIsAxisFacePolyhedron2 = !isMinPenetrationFaceNormalPolyhedron1; @@ -576,7 +576,7 @@ bool SATAlgorithm::testCollisionConvexPolyhedronVsConvexPolyhedron(NarrowPhaseIn // Compute the contact points between two faces of two convex polyhedra. if(computePolyhedronVsPolyhedronFaceContactPoints(isMinPenetrationFaceNormalPolyhedron1, polyhedron1, polyhedron2, polyhedron1ToPolyhedron2, polyhedron2ToPolyhedron1, minFaceIndex, - narrowPhaseInfoBatch, batchIndex, minPenetrationDepth)) { + narrowPhaseInfoBatch, batchIndex)) { lastFrameCollisionInfo->satIsAxisFacePolyhedron1 = isMinPenetrationFaceNormalPolyhedron1; lastFrameCollisionInfo->satIsAxisFacePolyhedron2 = !isMinPenetrationFaceNormalPolyhedron1; @@ -804,7 +804,7 @@ bool SATAlgorithm::testCollisionConvexPolyhedronVsConvexPolyhedron(NarrowPhaseIn // Compute the contact points between two faces of two convex polyhedra. bool contactsFound = computePolyhedronVsPolyhedronFaceContactPoints(isMinPenetrationFaceNormalPolyhedron1, polyhedron1, polyhedron2, polyhedron1ToPolyhedron2, polyhedron2ToPolyhedron1, - minFaceIndex, narrowPhaseInfoBatch, batchIndex, minPenetrationDepth); + minFaceIndex, narrowPhaseInfoBatch, batchIndex); // There should be clipping points here. If it is not the case, it might be // because of a numerical issue @@ -877,8 +877,7 @@ bool SATAlgorithm::testCollisionConvexPolyhedronVsConvexPolyhedron(NarrowPhaseIn bool SATAlgorithm::computePolyhedronVsPolyhedronFaceContactPoints(bool isMinPenetrationFaceNormalPolyhedron1, const ConvexPolyhedronShape* polyhedron1, const ConvexPolyhedronShape* polyhedron2, const Transform& polyhedron1ToPolyhedron2, const Transform& polyhedron2ToPolyhedron1, - uint minFaceIndex, NarrowPhaseInfoBatch& narrowPhaseInfoBatch, uint batchIndex, - decimal minPenetrationDepth) const { + uint minFaceIndex, NarrowPhaseInfoBatch& narrowPhaseInfoBatch, uint batchIndex) const { RP3D_PROFILE("SATAlgorithm::computePolyhedronVsPolyhedronFaceContactPoints", mProfiler); @@ -887,8 +886,6 @@ bool SATAlgorithm::computePolyhedronVsPolyhedronFaceContactPoints(bool isMinPene const Transform& referenceToIncidentTransform = isMinPenetrationFaceNormalPolyhedron1 ? polyhedron1ToPolyhedron2 : polyhedron2ToPolyhedron1; const Transform& incidentToReferenceTransform = isMinPenetrationFaceNormalPolyhedron1 ? polyhedron2ToPolyhedron1 : polyhedron1ToPolyhedron2; - assert(minPenetrationDepth > decimal(0.0)); - const Vector3 axisReferenceSpace = referencePolyhedron->getFaceNormal(minFaceIndex); const Vector3 axisIncidentSpace = referenceToIncidentTransform.getOrientation() * axisReferenceSpace; diff --git a/src/collision/narrowphase/SAT/SATAlgorithm.h b/src/collision/narrowphase/SAT/SATAlgorithm.h index 2d7afd4a..fbd44be5 100644 --- a/src/collision/narrowphase/SAT/SATAlgorithm.h +++ b/src/collision/narrowphase/SAT/SATAlgorithm.h @@ -132,7 +132,7 @@ class SATAlgorithm { bool computePolyhedronVsPolyhedronFaceContactPoints(bool isMinPenetrationFaceNormalPolyhedron1, const ConvexPolyhedronShape* polyhedron1, const ConvexPolyhedronShape* polyhedron2, const Transform& polyhedron1ToPolyhedron2, const Transform& polyhedron2ToPolyhedron1, uint minFaceIndex, - NarrowPhaseInfoBatch& narrowPhaseInfoBatch, uint batchIndex, decimal minPenetrationDepth) const; + NarrowPhaseInfoBatch& narrowPhaseInfoBatch, uint batchIndex) const; public : diff --git a/src/engine/DynamicsWorld.cpp b/src/engine/DynamicsWorld.cpp index 7af7f783..e6acd13c 100644 --- a/src/engine/DynamicsWorld.cpp +++ b/src/engine/DynamicsWorld.cpp @@ -405,7 +405,7 @@ Joint* DynamicsWorld::createJoint(const JointInfo& jointInfo) { if (!jointInfo.isCollisionEnabled) { // Add the pair of bodies in the set of body pairs that cannot collide with each other - mCollisionDetection.addNoCollisionPair(jointInfo.body1, jointInfo.body2); + mCollisionDetection.addNoCollisionPair(jointInfo.body1->getEntity(), jointInfo.body2->getEntity()); } RP3D_LOG(mLogger, Logger::Level::Information, Logger::Category::Joint, @@ -435,7 +435,7 @@ void DynamicsWorld::destroyJoint(Joint* joint) { if (!joint->isCollisionEnabled()) { // Remove the pair of bodies from the set of body pairs that cannot collide with each other - mCollisionDetection.removeNoCollisionPair(joint->getBody1(), joint->getBody2()); + mCollisionDetection.removeNoCollisionPair(joint->getBody1()->getEntity(), joint->getBody2()->getEntity()); } RigidBody* body1 = joint->getBody1(); diff --git a/src/engine/OverlappingPair.cpp b/src/engine/OverlappingPair.cpp index 6dacb6dd..d3779d27 100644 --- a/src/engine/OverlappingPair.cpp +++ b/src/engine/OverlappingPair.cpp @@ -35,7 +35,7 @@ using namespace reactphysics3d; OverlappingPair::OverlappingPair(ProxyShape* shape1, ProxyShape* shape2, MemoryAllocator& persistentMemoryAllocator, MemoryAllocator& temporaryMemoryAllocator, const WorldSettings& worldSettings) - : mPairID(computeID(shape1->getBroadPhaseId(), shape2->getBroadPhaseId())), mProxyShape1(shape1), mProxyShape2(shape2), + : mPairID(computeID(shape1->getBroadPhaseId(), shape2->getBroadPhaseId())), mProxyShape1(shape1->getEntity()), mProxyShape2(shape2->getEntity()), mPersistentAllocator(persistentMemoryAllocator), mTempMemoryAllocator(temporaryMemoryAllocator), mLastFrameCollisionInfos(mPersistentAllocator), mWorldSettings(worldSettings) { @@ -99,16 +99,12 @@ void OverlappingPair::clearObsoleteLastFrameCollisionInfos() { it = mLastFrameCollisionInfos.remove(it); } - else { + else { // If the collision info is not obsolete + + // Do not delete it but mark it as obsolete + it->second->isObsolete = true; + ++it; } } } - -// Make all the last frame collision infos obsolete -void OverlappingPair::makeLastFrameCollisionInfosObsolete() { - - for (auto it = mLastFrameCollisionInfos.begin(); it != mLastFrameCollisionInfos.end(); ++it) { - it->second->isObsolete = true; - } -} diff --git a/src/engine/OverlappingPair.h b/src/engine/OverlappingPair.h index 943bc1ed..b2567535 100644 --- a/src/engine/OverlappingPair.h +++ b/src/engine/OverlappingPair.h @@ -109,9 +109,11 @@ class OverlappingPair { /// Pair ID OverlappingPairId mPairID; - // TODO : Replace this by entities - ProxyShape* mProxyShape1; - ProxyShape* mProxyShape2; + /// Entity of the first proxy-shape of the overlapping pair + Entity mProxyShape1; + + /// Entity of the second proxy-shape of the overlapping pair + Entity mProxyShape2; /// Persistent memory allocator MemoryAllocator& mPersistentAllocator; @@ -149,11 +151,11 @@ class OverlappingPair { /// Return the Id of the pair OverlappingPairId getId() const; - /// Return the pointer to first proxy collision shape - ProxyShape* getShape1() const; + /// Return the entity of the first proxy-shape + Entity getProxyShape1() const; - /// Return the pointer to second body - ProxyShape* getShape2() const; + /// Return the entity of the second proxy-shape + Entity getProxyShape2() const; /// Return the last frame collision info LastFrameCollisionInfo* getLastFrameCollisionInfo(ShapeIdPair& shapeIds); @@ -161,9 +163,6 @@ class OverlappingPair { /// Return a reference to the temporary memory allocator MemoryAllocator& getTemporaryAllocator(); - /// Return true if one of the shapes of the pair is a concave shape - bool hasConcaveShape() const; - /// Add a new last frame collision info if it does not exist for the given shapes already LastFrameCollisionInfo* addLastFrameInfoIfNecessary(uint shapeId1, uint shapeId2); @@ -173,14 +172,11 @@ class OverlappingPair { /// Delete all the obsolete last frame collision info void clearObsoleteLastFrameCollisionInfos(); - /// Make all the last frame collision infos obsolete - void makeLastFrameCollisionInfosObsolete(); - /// Return the pair of bodies index static OverlappingPairId computeID(int shape1BroadPhaseId, int shape2BroadPhaseId); /// Return the pair of bodies index of the pair - static bodypair computeBodiesIndexPair(CollisionBody* body1, CollisionBody* body2); + static bodypair computeBodiesIndexPair(Entity body1Entity, Entity body2Entity); // -------------------- Friendship -------------------- // @@ -192,13 +188,13 @@ inline OverlappingPair::OverlappingPairId OverlappingPair::getId() const { return mPairID; } -// Return the pointer to first body -inline ProxyShape* OverlappingPair::getShape1() const { +// Return the entity of the first proxy-shape +inline Entity OverlappingPair::getProxyShape1() const { return mProxyShape1; } -// Return the pointer to second body -inline ProxyShape* OverlappingPair::getShape2() const { +// Return the entity of the second proxy-shape +inline Entity OverlappingPair::getProxyShape2() const { return mProxyShape2; } @@ -225,13 +221,12 @@ inline OverlappingPair::OverlappingPairId OverlappingPair::computeID(int shape1B } // Return the pair of bodies index -inline bodypair OverlappingPair::computeBodiesIndexPair(CollisionBody* body1, - CollisionBody* body2) { +inline bodypair OverlappingPair::computeBodiesIndexPair(Entity body1Entity, Entity body2Entity) { // Construct the pair of body index - bodypair indexPair = body1->getEntity().id < body2->getEntity().id ? - bodypair(body1->getEntity(), body2->getEntity()) : - bodypair(body2->getEntity(), body1->getEntity()); + bodypair indexPair = body1Entity.id < body2Entity.id ? + bodypair(body1Entity, body2Entity) : + bodypair(body2Entity, body1Entity); assert(indexPair.first != indexPair.second); return indexPair; } @@ -241,12 +236,6 @@ inline MemoryAllocator& OverlappingPair::getTemporaryAllocator() { return mTempMemoryAllocator; } -// Return true if one of the shapes of the pair is a concave shape -inline bool OverlappingPair::hasConcaveShape() const { - return !getShape1()->getCollisionShape()->isConvex() || - !getShape2()->getCollisionShape()->isConvex(); -} - // Return the last frame collision info for a given pair of shape ids inline LastFrameCollisionInfo* OverlappingPair::getLastFrameCollisionInfo(uint shapeId1, uint shapeId2) const { return mLastFrameCollisionInfos[ShapeIdPair(shapeId1, shapeId2)]; diff --git a/src/systems/BroadPhaseSystem.cpp b/src/systems/BroadPhaseSystem.cpp index 08aea7f8..120eba23 100644 --- a/src/systems/BroadPhaseSystem.cpp +++ b/src/systems/BroadPhaseSystem.cpp @@ -51,14 +51,16 @@ BroadPhaseSystem::BroadPhaseSystem(CollisionDetectionSystem& collisionDetection, } // Return true if the two broad-phase collision shapes are overlapping -// TODO : Use proxy-shape entities in parameters -bool BroadPhaseSystem::testOverlappingShapes(const ProxyShape* shape1, const ProxyShape* shape2) const { +bool BroadPhaseSystem::testOverlappingShapes(Entity proxyShape1Entity, Entity proxyShape2Entity) const { - if (shape1->getBroadPhaseId() == -1 || shape2->getBroadPhaseId() == -1) return false; + const int32 shape1BroadPhaseId = mProxyShapesComponents.getBroadPhaseId(proxyShape1Entity); + const int32 shape2BroadPhaseId = mProxyShapesComponents.getBroadPhaseId(proxyShape2Entity); + + if (shape1BroadPhaseId == -1 || shape2BroadPhaseId == -1) return false; // Get the two AABBs of the collision shapes - const AABB& aabb1 = mDynamicAABBTree.getFatAABB(shape1->getBroadPhaseId()); - const AABB& aabb2 = mDynamicAABBTree.getFatAABB(shape2->getBroadPhaseId()); + const AABB& aabb1 = mDynamicAABBTree.getFatAABB(shape1BroadPhaseId); + const AABB& aabb2 = mDynamicAABBTree.getFatAABB(shape2BroadPhaseId); // Check if the two AABBs are overlapping return aabb1.testCollision(aabb2); diff --git a/src/systems/BroadPhaseSystem.h b/src/systems/BroadPhaseSystem.h index a6ae9815..8e44f19e 100644 --- a/src/systems/BroadPhaseSystem.h +++ b/src/systems/BroadPhaseSystem.h @@ -189,7 +189,7 @@ class BroadPhaseSystem { ProxyShape* getProxyShapeForBroadPhaseId(int broadPhaseId) const; /// Return true if the two broad-phase collision shapes are overlapping - bool testOverlappingShapes(const ProxyShape* shape1, const ProxyShape* shape2) const; + bool testOverlappingShapes(Entity proxyShape1Entity, Entity proxyShape2Entity) const; /// Return the fat AABB of a given broad-phase shape const AABB& getFatAABB(int broadPhaseId) const; diff --git a/src/systems/CollisionDetectionSystem.cpp b/src/systems/CollisionDetectionSystem.cpp index 5dea49e9..9ac8c70a 100644 --- a/src/systems/CollisionDetectionSystem.cpp +++ b/src/systems/CollisionDetectionSystem.cpp @@ -82,7 +82,7 @@ CollisionDetectionSystem::CollisionDetectionSystem(CollisionWorld* world, ProxyS // Compute the collision detection void CollisionDetectionSystem::computeCollisionDetection() { - RP3D_PROFILE("CollisionDetection::computeCollisionDetection()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::computeCollisionDetection()", mProfiler); // Compute the broad-phase collision detection computeBroadPhase(); @@ -97,7 +97,7 @@ void CollisionDetectionSystem::computeCollisionDetection() { // Compute the broad-phase collision detection void CollisionDetectionSystem::computeBroadPhase() { - RP3D_PROFILE("CollisionDetection::computeBroadPhase()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::computeBroadPhase()", mProfiler); // Ask the broad-phase to compute all the shapes overlapping the shapes that // have moved or have been added in the last frame. This call can only add new @@ -120,11 +120,8 @@ void CollisionDetectionSystem::removeNonOverlappingPairs() { OverlappingPair* pair = it->second; - ProxyShape* shape1 = pair->getShape1(); - ProxyShape* shape2 = pair->getShape2(); - // Check if the two shapes are still overlapping. Otherwise, we destroy the overlapping pair - if (!mBroadPhaseSystem.testOverlappingShapes(shape1, shape2)) { + if (!mBroadPhaseSystem.testOverlappingShapes(pair->getProxyShape1(), pair->getProxyShape2())) { // Destroy the overlapping pair pair->~OverlappingPair(); @@ -154,12 +151,12 @@ void CollisionDetectionSystem::updateOverlappingPairs(const List> if (nodePair.first != nodePair.second) { // Get the two proxy-shapes - Entity proxyShape1Entity = mMapBroadPhaseIdToProxyShapeEntity[nodePair.first]; - Entity proxyShape2Entity = mMapBroadPhaseIdToProxyShapeEntity[nodePair.second]; + const Entity proxyShape1Entity = mMapBroadPhaseIdToProxyShapeEntity[nodePair.first]; + const Entity proxyShape2Entity = mMapBroadPhaseIdToProxyShapeEntity[nodePair.second]; // Get the two bodies - Entity body1Entity = mProxyShapesComponents.getBody(proxyShape1Entity); - Entity body2Entity = mProxyShapesComponents.getBody(proxyShape2Entity); + const Entity body1Entity = mProxyShapesComponents.getBody(proxyShape1Entity); + const Entity body2Entity = mProxyShapesComponents.getBody(proxyShape2Entity); // If the two proxy collision shapes are from the same body, skip it if (body1Entity != body2Entity) { @@ -212,14 +209,11 @@ void CollisionDetectionSystem::computeMiddlePhase(OverlappingPairMap& overlappin OverlappingPair* pair = it->second; - // Make all the last frame collision info obsolete - pair->makeLastFrameCollisionInfosObsolete(); + // Remove the obsolete last frame collision infos and mark all the others as obsolete + pair->clearObsoleteLastFrameCollisionInfos(); - const Entity proxyShape1Entity = pair->getShape1()->getEntity(); - const Entity proxyShape2Entity = pair->getShape2()->getEntity(); - - ProxyShape* shape1 = pair->getShape1(); - ProxyShape* shape2 = pair->getShape2(); + const Entity proxyShape1Entity = pair->getProxyShape1(); + const Entity proxyShape2Entity = pair->getProxyShape2(); assert(mProxyShapesComponents.getBroadPhaseId(proxyShape1Entity) != -1); assert(mProxyShapesComponents.getBroadPhaseId(proxyShape2Entity) != -1); @@ -229,11 +223,8 @@ void CollisionDetectionSystem::computeMiddlePhase(OverlappingPairMap& overlappin if ((mProxyShapesComponents.getCollideWithMaskBits(proxyShape1Entity) & mProxyShapesComponents.getCollisionCategoryBits(proxyShape2Entity)) != 0 && (mProxyShapesComponents.getCollisionCategoryBits(proxyShape1Entity) & mProxyShapesComponents.getCollideWithMaskBits(proxyShape2Entity)) != 0) { - CollisionBody* const body1 = shape1->getBody(); - CollisionBody* const body2 = shape2->getBody(); - - const Entity body1Entity = body1->getEntity(); - const Entity body2Entity = body2->getEntity(); + const Entity body1Entity = mProxyShapesComponents.getBody(proxyShape1Entity); + const Entity body2Entity = mProxyShapesComponents.getBody(proxyShape2Entity); const bool isStaticRigidBody1 = mWorld->mRigidBodyComponents.hasComponent(body1Entity) && mWorld->mRigidBodyComponents.getBodyType(body1Entity) == BodyType::STATIC; @@ -246,22 +237,25 @@ void CollisionDetectionSystem::computeMiddlePhase(OverlappingPairMap& overlappin if (!isBody1Active && !isBody2Active) continue; // Check if the bodies are in the set of bodies that cannot collide between each other - bodypair bodiesIndex = OverlappingPair::computeBodiesIndexPair(body1, body2); + bodypair bodiesIndex = OverlappingPair::computeBodiesIndexPair(body1Entity, body2Entity); if (mNoCollisionPairs.contains(bodiesIndex) > 0) continue; - bool isShape1Convex = shape1->getCollisionShape()->isConvex(); - bool isShape2Convex = shape2->getCollisionShape()->isConvex(); + CollisionShape* collisionShape1 = mProxyShapesComponents.getCollisionShape(proxyShape1Entity); + CollisionShape* collisionShape2 = mProxyShapesComponents.getCollisionShape(proxyShape2Entity); + + const bool isShape1Convex = collisionShape1->isConvex(); + const bool isShape2Convex = collisionShape2->isConvex(); // If both shapes are convex if (isShape1Convex && isShape2Convex) { // Select the narrow phase algorithm to use according to the two collision shapes - NarrowPhaseAlgorithmType algorithmType = mCollisionDispatch.selectNarrowPhaseAlgorithm(shape1->getCollisionShape()->getType(), - shape2->getCollisionShape()->getType()); + NarrowPhaseAlgorithmType algorithmType = mCollisionDispatch.selectNarrowPhaseAlgorithm(collisionShape1->getType(), + collisionShape2->getType()); // No middle-phase is necessary, simply create a narrow phase info // for the narrow-phase collision detection - narrowPhaseInput.addNarrowPhaseTest(pair, shape1->getCollisionShape(), shape2->getCollisionShape(), + narrowPhaseInput.addNarrowPhaseTest(pair, collisionShape1, collisionShape2, mProxyShapesComponents.getLocalToWorldTransform(proxyShape1Entity), mProxyShapesComponents.getLocalToWorldTransform(proxyShape2Entity), algorithmType, mMemoryManager.getSingleFrameAllocator()); @@ -277,9 +271,6 @@ void CollisionDetectionSystem::computeMiddlePhase(OverlappingPairMap& overlappin // Not handled continue; } - - // Remove the obsolete last frame collision infos - pair->clearObsoleteLastFrameCollisionInfos(); } } } @@ -288,10 +279,10 @@ void CollisionDetectionSystem::computeMiddlePhase(OverlappingPairMap& overlappin void CollisionDetectionSystem::computeConvexVsConcaveMiddlePhase(OverlappingPair* pair, MemoryAllocator& allocator, NarrowPhaseInput& narrowPhaseInput) { - RP3D_PROFILE("CollisionDetection::computeConvexVsConcaveMiddlePhase()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::computeConvexVsConcaveMiddlePhase()", mProfiler); - ProxyShape* shape1 = pair->getShape1(); - ProxyShape* shape2 = pair->getShape2(); + ProxyShape* shape1 = mProxyShapesComponents.getProxyShape(pair->getProxyShape1()); + ProxyShape* shape2 = mProxyShapesComponents.getProxyShape(pair->getProxyShape2()); ProxyShape* convexProxyShape; ProxyShape* concaveProxyShape; @@ -350,7 +341,7 @@ void CollisionDetectionSystem::computeConvexVsConcaveMiddlePhase(OverlappingPair #endif - bool isShape1Convex = pair->getShape1()->getCollisionShape()->isConvex(); + bool isShape1Convex = mProxyShapesComponents.getCollisionShape(pair->getProxyShape1())->isConvex(); ProxyShape* shape1 = isShape1Convex ? convexProxyShape : concaveProxyShape; ProxyShape* shape2 = isShape1Convex ? concaveProxyShape : convexProxyShape; @@ -445,7 +436,7 @@ void CollisionDetectionSystem::processAllPotentialContacts(NarrowPhaseInput& nar // Compute the narrow-phase collision detection void CollisionDetectionSystem::computeNarrowPhase() { - RP3D_PROFILE("CollisionDetection::computeNarrowPhase()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::computeNarrowPhase()", mProfiler); MemoryAllocator& allocator = mMemoryManager.getSingleFrameAllocator(); @@ -475,7 +466,7 @@ void CollisionDetectionSystem::computeNarrowPhase() { /// This method returns true if contacts are found. bool CollisionDetectionSystem::computeNarrowPhaseOverlapSnapshot(NarrowPhaseInput& narrowPhaseInput, OverlapCallback* callback) { - RP3D_PROFILE("CollisionDetection::computeNarrowPhaseOverlapSnapshot()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::computeNarrowPhaseOverlapSnapshot()", mProfiler); MemoryAllocator& allocator = mMemoryManager.getPoolAllocator(); @@ -518,7 +509,7 @@ void CollisionDetectionSystem::computeSnapshotContactPairs(NarrowPhaseInput& nar // Convert the potential overlapping bodies for the testOverlap() methods void CollisionDetectionSystem::computeSnapshotContactPairs(NarrowPhaseInfoBatch& narrowPhaseInfoBatch, List>& overlapPairs) const { - RP3D_PROFILE("CollisionDetection::computeSnapshotContactPairs()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::computeSnapshotContactPairs()", mProfiler); // For each narrow phase info object for(uint i=0; i < narrowPhaseInfoBatch.getNbObjects(); i++) { @@ -527,8 +518,8 @@ void CollisionDetectionSystem::computeSnapshotContactPairs(NarrowPhaseInfoBatch& if (narrowPhaseInfoBatch.isColliding[i]) { // Add the pair of bodies in contact into the list - overlapPairs.add(Pair(narrowPhaseInfoBatch.overlappingPairs[i]->getShape1()->getBody()->getEntity(), - narrowPhaseInfoBatch.overlappingPairs[i]->getShape2()->getBody()->getEntity())); + overlapPairs.add(Pair(mProxyShapesComponents.getBody(narrowPhaseInfoBatch.overlappingPairs[i]->getProxyShape1()), + mProxyShapesComponents.getBody(narrowPhaseInfoBatch.overlappingPairs[i]->getProxyShape2()))); } narrowPhaseInfoBatch.resetContactPoints(i); @@ -539,7 +530,7 @@ void CollisionDetectionSystem::computeSnapshotContactPairs(NarrowPhaseInfoBatch& // This method returns true if contacts are found. bool CollisionDetectionSystem::computeNarrowPhaseCollisionSnapshot(NarrowPhaseInput& narrowPhaseInput, CollisionCallback& callback) { - RP3D_PROFILE("CollisionDetection::computeNarrowPhaseCollisionSnapshot()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::computeNarrowPhaseCollisionSnapshot()", mProfiler); MemoryAllocator& allocator = mMemoryManager.getPoolAllocator(); @@ -675,7 +666,7 @@ void CollisionDetectionSystem::createSnapshotContacts(List& contact List& potentialContactManifolds, List& potentialContactPoints) { - RP3D_PROFILE("CollisionDetection::createSnapshotContacts()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::createSnapshotContacts()", mProfiler); contactManifolds.reserve(contactPairs.size()); contactPoints.reserve(contactManifolds.size()); @@ -830,8 +821,8 @@ void CollisionDetectionSystem::removeProxyCollisionShape(ProxyShape* proxyShape) OverlappingPair* pair = it->second; - if (pair->getShape1()->getBroadPhaseId() == proxyShape->getBroadPhaseId()|| - pair->getShape2()->getBroadPhaseId() == proxyShape->getBroadPhaseId()) { + if (mProxyShapesComponents.getBroadPhaseId(pair->getProxyShape1()) == proxyShape->getBroadPhaseId() || + mProxyShapesComponents.getBroadPhaseId(pair->getProxyShape2()) == proxyShape->getBroadPhaseId()) { // TODO : Remove all the contact manifold of the overlapping pair from the contact manifolds list of the two bodies involved @@ -856,7 +847,7 @@ void CollisionDetectionSystem::raycast(RaycastCallback* raycastCallback, const Ray& ray, unsigned short raycastWithCategoryMaskBits) const { - RP3D_PROFILE("CollisionDetection::raycast()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::raycast()", mProfiler); RaycastTest rayCastTest(raycastCallback); @@ -873,7 +864,7 @@ void CollisionDetectionSystem::processPotentialContacts(NarrowPhaseInfoBatch& na List* contactPairs, Map>& mapBodyToContactPairs) { - RP3D_PROFILE("CollisionDetection::processPotentialContacts()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::processPotentialContacts()", mProfiler); // For each narrow phase info object for(uint i=0; i < narrowPhaseInfoBatch.getNbObjects(); i++) { @@ -952,16 +943,18 @@ void CollisionDetectionSystem::processPotentialContacts(NarrowPhaseInfoBatch& na // If the overlapping pair contact does not exists yet if (pairContact == nullptr) { - Entity body1Entity = narrowPhaseInfoBatch.overlappingPairs[i]->getShape1()->getBody()->getEntity(); - Entity body2Entity = narrowPhaseInfoBatch.overlappingPairs[i]->getShape2()->getBody()->getEntity(); + const Entity proxyShape1Entity = narrowPhaseInfoBatch.overlappingPairs[i]->getProxyShape1(); + const Entity proxyShape2Entity = narrowPhaseInfoBatch.overlappingPairs[i]->getProxyShape2(); + + const Entity body1Entity = mProxyShapesComponents.getBody(proxyShape1Entity); + const Entity body2Entity = mProxyShapesComponents.getBody(proxyShape2Entity); assert(!mWorld->mCollisionBodyComponents.getIsEntityDisabled(body1Entity) || !mWorld->mCollisionBodyComponents.getIsEntityDisabled(body2Entity)); // TODO : We should probably use a single frame allocator here const uint newContactPairIndex = contactPairs->size(); ContactPair overlappingPairContact(pairId, body1Entity, body2Entity, - narrowPhaseInfoBatch.overlappingPairs[i]->getShape1()->getEntity(), - narrowPhaseInfoBatch.overlappingPairs[i]->getShape2()->getEntity(), + proxyShape1Entity, proxyShape2Entity, newContactPairIndex, mMemoryManager.getPoolAllocator()); contactPairs->add(overlappingPairContact); pairContact = &((*contactPairs)[newContactPairIndex]); @@ -1010,7 +1003,7 @@ void CollisionDetectionSystem::reducePotentialContactManifolds(List List& potentialContactManifolds, const List& potentialContactPoints) const { - RP3D_PROFILE("CollisionDetection::reducePotentialContactManifolds()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::reducePotentialContactManifolds()", mProfiler); // Reduce the number of potential contact manifolds in a contact pair for (uint i=0; i < contactPairs->size(); i++) { @@ -1057,7 +1050,7 @@ void CollisionDetectionSystem::reducePotentialContactManifolds(List // If there are two many contact points in the manifold if (manifold.potentialContactPointsIndices.size() > MAX_CONTACT_POINTS_IN_MANIFOLD) { - Transform shape1LocalToWorldTransoform = mOverlappingPairs[manifold.pairId]->getShape1()->getLocalToWorldTransform(); + Transform shape1LocalToWorldTransoform = mProxyShapesComponents.getLocalToWorldTransform(mOverlappingPairs[manifold.pairId]->getProxyShape1()); // Reduce the number of contact points in the manifold reduceContactPoints(manifold, shape1LocalToWorldTransoform, potentialContactPoints); @@ -1280,7 +1273,7 @@ void CollisionDetectionSystem::reportContacts() { void CollisionDetectionSystem::reportContacts(CollisionCallback& callback, List* contactPairs, List* manifolds, List* contactPoints) { - RP3D_PROFILE("CollisionDetection::reportContacts()", mProfiler); + RP3D_PROFILE("CollisionDetectionSystem::reportContacts()", mProfiler); // If there are contacts if (contactPairs->size() > 0) { @@ -1420,12 +1413,12 @@ void CollisionDetectionSystem::filterOverlappingPairs(Entity bodyEntity, Overlap OverlappingPair* pair = it->second; - if (pair->getShape1()->getBody()->getEntity() == bodyEntity || pair->getShape2()->getBody()->getEntity() == bodyEntity) { + if (mProxyShapesComponents.getBody(pair->getProxyShape1()) == bodyEntity || + mProxyShapesComponents.getBody(pair->getProxyShape2()) == bodyEntity) { outFilteredPairs.add(Pair, OverlappingPair*>(it->first, pair)); } } - } // Filter the overlapping pairs to keep only the pairs where two given bodies are involved @@ -1436,13 +1429,12 @@ void CollisionDetectionSystem::filterOverlappingPairs(Entity body1Entity, Entity OverlappingPair* pair = it->second; - if ((pair->getShape1()->getBody()->getEntity() == body1Entity && pair->getShape2()->getBody()->getEntity() == body2Entity) || - (pair->getShape1()->getBody()->getEntity() == body2Entity && pair->getShape2()->getBody()->getEntity() == body1Entity)) { + if ((mProxyShapesComponents.getBody(pair->getProxyShape1()) == body1Entity && mProxyShapesComponents.getBody(pair->getProxyShape2()) == body2Entity) || + (mProxyShapesComponents.getBody(pair->getProxyShape1()) == body2Entity && mProxyShapesComponents.getBody(pair->getProxyShape2()) == body1Entity)) { outFilteredPairs.add(Pair, OverlappingPair*>(it->first, pair)); } } - } // Return the world event listener diff --git a/src/systems/CollisionDetectionSystem.h b/src/systems/CollisionDetectionSystem.h index 87a27e86..525525ce 100644 --- a/src/systems/CollisionDetectionSystem.h +++ b/src/systems/CollisionDetectionSystem.h @@ -292,10 +292,10 @@ class CollisionDetectionSystem { void updateProxyShapes(decimal timeStep); /// Add a pair of bodies that cannot collide with each other - void addNoCollisionPair(CollisionBody* body1, CollisionBody* body2); + void addNoCollisionPair(Entity body1Entity, Entity body2Entity); /// Remove a pair of bodies that cannot collide with each other - void removeNoCollisionPair(CollisionBody* body1, CollisionBody* body2); + void removeNoCollisionPair(Entity body1Entity, Entity body2Entity); /// Ask for a collision shape to be tested again during broad-phase. void askForBroadPhaseCollisionCheck(ProxyShape* shape); @@ -373,15 +373,13 @@ inline void CollisionDetectionSystem::addProxyCollisionShape(ProxyShape* proxySh } // Add a pair of bodies that cannot collide with each other -inline void CollisionDetectionSystem::addNoCollisionPair(CollisionBody* body1, - CollisionBody* body2) { - mNoCollisionPairs.add(OverlappingPair::computeBodiesIndexPair(body1, body2)); +inline void CollisionDetectionSystem::addNoCollisionPair(Entity body1Entity, Entity body2Entity) { + mNoCollisionPairs.add(OverlappingPair::computeBodiesIndexPair(body1Entity, body2Entity)); } // Remove a pair of bodies that cannot collide with each other -inline void CollisionDetectionSystem::removeNoCollisionPair(CollisionBody* body1, - CollisionBody* body2) { - mNoCollisionPairs.remove(OverlappingPair::computeBodiesIndexPair(body1, body2)); +inline void CollisionDetectionSystem::removeNoCollisionPair(Entity body1Entity, Entity body2Entity) { + mNoCollisionPairs.remove(OverlappingPair::computeBodiesIndexPair(body1Entity, body2Entity)); } // Ask for a collision shape to be tested again during broad-phase.