6
\$\begingroup\$

Euler angles are much more intuitive to me than quaternions for representing 3-dimensional rotations. In fact, I barely understand quaternions at all. I use quaternions for rotation because people with more knowledge than me say they're better. (I'm familiar with the gimbal lock problem and axis-angle rotations, but that's getting away from the point.)

Given my nebulous understanding, what I'm trying to do might be really stupid. I want to rotate an object by applying an angular force (torque) which I'm representing as a quaternion plus a duration. To move the object, I do something like

abstract class PhysicsBody
    {
    protected Vector3 velocity = Vector3.Zero;

    public void ApplyForce(Vector3 force, float duration)
        {
        // mass and other concepts omitted for brevity
        this.velocity += force * duration;
        }
    }

and it works as expected. I figure rotation should work similarly, like so:

...

protected Quaternion orientation = Quaternion.Identity;

public void ApplyTorque(Quaternion torque, float duration)
    {
    this.orientation *= torque * duration;
    }

But of course it does not. If duration is less than 1, orientation does not change. If duration is greater than 1, things get weird and break after a few seconds.

I've experimented with renormalization, but I'm fumbling in the dark. What is the "correct" way to do this?

\$\endgroup\$

3 Answers 3

4
\$\begingroup\$

A torque has an axis and a magnitude, so in principle you can represent it as a quaternion. However, you have two problems. The first is that your parallel is wrong. torque :: force as orientation :: position, so you need to integrate it twice. Secondly, the way you're applying it is wrong.

Question: given a quaternion representing a rotation of a certain amount around a given axis, how do you derive the quaternion representing twice the rotation around the same axis?

The answer isn't "Multiply by two". You have to square the quaternion to apply the rotation twice. So scalar multiplication isn't what you're looking for.

You'll probably find that it's easiest to use axis-angle for the angular velocity and torque, and use quaternions only for the orientation. These links may also be helpful, but are too long to summarise here:

\$\endgroup\$
1
  • \$\begingroup\$ I haven't looked too closely at the second link yet, but the first link (and the rest of his stuff) is AWESOME! \$\endgroup\$
    – Metaphile
    Oct 6, 2011 at 16:57
4
\$\begingroup\$

Torque and angular momentum should probably be represented as ordinary 3D vectors, not quaternions. Angular momentum vectors add according to the parallelogram rule, and torque is the time derivative of angular momentum, so you apply a torque to change angular momentum exactly the same way as applying an acceleration to change velocity.

Then you multiply the angular momentum by the inverse of the inertia tensor, to get an angular velocity, and integrate it to get a quaternion for the orientation by using the rule: dq/dt = 1/2 omega q, where q is the quaternion representing the current orientation of the body, and omega is the angular velocity vector. Omega has to be converted to a quat by placing 0 in the scalar (real) component, so you can multiply it by q using quaternion multiplication.

\$\endgroup\$
1
\$\begingroup\$

You might want to check out slerp, it is used for rotating 'more or less' with quaternions. Just use an empty quaternion, the base quaternion and 'slerp' more or less.

\$\endgroup\$

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .