#ifndef TESTBULLETONLY_HAS_BEEN_INCLUDED #define TESTBULLETONLY_HAS_BEEN_INCLUDED #include "cppunit/TestFixture.h" #include "cppunit/extensions/HelperMacros.h" #include "btBulletDynamicsCommon.h" #include "BulletCollision/Gimpact/btGImpactCollisionAlgorithm.h" // --------------------------------------------------------------------------- class TestBulletOnly : public CppUnit::TestFixture { btCollisionConfiguration * mCollisionConfig; btCollisionDispatcher * mCollisionDispatch; btBroadphaseInterface * mBroadphase; btConstraintSolver * mConstraintSolver; btDiscreteDynamicsWorld * mWorld; btCollisionShape* mBodyShape; btRigidBody* mRigidBody; btDefaultMotionState* mMotionState; public: void setUp() { // Setup the world -- mCollisionConfig = new btDefaultCollisionConfiguration; mCollisionDispatch = new btCollisionDispatcher( mCollisionConfig ); mBroadphase = new btDbvtBroadphase(); mConstraintSolver = new btSequentialImpulseConstraintSolver(); mWorld = new btDiscreteDynamicsWorld( mCollisionDispatch, mBroadphase, mConstraintSolver, mCollisionConfig ); mWorld->setGravity( btVector3( 0, -9.81, 0 )); // Set up the rigid body -- mBodyShape = new btBoxShape( btVector3( 1, 1, 1 ) ); btScalar mass = 1; btVector3 localInertia(0,0,0); mBodyShape->calculateLocalInertia(mass,localInertia); btTransform bodyInitial; mMotionState = new btDefaultMotionState(); bodyInitial.setIdentity(); bodyInitial.setOrigin( btVector3( 0, 0, 0 ) ); mRigidBody = new btRigidBody( buildConstructionInfo(mass, 0.5, 0.5, 0, 0, *mMotionState, mBodyShape ) ); mWorld->addRigidBody( mRigidBody ); } void tearDown() { mWorld->removeRigidBody(mRigidBody); delete mRigidBody; delete mMotionState; delete mBodyShape; delete mWorld; delete mConstraintSolver; delete mBroadphase; delete mCollisionDispatch; delete mCollisionConfig; } btRigidBody::btRigidBodyConstructionInfo buildConstructionInfo( btScalar mass, btScalar friction, btScalar restitution, btScalar linearDamping, btScalar angularDamping, btDefaultMotionState & state, btCollisionShape * shape ) { btVector3 inertia(0,0,0); if (mass>0) shape->calculateLocalInertia( mass, inertia ); btRigidBody::btRigidBodyConstructionInfo info( mass, &state, shape, inertia ); info.m_friction = friction; info.m_restitution = restitution; info.m_linearDamping = linearDamping; info.m_angularDamping = angularDamping; return info; } void testKinematicVelocity0() { mRigidBody->setMassProps( 1, btVector3( 1, 1, 1 ) ); mRigidBody->updateInertiaTensor(); mRigidBody->setCollisionFlags( btCollisionObject::CF_KINEMATIC_OBJECT ); // -- . // Interpolate the velocity -- //btVector3 velocity( 1., 2., 3. ), spin( 0.1, 0.2, 0.3 ); btVector3 velocity( 1., 2., 3. ), spin( 0.1, 0.2, .3 ); btTransform interpolated; // TODO: This is inaccurate for small spins. btTransformUtil::integrateTransform( mRigidBody->getCenterOfMassTransform(), velocity, spin, 1.0f/60.f, interpolated ); mRigidBody->setInterpolationWorldTransform( interpolated ); mWorld->stepSimulation( 1.f/60.f, 60, 1.0f/60.f ); CPPUNIT_ASSERT_DOUBLES_EQUAL( mRigidBody->getLinearVelocity().length2(), velocity.length2(), 1e-8 ); #ifdef BT_USE_DOUBLE_PRECISION CPPUNIT_ASSERT_DOUBLES_EQUAL( mRigidBody->getAngularVelocity().length2(), spin.length2(), 1e-4 ); #else CPPUNIT_ASSERT_DOUBLES_EQUAL( mRigidBody->getAngularVelocity().length2(), spin.length2(), 5e-3 ); #endif //CPPUNIT_ASSERT_DOUBLES_EQUAL } CPPUNIT_TEST_SUITE(TestBulletOnly); CPPUNIT_TEST(testKinematicVelocity0); CPPUNIT_TEST_SUITE_END(); private: }; #endif