Ejemplo n.º 1
0
void	SerializeDemo::initPhysics()
{
	setTexturing(true);
	setShadows(true);

	setCameraDistance(btScalar(SCALING*50.));

	setupEmptyDynamicsWorld();
	
	btBulletWorldImporter* fileLoader = new btBulletWorldImporter(m_dynamicsWorld);
//	fileLoader->setVerboseMode(true);
	
	if (!fileLoader->loadFile("testFile.bullet"))
	{
		///create a few basic rigid bodies and save them to testFile.bullet
		btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(50.),btScalar(50.),btScalar(50.)));
	//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
		btCollisionObject* groundObject = 0;

		
		m_collisionShapes.push_back(groundShape);

		btTransform groundTransform;
		groundTransform.setIdentity();
		groundTransform.setOrigin(btVector3(0,-50,0));

		//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
		{
			btScalar mass(0.);

			//rigidbody is dynamic if and only if mass is non zero, otherwise static
			bool isDynamic = (mass != 0.f);

			btVector3 localInertia(0,0,0);
			if (isDynamic)
				groundShape->calculateLocalInertia(mass,localInertia);

			//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
			btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
			btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
			btRigidBody* body = new btRigidBody(rbInfo);

			//add the body to the dynamics world
			m_dynamicsWorld->addRigidBody(body);
			groundObject = body;
		}


		{
			//create a few dynamic rigidbodies
			// Re-using the same collision is better for memory usage and performance

			int numSpheres = 2;
			btVector3 positions[2] = {btVector3(0.1f,0.2f,0.3f),btVector3(0.4f,0.5f,0.6f)};
			btScalar	radii[2] = {0.3f,0.4f};

			btMultiSphereShape* colShape = new btMultiSphereShape(positions,radii,numSpheres);

			//btCollisionShape* colShape = new btCapsuleShapeZ(SCALING*1,SCALING*1);
			//btCollisionShape* colShape = new btCylinderShapeZ(btVector3(SCALING*1,SCALING*1,SCALING*1));
			//btCollisionShape* colShape = new btBoxShape(btVector3(SCALING*1,SCALING*1,SCALING*1));
			//btCollisionShape* colShape = new btSphereShape(btScalar(1.));
			m_collisionShapes.push_back(colShape);

			/// Create Dynamic Objects
			btTransform startTransform;
			startTransform.setIdentity();

			btScalar	mass(1.f);

			//rigidbody is dynamic if and only if mass is non zero, otherwise static
			bool isDynamic = (mass != 0.f);

			btVector3 localInertia(0,0,0);
			if (isDynamic)
				colShape->calculateLocalInertia(mass,localInertia);

			float start_x = START_POS_X - ARRAY_SIZE_X/2;
			float start_y = START_POS_Y;
			float start_z = START_POS_Z - ARRAY_SIZE_Z/2;

			for (int k=0;k<ARRAY_SIZE_Y;k++)
			{
				for (int i=0;i<ARRAY_SIZE_X;i++)
				{
					for(int j = 0;j<ARRAY_SIZE_Z;j++)
					{
						startTransform.setOrigin(SCALING*btVector3(
											btScalar(2.0*i + start_x),
											btScalar(20+2.0*k + start_y),
											btScalar(2.0*j + start_z)));

				
						//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
						btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
						btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,colShape,localInertia);
						btRigidBody* body = new btRigidBody(rbInfo);
						
						body->setActivationState(ISLAND_SLEEPING);

						m_dynamicsWorld->addRigidBody(body);
						body->setActivationState(ISLAND_SLEEPING);
					}
				}
			}
		}

		int maxSerializeBufferSize = 1024*1024*5;

		btDefaultSerializer*	serializer = new btDefaultSerializer(maxSerializeBufferSize);

		static char* groundName = "GroundName";
		serializer->registerNameForPointer(groundObject, groundName);

		for (int i=0;i<m_collisionShapes.size();i++)
		{
			char* name = new char[20];
			
			sprintf(name,"name%d",i);
			serializer->registerNameForPointer(m_collisionShapes[i],name);
		}

		btPoint2PointConstraint* p2p = new btPoint2PointConstraint(*(btRigidBody*)getDynamicsWorld()->getCollisionObjectArray()[2],btVector3(0,1,0));
		m_dynamicsWorld->addConstraint(p2p);
		
		const char* name = "constraintje";
		serializer->registerNameForPointer(p2p,name);

		m_dynamicsWorld->serialize(serializer);
		
		FILE* f2 = fopen("testFile.bullet","wb");
		fwrite(serializer->getBufferPointer(),serializer->getCurrentBufferSize(),1,f2);
		fclose(f2);
	}

	clientResetScene();

}
Ejemplo n.º 2
0
void	BasicDemo::initPhysics()
{
	setTexturing(true);
	setShadows(true);

	m_acceleratedRigidBodies = 0;

	setCameraDistance(btScalar(SCALING*20.));

	///collision configuration contains default setup for memory, collision setup
	m_collisionConfiguration = new btDefaultCollisionConfiguration();
	//m_collisionConfiguration->setConvexConvexMultipointIterations();

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);

	
#ifdef CL_PLATFORM_AMD
	m_dispatcher = new	CustomCollisionDispatcher(m_collisionConfiguration,	g_cxMainContext,g_clDevice,g_cqCommandQue);
	m_dispatcher->registerCollisionCreateFunc(CUSTOM_POLYHEDRAL_SHAPE_TYPE,CUSTOM_POLYHEDRAL_SHAPE_TYPE,new CustomConvexConvexPairCollision::CreateFunc(m_collisionConfiguration->getSimplexSolver(), m_collisionConfiguration->getPenetrationDepthSolver()));

#else
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);
#endif


	m_broadphase = new btDbvtBroadphase();

	///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
	btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
	m_solver = sol;

	m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
	
	m_dynamicsWorld->setGravity(btVector3(0,-10,0));

	m_dynamicsWorld->setDebugDrawer(&sDebugDraw);

	///create a few basic rigid bodies
	//btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(50.),btScalar(50.),btScalar(50.)));
#ifdef CL_PLATFORM_AMD
	CustomConvexShape* groundShape = new CustomConvexShape(BoxVtx2,BoxVtxCount,3*sizeof(float));
#else
	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),0);
#endif
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-1,0));

	//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);

		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);
	}


	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance

		//btCollisionShape* colShape = new btBoxShape(btVector3(SCALING*1,SCALING*1,SCALING*1));
		//btCollisionShape* colShape = new btSphereShape(btScalar(1.));
#ifdef USE_CUSTOM_HEIGHTFIELD_SHAPE
	CustomConvexShape* colShape = new CustomConvexShape(BarrelVtx2,BarrelVtxCount2,6*sizeof(float));

	//CustomConvexShape* colShape = new CustomConvexShape(BoxVtx,BoxVtxCount,3*sizeof(float));
#else
	btConvexHullShape* colShape = new btConvexHullShape(BarrelVtx2,BarrelVtxCount2,6*sizeof(float));
		colShape->setLocalScaling(btVector3(0.9,0.9,0.9));

#endif //USE_CUSTOM_HEIGHTFIELD_SHAPE
	btScalar scale = 0.5f;
	
	//btScalar scale = 1.f;

		//next line is already called inside the CustomConvexShape constructor
		//colShape->initializePolyhedralFeatures();

		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);

		float start_x = START_POS_X - ARRAY_SIZE_X/2;
		float start_y = START_POS_Y;
		float start_z = START_POS_Z - ARRAY_SIZE_Z/2;

		for (int k=0;k<ARRAY_SIZE_Y;k++)
		{
			for(int j = 0;j<ARRAY_SIZE_Z;j++)	
			{
				for (int i=0;i<ARRAY_SIZE_X;i++)
				{
					
					{
					//	if ((k>0) && ((j<2) || (j>(ARRAY_SIZE_Z-3))))
					//		continue;
					//	if ((k>0) && ((i<2) || (i>(ARRAY_SIZE_X-3))))
					//		continue;

					startTransform.setOrigin(SCALING*btVector3(
										btScalar(scale*2.0*i + start_x),
										btScalar(scale*1+scale*2.0*k + start_y),
										btScalar(scale*2.0*j + start_z)));

			
					//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
					btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
					btRigidBody* body=0;

					if (0)//k==0)
					{
						btVector3 zeroInertia(0,0,0);
						btRigidBody::btRigidBodyConstructionInfo rbInfo(0.f,myMotionState,colShape,zeroInertia);
						body = new btRigidBody(rbInfo);
					} else
					{
						btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,colShape,localInertia);
						body = new btRigidBody(rbInfo);
					}

					//m_acceleratedRigidBodies is used as a mapping to the accelerated rigid body index
					body->setCompanionId(m_acceleratedRigidBodies++);
					m_dynamicsWorld->addRigidBody(body);
						
					}
				}
			}
		}
	}


}
Ejemplo n.º 3
0
void	MultiDofDemo::initPhysics()
{	


	m_guiHelper->setUpAxis(1);

	if(g_firstInit)
	{
		m_guiHelper->getRenderInterface()->getActiveCamera()->setCameraDistance(btScalar(10.*scaling));
		m_guiHelper->getRenderInterface()->getActiveCamera()->setCameraPitch(50);
		g_firstInit = false;
	}	
	///collision configuration contains default setup for memory, collision setup
	m_collisionConfiguration = new btDefaultCollisionConfiguration();

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);

	m_broadphase = new btDbvtBroadphase();

	//Use the btMultiBodyConstraintSolver for Featherstone btMultiBody support
	btMultiBodyConstraintSolver* sol = new btMultiBodyConstraintSolver;
	m_solver = sol;

	//use btMultiBodyDynamicsWorld for Featherstone btMultiBody support
	btMultiBodyDynamicsWorld* world = new btMultiBodyDynamicsWorld(m_dispatcher,m_broadphase,sol,m_collisionConfiguration);
	m_dynamicsWorld = world;
//	m_dynamicsWorld->setDebugDrawer(&gDebugDraw);
	m_guiHelper->createPhysicsDebugDrawer(m_dynamicsWorld);
	m_dynamicsWorld->setGravity(btVector3(0,-10,0));

	///create a few basic rigid bodies
	btVector3 groundHalfExtents(50,50,50);
	btCollisionShape* groundShape = new btBoxShape(groundHalfExtents);
	//groundShape->initializePolyhedralFeatures();
//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-50,00));

	/////////////////////////////////////////////////////////////////	
	/////////////////////////////////////////////////////////////////
	
	bool damping = true;
	bool gyro = true;
	int numLinks = 5;
	bool spherical = true;					//set it ot false -to use 1DoF hinges instead of 3DoF sphericals		
	bool multibodyOnly = false;
	bool canSleep = true;
	bool selfCollide = true;
    bool multibodyConstraint = false;
	btVector3 linkHalfExtents(0.05, 0.37, 0.1);
	btVector3 baseHalfExtents(0.05, 0.37, 0.1);

	btMultiBody* mbC = createFeatherstoneMultiBody_testMultiDof(world, numLinks, btVector3(-0.4f, 3.f, 0.f), linkHalfExtents, baseHalfExtents, spherical, g_floatingBase);	
	//mbC->forceMultiDof();							//if !spherical, you can comment this line to check the 1DoF algorithm		

	g_floatingBase = ! g_floatingBase;
	mbC->setCanSleep(canSleep);	
	mbC->setHasSelfCollision(selfCollide);
	mbC->setUseGyroTerm(gyro);
	//
	if(!damping)
	{
		mbC->setLinearDamping(0.f);
		mbC->setAngularDamping(0.f);
	}else
	{	mbC->setLinearDamping(0.1f);
		mbC->setAngularDamping(0.9f);
	}
	//
	m_dynamicsWorld->setGravity(btVector3(0, -9.81 ,0));	
	//m_dynamicsWorld->getSolverInfo().m_numIterations = 100;
	//////////////////////////////////////////////
	if(numLinks > 0)
	{			
		btScalar q0 = 45.f * SIMD_PI/ 180.f;
		if(!spherical)
		{
			mbC->setJointPosMultiDof(0, &q0);
		}
		else
		{
			btQuaternion quat0(btVector3(1, 1, 0).normalized(), q0);
			quat0.normalize();
			mbC->setJointPosMultiDof(0, quat0);				
		}			
	}		
	///
	addColliders_testMultiDof(mbC, world, baseHalfExtents, linkHalfExtents);	

	
	/////////////////////////////////////////////////////////////////	
	btScalar groundHeight = -51.55;
	if (!multibodyOnly)
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		groundTransform.setIdentity();
		groundTransform.setOrigin(btVector3(0,groundHeight,0));
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);

		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body,1,1+2);//,1,1+2);

		


	}
	/////////////////////////////////////////////////////////////////
	if(!multibodyOnly)
	{
		btVector3 halfExtents(.5,.5,.5);
		btBoxShape* colShape = new btBoxShape(halfExtents);
		//btCollisionShape* colShape = new btSphereShape(btScalar(1.));
		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);

		startTransform.setOrigin(btVector3(
							btScalar(0.0),
							0.0,
							btScalar(0.0)));

			
		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,colShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);
					
		m_dynamicsWorld->addRigidBody(body);//,1,1+2);	

        if (multibodyConstraint) {
            btVector3 pointInA = -linkHalfExtents;
      //      btVector3 pointInB = halfExtents;
            btMatrix3x3 frameInA;
            btMatrix3x3 frameInB;
            frameInA.setIdentity();
            frameInB.setIdentity();
            btVector3 jointAxis(1.0,0.0,0.0);
            //btMultiBodySliderConstraint* p2p = new btMultiBodySliderConstraint(mbC,numLinks-1,body,pointInA,pointInB,frameInA,frameInB,jointAxis);
            btMultiBodyFixedConstraint* p2p = new btMultiBodyFixedConstraint(mbC,numLinks-1,mbC,numLinks-4,pointInA,pointInA,frameInA,frameInB);
            p2p->setMaxAppliedImpulse(2.0);
            m_dynamicsWorld->addMultiBodyConstraint(p2p);
        }
	}

	m_guiHelper->autogenerateGraphicsObjects(m_dynamicsWorld);

	/////////////////////////////////////////////////////////////////
}
Ejemplo n.º 4
0
int main() {
    btDefaultCollisionConfiguration *collisionConfiguration
            = new btDefaultCollisionConfiguration();
    btCollisionDispatcher *dispatcher = new btCollisionDispatcher(collisionConfiguration);
    btBroadphaseInterface *overlappingPairCache = new btDbvtBroadphase();
    btSequentialImpulseConstraintSolver* solver = new btSequentialImpulseConstraintSolver;
    btDiscreteDynamicsWorld *dynamicsWorld = new btDiscreteDynamicsWorld(
            dispatcher, overlappingPairCache, solver, collisionConfiguration);
    dynamicsWorld->setGravity(btVector3(0, gravity, 0));
    dynamicsWorld->setInternalTickCallback(myTickCallback);
    btAlignedObjectArray<btCollisionShape*> collisionShapes;

    // Ground.
    {
        btTransform groundTransform;
        groundTransform.setIdentity();
        groundTransform.setOrigin(btVector3(0, 0, 0));
        btCollisionShape* groundShape;
#if 0
        // x / z plane at y = -1 (not 0 to compensate the radius of the falling object).
        groundShape = new btStaticPlaneShape(btVector3(groundXNormal, 1, 0), -1);
#else
        // A cube of width 10 at y = -6 (upper surface at -1).
        // Does not fall because we won't call:
        // colShape->calculateLocalInertia
        // TODO: remove this from this example into a collision shape example.
        groundTransform.setOrigin(btVector3(-5, -6, 0));
        groundShape = new btBoxShape(
                btVector3(btScalar(5.0), btScalar(5.0), btScalar(5.0)));

#endif
        collisionShapes.push_back(groundShape);
        btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
        btRigidBody::btRigidBodyConstructionInfo rbInfo(0, myMotionState, groundShape, btVector3(0, 0, 0));
        btRigidBody* body = new btRigidBody(rbInfo);
        body->setRestitution(groundRestitution);
        dynamicsWorld->addRigidBody(body);
    }

    // Object.
    {
        btCollisionShape *colShape;
#if 0
        colShape = new btSphereShape(btScalar(1.0));
#else
        // Because of numerical instabilities, the cube bumps all over,
        // moving on the x and z directions as well as y.
        colShape = new btBoxShape(
                btVector3(btScalar(1.0), btScalar(1.0), btScalar(1.0)));
#endif
        collisionShapes.push_back(colShape);
        btTransform startTransform;
        startTransform.setIdentity();
        startTransform.setOrigin(btVector3(initialX, initialY, initialZ));
        btVector3 localInertia(0, 0, 0);
        btScalar mass(1.0f);
        colShape->calculateLocalInertia(mass, localInertia);
        btDefaultMotionState *myMotionState = new btDefaultMotionState(startTransform);
        btRigidBody *body = new btRigidBody(btRigidBody::btRigidBodyConstructionInfo(
                mass, myMotionState, colShape, localInertia));
        body->setRestitution(objectRestitution);
        body->setLinearVelocity(btVector3(initialLinearVelocityX, initialLinearVelocityY, initialLinearVelocityZ));
        dynamicsWorld->addRigidBody(body);
    }

    // Main loop.
    std::printf(COMMON_PRINTF_HEADER " collision a b normal\n");
    for (std::remove_const<decltype(nSteps)>::type step = 0; step < nSteps; ++step) {
        dynamicsWorld->stepSimulation(timeStep);
        auto nCollisionObjects = dynamicsWorld->getNumCollisionObjects();
        for (decltype(nCollisionObjects) objectIndex = 0; objectIndex < nCollisionObjects; ++objectIndex) {
            btRigidBody *body = btRigidBody::upcast(dynamicsWorld->getCollisionObjectArray()[objectIndex]);
            commonPrintBodyState(body, step, objectIndex);
            auto& manifoldPoints = objectsCollisions[body];
            if (manifoldPoints.empty()) {
                std::printf("0 ");
            } else {
                std::printf("1 ");
                for (auto& pt : manifoldPoints) {
                    std::vector<btVector3> data;
                    data.push_back(pt->getPositionWorldOnA());
                    data.push_back(pt->getPositionWorldOnB());
                    data.push_back(pt->m_normalWorldOnB);
                    for (auto& v : data) {
                        std::printf(
                            COMMON_PRINTF_FLOAT " " COMMON_PRINTF_FLOAT " " COMMON_PRINTF_FLOAT " ",
                            v.getX(), v.getY(), v.getZ()
                        );
                    }
                }
            }
            std::printf("\n");
        }
    }

    // Cleanup.
    for (int i = dynamicsWorld->getNumCollisionObjects() - 1; i >= 0; --i) {
        btCollisionObject* obj = dynamicsWorld->getCollisionObjectArray()[i];
        btRigidBody* body = btRigidBody::upcast(obj);
        if (body && body->getMotionState()) {
            delete body->getMotionState();
        }
        dynamicsWorld->removeCollisionObject(obj);
        delete obj;
    }
    for (int i = 0; i < collisionShapes.size(); ++i) {
        delete collisionShapes[i];
    }
    delete dynamicsWorld;
    delete solver;
    delete overlappingPairCache;
    delete dispatcher;
    delete collisionConfiguration;
    collisionShapes.clear();
}
Ejemplo n.º 5
0
void Dof6Spring2Setup::initPhysics()
{
	// Setup the basic world
	
	m_guiHelper->setUpAxis(1);

		m_collisionConfiguration = new btDefaultCollisionConfiguration();
		m_dispatcher = new btCollisionDispatcher(m_collisionConfiguration);
		btVector3 worldAabbMin(-10000,-10000,-10000);
		btVector3 worldAabbMax(10000,10000,10000);
		m_broadphase = new btAxisSweep3 (worldAabbMin, worldAabbMax);

/////// uncomment the corresponding line to test a solver.
		//m_solver = new btSequentialImpulseConstraintSolver;
		m_solver = new btNNCGConstraintSolver;
		//m_solver = new btMLCPSolver(new btSolveProjectedGaussSeidel());
		//m_solver = new btMLCPSolver(new btDantzigSolver());
		//m_solver = new btMLCPSolver(new btLemkeSolver());

		m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
		m_dynamicsWorld->getDispatchInfo().m_useContinuous = true;
	m_guiHelper->createPhysicsDebugDrawer(m_dynamicsWorld);
	
		m_dynamicsWorld->setGravity(btVector3(0,0,0));

		// Setup a big ground box
		{
			btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(200.),btScalar(5.),btScalar(200.)));
			btTransform groundTransform;
			groundTransform.setIdentity();
			groundTransform.setOrigin(btVector3(0,-10,0));
