# Rotation around maintained arbitrary axis.

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

## Recommended Posts

[color=#000000][font=verdana, geneva, lucida,]I've been racking my brain for days now and can't find the answer. I'm using C++ and DirectX but I figure that this is more of a math problem that can relate to all languages trying to work in 3D.[/font]

[color=#000000][font=verdana, geneva, lucida,]Basically, to rotate a flying vehicle (spaceship, airplane, whatever) I am using this system that I found for FPS camera control:[/font]

[color=#000000][font=verdana, geneva, lucida,] up=D3DXVECTOR3(0.0f, 1.0f, 0.0f); look=D3DXVECTOR3(0.0f, 0.0f, 1.0f); right=D3DXVECTOR3(1.0f, 0.0f, 0.0f); D3DXMATRIX yawMatrix; D3DXMatrixRotationAxis(&yawMatrix, &up, yaw); D3DXVec3TransformCoord(&look, &look, &yawMatrix); D3DXVec3TransformCoord(&right, &right, &yawMatrix); D3DXMATRIX pitchMatrix; D3DXMatrixRotationAxis(&pitchMatrix, &right, pitch); D3DXVec3TransformCoord(&look, &look, &pitchMatrix); D3DXVec3TransformCoord(&up, &up, &pitchMatrix); D3DXMATRIX rollMatrix; D3DXMatrixRotationAxis(&rollMatrix, &look, roll); D3DXVec3TransformCoord(&right, &right, &rollMatrix); D3DXVec3TransformCoord(&up, &up, &rollMatrix); rotMatrix = yawMatrix*pitchMatrix*rollMatrix; [/font]

[color=#000000][font=verdana, geneva, lucida,][background=rgb(251, 251, 251)]And you rotate by adjusting the yaw, pitch, and roll float values. The problem is that this code only seems to rotate around the default axis. For instance, if I make my little ship pitch down (lower the nose to fly downwards) and then wish to "roll" left or right, I want to rotate the ship around the look axis of the ship itself, but with this method it will only rotate around (0, 0, 1).[/background][/font]

[color=#000000][font=verdana, geneva, lucida,]Basically, what methods can I use to maintain a look, right, and up axis that stay aligned with the object in question and never revert to default so that I can rotate around them at will?[/font]

[color=#000000][font=verdana, geneva, lucida,]EDIT: Actually, to be more precise, this method will rotate properly around the look axis I want, but only because it does roll last after the look axis is already fully finished by the yaw and pitch rotations. Pitch rotates around a half formed right axis, and yaw rotates around the default (0, 1, 0) up axis.[/font] Edited by Zerocyde

##### Share on other sites
The D3DXMatrixRotationYawPitchRoll function might be closer to your requirements here.

##### Share on other sites

[color=#000000]Basically, what methods can I use to maintain a look, right, and up axis that stay aligned with the object in question and never revert to default so that I can rotate around them at will?

Why not just apply a cumulative rotation on every frame? (i.e., at the beginning of the game, the player has rotated 0 degrees about the Y axis. At some point, the player rotates 3 degrees on the Y axis. You need to save that state in some variable that persists throughout the game. Later, the player rotates another 2 degrees around the Y axis. Since you are keeping track of the rotation state, you can apply a rotation of the cumulative 5 degrees, rather than just 2 degrees).

##### Share on other sites
I found a solution. This is what ended up working for me:

 D3DXMATRIX yawMatrix, pitchMatrix, rollMatrix, combined; // rotate around your 3 maintained axis D3DXMatrixRotationAxis(&yawMatrix, &up, yaw); D3DXMatrixRotationAxis(&pitchMatrix, &right, pitch); D3DXMatrixRotationAxis(&rollMatrix, &look, roll); // combined them into one rotation matrix D3DXMatrixMultiply(&combined, &yawMatrix, &pitchMatrix); D3DXMatrixMultiply(&combined, &rollMatrix, &combined); // rotate 2 of the axis by the combined rotation matrix and build the third using cross product D3DXVec3TransformCoord(&right, &right, &combined); D3DXVec3TransformCoord(&up, &up, &combined); D3DXVec3Cross(&look, &right, &up); // normalize all 3 axis D3DXVec3Normalize(&right, &right); D3DXVec3Normalize(&up, &up); D3DXVec3Normalize(&look, &look); // build the final matrix like this rotMatrix = D3DXMATRIX ( right.x, right.y, right.z, 0.0f, up.x, up.y, up.z, 0.0f, look.x, look.y, look.z, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f );  Edited by Zerocyde