PDA

View Full Version : Positioning issue using transformation matrix



altreality
04-25-2011, 02:23 AM
I am trying to render a car using OpenGL. The car has a chassis and 4 wheels. The chassis is simply a cuboid and the wheels are cylinders. I have their positions from physics as openGL matrices. If I pass these matrices to glMultMatrixf() in turn and push and pop matrices correctly then I do get the car rendered correctly as it moves around.



//Render Ground Plane-------------------------------
float PLANE_EXTENT = 100.0f;
glBegin(GL_QUADS);
glTexCoord2f(0.0f, 1.0f); glVertex3f(-PLANE_EXTENT, 0.0f, -PLANE_EXTENT); // Top Left Of The Texture and Quad
glTexCoord2f(0.0f, 0.0f); glVertex3f(-PLANE_EXTENT, 0.0f, PLANE_EXTENT); // Bottom Left Of The Texture and Quad
glTexCoord2f(1.0f, 0.0f); glVertex3f( PLANE_EXTENT, 0.0f, PLANE_EXTENT); // Bottom Right Of The Texture and Quad
glTexCoord2f(1.0f, 1.0f); glVertex3f( PLANE_EXTENT, 0.0f, -PLANE_EXTENT); // Top Right Of The Texture and Quad
glEnd();

glColor3f(1.0,0,0);
//Render Chassis-----------------------------------
glPushMatrix();
glMultMatrixf(ptrShapes->m);
glMultMatrixf(ptrShapes->childMat);
drawBox(ptrShapes->halfExtent[0], ptrShapes->halfExtent[1], ptrShapes->halfExtent[2]);
glPopMatrix();

//Render the obstructing green box
glColor3f(0.0,1.0,0.0);
glPushMatrix();
glMultMatrixf(ptrShapes->m_box);
drawBox(ptrShapes->box_halfExtent[0], ptrShapes->box_halfExtent[1], ptrShapes->box_halfExtent[2]);
printf("\n box : %f, %f,%f", ptrShapes->box_halfExtent[0], ptrShapes->box_halfExtent[1], ptrShapes->box_halfExtent[2]);
glPopMatrix();


//Render the 4 wheels
glColor3f(1.0,1.0,0);

for (int i=0; i<4; i++){
glPushMatrix();
switch(i){
case 0 : glMultMatrixf(ptrShapes->m1);break;
case 1 : glMultMatrixf(ptrShapes->m2);break;
case 2 : glMultMatrixf(ptrShapes->m3);break;
case 3 : glMultMatrixf(ptrShapes->m4);break;
}

drawCylinder(ptrShapes->radius, ptrShapes->halfHeight, ptrShapes->upAxis);
printf("\n r : %f ht:%f", ptrShapes->radius, ptrShapes->halfHeight);
glPopMatrix();
}


//---------------Debug code : for pink wheel-----------------------
glColor3f(1.0,0.0,1.0);
glPushMatrix();
glMultMatrixf(ptrShapes->m);
glTranslatef(ptrShapes->m2[12] - ptrShapes->m[12],
ptrShapes->m2[13] - ptrShapes->m[13],
ptrShapes->m2[14] - ptrShapes->m[14]);
drawCylinder(ptrShapes->radius, ptrShapes->halfHeight, ptrShapes->upAxis);
glPopMatrix();


Now I am trying something different. I am trying to render one of the wheels without using glMultMatrixf(). So given the transformation matrix I am trying to simply translate the wheel into position(not bothered about orienting it at the moment). The code marked as //----debug code----- in the bottom shows this part.

So what I have is the wheel transformation matrices in the matrices m1, m2, m3, m4. I chose one of the wheels(forward left wheel) whose matrix is in m2 and tried to use the translation elements of the matrix to translate the wheel into position. But it does not work as expected and there is a difference in the mesh positions between the wheel rendered through glMultMatrixf() and that rendered through glTranslatef(). I used the following to understand the opengl matrix format :

http://www.songho.ca/opengl/files/gl_anglestoaxes01.png