#define CREATE_GROUND_COLLISION_OBJECT 1
#ifdef CREATE_GROUND_COLLISION_OBJECT
			btCollisionObject* fixedGround = new btCollisionObject();
			fixedGround->setCollisionShape(groundShape);
			fixedGround->setWorldTransform(groundTransform);
			m_dynamicsWorld->addCollisionObject(fixedGround);
#else
			localCreateRigidBody(btScalar(0.),groundTransform,groundShape);
#endif //CREATE_GROUND_COLLISION_OBJECT
		}

		m_dynamicsWorld->getSolverInfo().m_numIterations = 100;

		btCollisionShape* shape;
		btVector3 localInertia(0,0,0);
		btDefaultMotionState* motionState;
		btTransform bodyTransform;
		btScalar mass;
		btTransform localA;
		btTransform localB;
		CONSTRAINT_TYPE* constraint;

		//static body centered in the origo
		mass = 0.0;
		shape= new btBoxShape(btVector3(0.5,0.5,0.5));
		localInertia = btVector3(0,0,0);
		bodyTransform.setIdentity();
		motionState = new btDefaultMotionState(bodyTransform);
		btRigidBody* staticBody = new btRigidBody(mass,motionState,shape,localInertia);

/////////// box with undamped translate spring attached to static body
/////////// the box should oscillate left-to-right forever
		{
			mass = 1.0;
			shape= new btBoxShape(btVector3(0.5,0.5,0.5));
			shape->calculateLocalInertia(mass,localInertia);
			bodyTransform.setIdentity();
			bodyTransform.setOrigin(btVector3(-2,0,-5));
			motionState = new btDefaultMotionState(bodyTransform);
			m_data->m_TranslateSpringBody = new btRigidBody(mass,motionState,shape,localInertia);
			m_data->m_TranslateSpringBody->setActivationState(DISABLE_DEACTIVATION);
			m_dynamicsWorld->addRigidBody(m_data->m_TranslateSpringBody);
 			localA.setIdentity();localA.getOrigin() = btVector3(0,0,-5);
			localB.setIdentity();
 			constraint =  new CONSTRAINT_TYPE(*staticBody, *m_data->m_TranslateSpringBody, localA, localB EXTRAPARAMS);
			constraint->setLimit(0, 1,-1);
			constraint->setLimit(1, 0, 0);
			constraint->setLimit(2, 0, 0);
			constraint->setLimit(3, 0, 0);
			constraint->setLimit(4, 0, 0);
			constraint->setLimit(5, 0, 0);
			constraint->enableSpring(0, true);
			constraint->setStiffness(0, 100);
	#ifdef USE_6DOF2
			constraint->setDamping(0, 0);
	#else
			constraint->setDamping(0, 1);
	#endif
			constraint->setEquilibriumPoint(0, 0);
			constraint->setDbgDrawSize(btScalar(2.f));
			m_dynamicsWorld->addConstraint(constraint, true);  
		}

/////////// box with rotate spring, attached to static body
/////////// box should swing (rotate) left-to-right forever
		{
			mass = 1.0;
			shape= new btBoxShape(btVector3(0.5,0.5,0.5));
			shape->calculateLocalInertia(mass,localInertia);
			bodyTransform.setIdentity();
			bodyTransform.getBasis().setEulerZYX(0,0,M_PI_2);
			motionState = new btDefaultMotionState(bodyTransform);
			m_data->m_RotateSpringBody = new btRigidBody(mass,motionState,shape,localInertia);
			m_data->m_RotateSpringBody->setActivationState(DISABLE_DEACTIVATION);
			m_dynamicsWorld->addRigidBody(m_data->m_RotateSpringBody);
			localA.setIdentity();localA.getOrigin() = btVector3(0,0,0);
			localB.setIdentity();localB.setOrigin(btVector3(0,0.5,0));
			constraint =  new CONSTRAINT_TYPE(*staticBody, *m_data->m_RotateSpringBody, localA, localB EXTRAPARAMS);
			constraint->setLimit(0, 0, 0);
			constraint->setLimit(1, 0, 0);
			constraint->setLimit(2, 0, 0);
			constraint->setLimit(3, 0, 0);
			constraint->setLimit(4, 0, 0);
			constraint->setLimit(5, 1, -1);
			constraint->enableSpring(5, true);
			constraint->setStiffness(5, 100);
	#ifdef USE_6DOF2
			constraint->setDamping(5, 0);
	#else
			constraint->setDamping(5, 1);
	#endif
			constraint->setEquilibriumPoint(0, 0);
			constraint->setDbgDrawSize(btScalar(2.f));
			m_dynamicsWorld->addConstraint(constraint, true);
		}

/////////// box with bouncing constraint, translation is bounced at the positive x limit, but not at the negative limit
/////////// bouncing can not be set independently at low and high limits, so two constraints will be created: one that defines the low (non bouncing) limit, and one that defines the high (bouncing) limit
/////////// the box should move to the left (as an impulse will be applied to it periodically) until it reaches its limit, then bounce back 
		{
			mass = 1.0;
			shape= new btBoxShape(btVector3(0.5,0.5,0.5));
			shape->calculateLocalInertia(mass,localInertia);
			bodyTransform.setIdentity();
			bodyTransform.setOrigin(btVector3(0,0,-3));
			motionState = new btDefaultMotionState(bodyTransform);
			m_data->m_BouncingTranslateBody = new btRigidBody(mass,motionState,shape,localInertia);
			m_data->m_BouncingTranslateBody->setActivationState(DISABLE_DEACTIVATION);
			m_data->m_BouncingTranslateBody->setDeactivationTime(btScalar(20000000));
			m_dynamicsWorld->addRigidBody(m_data->m_BouncingTranslateBody);
			localA.setIdentity();localA.getOrigin() = btVector3(0,0,0);
			localB.setIdentity();
			constraint =  new CONSTRAINT_TYPE(*staticBody, *m_data->m_BouncingTranslateBody, localA, localB EXTRAPARAMS);
			constraint->setLimit(0, -2, SIMD_INFINITY);
			constraint->setLimit(1, 0, 0);
			constraint->setLimit(2, -3, -3);
			constraint->setLimit(3, 0, 0);
			constraint->setLimit(4, 0, 0);
			constraint->setLimit(5, 0, 0);
		#ifdef USE_6DOF2
			constraint->setBounce(0,0);
		#else //bounce is named restitution in 6dofspring, but not implemented for translational limit motor, so the following line has no effect
			constraint->getTranslationalLimitMotor()->m_restitution = 0.0;
		#endif
			constraint->setParam(BT_CONSTRAINT_STOP_ERP,0.995,0);
			constraint->setParam(BT_CONSTRAINT_STOP_CFM,0.0,0);
			constraint->setDbgDrawSize(btScalar(2.f));
			m_dynamicsWorld->addConstraint(constraint, true);
			constraint =  new CONSTRAINT_TYPE(*staticBody, *m_data->m_BouncingTranslateBody, localA, localB EXTRAPARAMS);
			constraint->setLimit(0, -SIMD_INFINITY, 2);
			constraint->setLimit(1, 0, 0);
			constraint->setLimit(2, -3, -3);
			constraint->setLimit(3, 0, 0);
			constraint->setLimit(4, 0, 0);
			constraint->setLimit(5, 0, 0);
		#ifdef USE_6DOF2
			constraint->setBounce(0,1);
		#else //bounce is named restitution in 6dofspring, but not implemented for translational limit motor, so the following line has no effect
			constraint->getTranslationalLimitMotor()->m_restitution = 1.0;
		#endif
			constraint->setParam(BT_CONSTRAINT_STOP_ERP,0.995,0);
			constraint->setParam(BT_CONSTRAINT_STOP_CFM,0.0,0);
			constraint->setDbgDrawSize(btScalar(2.f));
			m_dynamicsWorld->addConstraint(constraint, true);
		}

/////////// box with rotational motor, attached to static body
/////////// the box should rotate around the y axis
		{
			mass = 1.0;
			shape= new btBoxShape(btVector3(0.5,0.5,0.5));
			shape->calculateLocalInertia(mass,localInertia);
			bodyTransform.setIdentity();
			bodyTransform.setOrigin(btVector3(4,0,0));
			motionState = new btDefaultMotionState(bodyTransform);
			m_data->m_MotorBody = new btRigidBody(mass,motionState,shape,localInertia);
			m_data->m_MotorBody->setActivationState(DISABLE_DEACTIVATION);
			m_dynamicsWorld->addRigidBody(m_data->m_MotorBody);
			localA.setIdentity();localA.getOrigin() = btVector3(4,0,0);
			localB.setIdentity();
			constraint =  new CONSTRAINT_TYPE(*staticBody, *m_data->m_MotorBody, localA, localB EXTRAPARAMS);
			constraint->setLimit(0, 0, 0);
			constraint->setLimit(1, 0, 0);
			constraint->setLimit(2, 0, 0);
			constraint->setLimit(3, 0, 0);
			constraint->setLimit(4, 0, 0);
			constraint->setLimit(5, 1,-1);
		#ifdef USE_6DOF2
			constraint->enableMotor(5,true);
			constraint->setTargetVelocity(5,3.f);
			constraint->setMaxMotorForce(5,10.f);
		#else
			constraint->getRotationalLimitMotor(2)->m_enableMotor = true;
			constraint->getRotationalLimitMotor(2)->m_targetVelocity = 3.f;
			constraint->getRotationalLimitMotor(2)->m_maxMotorForce = 10;
		#endif
			constraint->setDbgDrawSize(btScalar(2.f));
			m_dynamicsWorld->addConstraint(constraint, true);
		}

/////////// box with rotational servo motor, attached to static body
/////////// the box should rotate around the y axis until it reaches its target
/////////// the target will be negated periodically
		{
			mass = 1.0;
			shape= new btBoxShape(btVector3(0.5,0.5,0.5));
			shape->calculateLocalInertia(mass,localInertia);
			bodyTransform.setIdentity();
			bodyTransform.setOrigin(btVector3(7,0,0));
			motionState = new btDefaultMotionState(bodyTransform);
			m_data->m_ServoMotorBody = new btRigidBody(mass,motionState,shape,localInertia);
			m_data->m_ServoMotorBody->setActivationState(DISABLE_DEACTIVATION);
			m_dynamicsWorld->addRigidBody(m_data->m_ServoMotorBody);
			localA.setIdentity();localA.getOrigin() = btVector3(7,0,0);
			localB.setIdentity();
			constraint =  new CONSTRAINT_TYPE(*staticBody, *m_data->m_ServoMotorBody, localA, localB EXTRAPARAMS);
			constraint->setLimit(0, 0, 0);
			constraint->setLimit(1, 0, 0);
			constraint->setLimit(2, 0, 0);
			constraint->setLimit(3, 0, 0);
			constraint->setLimit(4, 0, 0);
			constraint->setLimit(5, 1,-1);
		#ifdef USE_6DOF2
			constraint->enableMotor(5,true);
			constraint->setTargetVelocity(5,3.f);
			constraint->setMaxMotorForce(5,10.f);
			constraint->setServo(5,true);
			constraint->setServoTarget(5, M_PI_2);
		#else
			constraint->getRotationalLimitMotor(2)->m_enableMotor = true;
			constraint->getRotationalLimitMotor(2)->m_targetVelocity = 3.f;
			constraint->getRotationalLimitMotor(2)->m_maxMotorForce = 10;
			//servo motor is not implemented in 6dofspring constraint
		#endif
			constraint->setDbgDrawSize(btScalar(2.f));
			m_dynamicsWorld->addConstraint(constraint, true);
			m_data->m_ServoMotorConstraint = constraint;
		}

////////// chain of boxes linked together with fully limited rotational and translational constraints
////////// the chain will be pulled to the left and to the right periodically. They should strictly stick together.
		{
			btScalar limitConstraintStrength = 0.6;
			int bodycount = 10;
			btRigidBody* prevBody = 0;
			for(int i = 0; i < bodycount; ++i)
			{
				mass = 1.0;
				shape= new btBoxShape(btVector3(0.5,0.5,0.5));
				shape->calculateLocalInertia(mass,localInertia);
				bodyTransform.setIdentity();
				bodyTransform.setOrigin(btVector3(- i,0,3));
				motionState = new btDefaultMotionState(bodyTransform);
				btRigidBody* body = new btRigidBody(mass,motionState,shape,localInertia);
				body->setActivationState(DISABLE_DEACTIVATION);
				m_dynamicsWorld->addRigidBody(body);
				if(prevBody != 0)
				{
					localB.setIdentity();
					localB.setOrigin(btVector3(0.5,0,0));
					btTransform localA;
					localA.setIdentity();
					localA.setOrigin(btVector3(-0.5,0,0));
					CONSTRAINT_TYPE* constraint =  new CONSTRAINT_TYPE(*prevBody, *body, localA, localB EXTRAPARAMS);
					constraint->setLimit(0, -0.01, 0.01);
					constraint->setLimit(1, 0, 0);
					constraint->setLimit(2, 0, 0);
					constraint->setLimit(3, 0, 0);
					constraint->setLimit(4, 0, 0);
					constraint->setLimit(5, 0, 0);
					for(int a = 0; a < 6; ++a)
					{
						constraint->setParam(BT_CONSTRAINT_STOP_ERP,0.9,a);
						constraint->setParam(BT_CONSTRAINT_STOP_CFM,0.0,a);
					}
					constraint->setDbgDrawSize(btScalar(1.f));
					m_dynamicsWorld->addConstraint(constraint, true);

					if(i < bodycount - 1)
					{
						localA.setIdentity();localA.getOrigin() = btVector3(0,0,3);
						localB.setIdentity();
						CONSTRAINT_TYPE* constraintZY =  new CONSTRAINT_TYPE(*staticBody, *body, localA, localB EXTRAPARAMS);
						constraintZY->setLimit(0, 1, -1);
						constraintZY->setDbgDrawSize(btScalar(1.f));
						m_dynamicsWorld->addConstraint(constraintZY, true);
						
					}
				}
				else
				{
					localA.setIdentity();localA.getOrigin() = btVector3(bodycount,0,3);
					localB.setIdentity();
					localB.setOrigin(btVector3(0,0,0));
					m_data->m_ChainLeftBody = body;
					m_data->m_ChainLeftConstraint = new CONSTRAINT_TYPE(*staticBody, *body, localA, localB EXTRAPARAMS);
					m_data->m_ChainLeftConstraint->setLimit(3,0,0);
					m_data->m_ChainLeftConstraint->setLimit(4,0,0);
					m_data->m_ChainLeftConstraint->setLimit(5,0,0);
					for(int a = 0; a < 6; ++a)
					{
						m_data->m_ChainLeftConstraint->setParam(BT_CONSTRAINT_STOP_ERP,limitConstraintStrength,a);
						m_data->m_ChainLeftConstraint->setParam(BT_CONSTRAINT_STOP_CFM,0.0,a);
					}
					m_data->m_ChainLeftConstraint->setDbgDrawSize(btScalar(1.f));
					m_dynamicsWorld->addConstraint(m_data->m_ChainLeftConstraint, true);
				}
				prevBody = body;
			}
			m_data->m_ChainRightBody = prevBody;
			localA.setIdentity();localA.getOrigin() = btVector3(-bodycount,0,3);
			localB.setIdentity();
			localB.setOrigin(btVector3(0,0,0));
			m_data->m_ChainRightConstraint = new CONSTRAINT_TYPE(*staticBody, *m_data->m_ChainRightBody, localA, localB EXTRAPARAMS);
			m_data->m_ChainRightConstraint->setLimit(3,0,0);
			m_data->m_ChainRightConstraint->setLimit(4,0,0);
			m_data->m_ChainRightConstraint->setLimit(5,0,0);
			for(int a = 0; a < 6; ++a)
			{
				m_data->m_ChainRightConstraint->setParam(BT_CONSTRAINT_STOP_ERP,limitConstraintStrength,a);
				m_data->m_ChainRightConstraint->setParam(BT_CONSTRAINT_STOP_CFM,0.0,a);
			}
		}
		m_guiHelper->autogenerateGraphicsObjects(m_dynamicsWorld);
}
Ejemplo n.º 6
0
void initBullet()
{

	int i;

	///collision configuration contains default setup for memory, collision setup. 
	// Advanced users can create their own configuration.
	collisionConfiguration = new btDefaultCollisionConfiguration();

	///use the default collision dispatcher. For parallel processing you can 
	// use a diffent dispatcher (see Extras/BulletMultiThreaded)
	dispatcher = new	btCollisionDispatcher(collisionConfiguration);

	///btDbvtBroadphase is a good general purpose broadphase. 
	// You can also try out btAxis3Sweep.
	overlappingPairCache = new btDbvtBroadphase();

	///the default constraint solver. For parallel processing you can use a different 
	// solver (see Extras/BulletMultiThreaded)
	solver = new btSequentialImpulseConstraintSolver;

	dynamicsWorld = new btDiscreteDynamicsWorld(dispatcher,overlappingPairCache,solver,collisionConfiguration);

	dynamicsWorld->setGravity(btVector3(0,-10,0));

	///create a few basic rigid bodies
	groundShape = new btBoxShape(btVector3(btScalar(50.),btScalar(50.),btScalar(50.)));


	collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-56,0));

	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);

		//add the body to the dynamics world
		dynamicsWorld->addRigidBody(body);
	}


	{
		//create a dynamic rigidbody

		//btCollisionShape* colShape = new btBoxShape(btVector3(1,1,1));
		btCollisionShape* colShape = new btSphereShape(btScalar(1.));
		collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);

			startTransform.setOrigin(btVector3(2,10,0));
		
			//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
			btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
			btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,colShape,localInertia);
			btRigidBody* body = new btRigidBody(rbInfo);

			dynamicsWorld->addRigidBody(body);
	}



