[Cogl] [PATCH 3/6] Add a cogl_matrix_init_from_euler function

Robert Bragg robert at sixbynine.org
Wed Jun 20 03:20:43 PDT 2012


Cool, this looks good to land to me.

Reviewed-by: Robert Bragg <robert at linux.intel.com>

thanks,
- Robert

On Thu, May 17, 2012 at 11:40 PM, Neil Roberts <neil at linux.intel.com> wrote:
> This creates a matrix to represent the given euler rotation. This
> should be more efficient than creating the matrix by doing three
> separate rotations because no separate intermediate matrices are
> created and no matrix multiplication is needed.
> ---
>  cogl/cogl-matrix.c                     |   78 ++++++++++++++++++++++++++++++++
>  cogl/cogl-matrix.h                     |   11 +++++
>  doc/reference/cogl2/cogl2-sections.txt |    2 +
>  3 files changed, 91 insertions(+), 0 deletions(-)
>
> diff --git a/cogl/cogl-matrix.c b/cogl/cogl-matrix.c
> index 154203a..b9b72ee 100644
> --- a/cogl/cogl-matrix.c
> +++ b/cogl/cogl-matrix.c
> @@ -1751,6 +1751,84 @@ cogl_matrix_init_from_quaternion (CoglMatrix *matrix,
>   _cogl_matrix_init_from_quaternion (matrix, quaternion);
>  }
>
> +void
> +cogl_matrix_init_from_euler (CoglMatrix *matrix,
> +                             const CoglEuler *euler)
> +{
> +  /* Convert angles to radians */
> +  float heading_rad = euler->heading / 180.0f * G_PI;
> +  float pitch_rad = euler->pitch / 180.0f * G_PI;
> +  float roll_rad = euler->roll / 180.0f * G_PI;
> +  /* Pre-calculate the sin and cos */
> +  float sin_heading = sinf (heading_rad);
> +  float cos_heading = cosf (heading_rad);
> +  float sin_pitch = sinf (pitch_rad);
> +  float cos_pitch = cosf (pitch_rad);
> +  float sin_roll = sinf (roll_rad);
> +  float cos_roll = cosf (roll_rad);
> +
> +  /* These calculations are based on the following website but they
> +   * use a different order for the rotations so it has been modified
> +   * slightly.
> +   * http://www.euclideanspace.com/maths/geometry/
> +   *        rotations/conversions/eulerToMatrix/index.htm
> +   */
> +
> +  /* Heading rotation x=0, y=1, z=0 gives:
> +   *
> +   * [ ch   0   sh   0 ]
> +   * [ 0    1   0    0 ]
> +   * [ -sh  0   ch   0 ]
> +   * [ 0    0   0    1 ]
> +   *
> +   * Pitch rotation x=1, y=0, z=0 gives:
> +   * [ 1    0   0    0 ]
> +   * [ 0    cp  -sp  0 ]
> +   * [ 0    sp  cp   0 ]
> +   * [ 0    0   0    1 ]
> +   *
> +   * Roll rotation x=0, y=0, z=1 gives:
> +   * [ cr   -sr 0    0 ]
> +   * [ sr   cr  0    0 ]
> +   * [ 0    0   1    0 ]
> +   * [ 0    0   0    1 ]
> +   *
> +   * Heading matrix * pitch matrix =
> +   * [ ch   sh*sp    cp*sh   0  ]
> +   * [ 0    cp       -sp     0  ]
> +   * [ -sh  ch*sp    ch*cp   0  ]
> +   * [ 0    0        0       1  ]
> +   *
> +   * That matrix * roll matrix =
> +   * [ ch*cr + sh*sp*sr   sh*sp*cr - ch*sr       sh*cp       0 ]
> +   * [     cp*sr                cp*cr             -sp        0 ]
> +   * [ ch*sp*sr - sh*cr   sh*sr + ch*sp*cr       ch*cp       0 ]
> +   * [       0                    0                0         1 ]
> +   */
> +
> +  matrix->xx = cos_heading * cos_roll + sin_heading * sin_pitch * sin_roll;
> +  matrix->yx = cos_pitch * sin_roll;
> +  matrix->zx = cos_heading * sin_pitch * sin_roll - sin_heading * cos_roll;
> +  matrix->wx = 0.0f;
> +
> +  matrix->xy = sin_heading * sin_pitch * cos_roll - cos_heading * sin_roll;
> +  matrix->yy = cos_pitch * cos_roll;
> +  matrix->zy = sin_heading * sin_roll + cos_heading * sin_pitch * cos_roll;
> +  matrix->wy = 0.0f;
> +
> +  matrix->xz = sin_heading * cos_pitch;
> +  matrix->yz = -sin_pitch;
> +  matrix->zz = cos_heading * cos_pitch;
> +  matrix->wz = 0;
> +
> +  matrix->xw = 0;
> +  matrix->yw = 0;
> +  matrix->zw = 0;
> +  matrix->ww = 1;
> +
> +  matrix->flags = (MAT_FLAG_GENERAL | MAT_DIRTY_ALL);
> +}
> +
>  /*
>  * Transpose a float matrix.
>  */
> diff --git a/cogl/cogl-matrix.h b/cogl/cogl-matrix.h
> index 0c3d31c..10d0d8a 100644
> --- a/cogl/cogl-matrix.h
> +++ b/cogl/cogl-matrix.h
> @@ -491,6 +491,17 @@ cogl_matrix_get_array (const CoglMatrix *matrix);
>  void
>  cogl_matrix_init_from_quaternion (CoglMatrix *matrix,
>                                   const CoglQuaternion *quaternion);
> +
> +/**
> + * cogl_matrix_init_from_euler:
> + * @matrix: A 4x4 transformation matrix
> + * @euler: A #CoglEuler
> + *
> + * Initializes @matrix from a #CoglEuler rotation.
> + */
> +void
> +cogl_matrix_init_from_euler (CoglMatrix *matrix,
> +                             const CoglEuler *euler);
>  #endif
>
>  /**
> diff --git a/doc/reference/cogl2/cogl2-sections.txt b/doc/reference/cogl2/cogl2-sections.txt
> index 01d2d63..7223334 100644
> --- a/doc/reference/cogl2/cogl2-sections.txt
> +++ b/doc/reference/cogl2/cogl2-sections.txt
> @@ -498,6 +498,8 @@ CoglMatrix
>  cogl_matrix_init_identity
>  cogl_matrix_init_from_array
>  cogl_matrix_init_translation
> +cogl_matrix_init_from_quaternion
> +cogl_matrix_init_from_euler
>  cogl_matrix_copy
>  cogl_matrix_equal
>  cogl_matrix_free
> --
> 1.7.3.16.g9464b
>
> _______________________________________________
> Cogl mailing list
> Cogl at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/cogl


More information about the Cogl mailing list