The reason I subtract ptrShapes->m[...] from the respective x,y,z positions is because I have already translated to the position given by it using glMultMatrixf(). The postion given by m is the global position of the vehicle. Here is a video of the thing :

<object width="425" height="350"> <param name="movie" value="http://www.youtube.com/v/0iATE7MVTkE"></param> <param name="wmode" value="transparent"></param> <embed src="http://www.youtube.com/v/0iATE7MVTkE" type="application/x-shockwave-flash" wmode="transparent" width="425" height="350"> </embed></object>


Also if I dont subtract m and directly render the wheel using m2 then I get the desired effect. Here is the code


//---------Debug code------------
glColor3f(1.0,0.0,1.0);
glPushMatrix();
glTranslatef(ptrShapes->m2[12] ,
ptrShapes->m2[13],
ptrShapes->m2[14] );
drawCylinder(ptrShapes->radius, ptrShapes->halfHeight, ptrShapes->upAxis);
glPopMatrix();


Video :
<object width="425" height="350"> <param name="movie" value="http://www.youtube.com/v/E0hyQjclx58"></param> <param name="wmode" value="transparent"></param> <embed src="http://www.youtube.com/v/E0hyQjclx58" type="application/x-shockwave-flash" wmode="transparent" width="425" height="350"> </embed></object>

Now I cannot understand why the 2 don't match. If I have already translated to the proper vehicle position using m then if I render the wheel at the translated position with respect to the vehicle(by subtracting the translation elements of m from the translation elements of m2) I should get the same position. Obviously the rotations around the axes do not make a difference here as then I would not have got the right position by rendering at m2 directly.

I need to render the wheels using their positions with respect to the main vehicle(whose co-ordinates are in m) due to some restrictions in the API of the Orbiter Space flight simulation software in which I am trying to integrate the vehicle.

hound
04-25-2011, 04:33 AM
You don't mention what physics library you're using, so I'm guessing here...

As I remember it, PhysX vehicle physics (not sure if this is PhysX, but it looks similar) has suspension, which you're not taking into account in the first video (the purple wheel stays fixed at that height, while the yellow one moves up and down properly).

In the second video, I would guess that your problem is due to not taking into account the steering column. So while you're translating the wheel into the correct place, the rotation is wrong because it's not rotated from world space to the correct orientation. (Edit: although on re-reading, it looks like you know that already...)

altreality
04-25-2011, 11:31 AM
Thanks for the reply hound. I am using the Bullet Physics library specifically the btRayCastVehicle class.

The thing is, I already have the correct position of the wheel in the global opengl space(i guess this is what you call world space). This position is present in the matrix m2 above.

However I am trying to render this vehicle into a Space Flight Simulation software called Orbiter and in Orbiter I can move the wheels into the correct position only with respect to the vehicle's origin.

Lets call this co-ordinate system as "Vehicle Space". Here the origin is at the Vehicle's location in OpenGL World Space and the axes have the same orientation as OpenGL world space. Then what I need to do is render the wheel using its co-ordinates in vehicle space and not the co-ordinates in world space.(that would put the wheels too far away)

So I basically need to find the co-ordinates of the wheel with respect the vehicle location(origin of vehicle space) and use those instead of the world space co-ordinates.

Now the world space co-ordinates of the wheel already accounts for the suspension height. So I just need to do the calculation for converting co-ordinates from world space to vehicle space.

How would I do this in OpenGL given just the matrix representing the vehicle location and orientation in world space (in matrix m) and the wheel co-ordinates in world space (in matrix m2) ?

I hope I was able to clarify the issue clearly. In general if I wanted to find the co-ordinates of A with respect to B with both A and B's co-ordinates given in world space, then I would simply subtract B's location from A. Which is what I did in the top video.

But that does not seem to work. Is there a way to incorporate the rotation elements as well while calculating the co-ordinates with respect to another object in the world space.

Regarding the steering issue in the 2nd video, well, I am not worried about turning the wheel at the moment. I know how to turn the wheel once i am able to translate it into position.