Ejemplo n.º 1
0
// this callback is called for every contact between the two bodies
int Physics::genericContactProcess( const NewtonMaterial* p_material, const NewtonContact* p_contact )
{
    float speed0;
    float speed1;
    osg::Vec3f normal;

    // get the maximun normal speed of this impact.
    speed0 = NewtonMaterialGetContactNormalSpeed( p_material, p_contact );
    if ( speed0 > s_colStruct->_contactMaxNormalSpeed ) {
        // save the position of the contact ( e.g. for 3d sound for particle effects )
        s_colStruct->_contactMaxNormalSpeed = speed0;
        NewtonMaterialGetContactPositionAndNormal( p_material, &s_colStruct->_position._v[ 0 ], &normal._v[ 0 ] );
    }

    // get the maximun of the two sliding contact speeds
    speed0 = NewtonMaterialGetContactTangentSpeed( p_material, p_contact, 0 );
    speed1 = NewtonMaterialGetContactTangentSpeed( p_material, p_contact, 1 );
    if ( speed1 > speed0 )
        speed0 = speed1;

    // get the maximun tangent speed of this contact. this can be used e.g. for particles(sparks) or playing scratch sounds
    if ( speed0 > s_colStruct->_contactMaxTangentSpeed ) {
        // save the position of the contact (for 3d sound or particle effects)
        s_colStruct->_contactMaxTangentSpeed = speed0;
        NewtonMaterialGetContactPositionAndNormal( p_material, &s_colStruct->_position._v[ 0 ], &normal._v[ 0 ] );
    }

    // return one to tell Newton we want to accept this contact
    return 1;
}
Ejemplo n.º 2
0
void RenderContactPoints (NewtonWorld* const world)
{
	glDisable (GL_LIGHTING);
	glDisable(GL_TEXTURE_2D);

	glPointSize(8.0f);
	glColor3f(1.0f, 0.0f, 0.0f);
	glBegin(GL_POINTS);
	for (NewtonBody* body = NewtonWorldGetFirstBody(world); body; body = NewtonWorldGetNextBody(world, body)) {
		for (NewtonJoint* joint = NewtonBodyGetFirstContactJoint(body); joint; joint = NewtonBodyGetNextContactJoint(body, joint)) {
			if (NewtonJointIsActive (joint)) {
				for (void* contact = NewtonContactJointGetFirstContact (joint); contact; contact = NewtonContactJointGetNextContact (joint, contact)) {
					dVector point(0.0f);
					dVector normal(0.0f);	
					NewtonMaterial* const material = NewtonContactGetMaterial (contact);
					NewtonMaterialGetContactPositionAndNormal (material, body, &point.m_x, &normal.m_x);

					// if we are display debug info we need to block other threads from writing the data at the same time
					glVertex3f (point.m_x, point.m_y, point.m_z);
				}
			}
		}
	}
	glEnd();
	glPointSize(1.0f);
}
Ejemplo n.º 3
0
void GetForceOnStaticBody (NewtonBody* body, NewtonBody* staticBody)
{
	for (NewtonJoint* joint = NewtonBodyGetFirstContactJoint (body); joint; joint = NewtonBodyGetNextContactJoint (body, joint)) {
		NewtonBody* body0;
		NewtonBody* body1;

		body0 = NewtonJointGetBody0(joint);
		body1 = NewtonJointGetBody1(joint);
		if ((body0 == staticBody) || (body1 == staticBody)) {

			for (void* contact = NewtonContactJointGetFirstContact (joint); contact; contact = NewtonContactJointGetNextContact (joint, contact)) {

				float forceMag;
				dVector point;
				dVector normal;	
				NewtonMaterial* material;

				material = NewtonContactGetMaterial (contact);
				
				NewtonMaterialGetContactForce (material, &forceMag);
				NewtonMaterialGetContactPositionAndNormal (material, &point.m_x, &normal.m_x);

				dVector force (normal.Scale (-forceMag));

				// do wherever you want withteh force
			}
		}
	}
}
Ejemplo n.º 4
0
		void tContact::_newtonContactProcess(const NewtonJoint * contactJoint, dFloat timeStep, int threadIndex)
		{
			Vec3 contactPosit, contactNormal;

			float contactBestSpeed = 0.5f;

			tContact * mtl = NULL;
			const NewtonBody * body0 = NewtonJointGetBody0(contactJoint);

			void * contact = NewtonContactJointGetFirstContact (contactJoint);

			while (contact)
			{
				float contactNormalSpeed;
				NewtonMaterial * material;

				// get the material for this contact;
				material = NewtonContactGetMaterial (contact);

				contactNormalSpeed = NewtonMaterialGetContactNormalSpeed (material);
				if (contactNormalSpeed > contactBestSpeed){
					contactBestSpeed = contactNormalSpeed;
					contactBestSpeed = contactNormalSpeed;
					NewtonMaterialGetContactPositionAndNormal(material, &contactPosit.x, &contactNormal[0]);
					mtl = (tContact *)NewtonMaterialGetMaterialPairUserData(material);
				}

				contact = NewtonContactJointGetNextContact (contactJoint, contact);
			}
		
			if (mtl)
				mtl->OnContactProcess(&contactPosit, &contactNormal);
		}
