Archived

This topic is now archived and is closed to further replies.

rotating view from camera class

This topic is 5568 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Ok, I''ve been interested in writing a camera class that can move around a scene in like a quake style manner with the w, a, s ,d buttons and the mouse to move the view. I''ve read some code from gametutorials.com on how to move the camera''s view, and I''ve looked at some code in my computer graphics class book. In my computer graphics book, they just multiplied the three rotation matrices together to form one custom matrix. x * y * z, and that all seems fine and dandy, but I can''t figure out where the hell they got these calculations from on gametutorials.com
  
void CCamera::RotateView(float angle, float x, float y, float z)
{
	CVector3 vNewView;

	// Get the view vector (The direction we are facing)

	CVector3 vView = m_vView - m_vPosition;		

	// Calculate the sine and cosine of the angle once

	float cosTheta = (float)cos(angle);
	float sinTheta = (float)sin(angle);

	// Find the new x position for the new rotated point

	vNewView.x  = (cosTheta + (1 - cosTheta) * x * x)		* vView.x;
	vNewView.x += ((1 - cosTheta) * x * y - z * sinTheta)	* vView.y;
	vNewView.x += ((1 - cosTheta) * x * z + y * sinTheta)	* vView.z;

	// Find the new y position for the new rotated point

	vNewView.y  = ((1 - cosTheta) * x * y + z * sinTheta)	* vView.x;
	vNewView.y += (cosTheta + (1 - cosTheta) * y * y)		* vView.y;
	vNewView.y += ((1 - cosTheta) * y * z - x * sinTheta)	* vView.z;

	// Find the new z position for the new rotated point

	vNewView.z  = ((1 - cosTheta) * x * z - y * sinTheta)	* vView.x;
	vNewView.z += ((1 - cosTheta) * y * z + x * sinTheta)	* vView.y;
	vNewView.z += (cosTheta + (1 - cosTheta) * z * z)		* vView.z;

	// Now we just add the newly rotated vector to our position to set

	// our new rotated view of our camera.

	m_vView = m_vPosition + vNewView;
}
  
I understand multiplying the matrices together, but where in the hell did this come from? Anybody know a better way, or a way to explain this?

Share this post


Link to post
Share on other sites
It''s the way to find the vector where you are looking at, just from the angles, it''s like if you don have a D3DXMatrixRotationY, X or Z. the hard way, i just look it quickly so, I''m wrong please let me know.

Share this post


Link to post
Share on other sites
I've been looking at these tutorials too... and after a search online I stumbled across a set of tutorials that explained rotations in 2D and 3D. The 3D arbitrary rotation matrix is practically identical to the code in these programs.... I tried using just the matrix formula but apparently you need to add the following pieces of code :

CVector3 vView = m_vView - m_vPosition;

SetUpRotationMatrixBasedOnViewAndPositionButDontForgetToMultiplyToVViewForSomeReason

m_vView = m_vPosition + vNewView;

I couldn't see any reference to why these extra values are needed outside of the tutorials but I eventually tested the formulas given in those math tutorials along with those extra lines of code before and after the rotationsetup code ..


    

/*
dist is a new vector variable
rotator and rotatee are vector variables passed to the
routine and are basicaly the view and position of the
camera
axes is a vector variable passed to the routine which
holds the rotation axis. It doesn't currently test to
make sure that it doesn't fall over if you pass over 2
or more axis but its still in its early stages.
*/


dist = SubtractVectors(Rotator,Rotatee);
GLfloat ca = cos(angle);
GLfloat sa = sin(angle);


//This segment of code is the formula to calculate the

//new position in 3D space in relation to the y axis.

if (axes.x == 0 && axes.y == 1 && axes.z == 0)
{
rotation_matrix[0] = SetVector(ca,0,sa);
rotation_matrix[1] = SetVector(0,1,0);
rotation_matrix[2] = SetVector(-sa,0,ca);
}
//This segment of code is the formula to calculate the

//new position in 3D space in relation to the x axis.

if (axes.x == 1 && axes.y == 0 && axes.z == 0)
{
rotation_matrix[0] = SetVector(1,0,0);
rotation_matrix[1] = SetVector(0,ca,-sa);
rotation_matrix[2] = SetVector(0,sa,ca);
}
//This segment of code is the formula to calculate the

//new position in 3D space in relation to the z axis.

if (axes.x == 0 && axes.y == 0 && axes.z == 1)
{
rotation_matrix[0] = SetVector(ca,-sa,0);
rotation_matrix[1] = SetVector(sa,ca ,0);
rotation_matrix[2] = SetVector(0 , 0 ,1);
}
//The new point is then factored into the vector

//distance earlier calculated.

newv.x = GenerateVectorPoint(rotation_matrix[0],dist);
newv.y = GenerateVectorPoint(rotation_matrix[1],dist);
newv.z = GenerateVectorPoint(rotation_matrix[2],dist);
//And then finally added to the original position/view

//whatever is being rotated.

newv = AddVectors(newv,Rotatee);
return newv;
}


Using this function I can rotate the camera around a point, rotate the camera around/rotate the view around the camera and rotate an object around another object.

I haven't completed the program enough to place on to my websites mini gl apps page but if you're interested let me know and I'll speed that process up a bit.

Here's the set of tutorials...
http://www.fas.harvard.edu/~lib175/administration_2001/coursematerial.html
They might not be there long so you might want to quickly browse through the 3D Geometry tutorials as that is where I read about this formula.

EDIT:

Well, after rooting through all my maths books (even went out and bought one!!) I eventually found something that explained it a bit clearer... as I had thought it has something to do with the pythagoras theorem.

sin(Angle) = opposite/hypotenuse = (in ProgramSpeak)
sin(Angle) = new y axis / distance from origin
so
new y axis = sin(Angle) x distance from origin

cos(Angle) = adjacent/hypotenuse = (in ProgramSpeak)
cos(Angle) = new x axis / distance from origin
so
new x axis = cos(Angle) x distance from origin

The RotationMatrix stated in those tutorial is as follows:

(newx) = (oldx) x (cosA -sinA)
(newy) = (oldy) x (sinA cosA)

If you imagine a square on an xy chart with point A at (2,0) and point C at (0,2) which is then rotated around so that A is now at (0,2) and C is now at (-2,0). This then explains the above formula because sin(Angle) * 2 = 0 and cos(Angle) * 2 = 2 and cos(Angle) * -2 = -2.

Still haven't figured out how they get from that to that arbitrary rotation matrix but I'm sure its some sort of multiplication operation.

Also, I still can't see why the (1-cosTheta) was bought in. Although I now see that the view-position was needed to gather the distance which is used in the calculation..

Now to work out this matrix multiplication on the 3 rotation matrices... sigh!


Tina

[edited by - tinak on September 19, 2002 9:08:40 PM]

Share this post


Link to post
Share on other sites