# Quaternion Rotation

I am modelling rotations of a rectangular box (3 dimensions) in Matlab using Quaternion theory.

Using the theory found on https://en.wikipedia.org/wiki/Quaternions_and_spatial_rotation I have modelled the following. Wanting to rotate the box around the $x$- $y$- and $z$-axis I start with three angles, $\theta_x$, $\theta_y$, $\theta_z$.

To produce pure quaternions from these angles I write,

$q_x = [\; \cos(\theta_x/2)\; \sin(\theta_x/2) \; 0 \; 0\;]'$

$q_y = [\; \cos(\theta_x/2)\; 0 \; \sin(\theta_x/2) \; 0\;]'$

$q_z = [\; \cos(\theta_x/2)\; 0 \; 0 \; \sin(\theta_x/2)\;]'$

With the rotation quaternion about each axis determined I proceed to combine them by calculating the Hamilton Product. Fist combining $q_x$ and $q_y$,

$q_{xy} = \begin{bmatrix} q_y(1)\cdot q_x(1) - q_y(2)\cdot q_x(2) - q_y(3)\cdot q_x(3) - q_y(4)\cdot q_x(4) \\ q_y(1)\cdot q_x(2) + q_y(2)\cdot q_x(1) + q_y(3) \cdot q_x(4) - q_y(4) \cdot q_x(3) \\ q_y(1) \cdot q_x(3) - q_y(2) \cdot q_x(4) + q_y(3) \cdot q_x(1) + q_y(4) \cdot q_x(2) \\ q_y(1) \cdot q_x(4) + q_y(2) \cdot q_x(3) - q_y(3) \cdot q_x(2) + q_y(4) \cdot q_x(1) \end{bmatrix}$

Where 1-4 denotes the respective vector element.

The Hamilton product is applied again on new vector $q_{xy}$ and $q_z$. Combining all three quaternions can therefore be written,

$q_{xyz} = q_zq_yq_x$

where the Hamilton product is used.

Now back to the original problem: rotating the box.

The box has 8 cornerpoints in total which are described with vectors in the $xyz$-frame. Initially all these have individual values. Proceeding to apply the quaternion $q_{xyz}$ to each of the corner position vector we calculate,

$c'=q_{xyz}cq_{xyz}'$

where $c'$ is the rotated corner position vector and $q_{xyz}'$ is the quaternion conjugate found by,

$q_{xyz}' = [q_{xyz}(1)\; -q_{xyz}(2)\; -q_{xyz}(3)\; -q_{xyz}(4)]$

And here comes the problem:

If my resulting quaternion $q_{xyz}$ has a rotation that is not \textit{only} along only one of the $xyz$-axis, say some rotation along both the $x$ and $y$-axis, the box does not rotate back to its original position after two opposite rotations (back and forth). However, if the rotation is only along one axis it does return to its original position, after applying two opposite rotations to each corner position vector.

What is it that I am not understanding about Quaternions rotations since it only works for rotations along one axis at a time in the $xyz$-frame? I want to be able to rotate the box in other directions than along one axis at a time without introducing errors.

Thanks a lot!

If you have unit quaternion $q$ then formula $u \to qu\bar q$ define rotation of imaginary quaternion $u$ over axis $Im(q)$ and angle having cosine of half equal to $Re(q)$. The oposite rotation is obtained by conjugate quaternion $\bar q$ giving formula $u \to \bar quq$. If you combine both transformations you obtain $\bar q qu\bar q q$ which is equal to $u$ because $q$ is unit quaternion and multiplication of quaternions is associative.

If you do not obtain the same point after applying rotation $q$ and $\bar q$ then you must have done some mistake. It is hard to know where might be the mistake without seeing your code.

Why are you using a quaternion to represent a rotation defined by Euler angles? That is probably the most complex use of rotation quaternions I can think of.

The simplest case, the one I recommend to start with, is to define the quaternion using axis-angle representation, i.e. $$\mathbf{q} = cos\left(\frac{\varphi}{2}\right) + sin\left(\frac{\varphi}{2}\right) x \mathbf{i} + sin\left(\frac{\varphi}{2}\right) y \mathbf{j} + sin\left(\frac{\varphi}{2}\right) z \mathbf{k}$$ or, in your notation, $$\mathbf{q} = \left(cos\left(\frac{\varphi}{2}\right), sin\left(\frac{\varphi}{2}\right) x, sin\left(\frac{\varphi}{2}\right) y, sin\left(\frac{\varphi}{2}\right) z\right)$$ where $\varphi$ is the angle of the rotation, and $(x, y, z)$ defines the axis as an unit vector, $x^2+y^2+z^2=1$.

To invert the rotation described by an unit quaternion (also called a versor), you simply negate the scalar (first) component, or alternatively the other three components. (Negating all four components does not change the rotation the unit quaternion represents.)

If you use this to reverse the rotation applied, and your code is correct, you'll notice that this does indeed return to the original orientation.

Your rotation quaternion is defined as a sequence of three rotations, $$\mathbf{q} = \mathbf{q}_z \times \mathbf{q}_y \times \mathbf{q}_x$$ where $\times$ denotes a Hamilton product.

If you apply a rotation defined by Euler angles $(\theta_x, \theta_y, \theta_z)$, you first rotate by $\theta_x$ around the $x$ axis, then by $\theta_y$ around the $y$ axis, and finally by $\theta_z$ around the $z$ axis. This is the total rotation defined by the quaternion $\mathbf{q}$.

Now, I do believe the core of your question is

Why a rotation by $(\theta_x, \theta_y, \theta_z)$ followed by $(-\theta_x, -\theta_y, -\theta_z)$ does not return the original orientation?

The answer is simple: because you constructed the rotations as three consecutive rotations. Because Hamilton product is not commutative, to invert the rotation like that, you would need to invert the order of the three sub-rotations too; that is, you'd need to define $\mathbf{q}' = \mathbf{q}_x \times \mathbf{q}_y \times \mathbf{q}_z$ for the inverse rotation.

If you did do that, you'd find out that $\mathbf{q}(\theta_x, \theta_y, \theta_z)$ and $\mathbf{q}'(-\theta_x, -\theta_y, -\theta_z)$ only differ by either the sign of the scalar component, or by the sign of the three other components.