Cleaned up/simplified construction of a btRigidBody

Fixed memoryleak in btOptimizedBvh (delete []m_contiguousNodes;)
Changed DemoApplication::localCreateRigidBody, so it adds the rigidbody to the btDynamicsWorld.
Added check for duplicate objects in world when adding.
Added assert to prevent setLinearVelocity on static rigidbodies
Added btCollisionFilterGroups to btBroadphaseProxy
removed duplicate 'btBroadphaseProxy*	m_broadphaseProxy;' in btRigidBody
This commit is contained in:
ejcoumans
2006-10-04 23:46:27 +00:00
parent d85ecfe5c2
commit 323a1046fd
18 changed files with 96 additions and 59 deletions

View File

@@ -72,9 +72,7 @@ public:
//this create an internal copy of the vertices //this create an internal copy of the vertices
btCollisionShape* shape = new btConvexHullShape(&vertices[0],vertices.size()); btCollisionShape* shape = new btConvexHullShape(&vertices[0],vertices.size());
btRigidBody* body = m_demoApp->localCreateRigidBody(isDynamic, mass, startTransform,shape); btRigidBody* body = m_demoApp->localCreateRigidBody(mass, startTransform,shape);
assert(body);
m_demoApp->getDynamicsWorld()->addCollisionObject( body );
} }
} }
}; };

View File

@@ -243,6 +243,7 @@ void CcdPhysicsDemo::initPhysics()
btSequentialImpulseConstraintSolver* solver = new btSequentialImpulseConstraintSolver; btSequentialImpulseConstraintSolver* solver = new btSequentialImpulseConstraintSolver;
m_dynamicsWorld = new btDiscreteDynamicsWorld(dispatcher,broadphase,solver); m_dynamicsWorld = new btDiscreteDynamicsWorld(dispatcher,broadphase,solver);
//setGravity(btVector3(0,0,1));
m_dynamicsWorld->setDebugDrawer(&debugDrawer); m_dynamicsWorld->setDebugDrawer(&debugDrawer);
@@ -326,9 +327,8 @@ void CcdPhysicsDemo::initPhysics()
if (!isDyna) if (!isDyna)
mass = 0.f; mass = 0.f;
btRigidBody* body = localCreateRigidBody(isDyna,mass,trans,shape); btRigidBody* body = localCreateRigidBody(mass,trans,shape);
m_dynamicsWorld->addCollisionObject(body);
// Only do CCD if motion in one timestep (1.f/60.f) exceeds CUBE_HALF_EXTENTS // Only do CCD if motion in one timestep (1.f/60.f) exceeds CUBE_HALF_EXTENTS
body->m_ccdSquareMotionTreshold = CUBE_HALF_EXTENTS; body->m_ccdSquareMotionTreshold = CUBE_HALF_EXTENTS;

View File

@@ -81,8 +81,19 @@ class MyColladaConverter : public ColladaConverter
btCollisionShape* shape) btCollisionShape* shape)
{ {
btRigidBody* body = m_demoApp->localCreateRigidBody(isDynamic, mass, startTransform,shape); if (!isDynamic && (mass != 0.f))
m_demoApp->getDynamicsWorld()->addCollisionObject(body); {
printf("Warning: non-dynamic objects needs to have zero mass!\n");
mass = 0.f;
}
if (isDynamic && (mass == 0.f))
{
printf("Warning: dynamic rigidbodies needs nonzero mass!\n");
mass = 1.f;
}
btRigidBody* body = m_demoApp->localCreateRigidBody(mass, startTransform,shape);
return body; return body;
} }

View File

@@ -159,11 +159,10 @@ void ConcaveDemo::initPhysics()
startTransform.setIdentity(); startTransform.setIdentity();
startTransform.setOrigin(btVector3(0,0,0)); startTransform.setOrigin(btVector3(0,0,0));
btRigidBody* staticBody = localCreateRigidBody(isDynamic, mass, startTransform,trimeshShape); btRigidBody* staticBody = localCreateRigidBody(mass, startTransform,trimeshShape);
staticBody->m_collisionFlags |=btCollisionObject::isStatic; staticBody->m_collisionFlags |=btCollisionObject::isStatic;
getDynamicsWorld()->addCollisionObject(staticBody);
//enable custom material callback //enable custom material callback
staticBody->m_collisionFlags |= btCollisionObject::customMaterialCallback; staticBody->m_collisionFlags |= btCollisionObject::customMaterialCallback;
@@ -172,7 +171,7 @@ void ConcaveDemo::initPhysics()
{ {
btCollisionShape* boxShape = new btBoxShape(btVector3(1,1,1)); btCollisionShape* boxShape = new btBoxShape(btVector3(1,1,1));
startTransform.setOrigin(btVector3(2*i,1,1)); startTransform.setOrigin(btVector3(2*i,1,1));
getDynamicsWorld()->addCollisionObject(localCreateRigidBody(true, 1, startTransform,boxShape)); localCreateRigidBody(1, startTransform,boxShape);
} }
} }