/// Do some simulation



	for (i=0;i<100;i++)
	{
		dynamicsWorld->stepSimulation(1.f/60.f,10);
		
		//print positions of all objects
		for (int j=dynamicsWorld->getNumCollisionObjects()-1; j>=0 ;j--)
		{
			btCollisionObject* obj = dynamicsWorld->getCollisionObjectArray()[j];
			btRigidBody* body = btRigidBody::upcast(obj);
			if (body && body->getMotionState())
			{
				btTransform trans;
				body->getMotionState()->getWorldTransform(trans);
				printf("world pos = %f,%f,%f\n",float(trans.getOrigin().getX()),float(trans.getOrigin().getY()),float(trans.getOrigin().getZ()));
			}
		}
	}


	//cleanup in the reverse order of creation/initialization

	//remove the rigidbodies from the dynamics world and delete them
	for (i=dynamicsWorld->getNumCollisionObjects()-1; i>=0 ;i--)
	{
		btCollisionObject* obj = dynamicsWorld->getCollisionObjectArray()[i];
		btRigidBody* body = btRigidBody::upcast(obj);
		if (body && body->getMotionState())
		{
			delete body->getMotionState();
		}
		dynamicsWorld->removeCollisionObject( obj );
		delete obj;
	}

	finishBullet();
}
Ejemplo n.º 7
0
void	BasicDemo::initPhysics()
{

#ifdef FORCE_ZAXIS_UP
	m_cameraUp = btVector3(0,0,1);
	m_forwardAxis = 1;
#endif
	
	gContactAddedCallback = CustomMaterialCombinerCallback;

	setTexturing(true);
	setShadows(false);

	setCameraDistance(btScalar(SCALING*20.));
	this->m_azi = 90;

	///collision configuration contains default setup for memory, collision setup
	m_collisionConfiguration = new btDefaultCollisionConfiguration();
	//m_collisionConfiguration->setConvexConvexMultipointIterations();

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);

	m_broadphase = new btDbvtBroadphase();

	///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
	btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
	m_solver = sol;

	m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);

#ifdef FORCE_ZAXIS_UP
	m_dynamicsWorld->setGravity(btVector3(0,0,-10));
#else
	m_dynamicsWorld->setGravity(btVector3(0,-10,0));
#endif
	m_dynamicsWorld->getSolverInfo().m_solverMode |= SOLVER_DISABLE_VELOCITY_DEPENDENT_FRICTION_DIRECTION+SOLVER_USE_2_FRICTION_DIRECTIONS;
	m_dynamicsWorld->getSolverInfo().m_solverMode |= SOLVER_ENABLE_FRICTION_DIRECTION_CACHING;

#if 1
	m_blendReader = new BasicBlendReader(m_dynamicsWorld,this);


	//const char* fileName = "clubsilo_packed.blend";
	const char* fileName = "PhysicsAnimationBakingDemo.blend";
	
	char fullPath[512];
	
	if(!m_blendReader->openFile(fileName))
	{

		sprintf(fullPath,"../../%s",fileName);
		m_blendReader->openFile(fullPath);
		
	}

	if (m_blendReader)
	{
		m_blendReader->convertAllObjects();
	} else
	{
		printf("file not found\n");
	}
#endif

	///create a few basic rigid bodies
#if 0
	btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(50.),btScalar(50.),btScalar(50.)));
//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-60,0));


	//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);

		//enable custom material callback
		body->setCollisionFlags(body->getCollisionFlags()  | btCollisionObject::CF_CUSTOM_MATERIAL_CALLBACK);

		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);
	}
#endif

#if 0
	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance

		//btCollisionShape* colShape = new btBoxShape(btVector3(SCALING*1,SCALING*1,SCALING*1));
		//btCollisionShape* colShape = new btBoxShape(btVector3(SCALING*.1,SCALING*.1,SCALING*.1));
		btCollisionShape* colShape = new btSphereShape(SCALING*btScalar(1.));
		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);

	
		float start_x = -ARRAY_SIZE_X;
		float start_y = -ARRAY_SIZE_Y;
		float start_z = - ARRAY_SIZE_Z;


		for (int k=0;k<ARRAY_SIZE_Y;k++)
		{
			for (int i=0;i<ARRAY_SIZE_X;i++)
			{
				for(int j = 0;j<ARRAY_SIZE_Z;j++)
				{
					startTransform.setOrigin(1.*SCALING*btVector3(
										2.0*i + start_x,
										2.0*k + start_y,
										2.0*j + start_z));

			
					//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
					btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
					btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,colShape,localInertia);
					btRigidBody* body = new btRigidBody(rbInfo);
					//body->setContactProcessingThreshold(colShape->getContactBreakingThreshold());
					body->setActivationState(ISLAND_SLEEPING);
					body->setCollisionFlags(btCollisionObject::CF_NO_CONTACT_RESPONSE);

				//	m_dynamicsWorld->addRigidBody(body);
					body->setActivationState(ISLAND_SLEEPING);
				}
			}
		}
	}

	btTriangleIndexVertexArray* meshInterface = new btTriangleIndexVertexArray();
	btIndexedMesh indexMesh;
	
	indexMesh.m_numTriangles = BUNNY_NUM_TRIANGLES ;
	indexMesh.m_numVertices = BUNNY_NUM_VERTICES;
	indexMesh.m_vertexBase = (const unsigned char*) &gVerticesBunny[0];
	indexMesh.m_vertexStride = 3*sizeof(REAL);
	indexMesh.m_triangleIndexBase = (const unsigned char*)&gIndicesBunny[0];
	indexMesh.m_triangleIndexStride = 3*sizeof(int);
	meshInterface->addIndexedMesh(indexMesh);
	btBvhTriangleMeshShape* bunny = new btBvhTriangleMeshShape(meshInterface,true);
	bunny->setLocalScaling(btVector3(2,2,2));
	btCollisionObject* obj = new btCollisionObject();
	btTransform tr;
	tr.setIdentity();
	tr.setOrigin(btVector3(0,2,-20));
	obj ->setWorldTransform(tr);
	obj->setCollisionShape(bunny);
	m_dynamicsWorld->addCollisionObject(obj);
#endif

#if 0
	btConvexTriangleMeshShape* convexBun = new btConvexTriangleMeshShape(meshInterface);
	obj = new btCollisionObject();
	tr.setOrigin(btVector3(0,2,-14));
	obj ->setWorldTransform(tr);
	obj->setCollisionShape(convexBun);
	m_dynamicsWorld->addCollisionObject(obj);
#endif

#if 0
	btConvexTriangleMeshShape* convexBun = new btConvexTriangleMeshShape(meshInterface);
	obj = new btCollisionObject();
	tr.setOrigin(btVector3(0,2,-14));
	obj ->setWorldTransform(tr);
	obj->setCollisionShape(convexBun);
	m_dynamicsWorld->addCollisionObject(obj);


	
	
	//btDiscreteCollisionDetectorInterface::ClosestPointInput input;
	//input.m_maximumDistanceSquared = btScalar(BT_LARGE_FLOAT);///@todo: tighter bounds
	//input.m_transformA = sphereObj->getWorldTransform();
	//input.m_transformB = triObj->getWorldTransform();
	//bool swapResults = m_swapped;
	//detector.getClosestPoints(input,*resultOut,dispatchInfo.m_debugDraw,swapResults);


	
	for (int v=1;v<10;v++)
	{

		float VOXEL_SIZE = VOXEL_SIZE_START * v;
		
		btVoxelizationCallback voxelizationCallback;

		btCompoundShape* compoundBunny = new btCompoundShape();
		voxelizationCallback.m_bunnyCompound = compoundBunny;
		voxelizationCallback.m_sphereChildShape = new btSphereShape(VOXEL_SIZE);

	#if 1
		float start_x = -ARRAY_SIZE_X;
			float start_y = -ARRAY_SIZE_Y;
			float start_z = - ARRAY_SIZE_Z;


		for (int k=0;k<ARRAY_SIZE_Y;k++)
		{
			for (int i=0;i<ARRAY_SIZE_X;i++)
			{
				for(int j = 0;j<ARRAY_SIZE_Z;j++)
				{
					btVector3 pos =VOXEL_SIZE*SCALING*btVector3(
										2.0*i + start_x,
										2.0*k + start_y,
										2.0*j + start_z);
					btVector3 aabbMin(pos-btVector3(VOXEL_SIZE,VOXEL_SIZE,VOXEL_SIZE));
					btVector3 aabbMax(pos+btVector3(VOXEL_SIZE,VOXEL_SIZE,VOXEL_SIZE));
					voxelizationCallback.m_curSpherePos = pos;
					voxelizationCallback.m_oncePerSphere = false;

					bunny->processAllTriangles(&voxelizationCallback,aabbMin,aabbMax);
				}
			}
		}
		
		//btCollisionObject* obj2 = new btCollisionObject();
		//obj2->setCollisionShape(compoundBunny);
		//m_dynamicsWorld->addCollisionObject(obj2);

		btVector3 localInertia;
		compoundBunny->calculateLocalInertia(1,localInertia);
		btRigidBody* body = new btRigidBody(1,0,compoundBunny,localInertia);
		//m_dynamicsWorld->addRigidBody(body);
		btTransform start;
		start.setIdentity();
		start.setOrigin(btVector3(0,2,-12+6*v));
		localCreateRigidBody(1.,start,compoundBunny);
		printf("compoundBunny with %d spheres\n",compoundBunny->getNumChildShapes());

	#endif
}
#endif


	clientResetScene();
}
Ejemplo n.º 8
0
bool csBulletRigidBody::AddBulletObject ()
{
  // TODO: don't recompute everything if the internal scale hasn't changed

  if (insideWorld)
    RemoveBulletObject ();

  btVector3 localInertia (0.0f, 0.0f, 0.0f);
  float mass = GetMass ();

  btCollisionShape* shape;
  btTransform principalAxis;
  principalAxis.setIdentity ();
  btVector3 principalInertia(0,0,0);

  //Create btRigidBody
  if (compoundShape)
  {
    int shapeCount = compoundShape->getNumChildShapes ();
    CS_ALLOC_STACK_ARRAY(btScalar, masses, shapeCount); 
    for (int i = 0; i < shapeCount; i++)
      masses[i] = density * colliders[i]->GetVolume ();
    if (shapeChanged)
    {
      compoundShape->calculatePrincipalAxisTransform
        (masses, principalAxis, principalInertia);
      // apply principal axis
      // creation is faster using a new compound to store the shifted children
      btCompoundShape* newCompoundShape = new btCompoundShape();
      for (int i = 0; i < shapeCount; i++)
      {
        btTransform newChildTransform =
          principalAxis.inverse() * compoundShape->getChildTransform (i);
        newCompoundShape->addChildShape(newChildTransform,
          compoundShape->getChildShape (i));
        shapeChanged = false;
      }
      delete compoundShape;
      compoundShape = newCompoundShape;
    }

    shape = compoundShape;
  }
  else
  {
    shape = colliders[0]->shape;
    principalAxis = CSToBullet (relaTransforms[0], system->getInternalScale ());
  }

  // create new motion state
  btTransform trans;
  motionState->getWorldTransform (trans);
  trans = trans * motionState->inversePrincipalAxis;
  delete motionState;
  motionState = new csBulletMotionState (this, trans * principalAxis,
    principalAxis);

  //shape->calculateLocalInertia (mass, localInertia);

  btRigidBody::btRigidBodyConstructionInfo infos (mass, motionState,
    shape, localInertia);

  infos.m_friction = friction;
  infos.m_restitution = elasticity;
  infos.m_linearDamping = linearDampening;
  infos.m_angularDamping = angularDampening;

  // create new rigid body
  btBody = new btRigidBody (infos);
  btObject = btBody;

  if (haveStaticColliders > 0)
    physicalState = CS::Physics::STATE_STATIC;

  SetState (physicalState);

  sector->bulletWorld->addRigidBody (btBody, collGroup.value, collGroup.mask);
  btBody->setUserPointer (dynamic_cast<CS::Collisions::iCollisionObject*> (
    dynamic_cast<csBulletCollisionObject*>(this)));
 
  insideWorld = true;
  return true;
}
Ejemplo n.º 9
0
bool csBulletRigidBody::SetState (CS::Physics::RigidBodyState state)
{
  if (physicalState != state || !insideWorld)
  {
    CS::Physics::RigidBodyState previousState = physicalState;
    physicalState = state;

    if (!btBody)
      return false;

    if (haveStaticColliders > 0 && state != CS::Physics::STATE_STATIC)
      return false;

    if (insideWorld)
      sector->bulletWorld->removeRigidBody (btBody);

    btVector3 linearVelo = CSToBullet (linearVelocity, system->getInternalScale ());
    btVector3 angularVelo = btVector3 (angularVelocity.x, angularVelocity.y, angularVelocity.z);

    if (previousState == CS::Physics::STATE_KINEMATIC && insideWorld)
    {
      btBody->setCollisionFlags (btBody->getCollisionFlags()
        & ~btCollisionObject::CF_KINEMATIC_OBJECT);

      linearVelo = btBody->getInterpolationLinearVelocity ();
      angularVelo = btBody->getInterpolationAngularVelocity ();

      // create new motion state
      btTransform principalAxis = motionState->inversePrincipalAxis.inverse ();
      btTransform trans;
      motionState->getWorldTransform (trans);
      trans = trans * motionState->inversePrincipalAxis;
      delete motionState;
      motionState = new csBulletMotionState
        (this, trans * principalAxis, principalAxis);
      btBody->setMotionState (motionState);
    }

    if (state == CS::Physics::STATE_DYNAMIC)
    {
      btBody->setCollisionFlags (btBody->getCollisionFlags()
        & ~btCollisionObject::CF_STATIC_OBJECT);

      float mass = GetMass ();
      btVector3 localInertia (0.0f, 0.0f, 0.0f);

      if (compoundShape)
        compoundShape->calculateLocalInertia (mass, localInertia);
      else
        colliders[0]->shape->calculateLocalInertia (mass, localInertia);

      btBody->setMassProps (mass, localInertia);

      btBody->forceActivationState (ACTIVE_TAG);

      btBody->setLinearVelocity (linearVelo);
      btBody->setAngularVelocity (angularVelo);
      btBody->updateInertiaTensor ();
    }
    else if (state == CS::Physics::STATE_KINEMATIC)
    {
      if (!kinematicCb)
        kinematicCb.AttachNew (new csBulletDefaultKinematicCallback ());

      // create new motion state
      btTransform principalAxis = motionState->inversePrincipalAxis.inverse ();
      btTransform trans;
      motionState->getWorldTransform (trans);
      delete motionState;
      motionState = new csBulletKinematicMotionState
        (this, trans, principalAxis);
      btBody->setMotionState (motionState);

      // set body kinematic

      btBody->setMassProps (0.0f, btVector3 (0.0f, 0.0f, 0.0f));

      btBody->setCollisionFlags (btBody->getCollisionFlags()
        | btCollisionObject::CF_KINEMATIC_OBJECT
        & ~btCollisionObject::CF_STATIC_OBJECT);
      btBody->setActivationState (DISABLE_DEACTIVATION);    
      btBody->updateInertiaTensor ();
      btBody->setInterpolationWorldTransform (btBody->getWorldTransform ());
      btBody->setInterpolationLinearVelocity (btVector3(0.0f, 0.0f, 0.0f));
      btBody->setInterpolationAngularVelocity (btVector3(0.0f, 0.0f, 0.0f));
    }
    else if (state == CS::Physics::STATE_STATIC)
    {
      btBody->setCollisionFlags (btBody->getCollisionFlags()
        | btCollisionObject::CF_STATIC_OBJECT
        & ~btCollisionObject::CF_KINEMATIC_OBJECT);
      btBody->setActivationState (ISLAND_SLEEPING);    
      btBody->setMassProps (0.0f, btVector3 (0.0f, 0.0f, 0.0f));
      btBody->updateInertiaTensor ();
    }

    if (insideWorld)
      sector->bulletWorld->addRigidBody (btBody);
    return true;
  }
  else
    return false;
}
Ejemplo n.º 10
0
void BasicGpuDemo::createObjects()
{
		///create a few basic rigid bodies
	btBoxShape* groundShape = new btBoxShape(btVector3(btScalar(150.),btScalar(50.),btScalar(150.)));
	//groundShape->initializePolyhedralFeatures();
//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	
	m_collisionShapes.push_back(groundShape);
	if (0)
	{
		btTransform tr;
		tr.setIdentity();
		btVector3 faraway(-1e30,-1e30,-1e30);

		tr.setOrigin(faraway);
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(tr);
		btSphereShape* dummyShape = new btSphereShape(0.f);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,dummyShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);

		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);


	}
	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-50,0));
		//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		//btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,0,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);
		body->setWorldTransform(groundTransform);

		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);
	}
	
	
	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance

		btBoxShape* colShape = new btBoxShape(btVector3(SCALING*1,SCALING*1,SCALING*1));
		//btCollisionShape* colShape = new btSphereShape(btScalar(SCALING*1.f));
		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);

		float start_x = START_POS_X - ARRAY_SIZE_X/2;
		float start_y = START_POS_Y;
		float start_z = START_POS_Z - ARRAY_SIZE_Z/2;

		for (int k=0;k<ARRAY_SIZE_Y;k++)
		{
			for (int i=0;i<ARRAY_SIZE_X;i++)
			{
				for(int j = 0;j<ARRAY_SIZE_Z;j++)
				{
					startTransform.setOrigin(SCALING*btVector3(
										btScalar(2.*i + start_x),
										btScalar(6+2.0*k + start_y),
										btScalar(2.*j + start_z)));

			
					//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
					//btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
					btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,0,colShape,localInertia);
					btRigidBody* body = new btRigidBody(rbInfo);
					body->setWorldTransform(startTransform);
					

					m_dynamicsWorld->addRigidBody(body);
				}
			}
		}
	}

	


	m_np->writeAllBodiesToGpu();
	m_bp->writeAabbsToGpu();
	m_rbp->writeAllInstancesToGpu();

}
Ejemplo n.º 11
0
void	CcdPhysicsDemo::initPhysics()
{
	setTexturing(true);
	setShadows(true);
	
	m_ShootBoxInitialSpeed = 4000.f;

	m_defaultContactProcessingThreshold = 0.f;

	///collision configuration contains default setup for memory, collision setup
	m_collisionConfiguration = new btDefaultCollisionConfiguration();
//	m_collisionConfiguration->setConvexConvexMultipointIterations();

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);
	//m_dispatcher->registerCollisionCreateFunc(BOX_SHAPE_PROXYTYPE,BOX_SHAPE_PROXYTYPE,m_collisionConfiguration->getCollisionAlgorithmCreateFunc(CONVEX_SHAPE_PROXYTYPE,CONVEX_SHAPE_PROXYTYPE));

	m_broadphase = new btDbvtBroadphase();

	///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
	btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
	m_solver = sol;

	m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
	m_dynamicsWorld->getSolverInfo().m_solverMode |=SOLVER_USE_2_FRICTION_DIRECTIONS|SOLVER_RANDMIZE_ORDER;
	
	

	m_dynamicsWorld ->setDebugDrawer(&sDebugDrawer);

	//m_dynamicsWorld->getSolverInfo().m_splitImpulse=false;
	


	if (m_ccdMode==USE_CCD)
	{
		m_dynamicsWorld->getDispatchInfo().m_useContinuous=true;
	} else
	{
		m_dynamicsWorld->getDispatchInfo().m_useContinuous=false;
	}

	m_dynamicsWorld->setGravity(btVector3(0,-10,0));

	///create a few basic rigid bodies
	btBoxShape* box = new btBoxShape(btVector3(btScalar(110.),btScalar(1.),btScalar(110.)));
