Please help; trig knowledge a plus

Started by
8 comments, last by Bucket_Head 23 years, 11 months ago
Hello again everybody! I am making a 3D terrain engine and so far things are going pretty well. Thanks in no small part to you all, I now have objects showing up in the right spots, independant of the terrain and the camera, and that much is good. However, now my problem has to do with 3 dimensional movement. A given object has the following variables: float x, y, z; float roll, pitch, yaw; As we all know, planes don''t generally change their yaw directly; they roll to one side, pitch upward to turn, and then roll back to have changed their yaw. Therefore, if I am to be modeling the movements of a plane, I will need it where you can affect the yaw while only using controls that effect roll and pitch. I have made a function that does this:

void Pitch(OBJECT * obj, int code, float dist)
{
	float roll;
	float pitch;
	float yaw;
	switch (code)
	{
	case UP:
		roll  = obj->roll  * 3.14159f / 180.0f;
		pitch = (float)(cos(roll) * dist);
		yaw   = (float)(sin(roll) * dist);
		break;
	case DOWN:
		roll  = (obj->roll + 180)  * 3.14159f / 180.0f;
		pitch = (float)(cos(roll) * dist);
		yaw   = (float)(sin(roll) * dist);
		break;
	default: break;
	}
	obj->pitch += pitch;
	obj->yaw   += yaw;
}
 
...basically how this works is as such: when you hit left or right, you decrease or increase the roll. When you hit up or down, you call the above function with the described movement code, to update your pitch and yaw accordingly. If you see any problems with the above, let me know. Now, in my project, I am moving the plane along forward in whatever direction it''s facing, and I make the camera at the same position as the ship, but a bit behind it and above it, relative to the roll, pitch, and yaw of the plane. I am setting it up, at least for right now, such that wherever you turn, the plane will always be on the same spot on the screen as if it isn''t moving, but that everything else is; as if the camera and the ship are glued together in a sense. I don''t quite have that yet. Now, my current forward movement code is: x_move = (float)(sin(yaw) * cos(pitch) * dist); y_move = (float)(cos(yaw) * cos(pitch) * dist); z_move = -(float)(sin(pitch) * dist); As you may notice, I work with yaw and pitch but not roll for this. I figure that roll would not effect where you are going if you are going straight forward. This seems to work. However, if you are going in an upward direction, roll would very much effect things, but yaw wouldn''t - right? My formulae for moving upwards is as follows: pitch = (obj->pitch - 90.0f) * 3.14159f / 180.0f; x_move = (float)(sin(roll) * sin(pitch) * dist); y_move = (float)(cos(roll) * cos(pitch) * dist); z_move = -(float)(cos(roll) * sin(pitch) * dist); As you can see, I take the temporary pitch value and manipulate it so that I''m not going forward, but rotated 90 degrees to go upward... Well, the thing is, it all works fine if I start out and only manipulate the yaw, or if I start out and only manipulate the roll, or if I start out and only manipulate the pitch. Then it is 100% fine. However, when I start pitching AND rolling, or whatever, things get very funky and then my ship isn''t still on my screen. And then naturally I am very annoyed, and start to regret picking this project for my class, since it''s going to be due in a matter of weeks. Oh well. Please do help me, I would very much appreciate it. I just want it to where you can turn every which way and where the movement works as it should. Thank you for your time. - Hai, watashi no chichi no kuruma ga oishii deshita! ...or, in other words, "Yes, my dad's car was deliscious!"
- Hai, watashi no chichi no kuruma ga oishikatta desu!...or, in other words, "Yes, my dad's car was delicious!"
Advertisement
The main problem you need to solve here is given an orientation of the object (aero-plane), you need to work out two vectors: 1) the vector in the direction the plane is pointing and 2) the vector that points out of the top of the plane (lined up with its tail fin if you like). In order to roll the plane you then rotate about the unit vector in the direction the plane is pointing and in order to yaw you need to rotate about the vector that points out of the top of the plane. The function glRotatef() can be used to rotate about an arbitrary unit vector ( often you see it being used with parameters like ( angle, 1,0, 0 ) which is the most inefficient rotation it can be used for! ). Your only problem here is working out the vectors parallel to the rotation axis which shouldn''t be too hard with a maths text book by your side.

