Easy3D 2.6.1
|
The Quaternion class represents 3D rotations and orientations. More...
#include <easy3d/core/quat.h>
Public Types | |
typedef Vec< 3, FT > | Vec3 |
3D vector type | |
typedef Quat< FT > | thisclass |
Quaternion type. | |
Public Member Functions | |
Quat () | |
Default constructor, builds an identity rotation. | |
Quat (const Mat3< FT > &m) | |
Constructor from rotation matrix. See also set_from_rotation_matrix(). | |
Quat (const Vec3 &axis, FT angle) | |
Constructor from rotation axis (non null) and angle (in radians). See also set_axis_angle(). | |
Quat (const Vec3 &from, const Vec3 &to) | |
Constructs a quaternion that will rotate from the from direction to the to direction. | |
Quat (FT q0, FT q1, FT q2, FT q3) | |
Constructor from the four values of a Quaternion. First three values are axis*std::sin(angle/2) and the last one is std::cos(angle/2). | |
Quat (const thisclass &Q) | |
Quat & | operator= (const thisclass &Q) |
void | set_axis_angle (const Vec3 &axis, FT angle) |
void | set_value (FT q0, FT q1, FT q2, FT q3) |
void | set_from_rotation_matrix (const Mat3< FT > &m) |
Set the Quaternion from a (supposedly correct) 3x3 rotation matrix. The matrix is expressed in European format: its three columns are the images by the rotation of the three vectors of an orthogonal basis. See http://www.euclideanspace.com/maths/geometry/rotations/conversions/matrixToQuaternion/index.htm. | |
void | set_from_rotated_basis (const Vec3 &X, const Vec3 &Y, const Vec3 &Z) |
Set a Quaternion from the three axis of a rotated frame. It actually fills the three columns of a matrix with these rotated basis vectors and calls this method. | |
Vec3 | axis () const |
Returns the normalized axis direction of the rotation represented by the Quaternion. It is null for an identity Quaternion. See also angle() and get_axis_angle(). | |
FT | angle () const |
Returns the angle (in radians) of the rotation represented by the Quaternion. This value is always in the range [0-pi]. Larger rotational angles are obtained by inverting the axis() direction. See also axis() and get_axis_angle(). | |
void | get_axis_angle (Vec3 &axis, FT &angle) const |
Returns the axis vector and the angle (in radians) of the rotation represented by the Quaternion. | |
FT | operator[] (int i) const |
Bracket operator, with a constant return value. i must range in [0..3]. | |
FT & | operator[] (int i) |
Bracket operator returning an l-value. i must range in [0..3]. | |
Quat & | operator*= (const Quat &q) |
Quaternion rotation is composed with q. See operator*(), since this is equivalent to this = this * q. | |
Vec3 | rotate (const Vec3 &v) const |
Returns the image of v by the Quaternion rotation. | |
Vec3 | inverse_rotate (const Vec3 &v) const |
Returns the image of v by the Quaternion inverse() rotation. rotate() performs an inverse transformation. Same as inverse().rotate(v). | |
Quat | inverse () const |
Inversion. Returns the inverse Quaternion (inverse rotation). Result has a negated axis() direction and the same angle(). A composition (see operator*()) of a Quaternion and its inverse() results in an identity function. Use invert() to actually modify the Quaternion. | |
void | invert () |
Inverses the Quaternion (same rotation angle(), but negated axis()). | |
void | negate () |
Negates all the coefficients of the Quaternion. This results in an other representation of the same rotation (opposite rotation angle, but with a negated axis direction: the two cancel out). However, note that the results of axis() and angle() are unchanged after a call to this method since angle() always returns a value in [0,pi]. This method is mainly useful for Quaternion interpolation, so that the spherical interpolation takes the shortest path on the unit sphere. See slerp() for details. | |
FT | length () const |
Return the length of the quaternion. | |
FT | normalize () |
Normalizes the Quaternion coefficients. This method should not need to be called since we only deal with unit Quaternions. This is however useful to prevent numerical drifts, especially with small rotational increments. | |
Quat | normalized () const |
Returns a normalized version of the Quaternion. | |
Mat4< FT > | matrix () const |
Returns the Quaternion associated 4x4 rotation matrix. Use glMultMatrixf(q.matrix()) to apply the rotation represented by Quaternion q to the current OpenGL matrix. | |
Mat4< FT > | inverse_matrix () const |
Returns the associated 4x4 inverse rotation matrix. This is simply the matrix() of the inverse(). | |
Quat | log () |
Returns the logarithm of the Quaternion. See also exp(). | |
Quat | exp () |
Returns the exponential of the Quaternion. See also log(). | |
Static Public Member Functions | |
static Quat | slerp (const Quat< FT > &a, const Quat< FT > &b, FT t, bool allowFlip=true) |
Slerp(Spherical Linear intERPolation) interpolation. Returns the slerp interpolation of Quaternions a and b, at time t. t should range in [0,1]. Result is a when t=0 and b when t=1. When allowFlip is true (default) the slerp interpolation will always use the "shortest path" between the Quaternions' orientations, by "flipping" the source Quaternion if needed (see negate()). | |
static Quat | squad (const Quat< FT > &a, const Quat< FT > &tgA, const Quat< FT > &tgB, const Quat< FT > &b, FT t) |
Returns the slerp interpolation of the two Quaternions a and b, at time t, using tangents tgA and tgB. The resulting Quaternion is "between" a and b (result is a when t=0 and b for t=1). Use squad_tangent() to define the Quaternion tangents tgA and tgB. | |
static FT | dot (const Quat< FT > &a, const Quat< FT > &b) |
Returns the "dot" product of a and b: a[0]*b[0] + a[1]*b[1] + a[2]*b[2] + a[3]*b[3]. | |
static Quat | ln_dif (const Quat< FT > &a, const Quat< FT > &b) |
Returns log(a. inverse() * b). Useful for squad_tangent(). | |
static Quat | squad_tangent (const Quat< FT > &before, const Quat< FT > ¢er, const Quat< FT > &after) |
Returns a tangent Quaternion for center , defined by before and after Quaternions. Useful for smooth spline interpolation of Quaternion with squad() and slerp(). | |
static thisclass | random_quat () |
Returns a random unit Quaternion. You can create a randomly directed unit vector using: | |
Public Attributes | ||
union { | ||
struct { | ||
FT x | ||
FT y | ||
FT z | ||
FT w | ||
} | ||
FT _q [4] | ||
}; | ||
Friends | |
Quat | operator* (const Quat &a, const Quat &b) |
Returns the composition of the a and b rotations. The order is important. When applied to a Vec v (see operator*(const Quaternion&, const Vec&) and rotate()) the resulting Quaternion acts as if b was applied first and then a was applied. This is obvious since the image v' of v by the composited rotation satisfies: v'= (a*b) * v = a * (b*v) Note that a*b usually differs from b*a. | |
Vec3 | operator* (const Quat &q, const Vec3 &v) |
Returns the image of v by the rotation q. Same as q.rotate(v). | |
The Quaternion class represents 3D rotations and orientations.
The Quaternion is an appropriate (although not very intuitive) representation for 3D rotations and orientations. Many tools are provided to ease the definition of a Quaternion: see constructors, set_axis_angle(), set_from_rotation_matrix(), set_from_rotated_basis().
You can apply the rotation represented by the Quaternion to 3D points using rotate() and inverse_rotate().
You can apply the Quaternion q rotation to the OpenGL matrices using glMultMatrixd(q.matrix()); which is equivalent to glRotate(q.angle()*180.0/M_PI, q.axis().x, q.axis().y, q.axis().z);
Internal representation The internal representation of a Quaternion is a set of 4 numbers, [x y z w], which represents rotations the following way: x = axis.x * std::sin(angle / 2) y = axis.y * std::sin(angle / 2) z = axis.z * std::sin(angle / 2) w = std::cos(angle / 2)
A Quaternion is always normalized, so that its inverse() is actually its conjugate.
Euler angles VS Quaternion
Euler angles are the easiest way to represent rotation. This representation simply stores the three rotation angles around the X, Y and Z axes. These 3 rotations are then applied successively, usually in this order: first Y, then Z, then X (but not necessarily). Using a different order yields different results. Euler angles are usually used to set a character's orientation since game characters only rotate on the vertical axis. Therefore, it is easier to write, understand and maintain "float direction" than 3 different orientations. Another good use of Euler angles is an FPS camera: you have one angle for heading (Y), and one for up/down (X). However, when things get more complex, Euler angle will be hard to work with, eg.,:
Constructs a quaternion that will rotate from the from
direction to the to
direction.
from
and to
, minimizing the rotation angle. This method is robust and can handle small or almost identical vectors.
|
inline |
Constructor from the four values of a Quaternion. First three values are axis*std::sin(angle/2) and the last one is std::cos(angle/2).
|
inline |
|
inline |
Normalizes the Quaternion coefficients. This method should not need to be called since we only deal with unit Quaternions. This is however useful to prevent numerical drifts, especially with small rotational increments.
|
inline |
Returns a normalized version of the Quaternion.
Quaternion rotation is composed with q. See operator*(), since this is equivalent to this = this * q.
|
static |
Returns a random unit Quaternion. You can create a randomly directed unit vector using:
Returns the image of v by the Quaternion rotation.
void set_axis_angle | ( | const Vec3 & | axis, |
FT | angle ) |
brief Sets the Quaternion as a rotation of axis and angle (in radians). axis
does not need to be normalized. A null axis will result in an identity Quaternion.
|
inline |
brief Sets the Quaternion value.
|
static |
Slerp(Spherical Linear intERPolation) interpolation. Returns the slerp interpolation of Quaternions a and b, at time t. t should range in [0,1]. Result is a when t=0 and b when t=1. When allowFlip is true (default) the slerp interpolation will always use the "shortest path" between the Quaternions' orientations, by "flipping" the source Quaternion if needed (see negate()).
Interpolate between 2 quaternions
Returns the composition of the a and b rotations. The order is important. When applied to a Vec v (see operator*(const Quaternion&, const Vec&) and rotate()) the resulting Quaternion acts as if b was applied first and then a was applied. This is obvious since the image v' of v by the composited rotation satisfies: v'= (a*b) * v = a * (b*v) Note that a*b usually differs from b*a.
Returns the image of v by the rotation q. Same as q.rotate(v).