//	box->initializePolyhedralFeatures();
	btCollisionShape* groundShape = box;

//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	
	m_collisionShapes.push_back(groundShape);
	//m_collisionShapes.push_back(new btCylinderShape (btVector3(CUBE_HALF_EXTENTS,CUBE_HALF_EXTENTS,CUBE_HALF_EXTENTS)));
	m_collisionShapes.push_back(new btBoxShape (btVector3(CUBE_HALF_EXTENTS,CUBE_HALF_EXTENTS,CUBE_HALF_EXTENTS)));

	btTransform groundTransform;
	groundTransform.setIdentity();
	//groundTransform.setOrigin(btVector3(5,5,5));

	//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);
		body->setFriction(0.5);
		//body->setRollingFriction(0.3);
		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);
	}


	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance

		btCollisionShape* colShape = new btBoxShape(btVector3(1,1,1));

		//btCollisionShape* colShape = new btSphereShape(btScalar(1.));
		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);

		int gNumObjects = 120;//120;
		int i;
		for (i=0;i<gNumObjects;i++)
		{
			btCollisionShape* shape = m_collisionShapes[1];
			
			btTransform trans;
			trans.setIdentity();

			//stack them
			int colsize = 10;
			int row = (i*CUBE_HALF_EXTENTS*2)/(colsize*2*CUBE_HALF_EXTENTS);
			int row2 = row;
			int col = (i)%(colsize)-colsize/2;


			if (col>3)
			{
				col=11;
				row2 |=1;
			}

			btVector3 pos(col*2*CUBE_HALF_EXTENTS + (row2%2)*CUBE_HALF_EXTENTS,
				row*2*CUBE_HALF_EXTENTS+CUBE_HALF_EXTENTS+EXTRA_HEIGHT,0);

			trans.setOrigin(pos);
	
			float mass = 1.f;

			btRigidBody* body = localCreateRigidBody(mass,trans,shape);
			body->setAnisotropicFriction(shape->getAnisotropicRollingFrictionDirection(),btCollisionObject::CF_ANISOTROPIC_ROLLING_FRICTION);
			body->setFriction(0.5);

			//body->setRollingFriction(.3);	
			///when using m_ccdMode
			if (m_ccdMode==USE_CCD)
			{
				body->setCcdMotionThreshold(CUBE_HALF_EXTENTS);
				body->setCcdSweptSphereRadius(0.9*CUBE_HALF_EXTENTS);
			}
		}
	}

}
Ejemplo n.º 12
0
void FractureDemo::initPhysics()
{
	m_guiHelper->setUpAxis(1);

	///collision configuration contains default setup for memory, collision setup
	m_collisionConfiguration = new btDefaultCollisionConfiguration();
	//m_collisionConfiguration->setConvexConvexMultipointIterations();

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new btCollisionDispatcher(m_collisionConfiguration);

	m_broadphase = new btDbvtBroadphase();

	///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
	btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
	m_solver = sol;

	//m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);

	btFractureDynamicsWorld* fractureWorld = new btFractureDynamicsWorld(m_dispatcher, m_broadphase, m_solver, m_collisionConfiguration);
	m_dynamicsWorld = fractureWorld;
	m_guiHelper->createPhysicsDebugDrawer(m_dynamicsWorld);

	//m_splitImpulse removes the penetration resolution from the applied impulse, otherwise objects might fracture due to deep penetrations.
	m_dynamicsWorld->getSolverInfo().m_splitImpulse = true;

	{
		///create a few basic rigid bodies
		btCollisionShape* groundShape = new btBoxShape(btVector3(50, 1, 50));
		///	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),0);
		m_collisionShapes.push_back(groundShape);
		btTransform groundTransform;
		groundTransform.setIdentity();
		groundTransform.setOrigin(btVector3(0, 0, 0));
		createRigidBody(0.f, groundTransform, groundShape);
	}

	{
		///create a few basic rigid bodies
		btCollisionShape* shape = new btBoxShape(btVector3(1, 1, 1));
		m_collisionShapes.push_back(shape);
		btTransform tr;
		tr.setIdentity();
		tr.setOrigin(btVector3(5, 2, 0));
		createRigidBody(0.f, tr, shape);
	}

	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance

		btCollisionShape* colShape = new btBoxShape(btVector3(SCALING * 1, SCALING * 1, SCALING * 1));
		//btCollisionShape* colShape = new btCapsuleShape(SCALING*0.4,SCALING*1);
		//btCollisionShape* colShape = new btSphereShape(btScalar(1.));
		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0, 0, 0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass, localInertia);

		int gNumObjects = 10;

		for (int i = 0; i < gNumObjects; i++)
		{
			btTransform trans;
			trans.setIdentity();

			btVector3 pos(i * 2 * CUBE_HALF_EXTENTS, 20, 0);
			trans.setOrigin(pos);

			//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
			btDefaultMotionState* myMotionState = new btDefaultMotionState(trans);
			btRigidBody::btRigidBodyConstructionInfo rbInfo(mass, myMotionState, colShape, localInertia);
			btFractureBody* body = new btFractureBody(rbInfo, m_dynamicsWorld);
			body->setLinearVelocity(btVector3(0, -10, 0));

			m_dynamicsWorld->addRigidBody(body);
		}
	}

	fractureWorld->stepSimulation(1. / 60., 0);
	fractureWorld->glueCallback();

	m_guiHelper->autogenerateGraphicsObjects(m_dynamicsWorld);
}
Ejemplo n.º 13
0
bool BtBody::init(   PhysicsCollision *shape, 
                        F32 mass,
                        U32 bodyFlags,
                        SceneObject *obj, 
                        PhysicsWorld *world )
{
   AssertFatal( obj, "BtBody::init - Got a null scene object!" );
   AssertFatal( world, "BtBody::init - Got a null world!" );
   AssertFatal( dynamic_cast<BtWorld*>( world ), "BtBody::init - The world is the wrong type!" );
   AssertFatal( shape, "BtBody::init - Got a null collision shape!" );
   AssertFatal( dynamic_cast<BtCollision*>( shape ), "BtBody::init - The collision shape is the wrong type!" );
   AssertFatal( ((BtCollision*)shape)->getShape(), "BtBody::init - Got empty collision shape!" );
	 
   // Cleanup any previous actor.
   _releaseActor();

   mWorld = (BtWorld*)world;

   mColShape = (BtCollision*)shape;
   btCollisionShape *btColShape = mColShape->getShape();
   MatrixF localXfm = mColShape->getLocalTransform();
   btVector3 localInertia( 0, 0, 0 );   

   // If we have a mass then we're dynamic.
   mIsDynamic = mass > 0.0f;
   if ( mIsDynamic )
   {
      if ( btColShape->isCompound() )
      {
         btCompoundShape *btCompound = (btCompoundShape*)btColShape;

         btScalar *masses = new btScalar[ btCompound->getNumChildShapes() ];
         for ( U32 j=0; j < btCompound->getNumChildShapes(); j++ )
	         masses[j] = mass / btCompound->getNumChildShapes();

         btVector3 principalInertia;
         btTransform principal;
         btCompound->calculatePrincipalAxisTransform( masses, principal, principalInertia );
         delete [] masses;

	      // Create a new compound with the shifted children.
	      btColShape = mCompound = new btCompoundShape();
	      for ( U32 i=0; i < btCompound->getNumChildShapes(); i++ )
	      {
		      btTransform newChildTransform = principal.inverse() * btCompound->getChildTransform(i);
		      mCompound->addChildShape( newChildTransform, btCompound->getChildShape(i) );
	      }

         localXfm = btCast<MatrixF>( principal );
      }

      // Note... this looks like we're changing the shape, but 
      // we're not.  All this does is ask the shape to calculate the
      // local inertia vector from the mass... the shape doesn't change.
      btColShape->calculateLocalInertia( mass, localInertia );
   }

   // If we have a local transform then we need to
   // store it and the inverse to offset the center
   // of mass from the graphics origin.
   if ( !localXfm.isIdentity() )
   {
      mCenterOfMass = new MatrixF( localXfm );
      mInvCenterOfMass = new MatrixF( *mCenterOfMass );
      mInvCenterOfMass->inverse();
   }

   mMass = mass;
   mActor = new btRigidBody( mass, NULL, btColShape, localInertia );
   
   int btFlags = mActor->getCollisionFlags();

   if ( bodyFlags & BF_TRIGGER )
      btFlags |= btCollisionObject::CF_NO_CONTACT_RESPONSE;
   if ( bodyFlags & BF_KINEMATIC )
   {
      btFlags &= ~btCollisionObject::CF_STATIC_OBJECT;
      btFlags |= btCollisionObject::CF_KINEMATIC_OBJECT;
   }

   mActor->setCollisionFlags( btFlags );

   mWorld->getDynamicsWorld()->addRigidBody( mActor );
   mIsEnabled = true;

   mUserData.setObject( obj );
   mUserData.setBody( this );
   mActor->setUserPointer( &mUserData );

   return true;
}
Ejemplo n.º 14
0
void	Box2dDemo::initPhysics()
{
	
	m_dialogDynamicsWorld = new GL_DialogDynamicsWorld();

	//m_dialogDynamicsWorld->createDialog(100,110,200,50);
	//m_dialogDynamicsWorld->createDialog(100,00,100,100);
	//m_dialogDynamicsWorld->createDialog(0,0,100,100);
	GL_DialogWindow* settings = m_dialogDynamicsWorld->createDialog(50,0,200,120,"Settings");
	GL_ToggleControl* toggle = m_dialogDynamicsWorld->createToggle(settings,"Toggle 1");
	toggle = m_dialogDynamicsWorld->createToggle(settings,"Toggle 2");
	toggle ->m_active = true;
	toggle = m_dialogDynamicsWorld->createToggle(settings,"Toggle 3");
	//GL_SliderControl* slider = m_dialogDynamicsWorld->createSlider(settings,"Slider");

	GL_DialogWindow* dialog = m_dialogDynamicsWorld->createDialog(0,200,420,300,"Help");
	GL_TextControl* txt = new GL_TextControl;
	dialog->addControl(txt);
	txt->m_textLines.push_back("Mouse to move");
	txt->m_textLines.push_back("Test 2");
	txt->m_textLines.push_back("mouse to interact");
	txt->m_textLines.push_back("ALT + mouse to move camera");
	txt->m_textLines.push_back("space to reset");
	txt->m_textLines.push_back("cursor keys and z,x to navigate");
	txt->m_textLines.push_back("i to toggle simulation, s single step");
	txt->m_textLines.push_back("q to quit");
	txt->m_textLines.push_back(". to shoot box");
	txt->m_textLines.push_back("d to toggle deactivation");
	txt->m_textLines.push_back("g to toggle mesh animation (ConcaveDemo)");
	txt->m_textLines.push_back("h to toggle help text");
	txt->m_textLines.push_back("o to toggle orthogonal/perspective view");
	//txt->m_textLines.push_back("+- shooting speed = %10.2f",m_ShootBoxInitialSpeed);

	
	
	setTexturing(true);
	setShadows(true);

	setCameraDistance(btScalar(SCALING*50.));
	m_cameraTargetPosition.setValue(0,0,0);//0, ARRAY_SIZE_Y, 0);

	///collision configuration contains default setup for memory, collision setup
	m_collisionConfiguration = new btDefaultCollisionConfiguration();
	//m_collisionConfiguration->setConvexConvexMultipointIterations();

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);

	btVoronoiSimplexSolver* simplex = new btVoronoiSimplexSolver();
	btMinkowskiPenetrationDepthSolver* pdSolver = new btMinkowskiPenetrationDepthSolver();


	btConvex2dConvex2dAlgorithm::CreateFunc* convexAlgo2d = new btConvex2dConvex2dAlgorithm::CreateFunc(simplex,pdSolver);
	
	m_dispatcher->registerCollisionCreateFunc(CONVEX_2D_SHAPE_PROXYTYPE,CONVEX_2D_SHAPE_PROXYTYPE,convexAlgo2d);
	m_dispatcher->registerCollisionCreateFunc(BOX_2D_SHAPE_PROXYTYPE,CONVEX_2D_SHAPE_PROXYTYPE,convexAlgo2d);
	m_dispatcher->registerCollisionCreateFunc(CONVEX_2D_SHAPE_PROXYTYPE,BOX_2D_SHAPE_PROXYTYPE,convexAlgo2d);
	m_dispatcher->registerCollisionCreateFunc(BOX_2D_SHAPE_PROXYTYPE,BOX_2D_SHAPE_PROXYTYPE,new btBox2dBox2dCollisionAlgorithm::CreateFunc());

	m_broadphase = new btDbvtBroadphase();
	//m_broadphase = new btSimpleBroadphase();

	///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
	btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
	m_solver = sol;

	m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
	//m_dynamicsWorld->getSolverInfo().m_erp = 1.f;
	//m_dynamicsWorld->getSolverInfo().m_numIterations = 4;
	


	m_dynamicsWorld->setGravity(btVector3(0,-10,0));

	///create a few basic rigid bodies
	btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(150.),btScalar(50.),btScalar(150.)));
//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-43,0));

	//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);

		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);
	}


	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance

		btScalar u= btScalar(1*SCALING-0.04);
		btVector3 points[3] = {btVector3(0,u,0),btVector3(-u,-u,0),btVector3(u,-u,0)};
		btConvexShape* childShape0 = new btBoxShape(btVector3(btScalar(SCALING*1),btScalar(SCALING*1),btScalar(0.04)));
        btConvexShape* colShape= new btConvex2dShape(childShape0);
		//btCollisionShape* colShape = new btBox2dShape(btVector3(SCALING*1,SCALING*1,0.04));
        btConvexShape* childShape1 = new btConvexHullShape(&points[0].getX(),3);
		btConvexShape* colShape2= new btConvex2dShape(childShape1);
        btConvexShape* childShape2 = new btCylinderShapeZ(btVector3(btScalar(SCALING*1),btScalar(SCALING*1),btScalar(0.04)));
		btConvexShape* colShape3= new btConvex2dShape(childShape2);
		

        m_collisionShapes.push_back(colShape);
		m_collisionShapes.push_back(colShape2);
		m_collisionShapes.push_back(colShape3);

        m_collisionShapes.push_back(childShape0);
        m_collisionShapes.push_back(childShape1);
        m_collisionShapes.push_back(childShape2);
        

		//btUniformScalingShape* colShape = new btUniformScalingShape(convexColShape,1.f);
		colShape->setMargin(btScalar(0.03));
		//btCollisionShape* colShape = new btSphereShape(btScalar(1.));

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);

//		float start_x = START_POS_X - ARRAY_SIZE_X/2;
//		float start_y = START_POS_Y;
//		float start_z = START_POS_Z - ARRAY_SIZE_Z/2;

		btVector3 x(-ARRAY_SIZE_X, 8.0f,-20.f);
		btVector3 y;
		btVector3 deltaX(SCALING*1, SCALING*2,0.f);
		btVector3 deltaY(SCALING*2, 0.0f,0.f);

		for (int i = 0; i < ARRAY_SIZE_X; ++i)
		{
			y = x;

			for (int  j = i; j < ARRAY_SIZE_Y; ++j)
			{
					startTransform.setOrigin(y-btVector3(-10,0,0));

			
					//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
					btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
					btRigidBody::btRigidBodyConstructionInfo rbInfo(0,0,0);
					switch (j%3)
					{
#if 1
					case 0:
						rbInfo = btRigidBody::btRigidBodyConstructionInfo(mass,myMotionState,colShape,localInertia);
						break;
					case 1:
						rbInfo = btRigidBody::btRigidBodyConstructionInfo(mass,myMotionState,colShape3,localInertia);
						break;
#endif
					default:
						rbInfo = btRigidBody::btRigidBodyConstructionInfo(mass,myMotionState,colShape2,localInertia);
					}
					btRigidBody* body = new btRigidBody(rbInfo);
					//body->setContactProcessingThreshold(colShape->getContactBreakingThreshold());
					body->setActivationState(ISLAND_SLEEPING);
					body->setLinearFactor(btVector3(1,1,0));
					body->setAngularFactor(btVector3(0,0,1));

					m_dynamicsWorld->addRigidBody(body);
					body->setActivationState(ISLAND_SLEEPING);


			//	y += -0.8*deltaY;
				y += deltaY;
			}

			x += deltaX;
		}

	}


	clientResetScene();
}
Ejemplo n.º 15
0
void RigidBody::AddBodyToWorld()
{
    if (!physicsWorld_)
        return;

    URHO3D_PROFILE(AddBodyToWorld);

    if (mass_ < 0.0f)
        mass_ = 0.0f;

    if (body_)
        RemoveBodyFromWorld();
    else
    {
        // Correct inertia will be calculated below
        btVector3 localInertia(0.0f, 0.0f, 0.0f);
        body_ = new btRigidBody(mass_, this, shiftedCompoundShape_, localInertia);
        body_->setUserPointer(this);

        // Check for existence of the SmoothedTransform component, which should be created by now in network client mode.
        // If it exists, subscribe to its change events
        smoothedTransform_ = GetComponent<SmoothedTransform>();
        if (smoothedTransform_)
        {
            SubscribeToEvent(smoothedTransform_, E_TARGETPOSITION, URHO3D_HANDLER(RigidBody, HandleTargetPosition));
            SubscribeToEvent(smoothedTransform_, E_TARGETROTATION, URHO3D_HANDLER(RigidBody, HandleTargetRotation));
        }

        // Check if CollisionShapes already exist in the node and add them to the compound shape.
        // Do not update mass yet, but do it once all shapes have been added
        PODVector<CollisionShape*> shapes;
        node_->GetComponents<CollisionShape>(shapes);
        for (PODVector<CollisionShape*>::Iterator i = shapes.Begin(); i != shapes.End(); ++i)
            (*i)->NotifyRigidBody(false);

        // Check if this node contains Constraint components that were waiting for the rigid body to be created, and signal them
        // to create themselves now
        PODVector<Constraint*> constraints;
        node_->GetComponents<Constraint>(constraints);
        for (PODVector<Constraint*>::Iterator i = constraints.Begin(); i != constraints.End(); ++i)
            (*i)->CreateConstraint();
    }

    UpdateMass();
    UpdateGravity();

    int flags = body_->getCollisionFlags();
    if (trigger_)
        flags |= btCollisionObject::CF_NO_CONTACT_RESPONSE;
    else
        flags &= ~btCollisionObject::CF_NO_CONTACT_RESPONSE;
    if (kinematic_)
        flags |= btCollisionObject::CF_KINEMATIC_OBJECT;
    else
        flags &= ~btCollisionObject::CF_KINEMATIC_OBJECT;
    body_->setCollisionFlags(flags);
    body_->forceActivationState(kinematic_ ? DISABLE_DEACTIVATION : ISLAND_SLEEPING);

    if (!IsEnabledEffective())
        return;

    btDiscreteDynamicsWorld* world = physicsWorld_->GetWorld();
    world->addRigidBody(body_, (short)collisionLayer_, (short)collisionMask_);
    inWorld_ = true;
    readdBody_ = false;

    if (mass_ > 0.0f)
        Activate();
    else
    {
        SetLinearVelocity(Vector3::ZERO);
        SetAngularVelocity(Vector3::ZERO);
    }
}
Ejemplo n.º 16
0
void	RollingFrictionDemo::initPhysics()
{

    m_guiHelper->setUpAxis(2);


    ///collision configuration contains default setup for memory, collision setup
    m_collisionConfiguration = new btDefaultCollisionConfiguration();
    //m_collisionConfiguration->setConvexConvexMultipointIterations();

    ///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
    m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);

    m_broadphase = new btDbvtBroadphase();

    ///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
    btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
    m_solver = sol;

    m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
