RyanJuckett.com

Cyclic Coordinate Descent in 2D - Optimizing a joint Print E-mail
  
Wednesday, 11 February 2009 04:43
Article Index
Cyclic Coordinate Descent in 2D
Optimizing a joint
Visualizing CCD
Local Minima
Writing the code
All Pages
  

Optimizing a joint

In math, optimization in the process of finding a value that will minimize or maximize a function. In our case, we want to minimize the distance between the end effector and the target (i.e. minimize |\mathbf{e}-\mathbf{t}| for end effector, \mathbf e, and target, \mathbf t). Depending on how our joints behave, different equations will be used to find the optimal solution. For example, one joint might allow for translation while another joint might allow rotation.

 

For common joint behavior, we can develop an analytic solution to find the optimal value. I am going to walk through solving the optimization problem for rotational joints (the most common joint behavior in an animated character).

 

As a rotational joint, we can rotate the end effector in a circle about our position (see figure 1). The closest position to the target on our rotational circle is the intersection of the circle and the line segment between the current joint and the target.

 

fig_1

figure 1

 

To move the end effector to its optimal position, we need to rotate the joint by the unknown value \alpha. We know the current joint position, \mathbf j, the current end effector position, \mathbf e, and the target position, \mathbf t. To find \alpha, we need to find the angle that will rotate \mathbf e around \mathbf j onto the line (\mathbf{t} - \mathbf{j}). This makes \alpha the signed angle between the vectors (\mathbf{e} - \mathbf{j}) and (\mathbf{t} - \mathbf{j}) that rotates (\mathbf{e} - \mathbf{j}) to (\mathbf{t} - \mathbf{j}).

 

Solving for cosine 

The dot product can be geometrically interpreted as \mathbf{a} \cdot \mathbf{b} = |\mathbf{a}| |\mathbf{b}| \cos \theta where |\mathbf{a}| is the length of vector \mathbf{a}|\mathbf{b}| is the length of vector \mathbf{b}, and \theta is the smaller angle between vector \mathbf{a} and vector \mathbf{b}. Using this formula, we can solve for the cosine of \alpha.

 

(\mathbf{e} - \mathbf{j}) \cdot (\mathbf{t} - \mathbf{j}) = |\mathbf{e} - \mathbf{j}| |\mathbf{t} - \mathbf{j}| \cos \alpha

\cos \alpha = \frac{ (\mathbf{e} - \mathbf{j}) \cdot (\mathbf{t} - \mathbf{j})}{|\mathbf{e} - \mathbf{j}| |\mathbf{t} - \mathbf{j}| }

 

Solving for sine 

The cosine alone will help us find the magnitude of \alpha, but it won't supply us with the direction of rotation. To find the direction, we need to compute \sin \alpha. The three-dimensional cross product can be geometrically interpreted as \mathbf{a} \times \mathbf{b} = |\mathbf{a}| |\mathbf{b}| \sin \theta \mathbf{n} where \mathbf n is the unit vector perpendicular to vector \mathbf a and vector \mathbf b pointing in the direction defined by the right-hand rule, and \theta is the unsigned smaller angle between vector \mathbf{a} and vector \mathbf{b}. While \theta is an unsigned angle, we will be able to get the direction of our rotation based on the direction of \mathbf n

 

First, let's expand the cross product of two three-dimensional vectors.

\begin{bmatrix}a_x\\a_y\\a_z\end{bmatrix} \times \begin{bmatrix}b_x\\b_y\\b_z\end{bmatrix} = \begin{bmatrix}a_y b_z - a_z b_y\\a_z b_x - b_z a_x\\a_x b_y - a_y b_x\end{bmatrix}

 

If we interpret our two-dimensional vectors as three-dimensional vectors on the xy-plane, the cross product will result in a three dimensional vector pointing along the z-axis. 

\begin{bmatrix}a_x\\a_y\\0\end{bmatrix} \times \begin{bmatrix}b_x\\b_y\\0\end{bmatrix} = \begin{bmatrix}0\\0\\a_x b_y - a_y b_x\end{bmatrix}

 

Looking back at our geometric interpretation of the cross product, \mathbf{a} \times \mathbf{b} = |\mathbf{a}| |\mathbf{b}| \sin \theta \mathbf{n}, the unit vector \mathbf n must be either the negative or positive z-axis. Combining our expanded cross-product with the geometric interpretation, we get the following relation where n_z is either -1 or 1.

\begin{bmatrix}0\\0\\a_x b_y - a_y b_x\end{bmatrix} = |\mathbf{a}| |\mathbf{b}| \sin \theta \begin{bmatrix}0\\0\\n_z\end{bmatrix}

 

We can now focus on the z-components of our equation (x and y were zeros).

a_x b_y - a_y b_x = |\mathbf{a}| |\mathbf{b}| \sin \theta n_z

 

The value of n_z determines if we are rotating in clockwise or counter-clockwise direction. In a right-handed coordinate system where the x-axis points right and the y-axis points up, the z-axis will point forward. According to the right-hand rule, \mathbf n will be the negative z-axis when we are rotating clockwise and \mathbf n will be the positive z-axis when we are rotating counter-clockwise. This implies that n_z is -1 for clockwise rotations and 1 for counter-clockwise rotations.

 

Because \theta is the smaller angle between two vectors, it is in the positive range [0,\pi]. Positive angles result in counter-clockwise rotations. Negative angles result in clockwise rotations. Given that -\sin{x} = \sin (-x), when n_z is -1, n_z \sin \theta = -\sin \theta = \sin (-\theta). Previously, we concluded that a negative value of n_z implies a clockwise rotation which in turn implies a negative rotation angle. This will let us define a new signed angle, \phi that is the directional rotation from vector \mathbf a to vector \mathbf b.

 

a_x b_y - a_y b_x = |\mathbf{a}| |\mathbf{b}| \sin \theta n_z = |\mathbf{a}| |\mathbf{b}| \sin \phi

a_x b_y - a_y b_x =|\mathbf{a}| |\mathbf{b}| \sin \phi

 

Using this equation, we can substitute for a, b, and \phi to solve for the sine of \alpha.

 

(e_x - j_x)(t_y - j_y)-(e_y - j_y) (t_x - j_x) = |\mathbf{e} - \mathbf{j}| |\mathbf{t} - \mathbf{j}| \sin \alpha

sin \alpha = \frac {(e_x - j_x)(t_y - j_y)-(e_y - j_y)(t_x - j_x)} {|\mathbf{e} - \mathbf{j}| |\mathbf{t} - \mathbf{j}|}

 

We now have equations for solving the sine and cosine of a signed angle between two vectors. This will let us perform the appropriate rotation for our joint.

 



Last Updated ( Sunday, 02 May 2010 06:28 )
 

Creative Commons License
RyanJuckett.com site content by Ryan Juckett is licensed under a Creative Commons Attribution 3.0 United States License.