View File

@@ -62,16 +62,13 @@ void ConstraintDemo::initPhysics()
trans.setIdentity(); trans.setIdentity();
trans.setOrigin(btVector3(0,20,0)); trans.setOrigin(btVector3(0,20,0));
bool isDynamic = false; float mass = 0.f;
float mass = 1.f; btRigidBody* body0 = localCreateRigidBody( mass,trans,shape);
btRigidBody* body0 = localCreateRigidBody( isDynamic,mass,trans,shape);
getDynamicsWorld()->addCollisionObject(body0);
trans.setOrigin(btVector3(2*CUBE_HALF_EXTENTS,20,0)); trans.setOrigin(btVector3(2*CUBE_HALF_EXTENTS,20,0));
isDynamic = true;
btRigidBody* body1 = localCreateRigidBody( isDynamic,mass,trans,shape); mass = 1.f;
btRigidBody* body1 = localCreateRigidBody( mass,trans,shape);
body1->setDamping(0.3,0.3); body1->setDamping(0.3,0.3);
getDynamicsWorld()->addCollisionObject(body1);
clientResetScene(); clientResetScene();

View File

@@ -91,7 +91,7 @@ void ConvexDecompositionDemo::initPhysics(const char* filename)
startTransform.setIdentity(); startTransform.setIdentity();
startTransform.setOrigin(btVector3(0,-4,0)); startTransform.setOrigin(btVector3(0,-4,0));
localCreateRigidBody(false,0,startTransform,new btBoxShape(btVector3(30,2,30))); localCreateRigidBody(0.f,startTransform,new btBoxShape(btVector3(30,2,30)));
class MyConvexDecomposition : public ConvexDecomposition::ConvexDecompInterface class MyConvexDecomposition : public ConvexDecomposition::ConvexDecompInterface
{ {
@@ -192,8 +192,7 @@ void ConvexDecompositionDemo::initPhysics(const char* filename)
btTransform trans; btTransform trans;
trans.setIdentity(); trans.setIdentity();
trans.setOrigin(centroid); trans.setOrigin(centroid);
btRigidBody* body = m_convexDemo->localCreateRigidBody(isDynamic, mass, trans,convexShape); btRigidBody* body = m_convexDemo->localCreateRigidBody( mass, trans,convexShape);
m_convexDemo->getDynamicsWorld()->addCollisionObject(body);
mBaseCount+=result.mHullVcount; // advance the 'base index' counter. mBaseCount+=result.mHullVcount; // advance the 'base index' counter.
@@ -237,7 +236,7 @@ void ConvexDecompositionDemo::initPhysics(const char* filename)
startTransform.setIdentity(); startTransform.setIdentity();
startTransform.setOrigin(btVector3(20,2,0)); startTransform.setOrigin(btVector3(20,2,0));
localCreateRigidBody(isDynamic, mass, startTransform,convexShape); localCreateRigidBody(mass, startTransform,convexShape);
} }

View File

