Reputation: 24771
In this comment it was strongly suggested that we should never use Euler angles. I understand that there are some limitation to Euler angles, most notably gimbal lock, but I'd like to know the best technique, or the set of techniques, that one typically uses in the absence of Euler angles?
Most dicussions on this topic involve converting from an Euler angle to a quaternion and that is a simple thing to do. But the only way I have ever read about doing rotation without Euler angles at all is to create a quaternion from two vectors as described by the article "The Shortest Arc Quaternion" by Stan Melax in "Game Programming Gems", using this technique:
template <typename T>
inline QuaternionT<T> QuaternionT<T>::CreateFromVectors(const Vector3<T>& v0, const Vector3<T>& v1)
{
Vector3<T> c = v0.Cross(v1);
T d = v0.Dot(v1);
T s = std::sqrt((1 + d) * 2);
QuaternionT<T> q;
q.x = c.x / s;
q.y = c.y / s;
q.z = c.z / s;
q.w = s / 2.0f;
return q;
}
Is this the method referred to in the linked comment?
Upvotes: 4
Views: 4929
Reputation: 474416
An orientation is the way that a transform will orient an object within a coordinate system. An orientation is an absolute quantity, like a position or a scalar. An orientation is conceptually a value. And there are operations one can apply to orientations, depending on their representation.
Unlike vectors and scalars, orientations can be represented in a wide variety of ways.
Euler angles are a series of 3 rotations about 3 fixed, orthogonal axes. The order in which these are applied is important and is generally established by convention.
To "use Euler angles" means that Euler angles are how your code stores and manipulates the orientation of an object. How you eventually compose these angles to generate a matrix is of no consequence. What matters is that your code will treat the orientation as 3 angles. For example, when you apply a rotational offset to the orientation, it will be provided as offsets to rotation angles, and these offsets will be applied to the stored Euler angles directly.
I know nobody said that, but I have a point to make here.
To "use matrices" means that a rotation matrix is how your code stores and manipulates the orientation of an object. If some piece of code wants to rotate the object, they will apply a matrix to it, either on the left side or the right. Even if that matrix is computed via some axial rotation, the code is still performing the basic operation on a matrix, not an angle.
For the purposes of this discussion, a "quaternion" is a 4-element unit vector which is used to encode an orientation. Quaternions can have matrix-like operations done on them, such as composition and inversion. Quaternions must remain normalized in order to properly encode an orientation.
To "use quaternions" means that you are storing the orientation and manipulating of the object as a quaternion. All of your operations on orientations, at their most fundamental level, are dealing with quaternion math.
Euler angles are often used because they are (theoretically) intuitive to adjust: you just increment or decrement an angle. If you want to turn the object -10 degrees in the X, you just subtract 10 from the X axial rotation. But we don't want to use them, because they're terrible, so let's look at the other orientation representations.
To adjust an orientation as a matrix, you have to do two things. You must multiply the current orientation with an offset rotation matrix (if you want to rotate by -10 degrees in the X axis, you create an angle/axis matrix for that and right-multiply it). And then, because computers have finite precision, you must re-orthonormalize the matrix. If you don't do the second step, your matrix will eventually stop being orthonormal and thus stop being an orientation.
Orthonormalizing a matrix is hard. That's (part of) the reason why we use quaternions instead. Normalizing a quaternion is easy; it's just 4-element vector normalization. And since quaternions and matrices have analogous operations, the same math will work with both. So they look pretty much identical.
Upvotes: 3
Reputation: 4434
There are several mathematical models to describe the rotation of and object in 3D. Euler angle model is just one of them. Usually when people speak of Euler angles they actually talk about Tait-Bryan angles, Euler only proposed the modes where the first angle is duplicated for example ZXZ rotation. There is nothing particularity wrong with Euler angles if you use hem like they were intended, that is for static representation. Alternatively they are fine for a number of mechanical rotations that actually act like a gimbal.
There are two primary downsides to Euler angles. First is that people often think they understand Euler angular numeric representations better. While actually its only really true as long as there are only 2 and very few special 3 axis rotations rotations going on and even then its a bit questionable outside some limited cases. The second is that you can not really meaningfully interpolate the Euler model as it is not filling the rotation space uniformly. This means that some areas of the numeric space has different size. Imagine how a rectangular map gets distorted on a sphere.
Quite many of us today are doing either animation for graphics, engineering of simulation where this interpolation is of utmost importance. That means the Euler model is not really suited for most tasks. One of the weird things people get into mind trying to think interpolations in Euler model space is that you could actually rotate around 3 directions at once. But this is not physically possible there's only ever one rotation in a 3d space.
Now there are few other models you could use. One could use affine matrices as a bonus you get all of coordinate systems defined. But out of the all other models this is the worst solution it does not interpolate even just one axis meaningfully with numbers. Then again is a good model for storing the result in. One could use axis angles that are based on a vector and a rotation. This is physically very sane way of representing rotation, but has certain problems resolving shortest paths.Now the best model for interpolating may be quaternion which is a sort of axis angle encoded weird. It has several interesting properties such as having exactly 2 times the space of all possible rotations, and can thus be used to solve the shortest rotation between 2 poses as well as longest. The downside of quats is that most people can not read the result of the numeric values in any meaningful way.
So there you have it. Nothing wrong with Euler model to describe a rotation. As long as you don't need to do numeric interpolation except for a very small subset. Which happen to be what planes in air use. Or if you dont need a uniform space, no random generation of rotations, etc.
Nothing says you can not set values in one model and interpolate in another tough.
Upvotes: 1
Reputation: 28004
BTW ideally, I would hope to see an answer from an authoritative expert like the original commentor, @NicolBolas. But since he hasn't responded to your comment question so far, I'll take a stab at it.
I wonder if the confusion here is over the meaning of "Euler" angle vs. other angles.
You mention that "Most dicussions on this topic involve converting from a Euler angle to a quaternion". But are they really converting from an Euler angle?
The author of that comment is apparently the author of this tutorial. In example 8.1 of the tutorial, he shows a formula for quaternions from an axis and an angle. Is this the kind of thing you're referring to as "converting from an Euler angle to a quaternion"? Clearly he didn't mean you shouldn't create a quaternion from an angle.
From the wikipedia definition of Euler angles, they come in threes. In other words, what makes angles Euler angles is the way they are combined to represent an orientation. I suspect what the comment referred to was the fact that you are accumulating rotations in Euler angles pitchAccum and yawAccum, then converting each of those angles to a quaternion before combining them using quaternion multiplication.
If instead you created a quaternion at the beginning to represent orientation; then accumulated orientation state in the quaternion itself, instead of in Euler angles pitchAccum and yawAccum, then you would be doing what @NicolBolas (Jason) is advocating.
Upvotes: 0