//	m_dynamicsWorld->getSolverInfo().m_singleAxisRollingFrictionThreshold = 0.f;//faster but lower quality
    m_dynamicsWorld->setGravity(btVector3(0,0,-10));

    m_guiHelper->createPhysicsDebugDrawer(m_dynamicsWorld);

    {

        ///create a few basic rigid bodies
        btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(10.),btScalar(5.),btScalar(25.)));


        m_collisionShapes.push_back(groundShape);

        btTransform groundTransform;
        groundTransform.setIdentity();
        groundTransform.setOrigin(btVector3(0,0,-28));
        groundTransform.setRotation(btQuaternion(btVector3(0,1,0),SIMD_PI*0.03));
        //We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
        btScalar mass(0.);

        //rigidbody is dynamic if and only if mass is non zero, otherwise static
        bool isDynamic = (mass != 0.f);

        btVector3 localInertia(0,0,0);
        if (isDynamic)
            groundShape->calculateLocalInertia(mass,localInertia);

        //using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
        btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
        btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
        btRigidBody* body = new btRigidBody(rbInfo);
        body->setFriction(1);
        body->setRollingFriction(1);
        //add the body to the dynamics world
        m_dynamicsWorld->addRigidBody(body);
    }

    {

        ///create a few basic rigid bodies
        btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(100.),btScalar(100.),btScalar(50.)));

        m_collisionShapes.push_back(groundShape);

        btTransform groundTransform;
        groundTransform.setIdentity();
        groundTransform.setOrigin(btVector3(0,0,-54));
        //We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
        btScalar mass(0.);

        //rigidbody is dynamic if and only if mass is non zero, otherwise static
        bool isDynamic = (mass != 0.f);

        btVector3 localInertia(0,0,0);
        if (isDynamic)
            groundShape->calculateLocalInertia(mass,localInertia);

        //using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
        btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
        btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
        btRigidBody* body = new btRigidBody(rbInfo);
        body->setFriction(1);
        body->setRollingFriction(1);
        //add the body to the dynamics world
        m_dynamicsWorld->addRigidBody(body);
    }

    {
        //create a few dynamic rigidbodies
        // Re-using the same collision is better for memory usage and performance
#define NUM_SHAPES 10
        btCollisionShape* colShapes[NUM_SHAPES] = {
            new btSphereShape(btScalar(0.5)),
            new btCapsuleShape(0.25,0.5),
            new btCapsuleShapeX(0.25,0.5),
            new btCapsuleShapeZ(0.25,0.5),
            new btConeShape(0.25,0.5),
            new btConeShapeX(0.25,0.5),
            new btConeShapeZ(0.25,0.5),
            new btCylinderShape(btVector3(0.25,0.5,0.25)),
            new btCylinderShapeX(btVector3(0.5,0.25,0.25)),
            new btCylinderShapeZ(btVector3(0.25,0.25,0.5)),
        };
        for (int i=0; i<NUM_SHAPES; i++)
            m_collisionShapes.push_back(colShapes[i]);

        /// Create Dynamic Objects
        btTransform startTransform;
        startTransform.setIdentity();

        btScalar	mass(1.f);

        //rigidbody is dynamic if and only if mass is non zero, otherwise static

        float start_x = START_POS_X - ARRAY_SIZE_X/2;
        float start_y = START_POS_Y;
        float start_z = START_POS_Z - ARRAY_SIZE_Z/2;

        {
            int shapeIndex = 0;
            for (int k=0; k<ARRAY_SIZE_Y; k++)
            {
                for (int i=0; i<ARRAY_SIZE_X; i++)
                {
                    for(int j = 0; j<ARRAY_SIZE_Z; j++)
                    {
                        startTransform.setOrigin(SCALING*btVector3(
                                                     btScalar(2.0*i + start_x),
                                                     btScalar(2.0*j + start_z),
                                                     btScalar(20+2.0*k + start_y)));


                        shapeIndex++;
                        btCollisionShape* colShape = colShapes[shapeIndex%NUM_SHAPES];
                        bool isDynamic = (mass != 0.f);
                        btVector3 localInertia(0,0,0);

                        if (isDynamic)
                            colShape->calculateLocalInertia(mass,localInertia);

                        //using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
                        btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
                        btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,colShape,localInertia);
                        btRigidBody* body = new btRigidBody(rbInfo);
                        body->setFriction(1.f);
                        body->setRollingFriction(.3);
                        body->setAnisotropicFriction(colShape->getAnisotropicRollingFrictionDirection(),btCollisionObject::CF_ANISOTROPIC_ROLLING_FRICTION);


                        m_dynamicsWorld->addRigidBody(body);
                    }
                }
            }
        }
    }

    m_guiHelper->autogenerateGraphicsObjects(m_dynamicsWorld);

    if (0)
    {
        btSerializer* s = new btDefaultSerializer;
        m_dynamicsWorld->serialize(s);
        b3ResourcePath p;
        char resourcePath[1024];
        if (p.findResourcePath("slope.bullet",resourcePath,1024))
        {
            FILE* f = fopen(resourcePath,"wb");
            fwrite(s->getBufferPointer(),s->getCurrentBufferSize(),1,f);
            fclose(f);
        }
    }
}
Ejemplo n.º 17
0
void	BasicDemo3D::initPhysics()
{
	setTexturing(true);
	setShadows(false);

//	setCameraDistance(btScalar(SCALING*50.));
#if LARGE_DEMO
	setCameraDistance(btScalar(SCALING*50.));
#else
	setCameraDistance(btScalar(SCALING*20.));
#endif

	m_cameraTargetPosition.setValue(START_POS_X, -START_POS_Y-20, START_POS_Z);
	m_azi = btScalar(0.f);
	m_ele = btScalar(0.f);

	///collision configuration contains default setup for memory, collision setup

	btDefaultCollisionConstructionInfo dci;
	dci.m_defaultMaxPersistentManifoldPoolSize=100000;
	dci.m_defaultMaxCollisionAlgorithmPoolSize=100000;
	dci.m_customCollisionAlgorithmMaxElementSize = sizeof(SpuContactManifoldCollisionAlgorithm);	
	
	
	///SpuContactManifoldCollisionAlgorithm is larger than any of the other collision algorithms
//@@	dci.m_customMaxCollisionAlgorithmSize = sizeof(SpuContactManifoldCollisionAlgorithm);

	m_collisionConfiguration = new btDefaultCollisionConfiguration(dci);

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	//m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);
#ifndef WIN32
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);
#else
	unsigned int	maxNumOutstandingTasks =4;
	//createCollisionLocalStoreMemory();
	//processSolverTask
	Win32ThreadSupport::Win32ThreadConstructionInfo  threadConstructionInfo("narrowphase_multi",processCollisionTask,createCollisionLocalStoreMemory,maxNumOutstandingTasks);
	class	btThreadSupportInterface*	threadInterface = new Win32ThreadSupport(threadConstructionInfo);
	m_dispatcher = new SpuGatheringCollisionDispatcher(threadInterface,maxNumOutstandingTasks,m_collisionConfiguration);
#endif //SINGLE_THREADED_NARROWPHASE


//##	m_dispatcher->registerCollisionCreateFunc(BOX_SHAPE_PROXYTYPE,BOX_SHAPE_PROXYTYPE,new btEmptyAlgorithm::CreateFunc);
//##	m_dispatcher->registerCollisionCreateFunc(CUSTOM_CONVEX_SHAPE_TYPE,CUSTOM_CONVEX_SHAPE_TYPE,new btBox2dBox2dCollisionAlgorithm::CreateFunc);

//	m_broadphase = new btDbvtBroadphase();
	

//##	gPairCache = new (btAlignedAlloc(sizeof(btCudaDemoPairCache),16)) btCudaDemoPairCache(MAX_PROXIES, 24, MAX_SMALL_PROXIES); 
//	gPairCache = NULL;
	gPairCache = new (btAlignedAlloc(sizeof(btHashedOverlappingPairCache),16)) btHashedOverlappingPairCache(); 

	//m_broadphase = new btSimpleBroadphase(16384, gPairCache);

/*
btCudaBroadphase::btCudaBroadphase(	btOverlappingPairCache* overlappingPairCache,
									const btVector3& worldAabbMin,const btVector3& worldAabbMax, 
									int gridSizeX, int gridSizeY, int gridSizeZ, 
									int maxSmallProxies, int maxLargeProxies, int maxPairsPerBody,
									int maxBodiesPerCell,
									btScalar cellFactorAABB)
*/
//	btVector3 numOfCells = (gWorldMax - gWorldMin) / (2. * SCALING * 0.7);
	btVector3 numOfCells = (gWorldMax - gWorldMin) / (2. * SCALING);
	int numOfCellsX = (int)numOfCells[0];
	int numOfCellsY = (int)numOfCells[1];
	int numOfCellsZ = (int)numOfCells[2];

//	m_broadphase = new bt3DGridBroadphase(gPairCache, gWorldMin, gWorldMax,numOfCellsX, numOfCellsY, numOfCellsZ,MAX_SMALL_PROXIES,10,8,8,1./1.5);
//#define USE_CUDA_BROADPHASE 1
#ifdef USE_CUDA_BROADPHASE
	m_broadphase = new btCudaBroadphase(gPairCache, gWorldMin, gWorldMax,numOfCellsX, numOfCellsY, numOfCellsZ,MAX_SMALL_PROXIES,20,18,8,1./1.5);
#else
	
#if DBVT
	btDbvtBroadphase* dbvt = new btDbvtBroadphase(gPairCache);
	m_broadphase = dbvt;
	dbvt->m_deferedcollide=false;
	dbvt->m_prediction = 0.f;
#else
	m_broadphase = new btAxisSweep3(gWorldMin,gWorldMax,32000,gPairCache,true);//(btDbvtBroadphase(gPairCache);
#endif //DBVT

#endif	
	

	// create solvers for tests 
	///the default constraint solver
	sConstraintSolvers[0] = new btSequentialImpulseConstraintSolver();
/*
	sConstraintSolvers[1] = new btParallelBatchConstraintSolver();
	sConstraintSolvers[2] = new btCudaConstraintSolver();
	sConstraintSolvers[3] = new btParallelBatchConstraintSolver2();
	sConstraintSolvers[4] = new btParallelBatchConstraintSolver3();
	sConstraintSolvers[5] = new btCudaConstraintSolver3();
	sConstraintSolvers[6] = new btParallelBatchConstraintSolver4();
	sConstraintSolvers[7] = new btCudaConstraintSolver4();
	sConstraintSolvers[8] = new btParallelBatchConstraintSolver5();
	sConstraintSolvers[9] = new btParallelBatchConstraintSolver6();
	sConstraintSolvers[10] = new btCudaConstraintSolver6();
*/
	sCurrSolverIndex = 0;
	m_solver = sConstraintSolvers[sCurrSolverIndex];
	printf("\nUsing %s\n", sConstraintSolverNames[sCurrSolverIndex]);

//	sCudaMotionInterface = new btCudaMotionInterface(MAX_PROXIES);
//  m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration, sCudaMotionInterface);
//	m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
//##	btCudaDemoDynamicsWorld* pDdw = new btCudaDemoDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
	btCudaDemoDynamicsWorld3D* pDdw = new btCudaDemoDynamicsWorld3D(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
	m_dynamicsWorld = pDdw;
	pDdw->getDispatchInfo().m_enableSPU=true;
	pDdw->getSimulationIslandManager()->setSplitIslands(sCurrSolverIndex == 0);
	pDdw->setObjRad(SCALING);
	pDdw->setWorldMin(gWorldMin);
	pDdw->setWorldMax(gWorldMax);
#ifdef BT_USE_CUDA
	gUseCPUSolver = false;
#else
	gUseCPUSolver = true;
#endif
	pDdw->setUseCPUSolver(gUseCPUSolver);
//	pDdw->setUseSolver2(gUseSolver2);

//	m_dynamicsWorld->setGravity(btVector3(0,0,0));
	m_dynamicsWorld->setGravity(btVector3(0.f,-10.f,0.f));
	m_dynamicsWorld->getSolverInfo().m_numIterations = 4;


	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance


		//btCollisionShape* colShape = new btBoxShape(btVector3(SCALING*1,SCALING*1,0.1));//SCALING*1));
//##		btCollisionShape* colShape = new btBox2dShape(btVector3(SCALING*.7,SCALING*.7,0.1));//SCALING*1));
		btCollisionShape* colShape = new btBoxShape(btVector3(SCALING*.7,SCALING*.7, SCALING*.7));

		//btCollisionShape* colShape = new btSphereShape(btScalar(1.));
		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);
#if (!SPEC_TEST)
		float start_x = START_POS_X - ARRAY_SIZE_X * SCALING;
		float start_y = START_POS_Y - ARRAY_SIZE_Y * SCALING;
		float start_z = START_POS_Z - ARRAY_SIZE_Z * SCALING;

		for (int k=0;k<ARRAY_SIZE_Y;k++)
		{
			for (int i=0;i<ARRAY_SIZE_X;i++)
			{
				for(int j = 0;j<ARRAY_SIZE_Z;j++)
				{
					startTransform.setOrigin(SCALING*btVector3(
										2.0*SCALING*i + start_x,
										2.0*SCALING*k + start_y,
										2.0*SCALING*j + start_z));

			
					//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
					//btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
					btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,0,colShape,localInertia);
					rbInfo.m_startWorldTransform=startTransform;
					btRigidBody* body = new btRigidBody(rbInfo);
					m_dynamicsWorld->addRigidBody(body);
				}
			}
		}
#else
		// narrowphase test - 2 bodies at the same position
		float start_x = START_POS_X;
		float start_y = START_POS_Y;
		float start_z = START_POS_Z;
//		startTransform.setOrigin(SCALING*btVector3(start_x,start_y-14.f,start_z));
		startTransform.setOrigin(SCALING*btVector3(start_x,start_y-11.f,start_z));
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,0,colShape,localInertia);
		rbInfo.m_startWorldTransform=startTransform;
		btRigidBody* body = new btRigidBody(rbInfo);
		m_dynamicsWorld->addRigidBody(body);
//		startTransform.setOrigin(SCALING*btVector3(start_x+1.2f,start_y+1.4f-14.f,start_z));
		startTransform.setOrigin(SCALING*btVector3(start_x,start_y + 1.5f -11.f, start_z));
		rbInfo.m_startWorldTransform=startTransform;
		body = new btRigidBody(rbInfo);
		m_dynamicsWorld->addRigidBody(body);
#endif
	}


#if 0
	///create a few basic rigid bodies
//	btCollisionShape* groundShape = new btBox2dShape(btVector3(btScalar(50.),btScalar(1.),btScalar(50.)));
//	btCollisionShape* groundShape = new btBox2dShape(btVector3(btScalar(228.),btScalar(1.),btScalar(228.)));
//	btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(228.),btScalar(1.),btScalar(228.)));
//	btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(50.),btScalar(50.),btScalar(50.)));
//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	btCollisionShape* groundShape = new btBoxShape(btVector3(POS_OFFS_X, btScalar(1.), POS_OFFS_Z));
	
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0, gWorldMin[1], 0));

//	groundTransform.setOrigin(btVector3(0,-5,0));
//	groundTransform.setOrigin(btVector3(0,-50,0));

	//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);

		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);
	}