static void GetCollisionSubShape(const NewtonJoint* const contactJoint, NewtonBody* const body)
{
	NewtonCollisionInfoRecord collisionInfo;

	NewtonCollision* const collision = NewtonBodyGetCollision(body);
	NewtonCollisionGetInfo (collision, &collisionInfo);


	int count = 0;
	NewtonCollision* collidingSubShapeArrar[32];

	// see if this is a compound collision or any other collision with sub collision shapes  
	if (collisionInfo.m_collisionType == SERIALIZE_ID_COMPOUND) {

		// to get the torque we need the center of gravity in global space
		dVector origin;
		dMatrix bodyMatrix;
		NewtonBodyGetMatrix(body, &bodyMatrix[0][0]);
		NewtonBodyGetCentreOfMass(body, &origin[0]);
		origin = bodyMatrix.TransformVector(origin);

		for (void* contact = NewtonContactJointGetFirstContact (contactJoint); contact; contact = NewtonContactJointGetNextContact (contactJoint, contact)) {
			// get the material of this contact, 
			// this part contain all contact information, the sub colliding shape, 
			NewtonMaterial* const material = NewtonContactGetMaterial (contact);
			NewtonCollision* const subShape = NewtonMaterialGetBodyCollidingShape (material, body);
			int i = count - 1;
			for (; i >= 0; i --) {
				if (collidingSubShapeArrar[i] == subShape) {
					break;
				}
			}
			if (i < 0) {
				collidingSubShapeArrar[count] = subShape;
				count ++;
				dAssert (count < int (sizeof (collidingSubShapeArrar) / sizeof (collidingSubShapeArrar[0])));

				// you can also get the forces here, however when tho function is call form a contact material
				// we can only get resting forces, impulsive forces can not be read here since they has no being calculated yet.
				// whoever if this function function is call after the NetwonUpdate they the application can read the contact force, that was applied to each contact point
				dVector force;
				dVector posit;
				dVector normal;
				NewtonMaterialGetContactForce (material, body, &force[0]);
				NewtonMaterialGetContactPositionAndNormal (material, body, &posit[0], &normal[0]);
				// the torque on this contact is
				dVector torque ((origin - posit) * force);

				// do what ever you want wit this  


			}
		}
	}

	// here we should have an array of all colling sub shapes
	if (count) {
		// do what you need with this sub shape list
	}
}
Ejemplo n.º 6
0
void GetContactOnBody (NewtonBody* const body)
{
	for (NewtonJoint* joint = NewtonBodyGetFirstContactJoint (body); joint; joint = NewtonBodyGetNextContactJoint (body, joint)) {
		NewtonBody* const body0 = NewtonJointGetBody0(joint);
		NewtonBody* const body1 = NewtonJointGetBody1(joint);
		for (void* contact = NewtonContactJointGetFirstContact (joint); contact; contact = NewtonContactJointGetNextContact (joint, contact)) {
			NewtonMaterial* material = NewtonContactGetMaterial (contact);

			//dFloat forceMag;
			dVector point;
			dVector normal;	
			//NewtonMaterialGetContactForce (material, &forceMag);
			NewtonMaterialGetContactPositionAndNormal (material, body1, &point.m_x, &normal.m_x);
			NewtonMaterialGetContactPositionAndNormal (material, body0, &point.m_x, &normal.m_x);
			// do whatever you want with the force
		}
	}
}
Ejemplo n.º 7
0
//to get the collision points
void HandlecollisionPoints (NewtonJoint* const contactjoint)
{
	NewtonBody* const body0 = NewtonJointGetBody0(contactjoint);
	NewtonBody* const body1 = NewtonJointGetBody1(contactjoint);
	for (void* contact = NewtonContactJointGetFirstContact (contactjoint); contact; contact = NewtonContactJointGetNextContact (contactjoint, contact)) {

		NewtonMaterial* material = NewtonContactGetMaterial (contact);

		// do whatever you want here
		//dFloat forceMag;
		dVector point;
		dVector normal;	
		//NewtonMaterialGetContactForce (material, &forceMag);
		NewtonMaterialGetContactPositionAndNormal (material, body0, &point.m_x, &normal.m_x);
		NewtonMaterialGetContactPositionAndNormal (material, body1, &point.m_x, &normal.m_x);

		// do whatever you want with the force
	}
}
Ejemplo n.º 8
0
PyObject* Material::GetContactNormal()
{
    dFloat v[3];
    dFloat n[3];
    NewtonMaterialGetContactPositionAndNormal( m_material, v, n );
    PyObject* r = PyTuple_New( 3 );
    PyTuple_SetItem( r, 0, PyFloat_FromDouble( n[0] ) );
    PyTuple_SetItem( r, 1, PyFloat_FromDouble( n[1] ) );
    PyTuple_SetItem( r, 2, PyFloat_FromDouble( n[2] ) );
    return r;
}
Ejemplo n.º 9
0
static void RenderBodyContactsForces (NewtonBody* const body, dFloat scale)
{
	dFloat mass;
	dFloat Ixx;
	dFloat Iyy;
	dFloat Izz;
	NewtonBodyGetMassMatrix (body, &mass, &Ixx, &Iyy, &Izz);	

	//draw normal forces in term of acceleration.
	//this  mean that two bodies with same shape but different mass will display the same force
	if (mass > 0.0f) {
		scale = scale/mass;
		for (NewtonJoint* joint = NewtonBodyGetFirstContactJoint(body); joint; joint = NewtonBodyGetNextContactJoint(body, joint)) {
			if (NewtonJointIsActive (joint)) {
				for (void* contact = NewtonContactJointGetFirstContact (joint); contact; contact = NewtonContactJointGetNextContact (joint, contact)) {
					dVector point(0.0f);
					dVector normal(0.0f);	
					dVector tangnetDir0(0.0f);
					dVector tangnetDir1(0.0f);
					dVector contactForce(0.0f);	
					NewtonMaterial* const material = NewtonContactGetMaterial (contact);

					NewtonMaterialGetContactForce(material, body, &contactForce.m_x);
					NewtonMaterialGetContactPositionAndNormal (material, body, &point.m_x, &normal.m_x);
					dVector normalforce (normal.Scale (contactForce % normal));
					dVector p0 (point);
					dVector p1 (point + normalforce.Scale (scale));
					glVertex3f (p0.m_x, p0.m_y, p0.m_z);
					glVertex3f (p1.m_x, p1.m_y, p1.m_z);

					// these are the components of the tangents forces at the contact point, the can be display at the contact position point.
					NewtonMaterialGetContactTangentDirections(material, body, &tangnetDir0[0], &tangnetDir1[0]);
					dVector tangentForce1 (tangnetDir0.Scale ((contactForce % tangnetDir0) * scale));
					dVector tangentForce2 (tangnetDir1.Scale ((contactForce % tangnetDir1) * scale));

					p1 = point + tangentForce1.Scale (scale);
					glVertex3f(p0.m_x, p0.m_y, p0.m_z);
					glVertex3f(p1.m_x, p1.m_y, p1.m_z);

					p1 = point + tangentForce2.Scale (scale);
					glVertex3f(p0.m_x, p0.m_y, p0.m_z);
					glVertex3f(p1.m_x, p1.m_y, p1.m_z);
				}
			}
		}
	}
}
Ejemplo n.º 10
0
dVector ForceBetweenBody (NewtonBody* const body0, NewtonBody* const body1)
{
	dVector reactionforce (0.0f);
	for (NewtonJoint* joint = NewtonBodyGetFirstContactJoint(body0); joint; joint = NewtonBodyGetNextContactJoint(body0, joint)) {
		if (NewtonJointIsActive(joint) &&  (NewtonJointGetBody0(joint) == body0) || (NewtonJointGetBody0(joint) == body1)) {
			for (void* contact = NewtonContactJointGetFirstContact (joint); contact; contact = NewtonContactJointGetNextContact (joint, contact)) {
				dVector point(0.0f);
				dVector normal(0.0f);	
				dVector contactForce(0.0f);
				NewtonMaterial* const material = NewtonContactGetMaterial (contact);
				NewtonMaterialGetContactPositionAndNormal (material, body0, &point.m_x, &normal.m_x);
				NewtonMaterialGetContactForce(material, body0, &contactForce[0]);
				reactionforce += contactForce;
			}
			break;
		}
	}
	return reactionforce;
}
Ejemplo n.º 11
0
static void GenericContactProcess (const NewtonJoint* contactJoint, dFloat timestep, int threadIndex)
{
	dFloat contactBestSpeed;
	dVector contactPosit;
	SoundEffect* bestSound;

	bestSound = NULL;
	contactBestSpeed = 0.5f;
	NewtonBody* const body0 = NewtonJointGetBody0(contactJoint);
	for (void* contact = NewtonContactJointGetFirstContact (contactJoint); contact; contact = NewtonContactJointGetNextContact (contactJoint, contact)) {
		dFloat contactNormalSpeed;
		NewtonMaterial* material;

		// get the material for this contact;
		material = NewtonContactGetMaterial (contact);

		contactNormalSpeed = NewtonMaterialGetContactNormalSpeed (material);
		if (contactNormalSpeed > contactBestSpeed){
			dVector normal;
			contactBestSpeed = contactNormalSpeed;
			NewtonMaterialGetContactPositionAndNormal (material, body0, &contactPosit[0], &normal[0]);
			bestSound = (SoundEffect *)NewtonMaterialGetMaterialPairUserData (material);
		}
	}

	// now that we found we can play then
	if (bestSound) {
		// calculate the volume;
		dFloat volume;
		dFloat dist2;

		dVector eyePoint (GetCameraEyePoint() - contactPosit);
		dist2 = eyePoint % eyePoint;
		if (dist2 < (MAX_SOUND_DISTANCE * MAX_SOUND_DISTANCE)) {
			volume = 1.0f;
			if (dist2 > (MIN_SOUND_DISTANCE * MIN_SOUND_DISTANCE)) {
				volume = 1.0f - (dSqrt (dist2) - MIN_SOUND_DISTANCE) / (MAX_SOUND_DISTANCE -  MIN_SOUND_DISTANCE);
			}
			bestSound->m_manager->Play(bestSound->m_sound, volume, 0);
		}
	}
}
Ejemplo n.º 12
0
static void RenderBodyContactsAndTangentDiretions (NewtonBody* const body, dFloat length)
{
	for (NewtonJoint* joint = NewtonBodyGetFirstContactJoint(body); joint; joint = NewtonBodyGetNextContactJoint(body, joint)) {
		if (NewtonJointIsActive (joint)) {
			for (void* contact = NewtonContactJointGetFirstContact (joint); contact; contact = NewtonContactJointGetNextContact (joint, contact)) {
				dVector point(0.0f);
				dVector normal(0.0f);	
				NewtonMaterial* const material = NewtonContactGetMaterial (contact);
				NewtonMaterialGetContactPositionAndNormal (material, body, &point.m_x, &normal.m_x);

				dVector tangentDir0(0.0f);
				dVector tangentDir1(0.0f);
				NewtonMaterialGetContactTangentDirections(material, body, &tangentDir0[0], &tangentDir1[0]);

				// if we are display debug info we need to block other threads from writing the data at the same time
				dVector p1 (point + normal.Scale (length));
				dVector p0 (point);
				glVertex3f (p0.m_x, p0.m_y, p0.m_z);
				glVertex3f (p1.m_x, p1.m_y, p1.m_z);
			}
		}
	}
}
Ejemplo n.º 13
0
void GenericContactProcess (const NewtonJoint* contactJoint, dFloat timestep, int threadIndex)
{
#if 0 
	dFloat speed0;
	dFloat speed1;
	SpecialEffectStruct* currectEffect;

	// get the pointer to the special effect structure
	currectEffect = (SpecialEffectStruct *)NewtonMaterialGetMaterialPairUserData (material);

	// save the contact information
	NewtonMaterialGetContactPositionAndNormal (material, &currectEffect->m_position.m_x, &currectEffect->m_normal.m_x);
	NewtonMaterialGetContactTangentDirections (material, &currectEffect->m_tangentDir0.m_x, &currectEffect->m_tangentDir1.m_x);


	// Get the maximum normal speed of this impact. this can be used for positioning collision sound
	speed0 = NewtonMaterialGetContactNormalSpeed (material);
	if (speed0 > currectEffect->m_contactMaxNormalSpeed) {
		// save the position of the contact (for 3d sound of particles effects)
		currectEffect->m_contactMaxNormalSpeed = speed0;
	}

	// get the maximum of the two sliding contact speed
	speed0 = NewtonMaterialGetContactTangentSpeed (material, 0);
	speed1 = NewtonMaterialGetContactTangentSpeed (material, 1);
	if (speed1 > speed0) {
		speed0 = speed1;
	}

	// Get the maximum tangent speed of this contact. this can be used for particles(sparks) of playing scratch sounds 
	if (speed0 > currectEffect->m_contactMaxTangentSpeed) {
		// save the position of the contact (for 3d sound of particles effects)
		currectEffect->m_contactMaxTangentSpeed = speed0;
	}


#endif
	
	// read the table direction
//	dVector dir (tableDir);
//	dVector updir (TableDir);
//	NewtonBody* const body = NewtonJointGetBody0(contactJoint);
//	for (void* contact = NewtonContactJointGetFirstContact (contactJoint); contact; contact = NewtonContactJointGetNextContact (contactJoint, contact)) {
//		dFloat speed;
//		dVector point;
//		dVector normal;	
//		dVector dir0;	
//		dVector dir1;	
//		dVector force;
//		NewtonMaterial* material;
//
//		material = NewtonContactGetMaterial (contact);
//		NewtonMaterialGetContactPositionAndNormal (material, body, &point.m_x, &normal.m_x);
//
//		// if the normal is vertical is large the say 40 degrees
//		if (fabsf (normal % upDir) > 0.7f) {
//			// rotate the normal to be aligned with the table direction
//			NewtonMaterialContactRotateTangentDirections (material, dir);
//		}
//	}


	NewtonBody* const body = NewtonJointGetBody0(contactJoint);
	for (void* contact = NewtonContactJointGetFirstContact (contactJoint); contact; contact = NewtonContactJointGetNextContact (contactJoint, contact)) {
		dVector point;
		dVector normal;	
		dVector dir0;	
		dVector dir1;	
		dVector force;

		NewtonMaterial* const material = NewtonContactGetMaterial (contact);

		NewtonMaterialGetContactForce (material, body, &force.m_x);
		NewtonMaterialGetContactPositionAndNormal (material, body, &point.m_x, &normal.m_x);
		NewtonMaterialGetContactTangentDirections (material, body, &dir0.m_x, &dir1.m_x);
		//dFloat speed = NewtonMaterialGetContactNormalSpeed(material);

		//speed = NewtonMaterialGetContactNormalSpeed(material);
		// play sound base of the contact speed.
		//
	}
}
Ejemplo n.º 14
0
		void ApplyTracktionForce (dFloat timestep, const NewtonBody* track)
		{
			dVector veloc;
			dVector omega;
			dMatrix matrix;

			NewtonBodyGetOmega(m_body0, &omega[0]);
			NewtonBodyGetVelocity(m_body0, &veloc[0]);
			NewtonBodyGetMatrix (m_body0, &matrix[0][0]);
			

			// itetate over the contact list and condition each contact direction anc contact acclerations
			for (NewtonJoint* contactJoint = NewtonBodyGetFirstContactJoint (track); contactJoint; contactJoint = NewtonBodyGetNextContactJoint (track, contactJoint)) {
				_ASSERTE ((NewtonJointGetBody0 (contactJoint) == track) || (NewtonJointGetBody1 (contactJoint) == track));

				#ifdef REMOVE_REDUNDAT_CONTACT	
				int contactCount;
				contactCount = NewtonContactJointGetContactCount(contactJoint);
				if (contactCount > 2) {
					// project the contact to the bounday of the conve hull o fteh trhread foot ptint 
					dFloat maxDist;
					dFloat minDist;
					void* minContact;
					void* maxContact;
					
					dMatrix matrix;
			
					minContact = NULL;
				    maxContact = NULL;
					NewtonBodyGetMatrix (track, &matrix[0][0]);

					maxDist = -1.0e10f;
					minDist = -1.0e10f;
					//find the best two contacts and remove all others
					for (void* contact = NewtonContactJointGetFirstContact (contactJoint); contact; contact = NewtonContactJointGetNextContact (contactJoint, contact)) {
						dFloat dist;
						dVector point;
						dVector normal;
						NewtonMaterial* material;

					    material = NewtonContactGetMaterial (contact);
						NewtonMaterialGetContactPositionAndNormal(material, &point[0], &normal[0]);
						
						dist = matrix.m_front % point;
						if (dist > maxDist) {
							maxDist = dist;
							maxContact = contact;
						} 
						if (-dist > minDist) {
							minDist = -dist;
							minContact = contact;
						}
						
					}

					// now delete all reduntact contacts
					void* nextContact;
					NewtonWorld* world;

					world = NewtonBodyGetWorld (track);
					NewtonWorldCriticalSectionLock(world);
					for (void* contact = NewtonContactJointGetFirstContact (contactJoint); contact; contact = nextContact) {
						nextContact = NewtonContactJointGetNextContact (contactJoint, contact);
						if (!((contact == minContact) || (contact == maxContact))) {
							NewtonContactJointRemoveContact (contactJoint, contact);
						}
					}
					NewtonWorldCriticalSectionUnlock(world);
				}

				#endif

			
				for (void* contact = NewtonContactJointGetFirstContact (contactJoint); contact; contact = NewtonContactJointGetNextContact (contactJoint, contact)) {
					dFloat speed;
					dFloat accel;
					dVector point;
					dVector normal;
					dVector dir0;
					dVector dir1;
					NewtonMaterial* material;

				    material = NewtonContactGetMaterial (contact);
					NewtonMaterialContactRotateTangentDirections (material, &matrix.m_front[0]);
					NewtonMaterialGetContactPositionAndNormal(material, &point[0], &normal[0]);
					NewtonMaterialGetContactTangentDirections (material, &dir0[0], &dir1[0]);


					dVector posit (point - matrix.m_posit);
					veloc += omega * posit;
					speed = veloc % dir0;
				//	accel = m_accel - 0.1f * speed + (((posit % m_matrix.m_right) > 0.0f) ? m_turnAccel : - m_turnAccel);
					accel = m_veloc + (((posit % matrix.m_right) > 0.0f) ? m_turnVeloc : - m_turnVeloc);

					accel = (accel - speed) * 0.5f / timestep;

			//		NewtonMaterialSetContactStaticFrictionCoef (material, 1.0f, 0);
			//		NewtonMaterialSetContactKineticFrictionCoef (material, 1.0f, 0);
					NewtonMaterialSetContactFrictionCoef (material, 1.0f, 1.0f, 0);

			//		NewtonMaterialSetContactStaticFrictionCoef (material, 0.5f, 1);
			//		NewtonMaterialSetContactKineticFrictionCoef (material, 0.5f, 1);
					NewtonMaterialSetContactFrictionCoef (material, 0.5f, 0.5f, 1);
					
					NewtonMaterialSetContactTangentAcceleration (material, accel, 0);
				}

				// for debug purpose show the contact
				ShowJointContacts (contactJoint);
			}
		}
