9

I'm trying to understand how the quaternion rotations work, I found this mini tutorial http://www.julapy.com/blog/2008/12/22/quaternion-rotation/ but He makes some assumptions that I can't workout, like how can I do "work out the rotation vectors around each axis, simply by rotating the vector around an axis." and how does he calculate angleDegreesX, angleDegreesY and angleDegreesZ?

Can some one provide a working example or explanation?

Ricardo Sanchez
  • 4,935
  • 11
  • 56
  • 86
  • Ok I understand the angles thing, I have to provide the amount of rotation for each angle for this code to work, now I need to workout how to implement this using the arrow keys – Ricardo Sanchez Jun 08 '11 at 14:58

2 Answers2

21

The shortest possible summary is that a quaternion is just shorthand for a rotation matrix. Whereas a 4x4 matrix requires 16 individual values, a quaternion can represent the exact same rotation in 4.

For the mathematically inclined, I am fully aware that the above is super over-simplified.

To provide a little more detail, let's refer to the Wikipedia article:

Unit quaternions provide a convenient mathematical notation for representing orientations and rotations of objects in three dimensions. Compared to Euler angles they are simpler to compose and avoid the problem of gimbal lock. Compared to rotation matrices they are more numerically stable and may be more efficient

What isn't clear from that opening paragraph is that a quaternion is not only convenient, it's unique. If you have a particular orientation of an object, twisting on any number of axes, there exists a single unique quaternion that represents that orientation.

Again, for the mathematically inclined, my uniqueness comment above assumes right-handed rotations. There is an equivalent left-handed quaternion that rotates in the opposite direction around the opposite axis.

For the purpose of simple explanation, that is something of a distinction without a difference.

If you'd like to make a simple quaternion that represents rotation about an axis, here's a short series of steps that will get you there:

  1. Pick your axis of rotation v = {x, y, z}. Just for politeness, please pick a unit vector: if it's not already of length 1, divide all the components by the length of v.
  2. Pick an angle of rotation that you'd like to turn about this axis and call that theta.
  3. The equivalent unit quaternion can be computed using the sample code below:

Quaternion construction:

q = { cos(theta/2.0),     // This is the angle component 
      sin(theta/2.0) * x, // Remember, angle is in radians, not degrees!
      sin(theta/2.0) * y, // These capture the axis of rotation
      sin(theta/2.0) * z};

Note those divisions by two: those ensure that there's no confusion in the rotation. With a normal rotation matrix, rotating to the right 90 degrees is the same as rotating to the left by 270. The quaternions that are equivalent to those two rotations are distinct: you can't confuse one with the other.

EDIT: responding to the question in the comments:

Let's simplify the problem by setting the following frame of reference:

  1. Pick the center of the screen as the origin (we're going to rotate around that).
  2. X axis points to the right
  3. Y axis points up (top of the screen)
  4. Z axis points out of the screen at your face (forming a nice right handed coordinate system).

So, if we have an example object (say an arrow) that starts by pointing to the right (positive x axis). If we move the mouse up from the x axis, the mouse will provide us with a positive x and positive y. So, working through the series of steps:

double theta = Math.atan2(y, x);
// Remember, Z axis = {0, 0, 1};
// pseudo code for the quaternion:
q = { cos(theta/2.0),     // This is the angle component 
      sin(theta/2.0) * 0, // As you can see, the zero components are ignored
      sin(theta/2.0) * 0, // Left them in for clarity.
      sin(theta/2.0) * 1.0};
Bob Cross
  • 22,116
  • 12
  • 58
  • 95
  • So lets say I have an object in the center of the screen I want to rotate this object so it always face the target, the target is a vectorXYZ -> target(mouseX-width/2, mouseY-height/2, sin(elapsedMillis)), how do I calculate the rotation axis and angle? – Ricardo Sanchez Jun 08 '11 at 15:21
  • @Ricardo - hang on, I'll add more to the answer. – Bob Cross Jun 08 '11 at 17:41
  • Regarding your point about quaternions being "unique": Unit quaternions describe rotations in the range 0 - 720 degrees, therefore there are 2 quaternions that describe any single real world rotation. This does not invalidate the rest of your explanation, which does not depend on there being a 1 to 1 mapping from the 3d world to the unit quaternion space. – EdF Jun 08 '11 at 18:03
  • @EdF, there are two quaternions when you include rotating about the inverse of the previously considered axis of rotation in the opposite direction (left handed vs. right handed). While that is mathematically true, it seems to be a less useful point for someone who is puzzled by the concept in general. I'll add a note, though. – Bob Cross Jun 08 '11 at 18:51
  • The principle of handedness is separate again from the redundancy of the unit quaternion. As you note, the opposite (negative) rotation about the opposite (directionally negative) axis is the same rotation and this will be true when speaking only about right handed quat's or only about left handed quat's. To be concise, it is not a feature of their handedness. I appreciate, that this is all a little off topic but you may as well have it correct in your post or not mention it at all (which may be the better option) – EdF Jun 08 '11 at 21:23
0

You need some basic math to do what you need. Basically, you rotate a point around an axis by multiyplying the matrix representing that point with a rotation matrix. The result is the rotated matrix represantation of that point.

The line

angleX = angleDegreesX * DEGTORAD;

just converts the degrees representation into a radians reprensentation by a simple formular (see this Wikipedia entry on Radians)

You can find some more information and examples of rotation matrizes here: Rotation around arbitrary axes

There are probably tools in your programming framework to do that rotation work and retrieve the matrices. Unfortunately, I cannot help you with the quaternions but your problems seem to be a little bit more basic.

Michael Helwig
  • 225
  • 4
  • 10