#endif
	//clientResetScene();
}
Ejemplo n.º 18
0
void Fenettre::Init()
{
    /// Initialisation d'OpenGL
    // On active la lumière 0
    glEnable(GL_LIGHT0);
    glEnable(GL_LIGHTING);
	// Quelques autres options OpenGL
    glEnable(GL_DEPTH_TEST);
	glEnable(GL_CULL_FACE);
	glEnable(GL_COLOR_MATERIAL);
	glEnable(GL_NORMALIZE);
	glEnable(GL_COLOR);
	glEnable(GL_TEXTURE_2D);
    // Couleur de fond d'écran
    glClearColor(0.0,0.0,0.0,0);
	// l'espace d'affichage
	glViewport( 0, 0, 1200, 900 );
    glewInit();

    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    gluPerspective(70, 800.0/500.0, 0.001f, 1000.0f );

    /// Initialisation de Bullet
    CollisionConfiguration = new btDefaultCollisionConfiguration();
    Dispatcher = new btCollisionDispatcher(CollisionConfiguration);
    Broadphase = new btDbvtBroadphase();
    SequentialImpulseConstraintSolver = new btSequentialImpulseConstraintSolver;
    World = new btDiscreteDynamicsWorld(Dispatcher,Broadphase,SequentialImpulseConstraintSolver,CollisionConfiguration);
    World->setGravity( btVector3(0,GRAVITEE,0));


    btTransform Transform;
    Transform.setIdentity();
	Transform.setOrigin(btVector3(0,0,0));
    btDefaultMotionState* MotionState =new btDefaultMotionState(Transform);

    Terrain = new btStaticPlaneShape(btVector3(0,1,0),0);
    btVector3 localInertia(0,0,0);
    float mass=0;
    Terrain->calculateLocalInertia(mass,localInertia);
    btRigidBody *body = new btRigidBody(btRigidBody::btRigidBodyConstructionInfo(mass, MotionState, Terrain, localInertia));
    World->addRigidBody(body);

    //test = new RenderTerrain();

    /// Initialisation des shaders

    setActive();

    Prog[0] = new ShaderProgram("shader/mur.frag",sf::Shader::Fragment);
    Prog[0]->setTexture("Texture_Col","textures/Fieldstone.jpg");
    Prog[0]->setTexture("Texture_Normal","textures/FieldstoneBump.jpg");

    Prog[1] = new ShaderProgram("shader/mur.frag",sf::Shader::Fragment);
    Prog[1]->setTexture("Texture_Col","textures/redwall1_t.png");
    Prog[1]->setTexture("Texture_Normal","textures/redwall1_nm.png");


    /// Initialisation des truc perso
    setMouseCursorVisible(false);
    camera = new FreeFlyCamera(btVector3(-5,20,0));
};
Ejemplo n.º 19
0
bool Hair::create(HairSetup *setup, std::shared_ptr<Entity> parent_entity)
{
    // No setup or parent to link to - bypass function.

    if((!parent_entity) || (!setup) ||
       (setup->m_linkBody >= parent_entity->m_bf.bone_tags.size()) ||
       (!(parent_entity->m_bt.bt_body[setup->m_linkBody]))) return false;

    SkeletalModel* model = engine_world.getModelByID(setup->m_model);

    // No model to link to - bypass function.

    if((!model) || (model->mesh_count == 0)) return false;

    // Setup engine container. FIXME: DOESN'T WORK PROPERLY ATM.

    m_container.reset(new EngineContainer());
    m_container->room = parent_entity->m_self->room;
    m_container->object_type = OBJECT_HAIR;
    m_container->object = this;

    // Setup initial hair parameters.

    m_ownerChar = parent_entity;       // Entity to refer to.
    m_ownerBody = setup->m_linkBody;    // Entity body to refer to.

    // Setup initial position / angles.

    btTransform owner_body_transform = parent_entity->m_transform * parent_entity->m_bf.bone_tags[m_ownerBody].full_transform;
    // Number of elements (bodies) is equal to number of hair meshes.

    m_elements.clear();
    m_elements.resize(model->mesh_count);

    // Root index should be always zero, as it is how engine determines that it is
    // connected to head and renders it properly. Tail index should be always the
    // last element of the hair, as it indicates absence of "child" constraint.

    m_rootIndex = 0;
    m_tailIndex = m_elements.size() - 1;

    // Weight step is needed to determine the weight of each hair body.
    // It is derived from root body weight and tail body weight.

    btScalar weight_step = ((setup->m_rootWeight - setup->m_tailWeight) / m_elements.size());
    btScalar current_weight = setup->m_rootWeight;

    for(size_t i = 0; i < m_elements.size(); i++)
    {
        // Point to corresponding mesh.

        m_elements[i].mesh = model->mesh_tree[i].mesh_base;

        // Begin creating ACTUAL physical hair mesh.

        btVector3   localInertia(0, 0, 0);
        btTransform startTransform;

        // Make collision shape out of mesh.

        m_elements[i].shape.reset(BT_CSfromMesh(m_elements[i].mesh, true, true, false));
        m_elements[i].shape->calculateLocalInertia((current_weight * setup->m_hairInertia), localInertia);

        // Decrease next body weight to weight_step parameter.

        current_weight -= weight_step;

        // Initialize motion state for body.

        startTransform = owner_body_transform;
        btDefaultMotionState* motionState = new btDefaultMotionState(startTransform);

        // Make rigid body.

        m_elements[i].body.reset(new btRigidBody(current_weight, motionState, m_elements[i].shape.get(), localInertia));

        // Damping makes body stop in space by itself, to prevent it from continous movement.

        m_elements[i].body->setDamping(setup->m_hairDamping[0], setup->m_hairDamping[1]);

        // Restitution and friction parameters define "bounciness" and "dullness" of hair.

        m_elements[i].body->setRestitution(setup->m_hairRestitution);
        m_elements[i].body->setFriction(setup->m_hairFriction);

        // Since hair is always moving with Lara, even if she's in still state (like, hanging
        // on a ledge), hair bodies shouldn't deactivate over time.

        m_elements[i].body->forceActivationState(DISABLE_DEACTIVATION);

        // Hair bodies must not collide with each other, and also collide ONLY with kinematic
        // bodies (e. g. animated meshes), or else Lara's ghost object or anything else will be able to
        // collide with hair!

        m_elements[i].body->setUserPointer(m_container.get());
        bt_engine_dynamicsWorld->addRigidBody(m_elements[i].body.get(), COLLISION_GROUP_CHARACTERS, COLLISION_GROUP_KINEMATIC);

        m_elements[i].body->activate();
    }

    // GENERATE CONSTRAINTS.
    // All constraints are generic 6-DOF type, as they seem perfect fit for hair.

    // Joint count is calculated from overall body amount multiplied by per-body constraint
    // count.

    m_joints.resize(m_elements.size());

    // If multiple joints per body is specified, joints are placed in circular manner,
    // with obvious step of (SIMD_2_PI) / joint count. It means that all joints will form
    // circle-like figure.

    int curr_joint = 0;

    for(size_t i = 0; i < m_elements.size(); i++)
    {
        btScalar     body_length;
        btTransform localA; localA.setIdentity();
        btTransform localB; localB.setIdentity();

        btScalar joint_x = 0.0;
        btScalar joint_y = 0.0;

        std::shared_ptr<btRigidBody> prev_body;
        if(i == 0)  // First joint group
        {
            // Adjust pivot point A to parent body.

            localA.setOrigin(setup->m_headOffset + btVector3(joint_x, 0.0, joint_y));
            localA.getBasis().setEulerZYX(setup->m_rootAngle[0], setup->m_rootAngle[1], setup->m_rootAngle[2]);
            // Stealing this calculation because I need it for drawing
            m_ownerBodyHairRoot = localA;

            localB.setOrigin(btVector3(joint_x, 0.0, joint_y));
            localB.getBasis().setEulerZYX(0, -SIMD_HALF_PI, 0);

            prev_body = parent_entity->m_bt.bt_body[m_ownerBody];   // Previous body is parent body.
        }
        else
        {
            // Adjust pivot point A to previous mesh's length, considering mesh overlap multiplier.

            body_length = std::abs(m_elements[i - 1].mesh->m_bbMax[1] - m_elements[i - 1].mesh->m_bbMin[1]) * setup->m_jointOverlap;

            localA.setOrigin(btVector3(joint_x, body_length, joint_y));
            localA.getBasis().setEulerZYX(0, SIMD_HALF_PI, 0);

            // Pivot point B is automatically adjusted by Bullet.

            localB.setOrigin(btVector3(joint_x, 0.0, joint_y));
            localB.getBasis().setEulerZYX(0, SIMD_HALF_PI, 0);

            prev_body = m_elements[i - 1].body;   // Previous body is preceiding hair mesh.
        }

        // Create 6DOF constraint.

        m_joints[curr_joint].reset(new btGeneric6DofConstraint(*prev_body, *(m_elements[i].body), localA, localB, true));

        // CFM and ERP parameters are critical for making joint "hard" and link
        // to Lara's head. With wrong values, constraints may become "elastic".

        for(int axis = 0; axis <= 5; axis++)
        {
            m_joints[i]->setParam(BT_CONSTRAINT_STOP_CFM, setup->m_jointCfm, axis);
            m_joints[i]->setParam(BT_CONSTRAINT_STOP_ERP, setup->m_jointErp, axis);
        }

        if(i == 0)
        {
            // First joint group should be more limited in motion, as it is connected
            // right to the head. NB: Should we make it scriptable as well?

            m_joints[curr_joint]->setLinearLowerLimit(btVector3(0., 0., 0.));
            m_joints[curr_joint]->setLinearUpperLimit(btVector3(0., 0., 0.));
            m_joints[curr_joint]->setAngularLowerLimit(btVector3(-SIMD_HALF_PI, 0., -SIMD_HALF_PI*0.4));
            m_joints[curr_joint]->setAngularUpperLimit(btVector3(-SIMD_HALF_PI*0.3, 0., SIMD_HALF_PI*0.4));

            // Increased solver iterations make constraint even more stable.

            m_joints[curr_joint]->setOverrideNumSolverIterations(100);
        }
        else
        {
            // Normal joint with more movement freedom.

            m_joints[curr_joint]->setLinearLowerLimit(btVector3(0., 0., 0.));
            m_joints[curr_joint]->setLinearUpperLimit(btVector3(0., 0., 0.));
            m_joints[curr_joint]->setAngularLowerLimit(btVector3(-SIMD_HALF_PI*0.5, 0., -SIMD_HALF_PI*0.5));
            m_joints[curr_joint]->setAngularUpperLimit(btVector3(SIMD_HALF_PI*0.5, 0., SIMD_HALF_PI*0.5));
        }

        m_joints[curr_joint]->setDbgDrawSize(btScalar(5.f));    // Draw constraint axes.

        // Add constraint to the world.

        bt_engine_dynamicsWorld->addConstraint(m_joints[curr_joint].get(), true);

        curr_joint++;   // Point to the next joint.
    }

    createHairMesh(model);

    return true;
}
Ejemplo n.º 20
0
int main() {
    int i, j;

    btDefaultCollisionConfiguration *collisionConfiguration
            = new btDefaultCollisionConfiguration();
    btCollisionDispatcher *dispatcher = new btCollisionDispatcher(collisionConfiguration);
    btBroadphaseInterface *overlappingPairCache = new btDbvtBroadphase();
    btSequentialImpulseConstraintSolver* solver = new btSequentialImpulseConstraintSolver;
    btDiscreteDynamicsWorld *dynamicsWorld = new btDiscreteDynamicsWorld(
            dispatcher, overlappingPairCache, solver, collisionConfiguration);
    dynamicsWorld->setGravity(btVector3(0, gravity, 0));
    dynamicsWorld->setInternalTickCallback(myTickCallback);
    btAlignedObjectArray<btCollisionShape*> collisionShapes;

    // Ground.
    {
        btTransform groundTransform;
        groundTransform.setIdentity();
        groundTransform.setOrigin(btVector3(0, 0, 0));
        btCollisionShape* groundShape;
#if 1
        // x / z plane at y = -1.
        groundShape = new btStaticPlaneShape(btVector3(groundXNormal, 1, 0), -1);
#else
        // A cube of width 10 at y = -6.
        // Does not fall because we won't call:
        // colShape->calculateLocalInertia
        // TODO: remove this from this example into a collision shape example.
        groundTransform.setOrigin(btVector3(0, -6, 0));
        groundShape = new btBoxShape(
                btVector3(btScalar(5.0), btScalar(5.0), btScalar(5.0)));

#endif
        collisionShapes.push_back(groundShape);
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(0, myMotionState, groundShape, btVector3(0, 0, 0));
		btRigidBody* body = new btRigidBody(rbInfo);
		body->setRestitution(groundRestitution);
		dynamicsWorld->addRigidBody(body);
    }

    // Object.
    {
        btCollisionShape *colShape;
#if 1
        colShape = new btSphereShape(btScalar(1.0));
#else
        // Because of numerical instabilities, the cube spins all over,
        // moving on the x and y directions.
        colShape = new btBoxShape(
                btVector3(btScalar(1.0), btScalar(1.0), btScalar(1.0)));
#endif
        collisionShapes.push_back(colShape);
        btTransform startTransform;
        startTransform.setIdentity();
        startTransform.setOrigin(btVector3(0, initialY, 0));
        btVector3 localInertia(0, 0, 0);
        btScalar mass(1.0f);
        colShape->calculateLocalInertia(mass, localInertia);
        btDefaultMotionState *myMotionState = new btDefaultMotionState(startTransform);
        btRigidBody *body = new btRigidBody(btRigidBody::btRigidBodyConstructionInfo(
                mass, myMotionState, colShape, localInertia));
		body->setRestitution(objectRestitution);
        dynamicsWorld->addRigidBody(body);
    }

    // Main loop.
    std::printf("step body x y z collision a b normal\n");
    for (i = 0; i < maxNPoints; ++i) {
        dynamicsWorld->stepSimulation(timeStep);
        for (j = dynamicsWorld->getNumCollisionObjects() - 1; j >= 0; --j) {
            btCollisionObject *obj = dynamicsWorld->getCollisionObjectArray()[j];
            btRigidBody *body = btRigidBody::upcast(obj);
            btTransform trans;
            if (body && body->getMotionState()) {
                body->getMotionState()->getWorldTransform(trans);
            } else {
                trans = obj->getWorldTransform();
            }
            btVector3 origin = trans.getOrigin();
            std::printf("%d %d " PRINTF_FLOAT " " PRINTF_FLOAT " " PRINTF_FLOAT " ",
                    i, j, origin.getX(), origin.getY(), origin.getZ());
            auto& manifoldPoints = objectsCollisions[body];
            if (manifoldPoints.empty()) {
                std::printf("0 ");
            } else {
                std::printf("1 ");
                for (auto& pt : manifoldPoints) {
                    std::vector<btVector3> data;
                    data.push_back(pt->getPositionWorldOnA());
                    data.push_back(pt->getPositionWorldOnB());
                    data.push_back(pt->m_normalWorldOnB);
                    for (auto& v : data) {
                        std::printf(
                                PRINTF_FLOAT " " PRINTF_FLOAT " " PRINTF_FLOAT " ",
                                v.getX(), v.getY(), v.getZ());
                    }
                }
            }
            puts("");
        }
    }

    // Cleanup.
    for (i = dynamicsWorld->getNumCollisionObjects() - 1; i >= 0; --i) {
        btCollisionObject* obj = dynamicsWorld->getCollisionObjectArray()[i];
        btRigidBody* body = btRigidBody::upcast(obj);
        if (body && body->getMotionState()) {
            delete body->getMotionState();
        }
        dynamicsWorld->removeCollisionObject(obj);
        delete obj;
    }
    for (i = 0; i < collisionShapes.size(); ++i) {
        delete collisionShapes[i];
    }
    delete dynamicsWorld;
    delete solver;
    delete overlappingPairCache;
    delete dispatcher;
    delete collisionConfiguration;
    collisionShapes.clear();
}
void RigidBodySoftContact::initPhysics()
{
    
    
	m_guiHelper->setUpAxis(1);

	//createEmptyDynamicsWorld();
	{
		///collision configuration contains default setup for memory, collision setup
		m_collisionConfiguration = new btDefaultCollisionConfiguration();
		//m_collisionConfiguration->setConvexConvexMultipointIterations();

		///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
		m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);

		m_broadphase = new btDbvtBroadphase();

		///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
		btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
		//btMLCPSolver* sol = new btMLCPSolver(new btSolveProjectedGaussSeidel());
		m_solver = sol;

		m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher, m_broadphase, m_solver, m_collisionConfiguration);

		m_dynamicsWorld->setGravity(btVector3(0, -10, 0));
	}
	
	m_guiHelper->createPhysicsDebugDrawer(m_dynamicsWorld);

	if (m_dynamicsWorld->getDebugDrawer())
		m_dynamicsWorld->getDebugDrawer()->setDebugMode(btIDebugDraw::DBG_DrawWireframe+btIDebugDraw::DBG_DrawContactPoints);
	m_dynamicsWorld->getSolverInfo().m_erp2 = 0.f;
	m_dynamicsWorld->getSolverInfo().m_globalCfm = 0.f;
	m_dynamicsWorld->getSolverInfo().m_numIterations = 3;
	m_dynamicsWorld->getSolverInfo().m_solverMode = SOLVER_SIMD;// | SOLVER_RANDMIZE_ORDER;
	m_dynamicsWorld->getSolverInfo().m_splitImpulse = false;
	
	///create a few basic rigid bodies
	btBoxShape* groundShape = createBoxShape(btVector3(btScalar(50.),btScalar(50.),btScalar(50.)));
	

	//groundShape->initializePolyhedralFeatures();
//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-50,0));

	{
		btScalar mass(0.);
		btRigidBody* body = createRigidBody(mass,groundTransform,groundShape, btVector4(0,0,1,1));
        
        body->setContactStiffnessAndDamping(300,10);
		
	}


	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance

		//btBoxShape* colShape = createBoxShape(btVector3(1,1,1));
		

		btCollisionShape* childShape = new btSphereShape(btScalar(0.5));
		btCompoundShape* colShape = new btCompoundShape();
		colShape->addChildShape(btTransform::getIdentity(),childShape);

		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();
		
		startTransform.setRotation(btQuaternion(btVector3(1,1,1),SIMD_PI/10.));
		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);


		for (int k=0;k<ARRAY_SIZE_Y;k++)
		{
			for (int i=0;i<ARRAY_SIZE_X;i++)
			{
				for(int j = 0;j<ARRAY_SIZE_Z;j++)
				{
					startTransform.setOrigin(btVector3(
										btScalar(2.0*i+0.1),
										btScalar(3+2.0*k),
										btScalar(2.0*j)));

			
					btRigidBody* body = createRigidBody(mass,startTransform,colShape);
					//body->setAngularVelocity(btVector3(1,1,1));
					

				}
			}
		}
	}

	m_guiHelper->autogenerateGraphicsObjects(m_dynamicsWorld);
}
Ejemplo n.º 22
0
void	RaytestDemo::initPhysics()
{
	m_ele = 10;
	m_azi = 75;

	setTexturing(true);
	setShadows(true);

	setCameraDistance(btScalar(20.));

	///collision configuration contains default setup for memory, collision setup
	m_collisionConfiguration = new btDefaultCollisionConfiguration();
	//m_collisionConfiguration->setConvexConvexMultipointIterations();

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);

	m_broadphase = new btDbvtBroadphase();

	///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
	btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
	m_solver = sol;

	m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
	m_dynamicsWorld ->setDebugDrawer(&sDebugDraw);
	m_dynamicsWorld->setGravity(btVector3(0,-10,0));

	///create a few basic rigid bodies
	btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(50.),btScalar(50.),btScalar(50.)));
