camera movement or world movement

Started by
6 comments, last by messiah2k 22 years, 3 months ago
Hello I''m new with OpenGL. I have been working a bit on a program that lets you move freely in 3D space. Iv''e read in many places that you should move the world around you rather then the camera itself. Iv''e tried to do this using the following commands. GLTranslatef(xpos, ypos, zpos); //Can''t remeber the exact GLRotatef(xrot, yrot, zrot); //syntax Iv''e got the translate part to work but rotates get all mixed upp when you fly around and change many ?rot att once. I guess you need to do quite a lot of calculating here since the cameras system is always fixed cause you never move the cameras angeles. My question is if i''m on the right track or is it better to move the camera around. If anyone could give me some gidelines or some example codes i would be very happy. Is world movement realy that mush faster? //Messiah
//Messiah
Advertisement
speed is the least of your concerns
i think the problems u are having are to do with ''gimbal lock'' google it and u will prolly also find a solution
Yeah, rotating like that will only let you rotate at the start position.

You need some sine''s and -cosine''s in there...

----------[Development Journal]
You do need some sines and cosines for moving in 3D space, not just for viewing.
You need three variables: Pitch, Yaw, and Roll. Pitch is looking up and down, Yaw is right and left, and Roll is like popping your eyeballs out and turning them upside down (only games with flying vehicles use Roll).

Each variable is an angle between 0 and 360.
To set the camera up correctly, all you have to do is:

glRotatef(Pitch, 1.0f, 0.0f, 0.0f);
glRotatef(Yaw, 0.0f, 1.0f, 0.0f);
glRotatef(Roll, 0.0f, 0.0f, 1.0f);

glTranslatef(CameraX, CameraY, CameraZ);

Note: If you use -Pitch instead of Pitch, you get an inverse Y axis (up looks down and vice-versa).

Now, to actually move in 3D space is a different story. First, I wrote new sin and cos functions to use degrees instead of radians.

Here they are:

#define PI 3.141592654
#define DEG2RAD ((2*PI)/360)

GLfloat CosDeg(GLfloat Angle)
{

return ((GLfloat)cos( Angle*DEG2RAD) );

}

GLfloat SinDeg(GLfloat Angle) {

return ((GLfloat)sin( Angle*DEG2RAD) );

}

I won''t go into the math of moving forward in 3D space, but it''s pretty simple.

void MoveForward(GLfloat Distance)
{

GLfloat TempAngle;

Distance = (GLfloat)fabs(Distance);
Distance = -Distance;

TempAngle = 90 - Yaw;

CameraX += ( (CosDeg(TempAngle)*Distance) );
CameraY += ( (SinDeg(Pitch)*Distance) );
CameraZ += ( -(SinDeg(TempAngle)*Distance) );

}

If you want to move backwards, just remove the
Distance = -Distance. To move side to side (strafing), use this code:

void MoveLeft(GLfloat Distance)
{

Distance = (GLfloat)fabs(Distance);

CameraX += ( (CosDeg(Yaw)*Distance) );
CameraZ += ( (SinDeg(Yaw)*Distance) );

}

Stick a Distance = -Distance in there to move right.

Hope this helps!
Thank you everybody. Iv''e got the forward movement to work using trigonometric calculations simular to the ones above. I looked up the gimbal lock thing and understood the problem you get with Eulers representation. So I guess I will have to look into using quaternions ? If anyone is a expert on this I would appreciate some example code on this =)
//messiah
//Messiah
I am rather new to OGL but is it not better to use the Lookat() function directly rather than rotating the world around the camera?

A CRPG in development...

Need help? Well, go FAQ yourself.
Need help? Well, go FAQ yourself. "Just don't look at the hole." -- Unspoken_Magi
quote:Original post by Nazrix
I am rather new to OGL but is it not better to use the Lookat() function directly rather than rotating the world around the camera?


There is no difference gluLookAt composes a modelview matrix which rotates and moves the "world" as required. So do the routines
glRotate/glTranslate. You can also compose the matrix manually, which gives you much more control once you''ve understood how things work.

-Lev
using quaterions, here is the code to create a rotation matrix given and angle (radians) and an axis of rotation:
  void vector_copy(const double *v1, double *v2); //copy v1 in v2double vector_length(const double *v);		  //length of vvoid vector_scale(double *v, double div);	//v*divvoid vector_normal(double *v);				  //normalize v// build the quaternion, given an angle and an axisvoid axis_to_quat(double a[3], double phi, double q[4]){    vector_normal(a);    vector_copy(a,q);    vector_scale(q,sin(phi/2.0));    q[3] = cos(phi/2.0);}// build a rotation matrix given a quaternionvoid quat_to_matrix(double m[4][4], double q[4]){    m[0][0] = 1.0 - 2.0 * (q[1] * q[1] + q[2] * q[2]);    m[0][1] = 2.0 * (q[0] * q[1] - q[2] * q[3]);    m[0][2] = 2.0 * (q[2] * q[0] + q[1] * q[3]);    m[0][3] = 0.0;    m[1][0] = 2.0 * (q[0] * q[1] + q[2] * q[3]);    m[1][1]= 1.0 - 2.0 * (q[2] * q[2] + q[0] * q[0]);    m[1][2] = 2.0 * (q[1] * q[2] - q[0] * q[3]);    m[1][3] = 0.0;    m[2][0] = 2.0 * (q[2] * q[0] - q[1] * q[3]);    m[2][1] = 2.0 * (q[1] * q[2] + q[0] * q[3]);    m[2][2] = 1.0 - 2.0 * (q[1] * q[1] + q[0] * q[0]);    m[2][3] = 0.0;    m[3][0] = 0.0;    m[3][1] = 0.0;    m[3][2] = 0.0;    m[3][3] = 1.0;    }void build_rotmatrix(double angle, double axis[3], double rot_matrix[4][4]){    double q[4];      vector_normal(axis);  axis_to_quat(axis, angle,q);  quat_to_matrix(rot_matrix, q);}  


g

This topic is closed to new replies.

Advertisement