static void DestroyThisBodyCallback (const NewtonBody* body, const NewtonJoint* contactJoint)
{
	NewtonWorld* world;
	NewtonMesh* topMesh;
	NewtonMesh* bottomMesh;
	NewtonMesh* effectMesh;
	RenderPrimitive* srcPrimitive;
	dMatrix matrix;
	dFloat maxForce;
	dVector point;
	dVector dir0;
	dVector dir1;


	// Get the world;
	world = NewtonBodyGetWorld (body);

	// find a the strongest force 
	maxForce = 0.0f;
	for (void* contact = NewtonContactJointGetFirstContact (contactJoint); contact; contact = NewtonContactJointGetNextContact (contactJoint, contact)) {
		dVector force;
		NewtonMaterial* material;

		material = NewtonContactGetMaterial (contact);
		NewtonMaterialGetContactForce (material, &force.m_x);
		if (force.m_x > maxForce) {
			dVector normal;
			NewtonMaterialGetContactPositionAndNormal(material, &point[0], &normal[0]);
			NewtonMaterialGetContactTangentDirections (material, &dir0[0], &dir0[0]);
		}
	}

	// get the visual primitive
	srcPrimitive = (RenderPrimitive*) NewtonBodyGetUserData (body);

	// get the effect mesh that is use to create the debris pieces
	effectMesh = srcPrimitive->m_specialEffect;


	// calculate the cut plane plane
	NewtonBodyGetMatrix (body, &matrix[0][0]);

	dMatrix clipMatrix (dgGrammSchmidt(dir0) * 
						dYawMatrix(30.0f * 3.1416f/180.0f * RandomVariable(1.0f)) * 
						dRollMatrix(30.0f * 3.1416f/180.0f * RandomVariable(1.0f)));

	clipMatrix.m_posit = point;
	clipMatrix.m_posit.m_w = 1.0f;
	clipMatrix = clipMatrix * matrix.Inverse();

	// break the mesh into two pieces
	NewtonMeshClip (effectMesh, meshClipper, &clipMatrix[0][0], &topMesh, &bottomMesh);
	if (topMesh && bottomMesh) {
		dFloat volume;
		NewtonMesh* meshPartA = NULL;
		NewtonMesh* meshPartB = NULL;

		volume = NewtonConvexCollisionCalculateVolume (NewtonBodyGetCollision(body));

		// the clipper was able to make a cut now we can create new debris piece for replacement
		dMatrix clipMatrix1 (dgGrammSchmidt(dir1) * 
							 dYawMatrix(30.0f * 3.1416f/180.0f * RandomVariable(1.0f)) * 
							 dRollMatrix(30.0f * 3.1416f/180.0f * RandomVariable(1.0f)));
		NewtonMeshClip (bottomMesh, meshClipper, &clipMatrix1[0][0], &meshPartA, &meshPartB);
		if (meshPartA && meshPartB) {
			// creat another split (you can make as many depend of the FPS)
			CreateDebriPiece (body, meshPartA, volume);
			CreateDebriPiece (body, meshPartB, volume);

			NewtonMeshDestroy(meshPartA);
			NewtonMeshDestroy(meshPartB);
		} else {
			CreateDebriPiece (body, bottomMesh, volume);
		}
		NewtonMeshDestroy(bottomMesh);


		dMatrix clipMatrix2 (dgGrammSchmidt(dir1) * 
							 dYawMatrix(30.0f * 3.1416f/180.0f * RandomVariable(1.0f)) * 
			                 dRollMatrix(30.0f * 3.1416f/180.0f * RandomVariable(1.0f)));
		NewtonMeshClip (topMesh, meshClipper, &clipMatrix2[0][0], &meshPartA, &meshPartB);
		if (meshPartA && meshPartB) {
			// creat another split (you can make as many depend of the FPS)
			CreateDebriPiece (body, meshPartA, volume);
			CreateDebriPiece (body, meshPartB, volume);

			NewtonMeshDestroy(meshPartA);
			NewtonMeshDestroy(meshPartB);
		} else {
			CreateDebriPiece (body, topMesh, volume);
		}
		NewtonMeshDestroy(topMesh);


		// remove the old visual from graphics world
		SceneManager* system = (SceneManager*) NewtonWorldGetUserData(world);
		delete srcPrimitive;
		system->Remove(srcPrimitive);

		// finally destroy this body;
		NewtonDestroyBody(world, body);
	}
}
void ContactCallback::getContactPositionAndNormal( Ogre::Vector3& pos, Ogre::Vector3& norm ) const 
{
	NewtonMaterialGetContactPositionAndNormal( m_material, &pos.x, &norm.x );
}
Ejemplo n.º 17
0
	void cPhysicsMaterialNewton::ProcessContactCallback(const NewtonJoint* apJoint,
													   float afTimeStep,
													   int alThreadIndex)
	{
		cPhysicsContactData ContactData;
		int lContactNum = 0;
		iPhysicsBody * pContactBody1 = (iPhysicsBody*) NewtonBodyGetUserData(NewtonJointGetBody0(apJoint));
		iPhysicsBody * pContactBody2 = (iPhysicsBody*) NewtonBodyGetUserData(NewtonJointGetBody1(apJoint));

		for (void* pContact = NewtonContactJointGetFirstContact(apJoint);
			 pContact;
			 pContact = NewtonContactJointGetNextContact(apJoint, pContact))
		{
			NewtonMaterial* pMaterial = NewtonContactGetMaterial(pContact);
			//Log(" Process contact between body '%s' and '%s'.\n",pContactBody1->GetName().c_str(),
			//													pContactBody2->GetName().c_str());

			//Normal speed
			float fNormSpeed = NewtonMaterialGetContactNormalSpeed(pMaterial);
			if (ContactData.mfMaxContactNormalSpeed < fNormSpeed)
				ContactData.mfMaxContactNormalSpeed = fNormSpeed;

			//Tangent speed
			float fTanSpeed0 = NewtonMaterialGetContactTangentSpeed(pMaterial, 0);
			float fTanSpeed1 = NewtonMaterialGetContactTangentSpeed(pMaterial, 1);
			if(std::abs(ContactData.mfMaxContactTangentSpeed) < std::abs(fTanSpeed0))
				ContactData.mfMaxContactTangentSpeed = fTanSpeed0;
			if(std::abs(ContactData.mfMaxContactTangentSpeed) < std::abs(fTanSpeed1))
				ContactData.mfMaxContactTangentSpeed = fTanSpeed1;

			//Force
			cVector3f vForce;
			NewtonMaterialGetContactForce(pMaterial,vForce.v);
			ContactData.mvForce += vForce;

			//Position and normal
			cVector3f vPos, vNormal;
			NewtonMaterialGetContactPositionAndNormal(pMaterial,vPos.v, vNormal.v);

			ContactData.mvContactNormal += vNormal;
			ContactData.mvContactPosition += vPos;

			//Log(" Norm: %f Tan0: %f Tan1: %f\n",fNormSpeed, fTanSpeed0, fTanSpeed1);
			//Log("Force: %s step %f\n", vForce.ToString().c_str(), afTimestep);

			if(pContactBody1->GetWorld()->GetSaveContactPoints())
			{
				cCollidePoint collidePoint;
				collidePoint.mfDepth = 1;
				NewtonMaterialGetContactPositionAndNormal (pMaterial, collidePoint.mvPoint.v,
														   collidePoint.mvNormal.v);

				pContactBody1->GetWorld()->GetContactPoints()->push_back(collidePoint);
			}

			lContactNum++;
		}

		//Log("--- End contact between body '%s' and '%s'.\n",mpContactBody1->GetName().c_str(),
		//													mpContactBody2->GetName().c_str());

		if(lContactNum <= 0) return;

		iPhysicsMaterial *pMaterial1 = pContactBody1->GetMaterial();
		iPhysicsMaterial *pMaterial2 = pContactBody2->GetMaterial();

		ContactData.mvContactNormal = ContactData.mvContactNormal / (float)lContactNum;
		ContactData.mvContactPosition = ContactData.mvContactPosition / (float)lContactNum;

		pMaterial1->GetSurfaceData()->CreateImpactEffect(ContactData.mfMaxContactNormalSpeed,
													ContactData.mvContactPosition,
													lContactNum,pMaterial2->GetSurfaceData());

		int lPrio1 = pMaterial1->GetSurfaceData()->GetPriority();
		int lPrio2 = pMaterial2->GetSurfaceData()->GetPriority();

		if(lPrio1 >= lPrio2)
		{
			if(std::abs(ContactData.mfMaxContactNormalSpeed) > 0)
				pMaterial1->GetSurfaceData()->OnImpact(ContactData.mfMaxContactNormalSpeed,
														ContactData.mvContactPosition,
														lContactNum,pContactBody1);
			if(std::abs(ContactData.mfMaxContactTangentSpeed) > 0)
				pMaterial1->GetSurfaceData()->OnSlide(ContactData.mfMaxContactTangentSpeed,
														ContactData.mvContactPosition,
														lContactNum,pContactBody1,pContactBody2);
		}

		if(lPrio2 >= lPrio1 && pMaterial2 != pMaterial1)
		{
			if(std::abs(ContactData.mfMaxContactNormalSpeed) > 0)
				pMaterial2->GetSurfaceData()->OnImpact(ContactData.mfMaxContactNormalSpeed,
														ContactData.mvContactPosition,
														lContactNum,pContactBody2);
			if(std::abs(ContactData.mfMaxContactTangentSpeed) > 0)
				pMaterial2->GetSurfaceData()->OnSlide(ContactData.mfMaxContactTangentSpeed,
														ContactData.mvContactPosition,
														lContactNum,pContactBody2,pContactBody1);
		}

		pContactBody1->OnCollide(pContactBody2,&ContactData);
		pContactBody2->OnCollide(pContactBody1,&ContactData);
	}
Ejemplo n.º 18
0
 virtual void getContactPositionAndNormal(Math::Point3& _contactPosition, Math::Vector3& _contactNormal) const
 {
     NewtonMaterialGetContactPositionAndNormal(m_pMaterial, _contactPosition.m_array, _contactNormal.m_array);
 }