//------------------------------------------------------------------------ // NodeyBSPTree::ProcessAllTriangles_R //------------------------------------------------------------------------ // void NodeyBSPTree::ProcessAllTriangles_R( const Node* pNode, const AABB& aabb, btTriangleCallback* callback ) const { if ( pNode->IsInternal() ) { const E_PlaneSide eRelation = pNode->GetPlane().ClassifyVolumeRelation( aabb ); if ( eRelation == SIDE_FRONT ) { ProcessAllTriangles_R( pNode->FrontChild, aabb, callback ); } else if ( eRelation == SIDE_BACK ) { ProcessAllTriangles_R( pNode->BackChild, aabb, callback ); } else // SIDE_CROSS { #if 0 // Process all triangles in this node. for ( TIndex iTriIndex = 0; iTriIndex <= pNode->Data.NumTriangles; ++iTriIndex ) { const IndexTriple & rTri = m_pRenderMesh->Triangles[ iTriIndex + pNode->Data.FirstTriangle ]; btVector3 triangle[3]; for ( u32 i = 0; i < 3; i++ ) { Assign( triangle[i], m_pRenderMesh->GetPos( rTri[i] ) ); } if ( TestTriangleAgainstAabb2( triangle, Convert(aabb.MinEdge), Convert(aabb.MaxEdge) ) ) { callback->processTriangle( triangle, 0, (int)iTriIndex ); } } #else const Polygon * polygon = pNode->Faces; while ( polygon != NULL ) { const u32 numTriangles = polygon->NumVertices() - 2; const Vec3D & basePoint = polygon->Vertices[ 0 ].Pos; btVector3 triangle[3]; Assign( triangle[0], basePoint ); for ( u32 i = 1; i < numTriangles + 1; i++ ) { Assign( triangle[ 1 ], polygon->Vertices[ i ].Pos ); Assign( triangle[ 2 ], polygon->Vertices[ i+1 ].Pos ); //if ( TestTriangleAgainstAabb2( triangle, Convert(aabb.MinEdge), Convert(aabb.MaxEdge) ) ) { callback->processTriangle( triangle, 0, i ); } } polygon = polygon->GetNext(); } #endif ProcessAllTriangles_R( pNode->FrontChild, aabb, callback ); ProcessAllTriangles_R( pNode->BackChild, aabb, callback ); } }//End If Node Is Internal }
virtual void internalProcessTriangleIndex(btVector3* triangle,int partId,int triangleIndex) { if (TestTriangleAgainstAabb2(&triangle[0],m_aabbMin,m_aabbMax)) { //check aabb in triangle-space, before doing this m_callback->processTriangle(triangle,partId,triangleIndex); } }
void btConvexTriangleCallback::processTriangle(btVector3* triangle,int partId, int triangleIndex) { if (!TestTriangleAgainstAabb2(triangle, m_aabbMin, m_aabbMax)) { return; } //just for debugging purposes //printf("triangle %d",m_triangleCount++); const btCollisionObject* ob = const_cast<btCollisionObject*>(m_triBodyWrap->getCollisionObject()); btCollisionAlgorithmConstructionInfo ci; ci.m_dispatcher1 = m_dispatcher; //const btCollisionObject* ob = static_cast<btCollisionObject*>(m_triBodyWrap->getCollisionObject()); #if 0 ///debug drawing of the overlapping triangles if (m_dispatchInfoPtr && m_dispatchInfoPtr->m_debugDraw && (m_dispatchInfoPtr->m_debugDraw->getDebugMode() &btIDebugDraw::DBG_DrawWireframe )) { btVector3 color(1,1,0); btTransform& tr = ob->getWorldTransform(); m_dispatchInfoPtr->m_debugDraw->drawLine(tr(triangle[0]),tr(triangle[1]),color); m_dispatchInfoPtr->m_debugDraw->drawLine(tr(triangle[1]),tr(triangle[2]),color); m_dispatchInfoPtr->m_debugDraw->drawLine(tr(triangle[2]),tr(triangle[0]),color); } #endif if (m_convexBodyWrap->getCollisionShape()->isConvex()) { btTriangleShape tm(triangle[0],triangle[1],triangle[2]); tm.setMargin(m_collisionMarginTriangle); btCollisionObjectWrapper triObWrap(m_triBodyWrap,&tm,m_triBodyWrap->getCollisionObject(),m_triBodyWrap->getWorldTransform(),partId,triangleIndex);//correct transform? btCollisionAlgorithm* colAlgo = ci.m_dispatcher1->findAlgorithm(m_convexBodyWrap,&triObWrap,m_manifoldPtr); const btCollisionObjectWrapper* tmpWrap = 0; if (m_resultOut->getBody0Internal() == m_triBodyWrap->getCollisionObject()) { tmpWrap = m_resultOut->getBody0Wrap(); m_resultOut->setBody0Wrap(&triObWrap); m_resultOut->setShapeIdentifiersA(partId,triangleIndex); } else { tmpWrap = m_resultOut->getBody1Wrap(); m_resultOut->setBody1Wrap(&triObWrap); m_resultOut->setShapeIdentifiersB(partId,triangleIndex); } colAlgo->processCollision(m_convexBodyWrap,&triObWrap,*m_dispatchInfoPtr,m_resultOut); if (m_resultOut->getBody0Internal() == m_triBodyWrap->getCollisionObject()) { m_resultOut->setBody0Wrap(tmpWrap); } else { m_resultOut->setBody1Wrap(tmpWrap); } colAlgo->~btCollisionAlgorithm(); ci.m_dispatcher1->freeCollisionAlgorithm(colAlgo); } }
void btConvexTriangleCallback::processTriangle(btVector3* triangle, int partId, int triangleIndex) { if (!TestTriangleAgainstAabb2(triangle, m_aabbMin, m_aabbMax)) { return; } //just for debugging purposes //printf("triangle %d", m_triangleCount++); const btCollisionObject* ob = const_cast<btCollisionObject*>(m_triBodyWrap->getCollisionObject()); btCollisionAlgorithmConstructionInfo ci; ci.m_dispatcher1 = m_dispatcher; //const btCollisionObject* ob = static_cast<btCollisionObject*>(m_triBodyWrap->getCollisionObject()); #if 1 ///debug drawing of the overlapping triangles if (m_dispatchInfoPtr && m_dispatchInfoPtr->m_debugDraw && (m_dispatchInfoPtr->m_debugDraw->getDebugMode() &btIDebugDraw::DBG_DrawWireframe )) { btVector3 color(1,1,0); const btTransform& tr = ob->getWorldTransform(); m_dispatchInfoPtr->m_debugDraw->drawLine(tr(triangle[0]), tr(triangle[1]), color); m_dispatchInfoPtr->m_debugDraw->drawLine(tr(triangle[1]), tr(triangle[2]), color); m_dispatchInfoPtr->m_debugDraw->drawLine(tr(triangle[2]), tr(triangle[0]), color); } #endif if (m_convexBodyWrap->getCollisionShape()->isConvex()) { btTriangleShape tm(triangle[0], triangle[1], triangle[2]); tm.setMargin(m_collisionMarginTriangle); btCollisionObjectWrapper triObWrap(m_triBodyWrap, &tm, m_triBodyWrap->getCollisionObject(), m_triBodyWrap->getWorldTransform(), partId, triangleIndex);//correct transform? btCollisionAlgorithm* colAlgo = ci.m_dispatcher1->findAlgorithm(m_convexBodyWrap, &triObWrap, m_manifoldPtr); const btCollisionObjectWrapper* tmpWrap = 0; if (m_resultOut->getBody0Internal() == m_triBodyWrap->getCollisionObject()) { tmpWrap = m_resultOut->getBody0Wrap(); m_resultOut->setBody0Wrap(&triObWrap); m_resultOut->setShapeIdentifiersA(partId, triangleIndex); } else { tmpWrap = m_resultOut->getBody1Wrap(); m_resultOut->setBody1Wrap(&triObWrap); m_resultOut->setShapeIdentifiersB(partId, triangleIndex); } colAlgo->processCollision(m_convexBodyWrap, &triObWrap, *m_dispatchInfoPtr, m_resultOut); btIDebugDraw *drawer = NULL; if (m_dispatchInfoPtr) { drawer = m_dispatchInfoPtr->m_debugDraw; } // Compensate for any internal edge contact points btPersistentManifold *manifold = m_resultOut->getPersistentManifold(); for (int i = 0; i < manifold->getNumContacts(); i++) { btManifoldPoint &pt = manifold->getContactPoint(i); btAdjustInternalEdgeContacts(pt, &triObWrap, m_convexBodyWrap, partId, triangleIndex, BT_TRIANGLE_CONVEX_DOUBLE_SIDED | BT_TRIANGLE_CONCAVE_DOUBLE_SIDED, drawer); } if (m_resultOut->getBody0Internal() == m_triBodyWrap->getCollisionObject()) { m_resultOut->setBody0Wrap(tmpWrap); } else { m_resultOut->setBody1Wrap(tmpWrap); } colAlgo->~btCollisionAlgorithm(); ci.m_dispatcher1->freeCollisionAlgorithm(colAlgo); } }