Orienting a vehicle to the terrain?

Started by
5 comments, last by jameswren 18 years, 8 months ago
Hi all, I’m playing with different ideas on how to properly map a vehicle to the terrain below it. Let’s use a car an example for now. I’m thinking of taking the height above three of the four wheels, and orienting the car to that plane. I’m not sure how to do that, but leaving the math aside, I wanted to get opinions if this is a good idea? One issue is that the height above each car tire might not be the right height because it doesn’t take the rotation into account. Second, it doesn’t account for the 4th tire. Another option is if each tire has bones applied to it and I set the height of the tire object in the hierarchy to the height of the terrain. A friend is doing most of the .X modeling code for me, and he thinks if he moves the tire as a sub object, the rest of the model will auto rotate because that’s what the bones handle, but somehow I doubt it, can't be that easy? What are the rest of you doing to have a vehicle follow the contour of the terrain nicely? Thanks, Quad
3DMUVE is an amateur game development team, and the designer and developer of a new gaming technology “MUVE” for the gaming industry.
Advertisement
Perhaps this thread:

http://www.gamedev.net/community/forums/topic.asp?topic_id=301805

...could help you. Take a look at the adriano_usp's replies for r@ph.
Hi, QuadMV

I like your first idea. Here's how I would do it, which is like your first idea.

First, I would compute a bounding box for the object. I assume you already have this.

Second, take the vertices of the bounding box that are closest to the terrain and find the height of the terrain of that area. Here's a function from my sdk to find the height of an arbitrary position.

float CSWGHeightMapTerrain::GetHeight(float x, float z){	x = ((float)Width / 2.0f) + x;	z = ((float)Depth / 2.0f) - z;	x /= (float)CellSpacing;	z /= (float)CellSpacing;	float col = ::floorf(x);	float row = ::floorf(z);	float A = (float)GetHeightmapEntry(row,   col);	float B = (float)GetHeightmapEntry(row,   col+1);	float C = (float)GetHeightmapEntry(row+1, col);	float D = (float)GetHeightmapEntry(row+1, col+1);	float dx = x - col;	float dz = z - row;	float height = 0.0f;	if(dz < 1.0f - dx)	{		float uy = B - A;		float vy = C - A;		height = A + Lerp(0.0f, uy, dx) + Lerp(0.0f, vy, dz);	}	else	{		float uy = C - D;		float vy = B - D;		height = D + Lerp(0.0f, uy, 1.0f - dx) + Lerp(0.0f, vy, 1.0f - dz);	}	return height;}float Lerp(float a, float b, float t){	return a - (a*t) + (b*t);}


I don't know how you would rotate the object, perhaps compute an angle between a bounding box vertex and the height of the terrain at the center of the object because this is the center of rotation.

\a
-

a is the angle
the top of the diagonal line is the vertex
the horizontal line is the terrain

**I don't know if this would work, I haven't implemented this**

Hope this helps you,
ProgrammingNerd
Use a 3rd party physics/collision engine. It'll save you tons of time and the quality of the physics will be good :P.

I'm using a managed version of ODE and it works very nicely... http://www.thejamesrainenetwork.co.uk/ode/ode.html

You basically leave your terrain as-is but you gotta make your other movable objects be made up of a collection of primitive geoms (sphere, box etc). i.e. a car could be made up of a box + 4 cylinders + 4 joints. The physics engine will be able to tell you their position and rotation. using those values you apply the rotation and position to your world object mesh and voila, nice physics.



thanks all, all good ideas. I appreciate the feedback.

Quad
3DMUVE is an amateur game development team, and the designer and developer of a new gaming technology “MUVE” for the gaming industry.
If you're doing something advanced, you probably don't want to orientate the vehicle to the terrain.

Hmm.. a rough idea would be to find the height of the terrain where each tire should rest on the ground. Push each tire up individually to the terrain, if they are below it. Then make sure the tires are not too far up, using suspension settings. If any one tire is higher than the shocks allow, you need to rotate the entire car, including other wheels, to compensate. Finding the correct pivot point for this rotation could be tricky. You could start off using the opposite corner of the car to the raised wheel, but I think weight distribution has a lot to do with it. For example, if the front left wheel is too high, the entire front could lift up, or instead, the entire left side. Using the opposite corner would lift both.

Rotating on a pivot is not too difficult. You can use a matrix to move the space so the pivot is at zero, then rotate normally, then move the pivot back where it was.

Example:

Matrix mat;
mat.Translate( -PivotVector);
mat.AddRotate( Angle );
mat.AddTranslate( PivotVector );

You could use this one matrix to offset all of the parts of the car. But you would need to calculate a new one for each wheel that is too high. Anyway, after performing this excessive task, you simply apply gravity to the whole thing.
I'm trying to do a similar thing, but am having trouble calculating a matrix to transform the mesh. I know the plane my car is sitting on and the 3D direction it is facing, but can't figure out how to create a matrix to describe it's rotations. Can you give me any ideas?

This topic is closed to new replies.

Advertisement