@@ -335,7 +335,7 @@ void DemoApplication::keyboardCallback(unsigned char key, int x, int y)
break; break;
} }
if (getDynamicsWorld()->getDebugDrawer()) if (getDynamicsWorld() && getDynamicsWorld()->getDebugDrawer())
getDynamicsWorld()->getDebugDrawer()->setDebugMode(m_debugMode); getDynamicsWorld()->getDebugDrawer()->setDebugMode(m_debugMode);
glutPostRedisplay(); glutPostRedisplay();
@@ -393,8 +393,7 @@ void DemoApplication::shootBox(const btVector3& destination)
startTransform.setOrigin(camPos); startTransform.setOrigin(camPos);
btCollisionShape* boxShape = new btBoxShape(btVector3(1.f,1.f,1.f)); btCollisionShape* boxShape = new btBoxShape(btVector3(1.f,1.f,1.f));
btRigidBody* body = this->localCreateRigidBody(isDynamic, mass, startTransform,boxShape); btRigidBody* body = this->localCreateRigidBody(mass, startTransform,boxShape);
m_dynamicsWorld->addCollisionObject(body);
btVector3 linVel(destination[0]-camPos[0],destination[1]-camPos[1],destination[2]-camPos[2]); btVector3 linVel(destination[0]-camPos[0],destination[1]-camPos[1],destination[2]-camPos[2]);
linVel.normalize(); linVel.normalize();
@@ -606,30 +605,36 @@ void DemoApplication::mouseMotionFunc(int x,int y)
btRigidBody* DemoApplication::localCreateRigidBody(bool isDynamic, float mass, const btTransform& startTransform,btCollisionShape* shape) btRigidBody* DemoApplication::localCreateRigidBody(float mass, const btTransform& startTransform,btCollisionShape* shape)
{ {
//rigidbody is dynamic if and only if mass is non zero, otherwise static
bool isDynamic = (mass != 0.f);
btVector3 localInertia(0,0,0); btVector3 localInertia(0,0,0);
if (isDynamic) if (isDynamic)
shape->calculateLocalInertia(mass,localInertia); shape->calculateLocalInertia(mass,localInertia);
btMassProps massProps(0.f,localInertia); btRigidBody* body = new btRigidBody(mass,startTransform,shape,localInertia);
btRigidBody* body = new btRigidBody(massProps); //filtering allows to excluded collision pairs, early in the collision pipeline (broadphase)
body->m_collisionShape = shape; bool useFiltering = true;
body->m_worldTransform = startTransform; if (useFiltering)
if (!isDynamic)
{ {
body->m_collisionFlags = btCollisionObject::isStatic;//?? short collisionFilterGroup = isDynamic?
// body->getBroadphaseProxy()->m_collisionFilterGroup = 1;/btCcdConstructionInfo::StaticFilter; btBroadphaseProxy::DefaultFilter :
// body->getBroadphaseProxy()->m_collisionFilterMask = btCcdConstructionInfo::AllFilter ^ btCcdConstructionInfo::StaticFilter; btBroadphaseProxy::StaticFilter;
body->setMassProps( 0.f, localInertia); short collisionFilterMask = isDynamic?
btBroadphaseProxy::AllFilter :
btBroadphaseProxy::AllFilter ^ btBroadphaseProxy::StaticFilter;
m_dynamicsWorld->addCollisionObject(body,collisionFilterGroup,collisionFilterMask);
} else } else
{ {
body->setMassProps( mass, localInertia); //no collision filtering, so always create an overlapping pair, even between static-static etc.
body->m_collisionFlags = 0; m_dynamicsWorld->addCollisionObject(body);
} }
//Bullet uses per-object gravity
body->setGravity(m_gravity); body->setGravity(m_gravity);
return body; return body;

View File

@@ -147,7 +147,7 @@ public:
} }
btVector3 getRayTo(int x,int y); btVector3 getRayTo(int x,int y);
btRigidBody* localCreateRigidBody(bool isDynamic, float mass, const btTransform& startTransform,btCollisionShape* shape); btRigidBody* localCreateRigidBody(float mass, const btTransform& startTransform,btCollisionShape* shape);
///callback methods by glut ///callback methods by glut

View File

@@ -134,8 +134,7 @@ void UserCollisionAlgorithm::initPhysics()
startTransform.setIdentity(); startTransform.setIdentity();
startTransform.setOrigin(btVector3(0,-2,0)); startTransform.setOrigin(btVector3(0,-2,0));
btRigidBody* staticBody= localCreateRigidBody(isDynamic, mass, startTransform,trimeshShape); btRigidBody* staticBody= localCreateRigidBody(mass, startTransform,trimeshShape);
getDynamicsWorld()->addCollisionObject(staticBody);
//enable custom material callback //enable custom material callback
staticBody->m_collisionFlags |= btCollisionObject::customMaterialCallback; staticBody->m_collisionFlags |= btCollisionObject::customMaterialCallback;
@@ -144,12 +143,12 @@ void UserCollisionAlgorithm::initPhysics()
{ {
btCollisionShape* sphereShape = new btSphereShape(1); btCollisionShape* sphereShape = new btSphereShape(1);
startTransform.setOrigin(btVector3(1,2*i,1)); startTransform.setOrigin(btVector3(1,2*i,1));
btRigidBody* body = localCreateRigidBody(true, 1, startTransform,sphereShape); btRigidBody* body = localCreateRigidBody(1, startTransform,sphereShape);
getDynamicsWorld()->addCollisionObject(body);
} }
} }
m_dynamicsWorld->setDebugDrawer(&debugDrawer); m_dynamicsWorld->setDebugDrawer(&debugDrawer);
} }