//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-50,0));

	//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);
		body->setRollingFriction(1);
		body->setFriction(1);
		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);
	}


	{
		btVector3 convexPoints[]={ btVector3(-1,-1,-1),btVector3(-1,-1,1),btVector3(-1,1,1),btVector3(-1,1,-1),
			btVector3(2,0,0)};

		btVector3 quad[] = {
			btVector3(0,1,-1),
			btVector3(0,1,1),
			btVector3(0,-1,1),
			btVector3(0,-1,-1)};

		btTriangleMesh* mesh = new btTriangleMesh();
		mesh->addTriangle(quad[0],quad[1],quad[2],true);
		mesh->addTriangle(quad[0],quad[2],quad[3],true);

		//btBvhTriangleMeshShape* trimesh = new btBvhTriangleMeshShape(mesh,true,true);
		btGImpactMeshShape * trimesh = new btGImpactMeshShape(mesh);
		trimesh->updateBound();
		

#define NUM_SHAPES 6
			btCollisionShape* colShapes[NUM_SHAPES] = {
				trimesh,
				new btConvexHullShape(&convexPoints[0].getX(),sizeof(convexPoints)/sizeof(btVector3),sizeof(btVector3)),
				new btSphereShape(1),
				new btCapsuleShape(0.2,1),
				new btCylinderShape(btVector3(0.2,1,0.2)),
				new btBoxShape(btVector3(1,1,1))
			};

		for (int i=0;i<NUM_SHAPES;i++)
			m_collisionShapes.push_back(colShapes[i]);

		for (int i=0;i<6;i++)
		{
			//create a few dynamic rigidbodies
			// Re-using the same collision is better for memory usage and performance

	

			/// Create Dynamic Objects
			btTransform startTransform;
			startTransform.setIdentity();
			startTransform.setOrigin(btVector3((i-3)*5,1,0));


			btScalar	mass(1.f);

			if (!i)
				mass=0.f;

			//rigidbody is dynamic if and only if mass is non zero, otherwise static
			bool isDynamic = (mass != 0.f);

			btVector3 localInertia(0,0,0);
			btCollisionShape* colShape = colShapes[i%NUM_SHAPES];
			if (isDynamic)
				colShape->calculateLocalInertia(mass,localInertia);

			btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,0,colShape,localInertia);
			rbInfo.m_startWorldTransform = startTransform;
			btRigidBody* body = new btRigidBody(rbInfo);
			body->setRollingFriction(0.03);
			body->setFriction(1);
			body->setAnisotropicFriction(colShape->getAnisotropicRollingFrictionDirection(),btCollisionObject::CF_ANISOTROPIC_ROLLING_FRICTION);
		
			m_dynamicsWorld->addRigidBody(body);
	
		}

	}
}
Ejemplo n.º 23
0
void	BasicDemo::initPhysics()
{
	setTexturing(true);
	setShadows(true);

	setCameraDistance(btScalar(SCALING*50.));

	///collision configuration contains default setup for memory, collision setup
	m_collisionConfiguration = new btDefaultCollisionConfiguration();
	//m_collisionConfiguration->setConvexConvexMultipointIterations();

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);

	m_broadphase = new btDbvtBroadphase();

	///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
	btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
	m_solver = sol;

	m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);

	m_dynamicsWorld->setGravity(btVector3(0,-10,0));

	///create a few basic rigid bodies
	btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(50.),btScalar(50.),btScalar(50.)));
//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-50,0));

	//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);

		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);
	}


	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance

		btCollisionShape* colShape = new btBoxShape(btVector3(SCALING*1,SCALING*1,SCALING*1));
		//btCollisionShape* colShape = new btSphereShape(btScalar(1.));
		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);

		float start_x = START_POS_X - ARRAY_SIZE_X/2;
		float start_y = START_POS_Y;
		float start_z = START_POS_Z - ARRAY_SIZE_Z/2;

		for (int k=0;k<ARRAY_SIZE_Y;k++)
		{
			for (int i=0;i<ARRAY_SIZE_X;i++)
			{
				for(int j = 0;j<ARRAY_SIZE_Z;j++)
				{
					startTransform.setOrigin(SCALING*btVector3(
										btScalar(2.0*i + start_x),
										btScalar(20+2.0*k + start_y),
										btScalar(2.0*j + start_z)));

			
					//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
					btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
					btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,colShape,localInertia);
					btRigidBody* body = new btRigidBody(rbInfo);
					
					body->setActivationState(ISLAND_SLEEPING);

					m_dynamicsWorld->addRigidBody(body);
					body->setActivationState(ISLAND_SLEEPING);
				}
			}
		}
	}


	clientResetScene();


#ifdef TEST_SERIALIZATION
	//test serializing this 

	int maxSerializeBufferSize = 1024*1024*5;

	btDefaultSerializer*	serializer = new btDefaultSerializer(maxSerializeBufferSize);
	m_dynamicsWorld->serialize(serializer);
	
	FILE* f2 = fopen("testFile.bullet","wb");
	fwrite(serializer->m_buffer,serializer->m_currentSize,1,f2);
	fclose(f2);
#endif

#if 0
	bParse::btBulletFile* bulletFile2 = new bParse::btBulletFile("testFile.bullet");
	bool ok = (bulletFile2->getFlags()& bParse::FD_OK)!=0;
	bool verboseDumpAllTypes = true;
	if (ok)
		bulletFile2->parse(verboseDumpAllTypes);
	
	if (verboseDumpAllTypes)
	{
		bulletFile2->dumpChunks(bulletFile2->getFileDNA());
	}
#endif //TEST_SERIALIZATION

}
Ejemplo n.º 24
0
HeightmapNode::HeightmapNode(EditorScene * _scene, Landscape *_land)
    :   Entity()
    ,   position(0,0,0)
    ,   rotation(0)
{
    SetName("HeightmapNode");
    
    editorScene = _scene;
    SetVisible(false);

    land = _land;
    DVASSERT(land);
    
    //Get LandSize;
    Vector3 landSize;
    AABBox3 transformedBox;
    Matrix4 * worldTransformPtr = land->GetWorldTransformPtr();
    
    land->GetBoundingBox().GetTransformedBox(*worldTransformPtr, transformedBox);
    landSize = transformedBox.max - transformedBox.min;
    
    heightmap = land->GetHeightmap();
    sizeInMeters = landSize.x;
    areaScale = sizeInMeters / heightmap->Size();
    maxHeight = landSize.z;
    heightScale = maxHeight / 65535.f;
    float32 minHeight = 0.0f;
    
    
    uint16 *dt = heightmap->Data();
    size.x = (float32)heightmap->Size();
    size.y = (float32)heightmap->Size();
    hmap.resize(heightmap->Size() * heightmap->Size());

	for (int32 y = 0; y < heightmap->Size(); ++y)
	{
		for (int32 x = 0; x < heightmap->Size(); ++x)
		{
            int32 index = x + (y) * heightmap->Size();
            float32 mapValue = dt[index] * heightScale;
            SetValueToMap(x, y, mapValue, transformedBox);
		}
	}

	bool flipQuadEdges = true;

    colShape = new btHeightfieldTerrainShape(heightmap->Size(), heightmap->Size()
                                             , &hmap.front(), heightScale, minHeight, maxHeight
                                             , 2, PHY_FLOAT
                                             , flipQuadEdges);

    colShape->setLocalScaling(btVector3(areaScale, areaScale, 1.0f));
    
    // Create Dynamic Objects
    btTransform startTransform;
    startTransform.setIdentity();
    
    btScalar	mass(0.0f);

    //rigidbody is dynamic if and only if mass is non zero, otherwise static
    bool isDynamic = (mass != 0.f);
    
    btVector3 localInertia(0,0,0);
    if (isDynamic)
        colShape->calculateLocalInertia(mass,localInertia);
    
    startTransform.setOrigin(btVector3( btScalar(position.x),
                                       btScalar(position.y),
                                       btScalar(maxHeight/2.0f + position.z)));
    
    
    //using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
    motionSate = new btDefaultMotionState(startTransform);
    btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,motionSate,colShape,localInertia);
    rbInfo.m_friction = 0.9f;
    body = new btRigidBody(rbInfo);
    
    collisionObject = new btCollisionObject();
    collisionObject->setWorldTransform(startTransform);
    collisionObject->setCollisionShape(colShape);
    editorScene->landCollisionWorld->addCollisionObject(collisionObject);
	editorScene->landCollisionWorld->updateAabbs();
}
Ejemplo n.º 25
0
void	BasicDemo::initPhysics()
{
	setTexturing(false);
	setShadows(false);

#if OECAKE_LOADER
	setCameraDistance(80.);
	m_cameraTargetPosition.setValue(50, 10, 0);
#else
	#if LARGE_DEMO
		setCameraDistance(btScalar(SCALING*100.));
	#else
		setCameraDistance(btScalar(SCALING*20.));
	#endif
	m_cameraTargetPosition.setValue(START_POS_X, -START_POS_Y-20, START_POS_Z);
#endif
	m_azi = btScalar(0.f);
	m_ele = btScalar(0.f);

	///collision configuration contains default setup for memory, collision setup

	btDefaultCollisionConstructionInfo dci;
	dci.m_defaultMaxPersistentManifoldPoolSize=50000;
	dci.m_defaultMaxCollisionAlgorithmPoolSize=50000;

	m_collisionConfiguration = new btDefaultCollisionConfiguration(dci);

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);
	m_dispatcher->registerCollisionCreateFunc(BOX_SHAPE_PROXYTYPE,BOX_SHAPE_PROXYTYPE,new btEmptyAlgorithm::CreateFunc);

	m_dispatcher->setNearCallback(cudaDemoNearCallback);

	
#if USE_CUDA_DEMO_PAIR_CASHE
	gPairCache = new (btAlignedAlloc(sizeof(btGpuDemoPairCache),16)) btGpuDemoPairCache(MAX_PROXIES, 24, MAX_SMALL_PROXIES); 
#else
	gPairCache = new (btAlignedAlloc(sizeof(btHashedOverlappingPairCache),16))btHashedOverlappingPairCache(); 
#endif


//	btVector3 numOfCells = (gWorldMax - gWorldMin) / (2. * SCALING);
//	btVector3 numOfCells = (gWorldMax - gWorldMin) / CELL_SIZE;
//	int numOfCellsX = (int)numOfCells[0];
//	int numOfCellsY = (int)numOfCells[1];
//	int numOfCellsZ = (int)numOfCells[2];
//	if(!numOfCellsX) numOfCellsX = 1;
//	if(!numOfCellsY) numOfCellsY = 1;
//	if(!numOfCellsZ) numOfCellsZ = 1;
	btScalar maxDiam = 2.0f * SCALING;  
	btVector3 cellSize(maxDiam, maxDiam, maxDiam);
	btVector3 numOfCells = (gWorldMax - gWorldMin) / cellSize;
	int numOfCellsX = btGpu3DGridBroadphase::getFloorPowOfTwo((int)numOfCells[0]);
	int numOfCellsY = btGpu3DGridBroadphase::getFloorPowOfTwo((int)numOfCells[1]);
	int numOfCellsZ = btGpu3DGridBroadphase::getFloorPowOfTwo((int)numOfCells[2]);

//	m_broadphase = new btAxisSweep3(gWorldMin, gWorldMax, MAX_PROXIES,gPairCache);
//	m_broadphase = new btDbvtBroadphase(gPairCache);
//	m_broadphase = new btGpu3DGridBroadphase(gPairCache, gWorldMin, gWorldMax,numOfCellsX, numOfCellsY, numOfCellsZ,MAX_SMALL_PROXIES,20,24,24, 1.0f/1.5f);
//	m_broadphase = new btCudaBroadphase(gPairCache, gWorldMin, gWorldMax,numOfCellsX, numOfCellsY, numOfCellsZ,MAX_SMALL_PROXIES,10,24,24);
//	m_broadphase = new bt3dGridBroadphaseOCL(gPairCache, gWorldMin, gWorldMax,numOfCellsX, numOfCellsY, numOfCellsZ,MAX_SMALL_PROXIES,20,24,24,1./1.5);
	m_broadphase = new bt3dGridBroadphaseOCL(gPairCache, cellSize,numOfCellsX, numOfCellsY, numOfCellsZ,MAX_SMALL_PROXIES,20,24,10.f, 24);


	///the default constraint solver
	m_solver = new btSequentialImpulseConstraintSolver();

	btGpuDemoDynamicsWorld* pDdw = new btGpuDemoDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration, MAX_PROXIES);
	m_dynamicsWorld = pDdw;
	m_pWorld = pDdw;
	pDdw->getSimulationIslandManager()->setSplitIslands(true);
	pDdw->setObjRad(SCALING);
	pDdw->setWorldMin(gWorldMin);
	pDdw->setWorldMax(gWorldMax);
//	gUseCPUSolver = true;
	pDdw->setUseCPUSolver(gUseCPUSolver);
	gUseBulletNarrowphase = false;
	pDdw->setUseBulletNarrowphase(gUseBulletNarrowphase);

//	m_dynamicsWorld->setGravity(btVector3(0,0,0));
	m_dynamicsWorld->setGravity(btVector3(0,-10.,0));
	m_dynamicsWorld->getSolverInfo().m_numIterations = 4;

	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance



#if 1
		#define SPRADIUS btScalar(SCALING*0.1f)
		#define SPRPOS btScalar(SCALING*0.05f)
		static btVector3 sSphPos[8];
		
		for (int k=0;k<8;k++)
		{
			sSphPos[k].setValue((k-4)*0.25*SCALING,0,0);
		}
		
		btVector3 inertiaHalfExtents(SPRADIUS,  SPRADIUS,  SPRADIUS);
		static btScalar sSphRad[8] = 
		{
//			 SPRADIUS,  SPRADIUS,  SPRADIUS, SPRADIUS,SPRADIUS,  SPRADIUS,  SPRADIUS, 0.3
			 SPRADIUS,  SPRADIUS,  SPRADIUS, SPRADIUS,SPRADIUS,  SPRADIUS,  SPRADIUS, SPRADIUS
		};
//		sSphPos[0].setX(sSphPos[0].getX()-0.15);
		#undef SPR
		btMultiSphereShape* colShape[2];
		colShape[0] = new btMultiSphereShape( sSphPos, sSphRad, 8);
		colShape[1] = new btMultiSphereShape( sSphPos, sSphRad, 2);

		//btCollisionShape* colShape = new btSphereShape(btScalar(1.));
		m_collisionShapes.push_back(colShape[0]);
		m_collisionShapes.push_back(colShape[1]);
#endif

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(0.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
#if OECAKE_LOADER
	BasicDemoOecakeLoader	loader(this);
	if (!loader.processFile("test1.oec"))
	{
		loader.processFile("../../../../../Demos/Gpu2dDemo/test.oec");
	}
#if 0 // perfomance test : work-in-progress
	{ // add more object, but share their shapes
		int numNewObjects = 500;
		mass = 1.f;
		for(int n_obj = 0; n_obj < numNewObjects; n_obj++)
		{
			btDefaultMotionState* myMotionState= 0;
			btVector3 localInertia(0,0,0);
			btTransform worldTransform;
			worldTransform.setIdentity();
			btScalar fx = fRandMinMax(-30., 30.);
			btScalar fy = fRandMinMax(5., 30.);
			worldTransform.setOrigin(btVector3(fx, fy, 0.f));
			int sz = m_collisionShapes.size();
			btMultiSphereShape* multiSphere = (btMultiSphereShape*)m_collisionShapes[1];
			myMotionState = new btDefaultMotionState(worldTransform);
			multiSphere->calculateLocalInertia(mass, localInertia);
			btRigidBody* body = new btRigidBody(mass,myMotionState,multiSphere,localInertia);	
			body->setLinearFactor(btVector3(1,1,0));
			body->setAngularFactor(btVector3(0,0,1));
			body->setWorldTransform(worldTransform);
			getDynamicsWorld()->addRigidBody(body);
		}
	}
#endif

#else
#if (!SPEC_TEST)
		float start_x = START_POS_X - ARRAY_SIZE_X * SCALING;
		float start_y = START_POS_Y - ARRAY_SIZE_Y * SCALING;
		float start_z = START_POS_Z - ARRAY_SIZE_Z * SCALING;

		int collisionShapeIndex = 0;
		for (int k=0;k<ARRAY_SIZE_Y;k++)
		{
			for (int i=0;i<ARRAY_SIZE_X;i++)
			{
				for(int j = 0;j<ARRAY_SIZE_Z;j++)
				{
					float offs = (2. * (float)rand() / (float)RAND_MAX - 1.f) * 0.05f;
					startTransform.setOrigin(SCALING*btVector3(
										2.0*SCALING*i + start_x + offs,
										2.0*SCALING*k + start_y + offs,
										2.0*SCALING*j + start_z));

					if (isDynamic)
						colShape[collisionShapeIndex]->calculateLocalInertia(mass,localInertia);


			
					//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
					//btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
					btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,0,colShape[collisionShapeIndex],localInertia);
					collisionShapeIndex = 1 - collisionShapeIndex;
					rbInfo.m_startWorldTransform=startTransform;
					btRigidBody* body = new btRigidBody(rbInfo);
					m_dynamicsWorld->addRigidBody(body);
				}
			}
		}
#else//SPEC_TEST
		// narrowphase test - 2 bodies at the same position
		float start_x = START_POS_X;
//		float start_y = START_POS_Y;
		float start_y = gWorldMin[1] + SCALING * 0.7f + 5.f;
		float start_z = START_POS_Z;
		startTransform.setOrigin(SCALING*btVector3(start_x,start_y,start_z));
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,0,colShape[0],localInertia);
		rbInfo.m_startWorldTransform=startTransform;
		btRigidBody* body = new btRigidBody(rbInfo);
		m_dynamicsWorld->addRigidBody(body);

		btPoint2PointConstraint * p2pConstr =  new btPoint2PointConstraint(*body, btVector3(1., 0., 0.));
		m_dynamicsWorld->addConstraint(p2pConstr);

		startTransform.setOrigin(SCALING*btVector3(start_x-2.f, start_y,start_z));
		rbInfo.m_startWorldTransform=startTransform;
		btRigidBody* body1 = new btRigidBody(rbInfo);
		m_dynamicsWorld->addRigidBody(body1);

		p2pConstr =  new btPoint2PointConstraint(*body, *body1, btVector3(-1., 0., 0.), btVector3(1., 0., 0.));
		m_dynamicsWorld->addConstraint(p2pConstr);


#endif//SPEC_TEST
#endif //OE_CAKE_LOADER
	}
	// now set Ids used by collision detector and constraint solver
	int numObjects = m_dynamicsWorld->getNumCollisionObjects();
	btCollisionObjectArray& collisionObjects = m_dynamicsWorld->getCollisionObjectArray();
	for(int i = 0; i < numObjects; i++)
	{
		btCollisionObject* colObj = collisionObjects[i];
		colObj->setCompanionId(i+1); // 0 reserved for the "world" object
		btCollisionShape* pShape = colObj->getCollisionShape();
		int shapeType = pShape->getShapeType();
		if(shapeType == MULTI_SPHERE_SHAPE_PROXYTYPE)
		{
			btMultiSphereShape* pMs = (btMultiSphereShape*)pShape;
			int numSpheres = pMs->getSphereCount();
			pDdw->addMultiShereObject(numSpheres, i + 1);
			for(int j = 0; j < numSpheres; j++)
			{
				btVector3 sphPos = pMs->getSpherePosition(j);
				float sphRad = pMs->getSphereRadius(j);
				pDdw->addSphere(sphPos, sphRad);
			}
		}
		else
		{
			btAssert(0);
		}
	}
#if OECAKE_LOADER
	clientResetScene();