I did a demo that does the rotations in a similar way to which you are going about it but it also has problems whenyou go upside down etc and is quite inefficient. (The code is cursed I am afraid :-) ). http://www.cs.bris.ac.uk/~mp8557/opengl.html


Edited by - Khawk on 4/30/00 11:11:08 PM


Edited by - Khawk on 4/30/00 11:11:36 PM
Bucket_Head -

this would be a lot easier with matrices.. anyway, here's the rough outline of how I handle this in my engine, maybe it'll be of help. The object class contains, among other things, the position of the object (camera, plane, ship, rhesus monkey, whatever), the normalized direction vector and the roll angle. Pitch and yaw are implied from the direction vector, so I don't store them.
TObject:: Pitch(float angle) rotates the direction vector around the X axis of the local coordinate system (defined by the roll angle), TObject::Yaw(float angle) , which shouldn't really have to ever be called in a plane simulator, rotates the direction vector around the Y axis, etc. I don't actually update angles and calculate new matrices from those, since that can result in a gimble lock. Instead I calculate the new direction vector and calculate the resulting transformation matrix based on origin/target. Hope this helps some.

-goltrpoat



--
Float like a butterfly, bite like a crocodile.



Edited by - goltrpoat on 4/25/00 6:29:04 PM
--Float like a butterfly, bite like a crocodile.
Hmm...matrices...That's right, I should probably think of this in terms of how the matrices are set up! Hmm...Let me check my handy dandy red book to see how those rotation matrices are set up...

     [1   0    0   0]Rx = [0 cosA -sinA 0]     [0 sinA  cosA 0]     [0   0    0   1]//     [ cosA 0 sinA 0]Ry = [  0   1  0   0]     [-sinA 0 cosA 0]     [  0   0  0   1]//     [cosA -sinA 0 0]Rz = [sinA  cosA 0 0]     [  0     0  1 0]     [  0     0  0 1] 


So hmm...Another thing...in what order should I rotate things? X, then Y, then Z? At a default setting, that would be roll, then yaw, then pitch...However, I decided I wanted Z to be up, so I had the pitch modified so that now, rotating around y is rolling and rotating around z is changing the yaw, and so forth. That's just stuff to keep in mind...

Or is it that it doesn't really matter, as long as I am consistent? Hmm...In my application of moving forward, I ignore the roll...that would mean that of the rotation transformations, I am rolling last, right?

Urgh...this is a heck of a headache...

- Hai, watashi no chichi no kuruma ga oishii deshita!
...or, in other words, "Yes, my dad's car was deliscious!"

Edited by - Bucket_Head on 4/25/00 8:30:49 PM
- Hai, watashi no chichi no kuruma ga oishikatta desu!...or, in other words, "Yes, my dad's car was delicious!"
Still, the BEST solution to this (Aeroplane and such) is using quaternions. It avoids Gimbal Lock, it avoids problems with order of rotations, it avoids anything...

It leaves us with a clear defined rotation

RedRicK
----------------------------- For I have come to serve you and to support you...-----------------------------
Alright then, I am all ears; how does one utilize quaternions for a problem such as this?

- Hai, watashi no chichi no kuruma ga oishii deshita!
...or, in other words, "Yes, my dad's car was deliscious!"
- Hai, watashi no chichi no kuruma ga oishikatta desu!...or, in other words, "Yes, my dad's car was delicious!"
This problematics gets quite bigger than is possible to solve here...so here are few links to the FAQs helping (at least me)

ftp://ftp.netcom.com/pub/he/hexapod/matrixfaq.html

http://www.3dgamedev.com/articles/eulers_are_evil.htm

Hope it helps a bit...

BEWARE ... you have to gety through matrixfaq STEP by STEP...you have to truly understand given section before moving to the next ''cause when you lose a little detail, you will have a tough time grasping next one.

-----------------------------
For I have come to serve you
and to support you...
-----------------------------
----------------------------- For I have come to serve you and to support you...-----------------------------
Actually, Bucket_Head, it would be "Hai, watashi no chichi no kuruma ga oishikatta." Deshita is used for the past state of nouns and the na-adjectives.

This topic is closed to new replies.

Advertisement