PlaformEntityEntity (DemoEntityManager* const scene, DemoEntity* const source, NewtonBody* const triggerPort0, NewtonBody* const triggerPort1) :DemoEntity (source->GetNextMatrix(), NULL) { scene->Append(this); DemoMesh* const mesh = (DemoMesh*)source->GetMesh(); dAssert (mesh->IsType(DemoMesh::GetRttiType())); SetMesh(mesh, source->GetMeshMatrix()); const dFloat mass = 100.0f; dMatrix matrix (source->GetNextMatrix()) ; NewtonWorld* const world = scene->GetNewton(); // note: because the mesh matrix can have scale, for simplicity just apply the local mesh matrix to the vertex cloud dVector pool[128]; const dMatrix& meshMatrix = GetMeshMatrix(); meshMatrix.TransformTriplex(&pool[0].m_x, sizeof (dVector), mesh->m_vertex, 3 * sizeof (dFloat), mesh->m_vertexCount); NewtonCollision* const collision = NewtonCreateConvexHull(world, mesh->m_vertexCount, &pool[0].m_x, sizeof (dVector), 0, 0, NULL); NewtonBody* body = CreateSimpleBody (world, this, 100, matrix, collision, 0); NewtonDestroyCollision(collision); // attach a kinematic joint controller joint to move this body dVector pivot; NewtonBodyGetCentreOfMass (body, &pivot[0]); pivot = matrix.TransformVector(pivot); m_driver = new FerryDriver (body, pivot, triggerPort0, triggerPort1); m_driver->SetMaxLinearFriction (50.0f * dAbs (mass * DEMO_GRAVITY)); m_driver->SetMaxAngularFriction(50.0f * dAbs (mass * DEMO_GRAVITY)); }
NewtonCollision* CreateNewtonConvex (NewtonWorld* world, Entity *ent, int shapeId) { dVector minBox; dVector maxBox; NewtonCollision* collision; dVector* tmpArray = new dVector [ent->m_vertexCount]; // Get the Bounding Box for this entity ent->GetBBox (minBox, maxBox); dVector size (maxBox - minBox); dVector origin ((maxBox + minBox).Scale (0.5f)); size.m_w = 1.0f; origin.m_w = 1.0f; // Translate al the points to the origin point for (int i = 0; i < ent->m_vertexCount; i ++) { dVector tmp (ent->m_vertex[i * 3 + 0], ent->m_vertex[i * 3 + 1], ent->m_vertex[i * 3 + 2], 0.0f); tmpArray[i] = tmp - origin; } // make and offset Matrix for this collision shape. dMatrix offset (GetIdentityMatrix()); offset.m_posit = origin; // now create a convex hull shape from the vertex geometry collision = NewtonCreateConvexHull(world, ent->m_vertexCount, &tmpArray[0][0], sizeof (dVector), 0.1f, shapeId, &offset[0][0]); delete tmpArray; return collision; }
NewtonCollision* CreateNewtonConvex (NewtonWorld* world, StaticEntity *ent, int shapeId) { NewtonCollision* collision; glm::vec3* tmpArray = new glm::vec3 [ent->meshObj->totalVertices]; glm::vec3 size (ent->maxBox - ent->minBox); glm::vec3 origin ((ent->maxBox + ent->minBox)*0.5f); unsigned int i,u,counter; counter=0; // Translate all the points to the origin point for(i=0; i<ent->meshObj->mesh.size(); i++) { for(u=0; u<ent->meshObj->mesh.at(i)->numVertices; u++) { glm::vec3 tmp(ent->meshObj->mesh[i]->vertex[u].x, ent->meshObj->mesh[i]->vertex[u].y, ent->meshObj->mesh[i]->vertex[u].z); tmpArray[counter] = tmp - origin; counter++; } } // make and offset Matrix for this collision shape. glm::mat4 offset = glm::gtc::matrix_transform::translate(glm::mat4(1.0f),origin); // now create a convex hull shape from the vertex geometry collision = NewtonCreateConvexHull(world, ent->meshObj->totalVertices, &tmpArray[0][0], sizeof (glm::vec3), 0.1f, shapeId, &offset[0][0]); delete tmpArray; return collision; }
void CollisionDetection::createConvexHull( Entity *entity, bool enemy ) { size_t vertex_count; size_t index_count; Ogre::Vector3 *vertices; unsigned long *indices; GetMeshInformation( entity->getMesh(), vertex_count, vertices, index_count, indices, Vector3( 0.0, 0.0, 0.0 ),//entity->getParentNode()->getPosition(), Ogre::Quaternion::IDENTITY, //entity->getParentNode()->getOrientation() Ogre::Vector3(1,1,1));//entity->getParentNode()->_getDerivedScale() );//Ogre::Vector3(1,1,1)); dFloat *vertexCloud = new dFloat[vertex_count*3]; for( int i = 0; i < vertex_count; i++ ) { vertexCloud[i*3] = vertices[i].x; vertexCloud[i*3+1] = vertices[i].y; vertexCloud[i*3+2] = vertices[i].z; } shapeID++; NewtonCollision *newCol = NewtonCreateConvexHull (newtonWorld, vertex_count, vertexCloud, 12, 0.0, shapeID, NULL); if(enemy) { enemyEnt = newCol; } else { NewtonBody* rigidBodyBox = NewtonCreateBody (newtonWorld, newCol); //PROBLEM with the line as this comand should work, but terminates the app;Possibly a c++ issue //NewtonReleaseCollision( newtonWorld, enemyCol); collisionsMap.insert(pair<Entity*,NewtonCollision*>(entity,newCol)); bodysMap.insert(pair<Entity*,NewtonBody*>(entity,rigidBodyBox)); } }
NewtonCollision* MakeConvexHull(const DemoEntity* const bodyPart) const { dVector points[1024 * 16]; const DemoEntity* const meshEntity = FindMesh(bodyPart); DemoMesh* const mesh = (DemoMesh*)meshEntity->GetMesh(); dAssert(mesh->IsType(DemoMesh::GetRttiType())); dAssert(mesh->m_vertexCount && (mesh->m_vertexCount < int(sizeof(points) / sizeof(points[0])))); // go over the vertex array and find and collect all vertices's weighted by this bone. const dFloat* const array = mesh->m_vertex; for (int i = 0; i < mesh->m_vertexCount; i++) { points[i][0] = array[i * 3 + 0]; points[i][1] = array[i * 3 + 1]; points[i][2] = array[i * 3 + 2]; points[i][3] = 0.0f; } dMatrix matrix(meshEntity->GetMeshMatrix()); matrix = matrix * meshEntity->GetCurrentMatrix(); //matrix = matrix * bodyPart->GetParent()->GetCurrentMatrix(); matrix.TransformTriplex(&points[0][0], sizeof(dVector), &points[0][0], sizeof(dVector), mesh->m_vertexCount); // return NewtonCreateConvexHull(GetWorld(), mesh->m_vertexCount, &points[0][0], sizeof(dVector), 1.0e-3f, SERVO_VEHICLE_DEFINITION::m_bodyPart, NULL); return NewtonCreateConvexHull(GetWorld(), mesh->m_vertexCount, &points[0][0], sizeof(dVector), 1.0e-3f, 0, NULL); }
NewtonCollision* CreateChassisCollision (NewtonWorld* const world) const { dMatrix offset (dGetIdentityMatrix()); offset.m_posit.m_y = 0.7f; NewtonCollision* const convex0 = NewtonCreateConvexHull (world, 8, &VehicleHullShape0[0][0], 3 * sizeof (dFloat), 0.001f, 0, NULL); NewtonCollision* const convex1 = NewtonCreateConvexHull (world, 8, &VehicleHullShape1[0][0], 3 * sizeof (dFloat), 0.001f, 0, &offset[0][0]); NewtonCollision* const collision = NewtonCreateCompoundCollision(world, 0); NewtonCompoundCollisionBeginAddRemove(collision); NewtonCompoundCollisionAddSubCollision (collision, convex0); NewtonCompoundCollisionAddSubCollision (collision, convex1); NewtonCompoundCollisionEndAddRemove (collision); NewtonDestroyCollision (convex0); NewtonDestroyCollision (convex1); return collision; }
/* ============= CMod_PhysicsAddEntity ============= */ void CMod_PhysicsAddEntity(sharedEntity_t * gEnt) { NewtonCollision* collision = NULL; NewtonBody* body = NULL; std::map<int, bspCmodel>::iterator it = bspModels.find (gEnt->s.modelindex); if ( it == bspModels.end() ) { return; } vec3_t inertia, com; dMatrix matrix (GetIdentityMatrix()); bspCmodel* bmodel = &it->second; collision = NewtonCreateConvexHull (g_world, bmodel->vertices.size(), &bmodel->vertices[0].m_x, sizeof (dVector), 0.0f, &matrix[0][0]); body = NewtonCreateBody (g_world, collision); NewtonConvexCollisionCalculateVolume (collision); NewtonReleaseCollision (g_world, collision); bmodel->rigidBody = body; NewtonBodySetMaterialGroupID (body, defaultMaterialGroup); NewtonBodySetUserData (body, (void*)gEnt); NewtonBodySetDestructorCallback (body, PhysicsEntityDie); NewtonBodySetContinuousCollisionMode (body, 0); NewtonBodySetForceAndTorqueCallback (body, PhysicsEntityThink); NewtonBodySetTransformCallback (body, PhysicsEntitySetTransform); NewtonConvexCollisionCalculateInertialMatrix (collision, &inertia[0], &com[0]); NewtonBodySetCentreOfMass (body, &com[0]); VectorScale (inertia, 10.0f, inertia); // The inertia needs to be scaled by the mass. NewtonBodySetMassMatrix (body, 10.f, inertia[0], inertia[1], inertia[2]); matrix.m_posit.m_x = gEnt->s.origin[0] * UNITS_PER_METRE; matrix.m_posit.m_y = gEnt->s.origin[1] * UNITS_PER_METRE; matrix.m_posit.m_z = gEnt->s.origin[2] * UNITS_PER_METRE; NewtonBodySetMatrix (body, &matrix[0][0]); gEnt->s.pos.trType = TR_INTERPOLATE; VectorCopy (gEnt->s.origin, gEnt->s.pos.trBase); VectorCopy (gEnt->s.origin, gEnt->r.currentOrigin); gEnt->s.apos.trType = TR_INTERPOLATE; VectorCopy (gEnt->s.angles, gEnt->s.apos.trBase); VectorCopy (gEnt->s.angles, gEnt->r.currentAngles); }
void Newtonnode::initConvexHull(NewtonWorld *pWorld,const ion::video::Mesh& srcmesh,const float mass, const float Ixx,const float Iyy,const float Izz) { if (pWorld==0) { ion::base::log("Newtonnode::initConvexHull()",ion::base::Error) << "No NewtonWorld pointer given\n"; return; } if (!srcmesh.isValid()) { ion::base::log("Newtonnode::initConvexHull()",ion::base::Error) << "Source mesh is invalid\n"; return; } if (!srcmesh.vertexstream().isMapped()) { ion::base::log("Newtonnode::initConvexHull()",ion::base::Error) << "source mesh \"" << srcmesh.objIdentifier() << " is not mapped!\n"; return; } if ((m_pNewtonCollision!=0) && (m_pNewtonworld!=0)) NewtonReleaseCollision(m_pNewtonworld,m_pNewtonCollision); float *pPoints; { pPoints=new float[3*srcmesh.vertexstream().capacity()]; for (ion_uint32 v=0;v<srcmesh.vertexstream().capacity();++v) { const ion::math::Vector3f &rV=srcmesh.vertexstream().position(v); pPoints[v*3+0]=rV.x(); pPoints[v*3+1]=rV.y(); pPoints[v*3+2]=rV.z(); } } m_pNewtonworld=pWorld; m_pNewtonCollision=NewtonCreateConvexHull(m_pNewtonworld,srcmesh.vertexstream().capacity(),pPoints,12,0); m_pBody=NewtonCreateBody(m_pNewtonworld,m_pNewtonCollision); NewtonBodySetUserData(m_pBody,this); NewtonBodySetMassMatrix(m_pBody,mass,Ixx,Iyy,Izz); NewtonReleaseCollision(m_pNewtonworld,m_pNewtonCollision); NewtonBodySetTransformCallback (m_pBody, physicsSetTransform); NewtonBodySetForceAndTorqueCallback (m_pBody, physicsApplyForceAndTorque); delete [] pPoints; }
NewtonCollision* CreateNewtonConvex (NewtonWorld* world, Entity *ent, int shapeId) { // now create a convex hull shape from the vertex geometry return NewtonCreateConvexHull(world, ent->m_vertexCount, ent->m_vertex, 3 * sizeof (dFloat), 0.1f, shapeId, NULL); }
NewtonCollision* CreateConvexCollision (NewtonWorld* world, const dMatrix& srcMatrix, const dVector& originalSize, PrimitiveType type, int materialID__) { dVector size (originalSize); NewtonCollision* collision = NULL; switch (type) { case _NULL_PRIMITIVE: { collision = NewtonCreateNull (world); break; } case _SPHERE_PRIMITIVE: { // create the collision collision = NewtonCreateSphere (world, size.m_x * 0.5f, 0, NULL); break; } case _BOX_PRIMITIVE: { // create the collision collision = NewtonCreateBox (world, size.m_x, size.m_y, size.m_z, 0, NULL); break; } case _CONE_PRIMITIVE: { dFloat r = size.m_x * 0.5f; dFloat h = size.m_y; // create the collision collision = NewtonCreateCone (world, r, h, 0, NULL); break; } case _CYLINDER_PRIMITIVE: { // create the collision collision = NewtonCreateCylinder (world, size.m_x * 0.5f, size.m_y, 0, NULL); break; } case _CAPSULE_PRIMITIVE: { // create the collision collision = NewtonCreateCapsule (world, size.m_x * 0.5f, size.m_y, 0, NULL); break; } case _TAPERED_CAPSULE_PRIMITIVE: { // create the collision collision = NewtonCreateTaperedCapsule (world, size.m_x * 0.5f, size.m_z * 0.5f, size.m_y, 0, NULL); break; } case _CHAMFER_CYLINDER_PRIMITIVE: { // create the collision collision = NewtonCreateChamferCylinder (world, size.m_x * 0.5f, size.m_y, 0, NULL); break; } case _TAPERED_CYLINDER_PRIMITIVE: { // create the collision collision = NewtonCreateTaperedCylinder (world, size.m_x * 0.5f, size.m_z * 0.5f, size.m_y, 0, NULL); break; } case _RANDOM_CONVEX_HULL_PRIMITIVE: { // Create a clouds of random point around the origin #define SAMPLE_COUNT 200 dVector cloud [SAMPLE_COUNT]; // make sure that at least the top and bottom are present cloud [0] = dVector ( size.m_x * 0.5f, 0.0f, 0.0f, 0.0f); cloud [1] = dVector (-size.m_x * 0.5f, 0.0f, 0.0f, 0.0f); cloud [2] = dVector ( 0.0f, size.m_y * 0.5f, 0.0f, 0.0f); cloud [3] = dVector ( 0.0f, -size.m_y * 0.5f, 0.0f, 0.0f); cloud [4] = dVector (0.0f, 0.0f, size.m_z * 0.5f, 0.0f); cloud [5] = dVector (0.0f, 0.0f, -size.m_z * 0.5f, 0.0f); int count = 6; // populate the cloud with pseudo Gaussian random points for (int i = 6; i < SAMPLE_COUNT; i ++) { cloud [i].m_x = RandomVariable(size.m_x); cloud [i].m_y = RandomVariable(size.m_y); cloud [i].m_z = RandomVariable(size.m_z); count ++; } collision = NewtonCreateConvexHull (world, count, &cloud[0].m_x, sizeof (dVector), 0.01f, 0, NULL); break; } case _REGULAR_CONVEX_HULL_PRIMITIVE: { // Create a clouds of random point around the origin #define STEPS_HULL 6 //#define STEPS_HULL 3 dVector cloud [STEPS_HULL * 4 + 256]; int count = 0; dFloat radius = size.m_y; dFloat height = size.m_x * 0.999f; dFloat x = - height * 0.5f; dMatrix rotation (dPitchMatrix(2.0f * 3.141592f / STEPS_HULL)); for (int i = 0; i < 4; i ++) { dFloat pad = ((i == 1) || (i == 2)) * 0.25f * radius; dVector p (x, 0.0f, radius + pad); x += 0.3333f * height; dMatrix acc (dGetIdentityMatrix()); for (int j = 0; j < STEPS_HULL; j ++) { cloud[count] = acc.RotateVector(p); acc = acc * rotation; count ++; } } collision = NewtonCreateConvexHull (world, count, &cloud[0].m_x, sizeof (dVector), 0.02f, 0, NULL); break; } case _COMPOUND_CONVEX_CRUZ_PRIMITIVE: { //dMatrix matrix (GetIdentityMatrix()); dMatrix matrix (dPitchMatrix(15.0f * 3.1416f / 180.0f) * dYawMatrix(15.0f * 3.1416f / 180.0f) * dRollMatrix(15.0f * 3.1416f / 180.0f)); // NewtonCollision* const collisionA = NewtonCreateBox (world, size.m_x, size.m_x * 0.25f, size.m_x * 0.25f, 0, &matrix[0][0]); // NewtonCollision* const collisionB = NewtonCreateBox (world, size.m_x * 0.25f, size.m_x, size.m_x * 0.25f, 0, &matrix[0][0]); // NewtonCollision* const collisionC = NewtonCreateBox (world, size.m_x * 0.25f, size.m_x * 0.25f, size.m_x, 0, &matrix[0][0]); matrix.m_posit = dVector (size.m_x * 0.5f, 0.0f, 0.0f, 1.0f); NewtonCollision* const collisionA = NewtonCreateBox (world, size.m_x, size.m_x * 0.25f, size.m_x * 0.25f, 0, &matrix[0][0]); matrix.m_posit = dVector (0.0f, size.m_x * 0.5f, 0.0f, 1.0f); NewtonCollision* const collisionB = NewtonCreateBox (world, size.m_x * 0.25f, size.m_x, size.m_x * 0.25f, 0, &matrix[0][0]); matrix.m_posit = dVector (0.0f, 0.0f, size.m_x * 0.5f, 1.0f); NewtonCollision* const collisionC = NewtonCreateBox (world, size.m_x * 0.25f, size.m_x * 0.25f, size.m_x, 0, &matrix[0][0]); collision = NewtonCreateCompoundCollision (world, 0); NewtonCompoundCollisionBeginAddRemove(collision); NewtonCompoundCollisionAddSubCollision (collision, collisionA); NewtonCompoundCollisionAddSubCollision (collision, collisionB); NewtonCompoundCollisionAddSubCollision (collision, collisionC); NewtonCompoundCollisionEndAddRemove(collision); NewtonDestroyCollision(collisionA); NewtonDestroyCollision(collisionB); NewtonDestroyCollision(collisionC); break; } default: dAssert (0); } dMatrix matrix (srcMatrix); matrix.m_front = matrix.m_front.Scale (1.0f / dSqrt (matrix.m_front % matrix.m_front)); matrix.m_right = matrix.m_front * matrix.m_up; matrix.m_right = matrix.m_right.Scale (1.0f / dSqrt (matrix.m_right % matrix.m_right)); matrix.m_up = matrix.m_right * matrix.m_front; NewtonCollisionSetMatrix(collision, &matrix[0][0]); return collision; }
Car::Car(const ion::base::String& identifier,NewtonWorld *pWorld,const ion::video::Mesh& srcmesh,const float mass, const float Ixx,const float Iyy,const float Izz):Node(identifier),m_pNewtonChassisCollision(0),m_pBody(0), m_pNewtonworld(pWorld),m_pNewtonJoint(0) { if (pWorld==0) { ion::base::log("Car::Car()",ion::base::Error) << "No NewtonWorld pointer given\n"; return; } if (!srcmesh.isValid()) { ion::base::log("Car::Car()",ion::base::Error) << "Source mesh is invalid\n"; return; } if (!srcmesh.vertexstream().isMapped()) { ion::base::log("Car::Car()",ion::base::Error) << "source mesh \"" << srcmesh.objIdentifier() << " is not mapped!\n"; return; } if ((m_pNewtonChassisCollision!=0) && (m_pNewtonworld!=0)) NewtonReleaseCollision(m_pNewtonworld,m_pNewtonChassisCollision); float *pPoints; { pPoints=new float[3*srcmesh.vertexstream().capacity()]; for (ion_uint32 v=0;v<srcmesh.vertexstream().capacity();++v) { const ion::math::Vector3f &rV=srcmesh.vertexstream().position(v); pPoints[v*3+0]=rV.x(); pPoints[v*3+1]=rV.y(); pPoints[v*3+2]=rV.z(); } } ion::math::Matrix4f c; m_pNewtonworld=pWorld; m_pNewtonChassisCollision=NewtonCreateConvexHull(m_pNewtonworld,srcmesh.vertexstream().capacity(),pPoints,12,c); m_pBody=NewtonCreateBody(m_pNewtonworld,m_pNewtonChassisCollision); NewtonBodySetUserData(m_pBody,this); ion::math::Vector3f origin,inertia; // calculate the moment of inertia and the relative center of mass of the solid NewtonConvexCollisionCalculateInertialMatrix (m_pNewtonChassisCollision, &inertia[0], &origin[0]); float ixx = mass * inertia[0]; float iyy = mass * inertia[1]; float izz = mass * inertia[2]; // set the mass matrix NewtonBodySetMassMatrix (m_pBody, mass, ixx, iyy, izz); origin.y()=-1; NewtonBodySetCentreOfMass (m_pBody, &origin[0]); NewtonBodySetMatrix(m_pBody,localTransform().matrix()); NewtonReleaseCollision(m_pNewtonworld,m_pNewtonChassisCollision); NewtonBodySetTransformCallback (m_pBody, physicsSetTransform); NewtonBodySetForceAndTorqueCallback (m_pBody, physicsApplyForceAndTorque); float updir[3]={0,1,0}; m_pNewtonJoint=NewtonConstraintCreateVehicle(m_pNewtonworld,&updir[0],m_pBody); NewtonVehicleSetTireCallback(m_pNewtonJoint,tireUpdate); delete [] pPoints; }
void CustomPlayerController::Init(dFloat mass, dFloat outerRadius, dFloat innerRadius, dFloat height, dFloat stairStep, const dMatrix& localAxis) { dAssert (stairStep >= 0.0f); dAssert (innerRadius >= 0.0f); dAssert (outerRadius >= innerRadius); dAssert (height >= stairStep); dAssert (localAxis[0].m_w == dFloat (0.0f)); dAssert (localAxis[1].m_w == dFloat (0.0f)); CustomPlayerControllerManager* const manager = (CustomPlayerControllerManager*) GetManager(); NewtonWorld* const world = manager->GetWorld(); SetRestrainingDistance (0.0f); m_outerRadio = outerRadius; m_innerRadio = innerRadius; m_height = height; m_stairStep = stairStep; SetClimbSlope(45.0f * 3.1416f/ 180.0f); m_upVector = localAxis[0]; m_frontVector = localAxis[1]; m_groundPlane = dVector (0.0f, 0.0f, 0.0f, 0.0f); m_groundVelocity = dVector (0.0f, 0.0f, 0.0f, 0.0f); const int steps = 12; dVector convexPoints[2][steps]; // create an inner thin cylinder dFloat shapeHigh = height; dAssert (shapeHigh > 0.0f); dVector p0 (0.0f, m_innerRadio, 0.0f, 0.0f); dVector p1 (shapeHigh, m_innerRadio, 0.0f, 0.0f); for (int i = 0; i < steps; i ++) { dMatrix rotation (dPitchMatrix (i * 2.0f * 3.141592f / steps)); convexPoints[0][i] = localAxis.RotateVector(rotation.RotateVector(p0)); convexPoints[1][i] = localAxis.RotateVector(rotation.RotateVector(p1)); } NewtonCollision* const supportShape = NewtonCreateConvexHull(world, steps * 2, &convexPoints[0][0].m_x, sizeof (dVector), 0.0f, 0, NULL); // create the outer thick cylinder dMatrix outerShapeMatrix (localAxis); dFloat capsuleHigh = m_height - stairStep; dAssert (capsuleHigh > 0.0f); m_sphereCastOrigin = capsuleHigh * 0.5f + stairStep; outerShapeMatrix.m_posit = outerShapeMatrix[0].Scale(m_sphereCastOrigin); outerShapeMatrix.m_posit.m_w = 1.0f; NewtonCollision* const bodyCapsule = NewtonCreateCapsule(world, 0.25f, 0.5f, 0, &outerShapeMatrix[0][0]); NewtonCollisionSetScale(bodyCapsule, capsuleHigh, m_outerRadio * 4.0f, m_outerRadio * 4.0f); // compound collision player controller NewtonCollision* const playerShape = NewtonCreateCompoundCollision(world, 0); NewtonCompoundCollisionBeginAddRemove(playerShape); NewtonCompoundCollisionAddSubCollision (playerShape, supportShape); NewtonCompoundCollisionAddSubCollision (playerShape, bodyCapsule); NewtonCompoundCollisionEndAddRemove (playerShape); // create the kinematic body dMatrix locationMatrix (dGetIdentityMatrix()); m_body = NewtonCreateKinematicBody(world, playerShape, &locationMatrix[0][0]); // players must have weight, otherwise they are infinitely strong when they collide NewtonCollision* const shape = NewtonBodyGetCollision(m_body); NewtonBodySetMassProperties(m_body, mass, shape); // make the body collidable with other dynamics bodies, by default NewtonBodySetCollidable (m_body, true); dFloat castHigh = capsuleHigh * 0.4f; dFloat castRadio = (m_innerRadio * 0.5f > 0.05f) ? m_innerRadio * 0.5f : 0.05f; dVector q0 (0.0f, castRadio, 0.0f, 0.0f); dVector q1 (castHigh, castRadio, 0.0f, 0.0f); for (int i = 0; i < steps; i ++) { dMatrix rotation (dPitchMatrix (i * 2.0f * 3.141592f / steps)); convexPoints[0][i] = localAxis.RotateVector(rotation.RotateVector(q0)); convexPoints[1][i] = localAxis.RotateVector(rotation.RotateVector(q1)); } m_castingShape = NewtonCreateConvexHull(world, steps * 2, &convexPoints[0][0].m_x, sizeof (dVector), 0.0f, 0, NULL); m_supportShape = NewtonCompoundCollisionGetCollisionFromNode (shape, NewtonCompoundCollisionGetNodeByIndex (shape, 0)); m_upperBodyShape = NewtonCompoundCollisionGetCollisionFromNode (shape, NewtonCompoundCollisionGetNodeByIndex (shape, 1)); NewtonDestroyCollision (bodyCapsule); NewtonDestroyCollision (supportShape); NewtonDestroyCollision (playerShape); m_isJumping = false; }
static void LoadHangingBridge (DemoEntityManager* const scene, TriggerManager* const triggerManager, NewtonCollision* const sceneCollision, const char* const name, const dMatrix& location, NewtonBody* const playGroundBody) { NewtonWorld* const world = scene->GetNewton(); DemoEntityManager::dListNode* const bridgeNodes = scene->GetLast(); LoadScene(scene, name, location); // add bridge foundations for (DemoEntityManager::dListNode* node = bridgeNodes->GetNext(); node; node = node->GetNext()) { DemoEntity* const entity = node->GetInfo(); if (entity->GetName().Find("ramp") != -1) { DemoMesh* const mesh = (DemoMesh*)entity->GetMesh(); dAssert (mesh->IsType(DemoMesh::GetRttiType())); NewtonCollision* const collision = NewtonCreateConvexHull(world, mesh->m_vertexCount, mesh->m_vertex, 3 * sizeof (dFloat), 0, 0, NULL); void* const proxy = NewtonSceneCollisionAddSubCollision (sceneCollision, collision); NewtonDestroyCollision (collision); // get the location of this tire relative to the car chassis dMatrix matrix (entity->GetNextMatrix()); NewtonCollision* const bridgeCollision = NewtonSceneCollisionGetCollisionFromNode (sceneCollision, proxy); NewtonSceneCollisionSetSubCollisionMatrix (sceneCollision, proxy, &matrix[0][0]); NewtonCollisionSetUserData(bridgeCollision, entity); } } // add all the planks that form the bridge dTree<NewtonBody*, dString> planks; dFloat plankMass = 30.0f; for (DemoEntityManager::dListNode* node = bridgeNodes->GetNext(); node; node = node->GetNext()) { DemoEntity* const entity = node->GetInfo(); if (entity->GetName().Find("plank") != -1) { DemoMesh* const mesh = (DemoMesh*)entity->GetMesh(); dAssert (mesh->IsType(DemoMesh::GetRttiType())); // note: because the mesh matrix can have scale, for simplicity just apply the local mesh matrix to the vertex cloud dVector pool[128]; const dMatrix& meshMatrix = entity->GetMeshMatrix(); meshMatrix.TransformTriplex(&pool[0].m_x, sizeof (dVector), mesh->m_vertex, 3 * sizeof (dFloat), mesh->m_vertexCount); NewtonCollision* const collision = NewtonCreateConvexHull(world, mesh->m_vertexCount, &pool[0].m_x, sizeof (dVector), 0, 0, NULL); NewtonBody* const body = CreateSimpleBody (world, entity, plankMass, entity->GetNextMatrix(), collision, 0); NewtonDestroyCollision (collision); planks.Insert(body, entity->GetName()); } } // connect each plant with a hinge // calculate the with of a plank dFloat plankwidth = 0.0f; dVector planksideDir (1.0f, 0.0f, 0.0f, 0.0f); { NewtonBody* const body0 = planks.Find("plank01")->GetInfo(); NewtonBody* const body1 = planks.Find("plank02")->GetInfo(); dMatrix matrix0; dMatrix matrix1; NewtonBodyGetMatrix(body0, &matrix0[0][0]); NewtonBodyGetMatrix(body1, &matrix1[0][0]); planksideDir = matrix1.m_posit - matrix0.m_posit; planksideDir = planksideDir.Scale (1.0f / dSqrt (planksideDir % planksideDir)); dVector dir (matrix0.UnrotateVector(planksideDir)); NewtonCollision* const shape = NewtonBodyGetCollision(body0); dVector p0; dVector p1; NewtonCollisionSupportVertex(shape, &dir[0], &p0[0]); dVector dir1 (dir.Scale (-1.0f)); NewtonCollisionSupportVertex(shape, &dir1[0], &p1[0]); plankwidth = dAbs (0.5f * ((p1 - p0) % dir)); } dTree<NewtonBody*, dString>::Iterator iter (planks); iter.Begin(); dMatrix matrix0; NewtonBody* body0 = iter.GetNode()->GetInfo(); NewtonBodyGetMatrix(body0, &matrix0[0][0]); for (iter ++; iter; iter ++) { NewtonBody* const body1 = iter.GetNode()->GetInfo(); dMatrix matrix1; NewtonBodyGetMatrix(body1, &matrix1[0][0]); // calculate the hinge parameter form the matrix location of each plank dMatrix pinMatrix0 (dGetIdentityMatrix()); pinMatrix0[0] = pinMatrix0[1] * planksideDir; pinMatrix0[0] = pinMatrix0[0].Scale (1.0f / dSqrt (pinMatrix0[0] % pinMatrix0[0])); pinMatrix0[2] = pinMatrix0[0] * pinMatrix0[1]; pinMatrix0[0][3] = 0.0f; pinMatrix0[1][3] = 0.0f; pinMatrix0[2][3] = 0.0f; // calculate the pivot pinMatrix0[3] = matrix0.m_posit + pinMatrix0[2].Scale (plankwidth); pinMatrix0[3][3] = 1.0f; dMatrix pinMatrix1 (pinMatrix0); pinMatrix1[3] = matrix1.m_posit - pinMatrix1[2].Scale (plankwidth); pinMatrix1[3][3] = 1.0f; // connect these two plank by a hinge, there a wiggle space between eh hinge that give therefore use the alternate hinge constructor new CustomHinge (pinMatrix0, pinMatrix1, body0, body1); body0 = body1; matrix0 = matrix1; } // connect the last and first plank to the bridge base { iter.Begin(); body0 = iter.GetNode()->GetInfo(); NewtonBodyGetMatrix(body0, &matrix0[0][0]); dMatrix pinMatrix0 (dGetIdentityMatrix()); pinMatrix0[0] = pinMatrix0[1] * planksideDir; pinMatrix0[0] = pinMatrix0[0].Scale (1.0f / dSqrt (pinMatrix0[0] % pinMatrix0[0])); pinMatrix0[2] = pinMatrix0[0] * pinMatrix0[1]; pinMatrix0[0][3] = 0.0f; pinMatrix0[1][3] = 0.0f; pinMatrix0[2][3] = 0.0f; pinMatrix0[3] = matrix0.m_posit - pinMatrix0[2].Scale (plankwidth); new CustomHinge (pinMatrix0, body0, playGroundBody); } { iter.End(); body0 = iter.GetNode()->GetInfo(); NewtonBodyGetMatrix(body0, &matrix0[0][0]); dMatrix pinMatrix0 (dGetIdentityMatrix()); pinMatrix0[0] = pinMatrix0[1] * planksideDir; pinMatrix0[0] = pinMatrix0[0].Scale (1.0f / dSqrt (pinMatrix0[0] % pinMatrix0[0])); pinMatrix0[2] = pinMatrix0[0] * pinMatrix0[1]; pinMatrix0[0][3] = 0.0f; pinMatrix0[1][3] = 0.0f; pinMatrix0[2][3] = 0.0f; pinMatrix0[3] = matrix0.m_posit + pinMatrix0[2].Scale (plankwidth); new CustomHinge (pinMatrix0, body0, playGroundBody); } }
static void LoadSlide (DemoEntityManager* const scene, TriggerManager* const triggerManager, NewtonCollision* const sceneCollision, const char* const name, const dMatrix& location, NewtonBody* const playGroundBody) { NewtonWorld* const world = scene->GetNewton(); DemoEntityManager::dListNode* const bridgeNodes = scene->GetLast(); LoadScene(scene, name, location); // add bridge foundations for (DemoEntityManager::dListNode* node = bridgeNodes->GetNext(); node; node = node->GetNext()) { DemoEntity* const entity = node->GetInfo(); if (entity->GetName().Find("ramp") != -1) { DemoMesh* const mesh = (DemoMesh*)entity->GetMesh(); dAssert (mesh->IsType(DemoMesh::GetRttiType())); NewtonCollision* const collision = NewtonCreateConvexHull(world, mesh->m_vertexCount, mesh->m_vertex, 3 * sizeof (dFloat), 0, 0, NULL); void* const proxy = NewtonSceneCollisionAddSubCollision (sceneCollision, collision); NewtonDestroyCollision (collision); // get the location of this tire relative to the car chassis dMatrix matrix (entity->GetNextMatrix()); NewtonCollision* const bridgeCollision = NewtonSceneCollisionGetCollisionFromNode (sceneCollision, proxy); NewtonSceneCollisionSetSubCollisionMatrix (sceneCollision, proxy, &matrix[0][0]); NewtonCollisionSetUserData(bridgeCollision, entity); } } // add start triggers CustomTriggerController* trigger0 = NULL; CustomTriggerController* trigger1 = NULL; for (DemoEntityManager::dListNode* node = bridgeNodes->GetNext(); node;) { DemoEntity* const entity = node->GetInfo(); node = node->GetNext() ; if (entity->GetName().Find("startTrigger") != -1) { DemoMesh* const mesh = (DemoMesh*)entity->GetMesh(); dAssert (mesh->IsType(DemoMesh::GetRttiType())); // create a trigger to match his mesh NewtonCollision* const collision = NewtonCreateConvexHull(world, mesh->m_vertexCount, mesh->m_vertex, 3 * sizeof (dFloat), 0, 0, NULL); dMatrix matrix (entity->GetNextMatrix()); CustomTriggerController* const controller = triggerManager->CreateTrigger(matrix, collision, NULL); NewtonDestroyCollision (collision); if (!trigger0) { trigger0 = controller; } else { trigger1 = controller; } // remove this entity from the scene, since we do not wan the trigger to be visible // to see triggers click "show collision mesh, and or "show contact points" in the main menu. scene->RemoveEntity(entity); } } // add the platform object for (DemoEntityManager::dListNode* node = bridgeNodes->GetNext(); node;) { DemoEntity* const entity = node->GetInfo(); node = node->GetNext() ; if (entity->GetName().Find("platform") != -1) { // make a platform object PlaformEntityEntity* const platformEntity = new PlaformEntityEntity (scene, entity, trigger0->GetBody(), trigger1->GetBody()); // store the platform in the trigger use data trigger0->SetUserData(platformEntity); trigger1->SetUserData(platformEntity); // remove this entity from the scene scene->RemoveEntity(entity); } } }
NewtonCollision* ConvexCollider3D::CreateHandle(PhysWorld3D* world) const { return NewtonCreateConvexHull(world->GetHandle(), static_cast<int>(m_vertices.size()), reinterpret_cast<const float*>(m_vertices.data()), sizeof(Vector3f), m_tolerance, 0, m_matrix); }
NzConvexHullGeom::NzConvexHullGeom(NzPhysWorld* physWorld, const void* vertices, unsigned int vertexCount, unsigned int stride, float tolerance, const NzMatrix4f& transformMatrix) : NzBaseGeom(physWorld) { m_collision = NewtonCreateConvexHull(physWorld->GetHandle(), vertexCount, reinterpret_cast<const float*>(vertices), stride, tolerance, 0, transformMatrix); }
void CustomDGRayCastCar::AddSingleSuspensionTire ( void *userData, const dVector& localPosition, dFloat mass, dFloat radius, dFloat width, dFloat friction, dFloat suspensionLenght, dFloat springConst, dFloat springDamper, int castMode) { dVector relTirePos = localPosition; suspensionLenght = dAbs ( suspensionLenght ); dMatrix chassisMatrix; NewtonBodyGetMatrix (m_body0, &chassisMatrix[0][0]); chassisMatrix = chassisMatrix * chassisMatrix; relTirePos += chassisMatrix.m_up.Scale ( suspensionLenght ); m_tires[m_tiresCount].m_harpoint = m_localFrame.UntransformVector( relTirePos ); m_tires[m_tiresCount].m_localAxis = dVector (0.0f, 0.0f, 1.0f, 0.0f); m_tires[m_tiresCount].m_tireAxelPosit = dVector (0.0f, 0.0f, 0.0f, 1.0f); m_tires[m_tiresCount].m_tireAxelVeloc = dVector (0.0f, 0.0f, 0.0f, 1.0f); m_tires[m_tiresCount].m_lateralPin = dVector (0.0f, 0.0f, 0.0f, 1.0f); m_tires[m_tiresCount].m_longitudinalPin = dVector (0.0f, 0.0f, 0.0f, 1.0f); m_tires[m_tiresCount].m_hitBodyPointVelocity = dVector (0.0f, 0.0f, 0.0f, 1.0f); m_tires[m_tiresCount].m_HitBody = NULL; m_tires[m_tiresCount].m_userData = userData; m_tires[m_tiresCount].m_spinAngle = 0.0f; m_tires[m_tiresCount].m_steerAngle = 0.0f; m_tires[m_tiresCount].m_tireLoad = 0.0f; m_tires[m_tiresCount].m_posit = suspensionLenght; m_tires[m_tiresCount].m_tireIsOnAir = 1; m_tires[m_tiresCount].m_tireUseConvexCastMode = castMode; m_tires[m_tiresCount].m_springConst = springConst; m_tires[m_tiresCount].m_springDamper = springDamper; m_tires[m_tiresCount].m_suspensionLenght = suspensionLenght; m_tires[m_tiresCount].m_angularVelocity = 0.0f; m_tires[m_tiresCount].m_breakForce = 0.0f; m_tires[m_tiresCount].m_torque = 0.0f; m_tires[m_tiresCount].m_groundFriction = friction; m_tires[m_tiresCount].m_tireIsConstrained = 0; m_tires[m_tiresCount].m_mass = mass; m_tires[m_tiresCount].m_width = width; m_tires[m_tiresCount].m_radius = radius; m_tires[m_tiresCount].m_Ixx = mass * radius * radius / 2.0f; m_tires[m_tiresCount].m_IxxInv = 1.0f / m_tires[m_tiresCount].m_Ixx; #define TIRE_SHAPE_SIZE 12 dVector shapePoints[TIRE_SHAPE_SIZE * 2]; for ( int i = 0; i < TIRE_SHAPE_SIZE; i ++ ) { shapePoints[i].m_x = -width * 0.5f; shapePoints[i].m_y = radius * dCos ( 2.0f * 3.14159265f * dFloat( i )/ dFloat( TIRE_SHAPE_SIZE ) ); shapePoints[i].m_z = radius * dSin ( 2.0f * 3.14159265f * dFloat( i )/ dFloat( TIRE_SHAPE_SIZE ) ); shapePoints[i + TIRE_SHAPE_SIZE].m_x = -shapePoints[i].m_x; shapePoints[i + TIRE_SHAPE_SIZE].m_y = shapePoints[i].m_y; shapePoints[i + TIRE_SHAPE_SIZE].m_z = shapePoints[i].m_z; } m_tires[m_tiresCount].m_shape = NewtonCreateConvexHull ( m_world, TIRE_SHAPE_SIZE * 2, &shapePoints[0].m_x, sizeof (dVector), 0.0f, 0, NULL ); // NewtonCreateChamferCylinder(m_world,radius,width,NULL); // NewtonCreateSphere(m_world,radius,radius,radius,&offmat[0][0]); // NewtonCreateCone(m_world,radius,width,NULL); // NewtonCreateCapsule(m_world,radius,width,NULL); // NewtonCreateChamferCylinder(m_world,radius,width,NULL); // NewtonCreateCylinder(m_world,radius*2,width*2,NULL); // NewtonCreateBox(m_world,radius*2,radius*2,radius*2,NULL); // NewtonCreateConvexHull (m_world, TIRE_SHAPE_SIZE * 2, &shapePoints[0].m_x, sizeof (dVector), 0.0f, NULL); m_tiresCount ++; }
dNewtonCollisionConvexHull::dNewtonCollisionConvexHull(dNewtonWorld* const world, int vertexCount, const dFloat* const vertexCloud, dFloat tolerance) :dNewtonCollision(world, 0) { NewtonWaitForUpdateToFinish(m_myWorld->m_world); SetShape(NewtonCreateConvexHull(m_myWorld->m_world, vertexCount, vertexCloud, 3 * sizeof (dFloat), tolerance, 0, NULL)); }