#endif
}
Ejemplo n.º 26
0
void	BasicDemo::initPhysics()
{
	setTexturing(true);
	setShadows(true);

	setCameraDistance(btScalar(SCALING*50.));

	///collision configuration contains default setup for memory, collision setup
	m_collisionConfiguration = new btDefaultCollisionConfiguration();
	//m_collisionConfiguration->setConvexConvexMultipointIterations();

	///use the default collision dispatcher. For parallel processing you can use a diffent dispatcher (see Extras/BulletMultiThreaded)
	m_dispatcher = new	btCollisionDispatcher(m_collisionConfiguration);

	m_broadphase = new btDbvtBroadphase();

	///the default constraint solver. For parallel processing you can use a different solver (see Extras/BulletMultiThreaded)
	btSequentialImpulseConstraintSolver* sol = new btSequentialImpulseConstraintSolver;
        //btParallelConstraintSolver* sol = new btParallelConstraintSolver;
	m_solver = sol;

	m_dynamicsWorld = new btDiscreteDynamicsWorld(m_dispatcher,m_broadphase,m_solver,m_collisionConfiguration);
	
	m_dynamicsWorld->setGravity(btVector3(0,-10,0));

	///create a few basic rigid bodies
	btCollisionShape* groundShape = new btBoxShape(btVector3(btScalar(50.),btScalar(50.),btScalar(50.)));
//	btCollisionShape* groundShape = new btStaticPlaneShape(btVector3(0,1,0),50);
	
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0,-50,0));

	//We can also use DemoApplication::localCreateRigidBody, but for clarity it is provided here:
	{
		btScalar mass(0.);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			groundShape->calculateLocalInertia(mass,localInertia);

		//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
		btDefaultMotionState* myMotionState = new btDefaultMotionState(groundTransform);
		btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,groundShape,localInertia);
		btRigidBody* body = new btRigidBody(rbInfo);

		//add the body to the dynamics world
		m_dynamicsWorld->addRigidBody(body);
	}


	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance

		btCollisionShape* colShape = new btBoxShape(btVector3(SCALING*1,SCALING*1,SCALING*1));
		//btCollisionShape* colShape = new btSphereShape(btScalar(1.));
		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar	mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0,0,0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass,localInertia);

		float start_x = START_POS_X - ARRAY_SIZE_X/2;
		float start_y = START_POS_Y;
		float start_z = START_POS_Z - ARRAY_SIZE_Z/2;

		for (int k=0;k<ARRAY_SIZE_Y;k++)
		{
			for (int i=0;i<ARRAY_SIZE_X;i++)
			{
				for(int j = 0;j<ARRAY_SIZE_Z;j++)
				{
					startTransform.setOrigin(SCALING*btVector3(
										btScalar(2.0*i + start_x),
										btScalar(20+2.0*k + start_y),
										btScalar(2.0*j + start_z)));

			
					//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
					btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);
					btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,myMotionState,colShape,localInertia);
					btRigidBody* body = new btRigidBody(rbInfo);
					

					m_dynamicsWorld->addRigidBody(body);
				}
			}
		}
	}


}
Ejemplo n.º 27
0
PintObjectHandle Bullet::CreateObject(const PINT_OBJECT_CREATE& desc)
{
	udword NbShapes = desc.GetNbShapes();
	if(!NbShapes)
		return null;

	ASSERT(mDynamicsWorld);

	const PINT_SHAPE_CREATE* CurrentShape = desc.mShapes;

	float FrictionCoeff = 0.5f;
	float RestitutionCoeff = 0.0f;
	btCollisionShape* colShape = null;
	if(NbShapes>1)
	{
		btCompoundShape* CompoundShape = new btCompoundShape();
		colShape = CompoundShape;
		mCollisionShapes.push_back(colShape);

		while(CurrentShape)
		{
			if(CurrentShape->mMaterial)
			{
				FrictionCoeff		= CurrentShape->mMaterial->mDynamicFriction;
				RestitutionCoeff	= CurrentShape->mMaterial->mRestitution;
			}

			const btTransform LocalPose(ToBtQuaternion(CurrentShape->mLocalRot), ToBtVector3(CurrentShape->mLocalPos));

			// ### TODO: where is this deleted?
			btCollisionShape* subShape = CreateBulletShape(*CurrentShape);
			if(subShape)
			{
				CompoundShape->addChildShape(LocalPose, subShape);
			}

			CurrentShape = CurrentShape->mNext;
		}
	}
	else
	{
		colShape = CreateBulletShape(*CurrentShape);

		if(CurrentShape->mMaterial)
		{
			FrictionCoeff		= CurrentShape->mMaterial->mDynamicFriction;
			RestitutionCoeff	= CurrentShape->mMaterial->mRestitution;
		}
	}

	const bool isDynamic = (desc.mMass != 0.0f);

	btVector3 localInertia(0,0,0);
	if(isDynamic)
		colShape->calculateLocalInertia(desc.mMass, localInertia);

	const btTransform startTransform(ToBtQuaternion(desc.mRotation), ToBtVector3(desc.mPosition));

	//using motionstate is recommended, it provides interpolation capabilities, and only synchronizes 'active' objects
	btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);

	btRigidBody::btRigidBodyConstructionInfo rbInfo(desc.mMass, myMotionState, colShape, localInertia);
	{
		rbInfo.m_friction		= FrictionCoeff;
		rbInfo.m_restitution	= RestitutionCoeff;

	//	rbInfo.m_startWorldTransform;
		rbInfo.m_linearDamping				= gLinearDamping;
		rbInfo.m_angularDamping				= gAngularDamping;
		if(!gEnableSleeping)
		{
//			rbInfo.m_linearSleepingThreshold	= 99999999.0f;
//			rbInfo.m_angularSleepingThreshold	= 99999999.0f;
//			rbInfo.m_linearSleepingThreshold	= 0.0f;
//			rbInfo.m_angularSleepingThreshold	= 0.0f;
		}
	//	rbInfo.m_additionalDamping;
	//	rbInfo.m_additionalDampingFactor;
	//	rbInfo.m_additionalLinearDampingThresholdSqr;
	//	rbInfo.m_additionalAngularDampingThresholdSqr;
	//	rbInfo.m_additionalAngularDampingFactor;
	}
	btRigidBody* body = new btRigidBody(rbInfo);
	ASSERT(body);
	if(!gEnableSleeping)
		body->setActivationState(DISABLE_DEACTIVATION);

	sword collisionFilterGroup, collisionFilterMask;

	if(isDynamic)
	{
		body->setLinearVelocity(ToBtVector3(desc.mLinearVelocity));
		body->setAngularVelocity(ToBtVector3(desc.mAngularVelocity));

		collisionFilterGroup = short(btBroadphaseProxy::DefaultFilter);
		collisionFilterMask = short(btBroadphaseProxy::AllFilter);

		if(desc.mCollisionGroup)
		{
			const udword btGroup = RemapCollisionGroup(desc.mCollisionGroup);
			ASSERT(btGroup<32);
			collisionFilterGroup = short(1<<btGroup);
			collisionFilterMask = short(mGroupMasks[btGroup]);
		}
	}
	else
	{
//		body->setCollisionFlags(btCollisionObject::CF_STATIC_OBJECT);
		body->setCollisionFlags(btCollisionObject::CF_STATIC_OBJECT|btCollisionObject::CF_CUSTOM_MATERIAL_CALLBACK);

		collisionFilterGroup = short(btBroadphaseProxy::StaticFilter);
		collisionFilterMask = short(btBroadphaseProxy::AllFilter ^ btBroadphaseProxy::StaticFilter);
	}

	if(desc.mAddToWorld)
//		mDynamicsWorld->addRigidBody(body);
		mDynamicsWorld->addRigidBody(body, collisionFilterGroup, collisionFilterMask);

	if(gUseCCD)
	{
//		body->setCcdMotionThreshold(1e-7);
//		body->setCcdSweptSphereRadius(0.9*CUBE_HALF_EXTENTS);

		body->setCcdMotionThreshold(0.0001f);
		body->setCcdSweptSphereRadius(0.4f);
	}
	return body;
}
Ejemplo n.º 28
0
void RigidBody::UpdateMass()
{
    if (!body_ || !enableMassUpdate_)
        return;

    btTransform principal;
    principal.setRotation(btQuaternion::getIdentity());
    principal.setOrigin(btVector3(0.0f, 0.0f, 0.0f));

    // Calculate center of mass shift from all the collision shapes
    unsigned numShapes = (unsigned)compoundShape_->getNumChildShapes();
    if (numShapes)
    {
        PODVector<float> masses(numShapes);
        for (unsigned i = 0; i < numShapes; ++i)
        {
            // The actual mass does not matter, divide evenly between child shapes
            masses[i] = 1.0f;
        }

        btVector3 inertia(0.0f, 0.0f, 0.0f);
        compoundShape_->calculatePrincipalAxisTransform(&masses[0], principal, inertia);
    }

    // Add child shapes to shifted compound shape with adjusted offset
    while (shiftedCompoundShape_->getNumChildShapes())
        shiftedCompoundShape_->removeChildShapeByIndex(shiftedCompoundShape_->getNumChildShapes() - 1);
    for (unsigned i = 0; i < numShapes; ++i)
    {
        btTransform adjusted = compoundShape_->getChildTransform(i);
        adjusted.setOrigin(adjusted.getOrigin() - principal.getOrigin());
        shiftedCompoundShape_->addChildShape(adjusted, compoundShape_->getChildShape(i));
    }

    // If shifted compound shape has only one child with no offset/rotation, use the child shape
    // directly as the rigid body collision shape for better collision detection performance
    bool useCompound = !numShapes || numShapes > 1;
    if (!useCompound)
    {
        const btTransform& childTransform = shiftedCompoundShape_->getChildTransform(0);
        if (!ToVector3(childTransform.getOrigin()).Equals(Vector3::ZERO) ||
            !ToQuaternion(childTransform.getRotation()).Equals(Quaternion::IDENTITY))
            useCompound = true;
    }
    body_->setCollisionShape(useCompound ? shiftedCompoundShape_ : shiftedCompoundShape_->getChildShape(0));

    // If we have one shape and this is a triangle mesh, we use a custom material callback in order to adjust internal edges
    if (!useCompound && body_->getCollisionShape()->getShapeType() == SCALED_TRIANGLE_MESH_SHAPE_PROXYTYPE &&
        physicsWorld_->GetInternalEdge())
        body_->setCollisionFlags(body_->getCollisionFlags() | btCollisionObject::CF_CUSTOM_MATERIAL_CALLBACK);
    else
        body_->setCollisionFlags(body_->getCollisionFlags() & ~btCollisionObject::CF_CUSTOM_MATERIAL_CALLBACK);

    // Reapply rigid body position with new center of mass shift
    Vector3 oldPosition = GetPosition();
    centerOfMass_ = ToVector3(principal.getOrigin());
    SetPosition(oldPosition);

    // Calculate final inertia
    btVector3 localInertia(0.0f, 0.0f, 0.0f);
    if (mass_ > 0.0f)
        shiftedCompoundShape_->calculateLocalInertia(mass_, localInertia);
    body_->setMassProps(mass_, localInertia);
    body_->updateInertiaTensor();

    // Reapply constraint positions for new center of mass shift
    if (node_)
    {
        for (PODVector<Constraint*>::Iterator i = constraints_.Begin(); i != constraints_.End(); ++i)
            (*i)->ApplyFrames();
    }
}
Ejemplo n.º 29
0
CFootballPlayer::CFootballPlayer(CSimulationManager *simulationManager, const CPfTeamPlayers *teamPlayer, int number, CTeam *team, bool sideLeft)
:CMovingEntity()
{
	m_simulationManager = simulationManager;

	Ogre::SceneManager *scnMgr = Ogre::Root::getSingletonPtr()->getSceneManager(SIMULATION_SCENE_MANAGER_NODE_NAME);

    m_teamPlayer = new CPfTeamPlayers(*teamPlayer);
    m_stateMachine = new CStateMachine<CFootballPlayer>(this);
    Ogre::String id;
    std::ostringstream charId;
    m_centerOfMassOffset.setOrigin(btVector3(0,-0.9,0));
    m_sideLeft = sideLeft;
    m_team = team;
    m_number = number; //TODO
    m_lastKickBallCycle = -1;

    CSystemOptionManager* optionManager = CSystemOptionManager::getInstance();
    int maxPlayerVelocity = optionManager->getSimulationMaxPlayerVelocity();
    int maxKickPower      = optionManager->getSimulationMaxKickPower();
    m_maxVelocity  = maxPlayerVelocity * (m_teamPlayer->getNVelocity()/100.0);
    m_maxKickPower = maxKickPower      * (m_teamPlayer->getNKickPower()/100.0);
    m_maxKickDistance = optionManager->getSimulationMaxKickDistance();

    //m_direction.normalize();
    charId << team->getName().c_str() << m_number;
    id = charId.str();
    m_entity = scnMgr->createEntity("Player"+id, "Human.mesh");
    if(sideLeft) {
        if(m_number == 1) {
            m_entity->setMaterialName("goalie_red");
        } else {
            m_entity->setMaterialName("player_red");
        }
    } else {
        if(m_number == 1) {
            m_entity->setMaterialName("goalie_yellow");
        } else {
            m_entity->setMaterialName("player_yellow");
        }
    }
    btVector3 *initialPos = team->getPlayerStrategicPosition(m_number)->getInitialPosition();
    btVector3 pos(initialPos->x(), initialPos->y(), initialPos->z());
    if(!m_sideLeft) {
        pos.setX(-pos.x());
        pos.setZ(-pos.z());
    }
    m_node = scnMgr->getRootSceneNode()->createChildSceneNode("PlayerNode"+id, Ogre::Vector3(pos.x(), pos.y(), pos.z()));
    m_node->attachObject(m_entity);
    m_shape = new btCylinderShape(btVector3(btScalar(0.5),btScalar(0.9),btScalar(0.5)));
    btScalar mass(70.0);

    //rigidbody is dynamic if and only if mass is non zero, otherwise static
    bool isDynamic = (mass != 0.f);

    btVector3 localInertia(0,0,0);
    if (isDynamic)
        m_shape->calculateLocalInertia(mass,localInertia);
    btRigidBody::btRigidBodyConstructionInfo rbInfo(mass,this,m_shape,localInertia);
    m_body = new btRigidBody(rbInfo);
    m_body->setAngularFactor(btScalar(0));
    m_body->setActivationState(DISABLE_DEACTIVATION);

    m_steeringBehavior = new CSteeringBehaviors(this);


    //Draw Circle
    Ogre::ManualObject * circle = scnMgr->createManualObject("circle_name"+id);

    float const radius = 1.5,
                thickness = 0.7, // Of course this must be less than the radius value.
                accuracy = 5,
                height = 0.01;

    Ogre::MaterialPtr matptr;
    Ogre::Pass* pass;

    if(sideLeft) {
        matptr = Ogre::MaterialManager::getSingleton().createOrRetrieve("Red"+id, "General").first;
        matptr->setReceiveShadows(true);
        pass = matptr->getTechnique(0)->getPass(0);
        Ogre::ColourValue colour = Ogre::ColourValue::Red;
        pass->setDiffuse(colour);
        pass->setAmbient(colour);
        pass->setDepthWriteEnabled(true);
    } else {
        matptr = Ogre::MaterialManager::getSingleton().createOrRetrieve("Blue"+id, "General").first;
        matptr->setReceiveShadows(true);
        pass = matptr->getTechnique(0)->getPass(0);
        Ogre::ColourValue colour = Ogre::ColourValue::Blue;
        pass->setDiffuse(colour);
        pass->setAmbient(colour);
        pass->setDepthWriteEnabled(true);
    }
    circle->begin(matptr->getName(), Ogre::RenderOperation::OT_TRIANGLE_LIST);

    unsigned point_index = 0;
    for(float theta = 0; theta <= 2 * Ogre::Math::PI; theta += Ogre::Math::PI / (radius * accuracy)) {
        circle->position(radius * cos(theta),
                         height,
                         radius * sin(theta));
        circle->position(radius * cos(theta - Ogre::Math::PI / (radius * accuracy)),
                         height,
                         radius * sin(theta - Ogre::Math::PI / (radius * accuracy)));
        circle->position((radius - thickness) * cos(theta - Ogre::Math::PI / (radius * accuracy)),
                         height,
                         (radius - thickness) * sin(theta - Ogre::Math::PI / (radius * accuracy)));
        circle->position((radius - thickness) * cos(theta),
                         height,
                         (radius - thickness) * sin(theta));
        // Join the 4 vertices created above to form a quad.
        circle->quad(point_index, point_index + 1, point_index + 2, point_index + 3);
        point_index += 4;
    }

    circle->end();

    m_ringNode = m_node->createChildSceneNode();
    m_ringNode->attachObject(circle);
}
Ejemplo n.º 30
0
void SimpleJointExample::initPhysics()
{
	m_guiHelper->setUpAxis(1);

	createEmptyDynamicsWorld();

	m_guiHelper->createPhysicsDebugDrawer(m_dynamicsWorld);

	if (m_dynamicsWorld->getDebugDrawer())
		m_dynamicsWorld->getDebugDrawer()->setDebugMode(btIDebugDraw::DBG_DrawWireframe + btIDebugDraw::DBG_DrawContactPoints);

	///create a few basic rigid bodies
	btBoxShape* groundShape = createBoxShape(btVector3(btScalar(50.), btScalar(50.), btScalar(50.)));
	m_collisionShapes.push_back(groundShape);

	btTransform groundTransform;
	groundTransform.setIdentity();
	groundTransform.setOrigin(btVector3(0, -50, 0));
	{
		btScalar mass(0.);
		createRigidBody(mass, groundTransform, groundShape, btVector4(0, 0, 1, 1));
	}

	{
		//create a few dynamic rigidbodies
		// Re-using the same collision is better for memory usage and performance
		btBoxShape* colShape = createBoxShape(btVector3(1, 1, 1));

		m_collisionShapes.push_back(colShape);

		/// Create Dynamic Objects
		btTransform startTransform;
		startTransform.setIdentity();

		btScalar mass(1.f);

		//rigidbody is dynamic if and only if mass is non zero, otherwise static
		bool isDynamic = (mass != 0.f);

		btVector3 localInertia(0, 0, 0);
		if (isDynamic)
			colShape->calculateLocalInertia(mass, localInertia);

		startTransform.setOrigin(btVector3(
			btScalar(0),
			btScalar(10),
			btScalar(0)));
		btRigidBody* dynamicBox = createRigidBody(mass, startTransform, colShape);

		//create a static rigid body
		mass = 0;
		startTransform.setOrigin(btVector3(
			btScalar(0),
			btScalar(20),
			btScalar(0)));

		btRigidBody* staticBox = createRigidBody(mass, startTransform, colShape);

		//create a simple p2pjoint constraint
		btPoint2PointConstraint* p2p = new btPoint2PointConstraint(*dynamicBox, *staticBox, btVector3(0, 3, 0), btVector3(0, 0, 0));
		p2p->m_setting.m_damping = 0.0625;
		p2p->m_setting.m_impulseClamp = 0.95;
		m_dynamicsWorld->addConstraint(p2p);
	}

	m_guiHelper->autogenerateGraphicsObjects(m_dynamicsWorld);
}