View File

@@ -59,6 +59,16 @@ CONCAVE_SHAPES_END_HERE,
struct btBroadphaseProxy struct btBroadphaseProxy
{ {
///optional filtering to cull potential collisions
enum CollisionFilterGroups
{
DefaultFilter = 1,
StaticFilter = 2,
KinematicFilter = 4,
DebrisFilter = 8,
AllFilter = DefaultFilter | StaticFilter | KinematicFilter | DebrisFilter,
};
//Usually the client btCollisionObject or Rigidbody class //Usually the client btCollisionObject or Rigidbody class
void* m_clientObject; void* m_clientObject;
short int m_collisionFilterGroup; short int m_collisionFilterGroup;

View File

@@ -48,6 +48,9 @@ struct btCollisionObject
customMaterialCallback = 4,//this allows per-triangle material (friction/restitution) customMaterialCallback = 4,//this allows per-triangle material (friction/restitution)
}; };
int m_collisionFlags; int m_collisionFlags;
int m_islandTag1; int m_islandTag1;

View File

@@ -89,6 +89,12 @@ btCollisionWorld::~btCollisionWorld()
void btCollisionWorld::addCollisionObject(btCollisionObject* collisionObject,short int collisionFilterGroup,short int collisionFilterMask) void btCollisionWorld::addCollisionObject(btCollisionObject* collisionObject,short int collisionFilterGroup,short int collisionFilterMask)
{ {
//check that the object isn't already added
std::vector<btCollisionObject*>::iterator i = std::find(m_collisionObjects.begin(), m_collisionObjects.end(), collisionObject);
assert(i == m_collisionObjects.end());
m_collisionObjects.push_back(collisionObject); m_collisionObjects.push_back(collisionObject);
//calculate new AABB //calculate new AABB

View File

@@ -88,7 +88,7 @@ void btOptimizedBvh::build(btStridingMeshInterface* triangles)
btOptimizedBvh::~btOptimizedBvh() btOptimizedBvh::~btOptimizedBvh()
{ {
if (m_contiguousNodes) if (m_contiguousNodes)
delete m_contiguousNodes; delete []m_contiguousNodes;
} }
btOptimizedBvhNode* btOptimizedBvh::buildTree (NodeArray& leafNodes,int startIndex,int endIndex) btOptimizedBvhNode* btOptimizedBvh::buildTree (NodeArray& leafNodes,int startIndex,int endIndex)

View File

@@ -18,7 +18,7 @@ subject to the following restrictions:
#include "BulletDynamics/Dynamics/btRigidBody.h" #include "BulletDynamics/Dynamics/btRigidBody.h"
#include "BulletDynamics/Dynamics/btMassProps.h" #include "BulletDynamics/Dynamics/btMassProps.h"
static btRigidBody s_fixed(btMassProps(0,btVector3(0.f,0.f,0.f)),0.f,0.f,1.f,1.f); static btRigidBody s_fixed(0, btTransform::getIdentity(),0);
btTypedConstraint::btTypedConstraint() btTypedConstraint::btTypedConstraint()
: m_userConstraintType(-1), : m_userConstraintType(-1),

View File

@@ -28,7 +28,7 @@ float gLinearSleepingTreshold = 0.8f;
float gAngularSleepingTreshold = 1.0f; float gAngularSleepingTreshold = 1.0f;
static int uniqueId = 0; static int uniqueId = 0;
btRigidBody::btRigidBody( const btMassProps& massProps,btScalar linearDamping,btScalar angularDamping,btScalar friction,btScalar restitution) btRigidBody::btRigidBody( float mass,const btTransform& worldTransform,btCollisionShape* collisionShape,const btVector3& localInertia,btScalar linearDamping,btScalar angularDamping,btScalar friction,btScalar restitution)
: :
m_gravity(0.0f, 0.0f, 0.0f), m_gravity(0.0f, 0.0f, 0.0f),
m_totalForce(0.0f, 0.0f, 0.0f), m_totalForce(0.0f, 0.0f, 0.0f),
@@ -42,18 +42,23 @@ btRigidBody::btRigidBody( const btMassProps& massProps,btScalar linearDamping,bt
m_frictionSolverType(0) m_frictionSolverType(0)
{ {
if (mass == 0.f)
m_collisionFlags = btCollisionObject::isStatic;
m_worldTransform = worldTransform;
//moved to btCollisionObject //moved to btCollisionObject
m_friction = friction; m_friction = friction;
m_restitution = restitution; m_restitution = restitution;
m_collisionShape = collisionShape;
m_debugBodyId = uniqueId++; m_debugBodyId = uniqueId++;
//m_internalOwner is to allow upcasting from collision object to rigid body //m_internalOwner is to allow upcasting from collision object to rigid body
m_internalOwner = this; m_internalOwner = this;
setMassProps(massProps.m_mass, massProps.m_inertiaLocal); setMassProps(mass, localInertia);
setDamping(linearDamping, angularDamping); setDamping(linearDamping, angularDamping);
m_worldTransform.setIdentity();
updateInertiaTensor(); updateInertiaTensor();
} }
@@ -61,7 +66,7 @@ btRigidBody::btRigidBody( const btMassProps& massProps,btScalar linearDamping,bt
void btRigidBody::setLinearVelocity(const btVector3& lin_vel) void btRigidBody::setLinearVelocity(const btVector3& lin_vel)
{ {
assert (m_collisionFlags != btCollisionObject::isStatic);
m_linearVelocity = lin_vel; m_linearVelocity = lin_vel;
} }

View File

@@ -57,11 +57,9 @@ class btRigidBody : public btCollisionObject
btScalar m_kinematicTimeStep; btScalar m_kinematicTimeStep;
btBroadphaseProxy* m_broadphaseProxy;
public: public:
btRigidBody(const btMassProps& massProps,btScalar linearDamping=0.f,btScalar angularDamping=0.f,btScalar friction=0.5f,btScalar restitution=0.f); btRigidBody(float mass, const btTransform& worldTransform, btCollisionShape* collisionShape, const btVector3& localInertia=btVector3(0,0,0),btScalar linearDamping=0.f,btScalar angularDamping=0.f,btScalar friction=0.5f,btScalar restitution=0.f);
void proceedToTransform(const btTransform& newTrans); void proceedToTransform(const btTransform& newTrans);
@@ -266,15 +264,15 @@ public:
const btBroadphaseProxy* getBroadphaseProxy() const const btBroadphaseProxy* getBroadphaseProxy() const
{ {
return m_broadphaseProxy; return m_broadphaseHandle;
} }
btBroadphaseProxy* getBroadphaseProxy() btBroadphaseProxy* getBroadphaseProxy()
{ {
return m_broadphaseProxy; return m_broadphaseHandle;
} }
void setBroadphaseProxy(btBroadphaseProxy* broadphaseProxy) void setNewBroadphaseProxy(btBroadphaseProxy* broadphaseProxy)
{ {
m_broadphaseProxy = broadphaseProxy; m_broadphaseHandle = broadphaseProxy;
} }
//for experimental overriding of friction/contact solver func //for experimental overriding of friction/contact solver func

View File

@@ -23,7 +23,7 @@
static btRigidBody s_fixedObject( btMassProps ( 0.0f, btVector3(0,0,0) ),0.f,0.f,0.f,0.f); static btRigidBody s_fixedObject( 0,btTransform(btQuaternion(0,0,0,1)),0);
btRaycastVehicle::btRaycastVehicle(const btVehicleTuning& tuning,btRigidBody* chassis, btVehicleRaycaster* raycaster ) btRaycastVehicle::btRaycastVehicle(const btVehicleTuning& tuning,btRigidBody* chassis, btVehicleRaycaster* raycaster )
:m_vehicleRaycaster(raycaster), :m_vehicleRaycaster(raycaster),

View File

@@ -159,6 +159,13 @@ public:
btTransform operator*(const btTransform& t) const; btTransform operator*(const btTransform& t) const;
static btTransform getIdentity()
{
btTransform tr;
tr.setIdentity();
return tr;
}
private: private:
btMatrix3x3 m_basis; btMatrix3x3 m_basis;