Rework the cairo_matrix_t interface in several ways. Expose a struct for cairo_matrix_t.

Add new function to return current matrix: cairo_get_matrix
Deprecate the following functions (in documentation): cairo_matrix_create cairo_matrix_destroy cairo_matrix_get_affine
Rename: cairo_matrix_set_affine -> cairo_matrix_init cairo_matrix_set_identity -> cairo_matrix_init_identity
Add other new matrix initialization functions: cairo_matrix_init_translate cairo_matrix_init_scale cairo_matrix_init_rotate
Change return type of almost all cairo_matrix functions from cairo_status_t to void.
Track changes to cairo_matrix_t interface.
Add a test case showing the same path drawn under various transforms, (including skews set directly by initializing a cairo_matrix_t).
This commit is contained in:
Carl Worth 2005-04-07 10:01:49 +00:00
parent 92060c12ee
commit d135938efd
20 changed files with 499 additions and 304 deletions

View file

@ -1,3 +1,49 @@
2005-04-06 Carl Worth <cworth@cworth.org>
* src/cairo.h: Rework the cairo_matrix_t interface in several ways.
Expose a struct for cairo_matrix_t.
Add new function to return current matrix:
cairo_get_matrix
Deprecate the following functions (in documentation):
cairo_matrix_create
cairo_matrix_destroy
cairo_matrix_get_affine
Rename:
cairo_matrix_set_affine -> cairo_matrix_init
cairo_matrix_set_identity -> cairo_matrix_init_identity
Add other new matrix initialization functions:
cairo_matrix_init_translate
cairo_matrix_init_scale
cairo_matrix_init_rotate
Change return type of almost all cairo_matrix functions from
cairo_status_t to void.
* src/cairo-atsui-font.c:
* src/cairo-ft-font.c:
* src/cairo-gstate.c:
* src/cairo-image-surface.c:
* src/cairo-matrix.c:
* src/cairo-pattern.c:
* src/cairo-pdf-surface.c:
* src/cairo-pen.c:
* src/cairo-surface.c:
* src/cairo-win32-font.c:
* src/cairo-xlib-surface.c:
* src/cairo.c:
* src/cairoint.h: Track changes to cairo_matrix_t interface.
* test/.cvsignore:
* test/Makefile.am:
* test/transforms-ref.png:
* test/transforms.c: Add a test case showing the same path drawn
under various transforms, (including skews set directly by
initializing a cairo_matrix_t).
2005-04-06 Carl Worth <cworth@cworth.org>
* src/cairo.h: Make handling of unsigned char* vs. char*

2
TODO
View file

@ -20,7 +20,7 @@ PD default matrix
cairo_begin_group, cairo_end_group, cairo_get_group
Making set_source consistent
----- cairo_stroke_path -> cairo_stroke_to_path
cairo_current_matrix
PD T cairo_current_matrix
cairo_mask
cairo_create and eliminating cairo_set_target_surface
cairo_fill_preserve, cairo_stroke_preserve, cairo_clip_preserve

View file

@ -667,9 +667,9 @@ _cairo_atsui_font_glyph_path(void *abstract_font,
GlyphID theGlyph = glyphs[i].index;
cairo_matrix_set_affine(&info.scale,
1.0, 0.0,
0.0, 1.0, glyphs[i].x, glyphs[i].y);
cairo_matrix_init(&info.scale,
1.0, 0.0,
0.0, 1.0, glyphs[i].x, glyphs[i].y);
err = ATSUGlyphGetCubicPaths(font->style,

View file

@ -418,12 +418,12 @@ _compute_transform (ft_font_transform_t *sf,
* freetype's transformation.
*/
cairo_matrix_set_affine (&normalized,
sc->matrix[0][0],
sc->matrix[0][1],
sc->matrix[1][0],
sc->matrix[1][1],
0, 0);
cairo_matrix_init (&normalized,
sc->matrix[0][0],
sc->matrix[0][1],
sc->matrix[1][0],
sc->matrix[1][1],
0, 0);
_cairo_matrix_compute_scale_factors (&normalized,
&sf->x_scale, &sf->y_scale,

View file

@ -213,11 +213,6 @@ _cairo_gstate_fini (cairo_gstate_t *gstate)
cairo_pattern_destroy (gstate->pattern);
_cairo_matrix_fini (&gstate->font_matrix);
_cairo_matrix_fini (&gstate->ctm);
_cairo_matrix_fini (&gstate->ctm_inverse);
_cairo_path_fixed_fini (&gstate->path);
_cairo_pen_fini (&gstate->pen_regular);
@ -574,8 +569,14 @@ _cairo_gstate_get_miter_limit (cairo_gstate_t *gstate)
return gstate->miter_limit;
}
cairo_matrix_t
_cairo_gstate_get_matrix (cairo_gstate_t *gstate)
{
return gstate->ctm;
}
void
_cairo_gstate_get_matrix (cairo_gstate_t *gstate, cairo_matrix_t *matrix)
_cairo_gstate_current_matrix (cairo_gstate_t *gstate, cairo_matrix_t *matrix)
{
cairo_matrix_copy (matrix, &gstate->ctm);
}
@ -587,10 +588,10 @@ _cairo_gstate_translate (cairo_gstate_t *gstate, double tx, double ty)
_cairo_gstate_unset_font (gstate);
_cairo_matrix_set_translate (&tmp, tx, ty);
cairo_matrix_init_translate (&tmp, tx, ty);
cairo_matrix_multiply (&gstate->ctm, &tmp, &gstate->ctm);
_cairo_matrix_set_translate (&tmp, -tx, -ty);
cairo_matrix_init_translate (&tmp, -tx, -ty);
cairo_matrix_multiply (&gstate->ctm_inverse, &gstate->ctm_inverse, &tmp);
return CAIRO_STATUS_SUCCESS;
@ -606,10 +607,10 @@ _cairo_gstate_scale (cairo_gstate_t *gstate, double sx, double sy)
_cairo_gstate_unset_font (gstate);
_cairo_matrix_set_scale (&tmp, sx, sy);
cairo_matrix_init_scale (&tmp, sx, sy);
cairo_matrix_multiply (&gstate->ctm, &tmp, &gstate->ctm);
_cairo_matrix_set_scale (&tmp, 1/sx, 1/sy);
cairo_matrix_init_scale (&tmp, 1/sx, 1/sy);
cairo_matrix_multiply (&gstate->ctm_inverse, &gstate->ctm_inverse, &tmp);
return CAIRO_STATUS_SUCCESS;
@ -622,10 +623,10 @@ _cairo_gstate_rotate (cairo_gstate_t *gstate, double angle)
_cairo_gstate_unset_font (gstate);
_cairo_matrix_set_rotate (&tmp, angle);
cairo_matrix_init_rotate (&tmp, angle);
cairo_matrix_multiply (&gstate->ctm, &tmp, &gstate->ctm);
_cairo_matrix_set_rotate (&tmp, -angle);
cairo_matrix_init_rotate (&tmp, -angle);
cairo_matrix_multiply (&gstate->ctm_inverse, &gstate->ctm_inverse, &tmp);
return CAIRO_STATUS_SUCCESS;
@ -670,8 +671,8 @@ _cairo_gstate_identity_matrix (cairo_gstate_t *gstate)
{
_cairo_gstate_unset_font (gstate);
cairo_matrix_set_identity (&gstate->ctm);
cairo_matrix_set_identity (&gstate->ctm_inverse);
cairo_matrix_init_identity (&gstate->ctm);
cairo_matrix_init_identity (&gstate->ctm_inverse);
return CAIRO_STATUS_SUCCESS;
}
@ -1800,10 +1801,9 @@ extract_transformed_rectangle(cairo_matrix_t *mat,
pixman_box16_t *box)
{
double a, b, c, d, tx, ty;
cairo_status_t st;
st = cairo_matrix_get_affine (mat, &a, &b, &c, &d, &tx, &ty);
if (!(st == CAIRO_STATUS_SUCCESS && b == 0. && c == 0.))
cairo_matrix_get_affine (mat, &a, &b, &c, &d, &tx, &ty);
if (!(b == 0. && c == 0.))
return 0;
if (tr->num_traps == 1
@ -2037,7 +2037,7 @@ _cairo_gstate_show_surface (cairo_gstate_t *gstate,
if (gstate->surface) {
cairo_matrix_t device_to_backend;
_cairo_matrix_set_translate (&device_to_backend,
cairo_matrix_init_translate (&device_to_backend,
gstate->surface->device_x_offset,
gstate->surface->device_y_offset);
cairo_matrix_multiply (&image_to_backend, &image_to_device, &device_to_backend);
@ -2147,7 +2147,7 @@ _cairo_gstate_select_font (cairo_gstate_t *gstate,
gstate->font_slant = slant;
gstate->font_weight = weight;
cairo_matrix_set_identity (&gstate->font_matrix);
cairo_matrix_init_identity (&gstate->font_matrix);
return CAIRO_STATUS_SUCCESS;
}
@ -2158,7 +2158,9 @@ _cairo_gstate_scale_font (cairo_gstate_t *gstate,
{
_cairo_gstate_unset_font (gstate);
return cairo_matrix_scale (&gstate->font_matrix, scale, scale);
cairo_matrix_scale (&gstate->font_matrix, scale, scale);
return CAIRO_STATUS_SUCCESS;
}
cairo_status_t
@ -2171,8 +2173,10 @@ _cairo_gstate_transform_font (cairo_gstate_t *gstate,
_cairo_gstate_unset_font (gstate);
cairo_matrix_get_affine (matrix, &a, &b, &c, &d, &tx, &ty);
cairo_matrix_set_affine (&tmp, a, b, c, d, 0, 0);
return cairo_matrix_multiply (&gstate->font_matrix, &gstate->font_matrix, &tmp);
cairo_matrix_init (&tmp, a, b, c, d, 0, 0);
cairo_matrix_multiply (&gstate->font_matrix, &gstate->font_matrix, &tmp);
return CAIRO_STATUS_SUCCESS;
}

View file

@ -325,13 +325,13 @@ _cairo_image_surface_set_matrix (cairo_image_surface_t *surface,
{
pixman_transform_t pixman_transform;
pixman_transform.matrix[0][0] = _cairo_fixed_from_double (matrix->m[0][0]);
pixman_transform.matrix[0][1] = _cairo_fixed_from_double (matrix->m[1][0]);
pixman_transform.matrix[0][2] = _cairo_fixed_from_double (matrix->m[2][0]);
pixman_transform.matrix[0][0] = _cairo_fixed_from_double (matrix->xx);
pixman_transform.matrix[0][1] = _cairo_fixed_from_double (matrix->xy);
pixman_transform.matrix[0][2] = _cairo_fixed_from_double (matrix->x0);
pixman_transform.matrix[1][0] = _cairo_fixed_from_double (matrix->m[0][1]);
pixman_transform.matrix[1][1] = _cairo_fixed_from_double (matrix->m[1][1]);
pixman_transform.matrix[1][2] = _cairo_fixed_from_double (matrix->m[2][1]);
pixman_transform.matrix[1][0] = _cairo_fixed_from_double (matrix->yx);
pixman_transform.matrix[1][1] = _cairo_fixed_from_double (matrix->yy);
pixman_transform.matrix[1][2] = _cairo_fixed_from_double (matrix->y0);
pixman_transform.matrix[2][0] = 0;
pixman_transform.matrix[2][1] = 0;

View file

@ -40,14 +40,6 @@
#include "cairoint.h"
static cairo_matrix_t const CAIRO_MATRIX_IDENTITY = {
{
{1, 0},
{0, 1},
{0, 0}
}
};
static void
_cairo_matrix_scalar_multiply (cairo_matrix_t *matrix, double scalar);
@ -61,6 +53,11 @@ _cairo_matrix_compute_adjoint (cairo_matrix_t *matrix);
*
* Return value: a newly created matrix; free with cairo_matrix_destroy(),
* or %NULL if memory couldn't be allocated.
*
* WARNING: This function is deprecated and will be disappearing
* shortly. Now that the structure of #cairo_matrix_t is exposed,
* users can manage the memory on their own, (in particular by putting
* a cairo_matrix_t on the stack).
**/
cairo_matrix_t *
cairo_matrix_create (void)
@ -71,33 +68,25 @@ cairo_matrix_create (void)
if (matrix == NULL)
return NULL;
_cairo_matrix_init (matrix);
cairo_matrix_init_identity (matrix);
return matrix;
}
void
_cairo_matrix_init (cairo_matrix_t *matrix)
{
cairo_matrix_set_identity (matrix);
}
void
_cairo_matrix_fini (cairo_matrix_t *matrix)
{
/* nothing to do here */
}
/**
* cairo_matrix_destroy:
* @matrix: a #cairo_matrix_t
*
* Frees a matrix created with cairo_matrix_create.
*
* WARNING: This function is deprecated and will be disappearing
* shortly. Now that the structure of #cairo_matrix_t is exposed,
* users can manage the memory on their own, (in particular by putting
* a cairo_matrix_t on the stack).
**/
void
cairo_matrix_destroy (cairo_matrix_t *matrix)
{
_cairo_matrix_fini (matrix);
free (matrix);
}
@ -108,67 +97,64 @@ cairo_matrix_destroy (cairo_matrix_t *matrix)
*
* Modifies @matrix to be identical to @other.
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
* WARNING: This function is deprecated and will be disappearing
* shortly. Now that the structure of #cairo_matrix_t is exposed,
* users can copy a matrix by direct assignment.
**/
cairo_status_t
void
cairo_matrix_copy (cairo_matrix_t *matrix, const cairo_matrix_t *other)
{
*matrix = *other;
return CAIRO_STATUS_SUCCESS;
}
slim_hidden_def(cairo_matrix_copy);
/**
* cairo_matrix_set_identity:
* cairo_matrix_init_identity:
* @matrix: a #cairo_matrix_t
*
* Modifies @matrix to be an identity transformation.
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
**/
cairo_status_t
cairo_matrix_set_identity (cairo_matrix_t *matrix)
void
cairo_matrix_init_identity (cairo_matrix_t *matrix)
{
*matrix = CAIRO_MATRIX_IDENTITY;
return CAIRO_STATUS_SUCCESS;
return cairo_matrix_init (matrix,
1, 0,
0, 1,
0, 0);
}
slim_hidden_def(cairo_matrix_set_identity);
slim_hidden_def(cairo_matrix_init_identity);
DEPRECATE(cairo_matrix_set_identity, cairo_matrix_init_identity);
/**
* cairo_matrix_set_affine:
* cairo_matrix_init:
* @matrix: a cairo_matrix_t
* @a: a component of the affine transformation
* @b: b component of the affine transformation
* @c: c component of the affine transformation
* @d: d component of the affine transformation
* @tx: X translation component of the affine transformation
* @ty: Y translation component of the affine transformation
* @xx: xx component of the affine transformation
* @yx: yx component of the affine transformation
* @xy: xy component of the affine transformation
* @yy: yy component of the affine transformation
* @x0: X translation component of the affine transformation
* @y0: Y translation component of the affine transformation
*
* Sets @matrix to be the affine transformation given by
* @a, b, @c, @d, @tx, @ty. The transformation is given
* @xx, @yx, @xy, @yy, @x0, @y0. The transformation is given
* by:
* <programlisting>
* x_new = x * a + y * c + tx;
* y_new = x * b + y * d + ty;
* x_new = xx * x + xy * y + x0;
* y_new = yx * x + yy * y + y0;
* </programlisting>
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
**/
cairo_status_t
cairo_matrix_set_affine (cairo_matrix_t *matrix,
double a, double b,
double c, double d,
double tx, double ty)
void
cairo_matrix_init (cairo_matrix_t *matrix,
double xx, double yx,
double xy, double yy,
double x0, double y0)
{
matrix->m[0][0] = a; matrix->m[0][1] = b;
matrix->m[1][0] = c; matrix->m[1][1] = d;
matrix->m[2][0] = tx; matrix->m[2][1] = ty;
return CAIRO_STATUS_SUCCESS;
matrix->xx = xx; matrix->yx = yx;
matrix->xy = xy; matrix->yy = yy;
matrix->x0 = x0; matrix->y0 = y0;
}
slim_hidden_def(cairo_matrix_set_affine);
slim_hidden_def(cairo_matrix_init);
DEPRECATE(cairo_matrix_set_affine, cairo_matrix_init);
/**
* cairo_matrix_get_affine:
@ -181,43 +167,53 @@ slim_hidden_def(cairo_matrix_set_affine);
* @ty: location to store Y-translation component of affine transformation, or %NULL
*
* Gets the matrix values for the affine tranformation that @matrix represents.
* See cairo_matrix_set_affine().
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
* See cairo_matrix_init().
*
* WARNING: This function is deprecated and will be disappearing
* shortly. Now that the structure of #cairo_matrix_t is exposed,
* users can just examine the matrix values directly.
**/
cairo_status_t
void
cairo_matrix_get_affine (cairo_matrix_t *matrix,
double *a, double *b,
double *c, double *d,
double *tx, double *ty)
double *xx, double *yx,
double *xy, double *yy,
double *x0, double *y0)
{
if (a)
*a = matrix->m[0][0];
if (b)
*b = matrix->m[0][1];
if (xx)
*xx = matrix->xx;
if (yx)
*yx = matrix->yx;
if (c)
*c = matrix->m[1][0];
if (d)
*d = matrix->m[1][1];
if (xy)
*xy = matrix->xy;
if (yy)
*yy = matrix->yy;
if (tx)
*tx = matrix->m[2][0];
if (ty)
*ty = matrix->m[2][1];
return CAIRO_STATUS_SUCCESS;
if (x0)
*x0 = matrix->x0;
if (y0)
*y0 = matrix->y0;
}
cairo_status_t
_cairo_matrix_set_translate (cairo_matrix_t *matrix,
/**
* cairo_matrix_init_translate:
* @matrix: a cairo_matrix_t
* @tx: amount to translate in the X direction
* @ty: amount to translate in the Y direction
*
* Initializes @matrix to a transformation that translates by @tx and
* @ty in the X and Y dimensions, respectively.
**/
void
cairo_matrix_init_translate (cairo_matrix_t *matrix,
double tx, double ty)
{
return cairo_matrix_set_affine (matrix,
1, 0,
0, 1,
tx, ty);
cairo_matrix_init (matrix,
1, 0,
0, 1,
tx, ty);
}
slim_hidden_def(cairo_matrix_init_translate);
/**
* cairo_matrix_translate:
@ -229,34 +225,42 @@ _cairo_matrix_set_translate (cairo_matrix_t *matrix,
* @matrix. The effect of the new transformation is to first translate
* the coordinates by @tx and @ty, then apply the original transformation
* to the coordinates.
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
**/
cairo_status_t
void
cairo_matrix_translate (cairo_matrix_t *matrix, double tx, double ty)
{
cairo_matrix_t tmp;
_cairo_matrix_set_translate (&tmp, tx, ty);
cairo_matrix_init_translate (&tmp, tx, ty);
return cairo_matrix_multiply (matrix, &tmp, matrix);
cairo_matrix_multiply (matrix, &tmp, matrix);
}
cairo_status_t
_cairo_matrix_set_scale (cairo_matrix_t *matrix,
/**
* cairo_matrix_init_scale:
* @matrix: a cairo_matrix_t
* @sx: scale factor in the X direction
* @sy: scale factor in the Y direction
*
* Initializes @matrix to a transformation that scales by @sx and @sy
* in the X and Y dimensions, respectively.
**/
void
cairo_matrix_init_scale (cairo_matrix_t *matrix,
double sx, double sy)
{
return cairo_matrix_set_affine (matrix,
sx, 0,
0, sy,
0, 0);
cairo_matrix_init (matrix,
sx, 0,
0, sy,
0, 0);
}
slim_hidden_def(cairo_matrix_init_scale);
/**
* cairo_matrix_scale:
* @matrix: a #cairo_matrix_t
* @sx: Scale factor in the X direction
* @sy: Scale factor in the Y direction
* @sx: scale factor in the X direction
* @sy: scale factor in the Y direction
*
* Applies scaling by @tx, @ty to the transformation in @matrix. The
* effect of the new transformation is to first scale the coordinates
@ -264,20 +268,31 @@ _cairo_matrix_set_scale (cairo_matrix_t *matrix,
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
**/
cairo_status_t
void
cairo_matrix_scale (cairo_matrix_t *matrix, double sx, double sy)
{
cairo_matrix_t tmp;
_cairo_matrix_set_scale (&tmp, sx, sy);
cairo_matrix_init_scale (&tmp, sx, sy);
return cairo_matrix_multiply (matrix, &tmp, matrix);
cairo_matrix_multiply (matrix, &tmp, matrix);
}
slim_hidden_def(cairo_matrix_scale);
cairo_status_t
_cairo_matrix_set_rotate (cairo_matrix_t *matrix,
double radians)
/**
* cairo_matrix_init_rotate:
* @matrix: a cairo_matrix_t
* @radians: angle of rotation, in radians. The direction of rotation
* is defined such that positive angles rotate in the direction from
* the positive X axis toward the positive Y axis. With the default
* axis orientation of cairo, positive angles rotate in a clockwise
* direction.
*
* Initialized @matrix to a transformation that rotates by @radians.
**/
void
cairo_matrix_init_rotate (cairo_matrix_t *matrix,
double radians)
{
double s;
double c;
@ -287,36 +302,35 @@ _cairo_matrix_set_rotate (cairo_matrix_t *matrix,
s = sin (radians);
c = cos (radians);
#endif
return cairo_matrix_set_affine (matrix,
c, s,
-s, c,
0, 0);
cairo_matrix_init (matrix,
c, s,
-s, c,
0, 0);
}
slim_hidden_def(cairo_matrix_init_rotate);
/**
* cairo_matrix_rotate:
* @matrix: a @cairo_matrix_t
* @radians: angle of rotation, in radians. Angles are defined
* so that an angle of 90 degrees (%M_PI/2 radians) rotates the
* positive X axis into the positive Y axis. With the default
* cairo choice of axis orientation, positive rotations are
* clockwise.
* @radians: angle of rotation, in radians. The direction of rotation
* is defined such that positive angles rotate in the direction from
* the positive X axis toward the positive Y axis. With the default
* axis orientation of cairo, positive angles rotate in a clockwise
* direction.
*
* Applies rotation by @radians to the transformation in
* @matrix. The effect of the new transformation is to first rotate the
* coordinates by @radians, then apply the original transformation
* to the coordinates.
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
**/
cairo_status_t
void
cairo_matrix_rotate (cairo_matrix_t *matrix, double radians)
{
cairo_matrix_t tmp;
_cairo_matrix_set_rotate (&tmp, radians);
cairo_matrix_init_rotate (&tmp, radians);
return cairo_matrix_multiply (matrix, &tmp, matrix);
cairo_matrix_multiply (matrix, &tmp, matrix);
}
/**
@ -331,7 +345,7 @@ cairo_matrix_rotate (cairo_matrix_t *matrix, double radians)
* coordinates and then apply the transformation in @b to the
* coordinates.
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
* It is allowable for @result to be identical to either @a or @b.
**/
/*
* XXX: The ordering of the arguments to this function corresponds
@ -339,29 +353,21 @@ cairo_matrix_rotate (cairo_matrix_t *matrix, double radians)
* then we need to switch the two arguments and fix up all
* uses.
*/
cairo_status_t
void
cairo_matrix_multiply (cairo_matrix_t *result, const cairo_matrix_t *a, const cairo_matrix_t *b)
{
cairo_matrix_t r;
int row, col, n;
double t;
for (row = 0; row < 3; row++) {
for (col = 0; col < 2; col++) {
if (row == 2)
t = b->m[2][col];
else
t = 0;
for (n = 0; n < 2; n++) {
t += a->m[row][n] * b->m[n][col];
}
r.m[row][col] = t;
}
}
r.xx = a->xx * b->xx + a->yx * b->xy;
r.yx = a->xx * b->yx + a->yx * b->yy;
r.xy = a->xy * b->xx + a->yy * b->xy;
r.yy = a->xy * b->yx + a->yy * b->yy;
r.x0 = a->x0 * b->xx + a->y0 * b->xy + b->x0;
r.y0 = a->x0 * b->yx + a->y0 * b->yy + b->y0;
*result = r;
return CAIRO_STATUS_SUCCESS;
}
slim_hidden_def(cairo_matrix_multiply);
@ -385,23 +391,17 @@ slim_hidden_def(cairo_matrix_multiply);
* always transforms to the same vector. If (@x1,@y1) transforms
* to (@x2,@y2) then (@x1+@dx1,@y1+@dy1) will transform to
* (@x1+@dx2,@y1+@dy2) for all values of @x1 and @x2.
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
**/
cairo_status_t
void
cairo_matrix_transform_distance (cairo_matrix_t *matrix, double *dx, double *dy)
{
double new_x, new_y;
new_x = (matrix->m[0][0] * *dx
+ matrix->m[1][0] * *dy);
new_y = (matrix->m[0][1] * *dx
+ matrix->m[1][1] * *dy);
new_x = (matrix->xx * *dx + matrix->xy * *dy);
new_y = (matrix->yx * *dx + matrix->yy * *dy);
*dx = new_x;
*dy = new_y;
return CAIRO_STATUS_SUCCESS;
}
slim_hidden_def(cairo_matrix_transform_distance);
@ -412,22 +412,18 @@ slim_hidden_def(cairo_matrix_transform_distance);
* @y: Y position. An in/out parameter
*
* Transforms the point (@x, @y) by @matrix.
*
* Return value: %CAIRO_STATUS_SUCCESS, always.
**/
cairo_status_t
void
cairo_matrix_transform_point (cairo_matrix_t *matrix, double *x, double *y)
{
cairo_matrix_transform_distance (matrix, x, y);
*x += matrix->m[2][0];
*y += matrix->m[2][1];
return CAIRO_STATUS_SUCCESS;
*x += matrix->x0;
*y += matrix->y0;
}
slim_hidden_def(cairo_matrix_transform_point);
cairo_status_t
void
_cairo_matrix_transform_bounding_box (cairo_matrix_t *matrix,
double *x, double *y,
double *width, double *height)
@ -477,18 +473,19 @@ _cairo_matrix_transform_bounding_box (cairo_matrix_t *matrix,
*y = min_y;
*width = max_x - min_x;
*height = max_y - min_y;
return CAIRO_STATUS_SUCCESS;
}
static void
_cairo_matrix_scalar_multiply (cairo_matrix_t *matrix, double scalar)
{
int row, col;
matrix->xx *= scalar;
matrix->yx *= scalar;
for (row = 0; row < 3; row++)
for (col = 0; col < 2; col++)
matrix->m[row][col] *= scalar;
matrix->xy *= scalar;
matrix->yy *= scalar;
matrix->x0 *= scalar;
matrix->y0 *= scalar;
}
/* This function isn't a correct adjoint in that the implicit 1 in the
@ -501,14 +498,15 @@ _cairo_matrix_compute_adjoint (cairo_matrix_t *matrix)
/* adj (A) = transpose (C:cofactor (A,i,j)) */
double a, b, c, d, tx, ty;
a = matrix->m[0][0]; b = matrix->m[0][1];
c = matrix->m[1][0]; d = matrix->m[1][1];
tx = matrix->m[2][0]; ty = matrix->m[2][1];
cairo_matrix_get_affine (matrix,
&a, &b,
&c, &d,
&tx, &ty);
cairo_matrix_set_affine (matrix,
d, -b,
-c, a,
c*ty - d*tx, b*tx - a*ty);
cairo_matrix_init (matrix,
d, -b,
-c, a,
c*ty - d*tx, b*tx - a*ty);
}
/**
@ -542,20 +540,18 @@ cairo_matrix_invert (cairo_matrix_t *matrix)
}
slim_hidden_def(cairo_matrix_invert);
cairo_status_t
void
_cairo_matrix_compute_determinant (cairo_matrix_t *matrix, double *det)
{
double a, b, c, d;
a = matrix->m[0][0]; b = matrix->m[0][1];
c = matrix->m[1][0]; d = matrix->m[1][1];
a = matrix->xx; b = matrix->yx;
c = matrix->xy; d = matrix->yy;
*det = a*d - b*c;
return CAIRO_STATUS_SUCCESS;
}
cairo_status_t
void
_cairo_matrix_compute_eigen_values (cairo_matrix_t *matrix, double *lambda1, double *lambda2)
{
/* The eigenvalues of an NxN matrix M are found by solving the polynomial:
@ -577,16 +573,12 @@ _cairo_matrix_compute_eigen_values (cairo_matrix_t *matrix, double *lambda1, dou
double a, b, c, d, rad;
a = matrix->m[0][0];
b = matrix->m[0][1];
c = matrix->m[1][0];
d = matrix->m[1][1];
a = matrix->xx; b = matrix->yx;
c = matrix->xy; d = matrix->yy;
rad = sqrt (a*a + 2*a*d + d*d - 4*(a*d - b*c));
*lambda1 = (a + d + rad) / 2.0;
*lambda2 = (a + d - rad) / 2.0;
return CAIRO_STATUS_SUCCESS;
}
/* Compute the amount that each basis vector is scaled by. */

View file

@ -58,7 +58,7 @@ _cairo_pattern_init (cairo_pattern_t *pattern, cairo_pattern_type_t type)
pattern->filter = CAIRO_FILTER_DEFAULT;
pattern->alpha = 1.0;
_cairo_matrix_init (&pattern->matrix);
cairo_matrix_init_identity (&pattern->matrix);
}
static cairo_status_t
@ -354,13 +354,17 @@ cairo_pattern_add_color_stop (cairo_pattern_t *pattern,
cairo_status_t
cairo_pattern_set_matrix (cairo_pattern_t *pattern, cairo_matrix_t *matrix)
{
return cairo_matrix_copy (&pattern->matrix, matrix);
cairo_matrix_copy (&pattern->matrix, matrix);
return CAIRO_STATUS_SUCCESS;
}
cairo_status_t
cairo_pattern_get_matrix (cairo_pattern_t *pattern, cairo_matrix_t *matrix)
{
return cairo_matrix_copy (matrix, &pattern->matrix);
cairo_matrix_copy (matrix, &pattern->matrix);
return CAIRO_STATUS_SUCCESS;
}
cairo_status_t
@ -953,7 +957,7 @@ _cairo_pattern_acquire_surface_for_gradient (cairo_gradient_pattern_t *pattern,
attr->x_offset = -x;
attr->y_offset = -y;
cairo_matrix_set_identity (&attr->matrix);
cairo_matrix_init_identity (&attr->matrix);
attr->extend = repeat ? CAIRO_EXTEND_REPEAT : CAIRO_EXTEND_NONE;
attr->filter = CAIRO_FILTER_NEAREST;
attr->acquired = FALSE;
@ -986,7 +990,7 @@ _cairo_pattern_acquire_surface_for_solid (cairo_solid_pattern_t *pattern,
return CAIRO_STATUS_NO_MEMORY;
attribs->x_offset = attribs->y_offset = 0;
cairo_matrix_set_identity (&attribs->matrix);
cairo_matrix_init_identity (&attribs->matrix);
attribs->extend = CAIRO_EXTEND_REPEAT;
attribs->filter = CAIRO_FILTER_NEAREST;
attribs->acquired = FALSE;
@ -1074,7 +1078,7 @@ _cairo_pattern_acquire_surface_for_surface (cairo_surface_pattern_t *pattern,
attr->extend = CAIRO_EXTEND_NONE;
attr->filter = CAIRO_FILTER_NEAREST;
cairo_matrix_set_identity (&attr->matrix);
cairo_matrix_init_identity (&attr->matrix);
}
else
{
@ -1100,7 +1104,7 @@ _cairo_pattern_acquire_surface_for_surface (cairo_surface_pattern_t *pattern,
if (_cairo_matrix_is_integer_translation (&pattern->base.matrix,
&tx, &ty))
{
cairo_matrix_set_identity (&attr->matrix);
cairo_matrix_init_identity (&attr->matrix);
attr->x_offset = tx;
attr->y_offset = ty;
}

View file

@ -1293,9 +1293,9 @@ _cairo_pdf_surface_composite_image (cairo_pdf_surface_t *dst,
_cairo_output_stream_printf (output,
"q %f %f %f %f %f %f cm /res%d Do Q\r\n",
i2u.m[0][0], i2u.m[0][1],
i2u.m[1][0], i2u.m[1][1],
i2u.m[2][0], i2u.m[2][1],
i2u.xx, i2u.yx,
i2u.xy, i2u.yy,
i2u.x0, i2u.y0,
id);
bail:
@ -1337,9 +1337,9 @@ _cairo_pdf_surface_composite_pdf (cairo_pdf_surface_t *dst,
_cairo_output_stream_printf (output,
"q %f %f %f %f %f %f cm",
i2u.m[0][0], i2u.m[0][1],
i2u.m[1][0], i2u.m[1][1],
i2u.m[2][0], i2u.m[2][1]);
i2u.xx, i2u.yx,
i2u.xy, i2u.yy,
i2u.x0, i2u.y0);
num_streams = _cairo_array_num_elements (&src->streams);
for (i = 0; i < num_streams; i++) {
@ -1461,7 +1461,7 @@ emit_surface_pattern (cairo_pdf_surface_t *dst,
/* BBox must be smaller than XStep by YStep or acroread wont
* display the pattern. */
cairo_matrix_set_identity (&pm);
cairo_matrix_init_identity (&pm);
cairo_matrix_scale (&pm, image->width, image->height);
cairo_matrix_copy (&pm, &pattern->base.matrix);
cairo_matrix_invert (&pm);
@ -1476,9 +1476,9 @@ emit_surface_pattern (cairo_pdf_surface_t *dst,
" /Resources << /XObject << /res%d %d 0 R >> >>\r\n"
" /Matrix [ %f %f %f %f %f %f ]\r\n",
id, id,
pm.m[0][0], pm.m[0][1],
pm.m[1][0], pm.m[1][1],
pm.m[2][0], pm.m[2][1]);
pm.xx, pm.yx,
pm.xy, pm.yy,
pm.x0, pm.y0);
stream = _cairo_pdf_document_open_stream (document, entries);

View file

@ -374,8 +374,8 @@ _cairo_pen_vertices_needed (double tolerance,
double radius,
cairo_matrix_t *matrix)
{
double a = matrix->m[0][0], c = matrix->m[0][1];
double b = matrix->m[1][0], d = matrix->m[1][1];
double a = matrix->xx, b = matrix->yx;
double c = matrix->xy, d = matrix->yy;
double i = a*a + c*c;
double j = b*b + d*d;

View file

@ -56,7 +56,7 @@ _cairo_surface_init (cairo_surface_t *surface,
_cairo_array_init (&surface->user_data_slots,
sizeof (cairo_user_data_slot_t));
_cairo_matrix_init (&surface->matrix);
cairo_matrix_init_identity (&surface->matrix);
surface->filter = CAIRO_FILTER_NEAREST;
surface->repeat = 0;
@ -476,7 +476,9 @@ cairo_surface_set_matrix (cairo_surface_t *surface, cairo_matrix_t *matrix)
if (surface == NULL)
return CAIRO_STATUS_NULL_POINTER;
return cairo_matrix_copy (&surface->matrix, matrix);
cairo_matrix_copy (&surface->matrix, matrix);
return CAIRO_STATUS_SUCCESS;
}
slim_hidden_def(cairo_surface_set_matrix);
@ -489,7 +491,9 @@ cairo_surface_get_matrix (cairo_surface_t *surface, cairo_matrix_t *matrix)
if (surface == NULL)
return CAIRO_STATUS_NULL_POINTER;
return cairo_matrix_copy (matrix, &surface->matrix);
cairo_matrix_copy (matrix, &surface->matrix);
return CAIRO_STATUS_SUCCESS;
}
slim_hidden_def(cairo_surface_get_matrix);

View file

@ -138,12 +138,12 @@ _compute_transform (cairo_win32_font_t *font,
/* The font matrix has x and y "scale" components which we extract and
* use as character scale values.
*/
cairo_matrix_set_affine (&font->logical_to_device,
sc->matrix[0][0],
sc->matrix[0][1],
sc->matrix[1][0],
sc->matrix[1][1],
0, 0);
cairo_matrix_init (&font->logical_to_device,
sc->matrix[0][0],
sc->matrix[0][1],
sc->matrix[1][0],
sc->matrix[1][1],
0, 0);
if (!font->preserve_axes) {
_cairo_matrix_compute_scale_factors (&font->logical_to_device,
@ -159,7 +159,7 @@ _compute_transform (cairo_win32_font_t *font,
font->device_to_logical = font->logical_to_device;
if (!CAIRO_OK (cairo_matrix_invert (&font->device_to_logical)))
cairo_matrix_set_identity (&font->device_to_logical);
cairo_matrix_init_identity (&font->device_to_logical);
}
static BYTE

View file

@ -465,13 +465,13 @@ _cairo_xlib_surface_set_matrix (cairo_xlib_surface_t *surface,
if (!surface->picture)
return CAIRO_STATUS_SUCCESS;
xtransform.matrix[0][0] = _cairo_fixed_from_double (matrix->m[0][0]);
xtransform.matrix[0][1] = _cairo_fixed_from_double (matrix->m[1][0]);
xtransform.matrix[0][2] = _cairo_fixed_from_double (matrix->m[2][0]);
xtransform.matrix[0][0] = _cairo_fixed_from_double (matrix->xx);
xtransform.matrix[0][1] = _cairo_fixed_from_double (matrix->xy);
xtransform.matrix[0][2] = _cairo_fixed_from_double (matrix->x0);
xtransform.matrix[1][0] = _cairo_fixed_from_double (matrix->m[0][1]);
xtransform.matrix[1][1] = _cairo_fixed_from_double (matrix->m[1][1]);
xtransform.matrix[1][2] = _cairo_fixed_from_double (matrix->m[2][1]);
xtransform.matrix[1][0] = _cairo_fixed_from_double (matrix->yx);
xtransform.matrix[1][1] = _cairo_fixed_from_double (matrix->yy);
xtransform.matrix[1][2] = _cairo_fixed_from_double (matrix->y0);
xtransform.matrix[2][0] = 0;
xtransform.matrix[2][1] = 0;

View file

@ -1698,7 +1698,7 @@ cairo_transform_font (cairo_t *cr, cairo_matrix_t *matrix)
**/
void
cairo_text_extents (cairo_t *cr,
const char *utf8,
const char *utf8,
cairo_text_extents_t *extents)
{
cairo_glyph_t *glyphs = NULL;
@ -2048,21 +2048,39 @@ cairo_get_miter_limit (cairo_t *cr)
}
DEPRECATE (cairo_current_miter_limit, cairo_get_miter_limit);
/**
* cairo_get_matrix:
* @cr: a cairo context
*
* Gets the current transformation matrix (CTM), a matrix which
* transforms from user space to device space.
*
* Return value: the current transformation matrix.
**/
cairo_matrix_t
cairo_get_matrix (cairo_t *cr)
{
CAIRO_CHECK_SANITY (cr);
return _cairo_gstate_get_matrix (cr->gstate);
}
/**
* cairo_get_matrix:
* @cr: a cairo context
* @matrix: return value for the matrix
*
* Stores the current transformation matrix (CTM) into @matrix.
*
* WARNING: This function is deprecated and will be disappearing
* shortly.
**/
void
cairo_get_matrix (cairo_t *cr, cairo_matrix_t *matrix)
cairo_current_matrix (cairo_t *cr, cairo_matrix_t *matrix)
{
CAIRO_CHECK_SANITY (cr);
_cairo_gstate_get_matrix (cr->gstate, matrix);
_cairo_gstate_current_matrix (cr->gstate, matrix);
CAIRO_CHECK_SANITY (cr);
}
DEPRECATE (cairo_current_matrix, cairo_get_matrix);
/**
* cairo_get_target_surface:

View file

@ -94,7 +94,12 @@ typedef struct _cairo_surface cairo_surface_t;
* A #cairo_matrix_t holds an affine transformation, such as a scale,
* rotation, or shear, or a combination of those.
**/
typedef struct _cairo_matrix cairo_matrix_t;
typedef struct _cairo_matrix {
double xx; double yx;
double xy; double yy;
double x0; double y0;
} cairo_matrix_t;
typedef struct _cairo_pattern cairo_pattern_t;
typedef enum cairo_status {
@ -668,8 +673,12 @@ cairo_get_miter_limit (cairo_t *cr);
/* XXX: How to do cairo_get_dash??? Do we want to switch to a cairo_dash object? */
cairo_matrix_t
cairo_get_matrix (cairo_t *cr);
/* XXX: cairo_current_matrix is deprecated in favor of cairo_get_matrix. */
void
cairo_get_matrix (cairo_t *cr, cairo_matrix_t *matrix);
cairo_current_matrix (cairo_t *cr, cairo_matrix_t *matrix);
/* XXX: Need to decide the memory management semantics of this
function. Should it reference the surface again? */
@ -970,51 +979,67 @@ cairo_pattern_get_filter (cairo_pattern_t *pattern);
/* Matrix functions */
/* XXX: Rename all of these to cairo_transform_t */
/* XXX: Deprecated. To be removed in favor of a structure of known size. */
cairo_matrix_t *
cairo_matrix_create (void);
/* XXX: Deprecated. To be removed in favor of a structure of known size. */
void
cairo_matrix_destroy (cairo_matrix_t *matrix);
cairo_status_t
/* XXX: Deprecated. To be removed in favor of direct assignment. */
void
cairo_matrix_copy (cairo_matrix_t *matrix, const cairo_matrix_t *other);
cairo_status_t
cairo_matrix_set_identity (cairo_matrix_t *matrix);
void
cairo_matrix_init (cairo_matrix_t *matrix,
double a, double b,
double c, double d,
double tx, double ty);
cairo_status_t
cairo_matrix_set_affine (cairo_matrix_t *matrix,
double a, double b,
double c, double d,
double tx, double ty);
void
cairo_matrix_init_identity (cairo_matrix_t *matrix);
cairo_status_t
void
cairo_matrix_init_translate (cairo_matrix_t *matrix,
double tx, double ty);
void
cairo_matrix_init_scale (cairo_matrix_t *matrix,
double sx, double sy);
void
cairo_matrix_init_rotate (cairo_matrix_t *matrix,
double radians);
/* XXX: Deprecated. To be removed in favor of direct access. */
void
cairo_matrix_get_affine (cairo_matrix_t *matrix,
double *a, double *b,
double *c, double *d,
double *tx, double *ty);
cairo_status_t
void
cairo_matrix_translate (cairo_matrix_t *matrix, double tx, double ty);
cairo_status_t
void
cairo_matrix_scale (cairo_matrix_t *matrix, double sx, double sy);
cairo_status_t
void
cairo_matrix_rotate (cairo_matrix_t *matrix, double radians);
cairo_status_t
cairo_matrix_invert (cairo_matrix_t *matrix);
cairo_status_t
cairo_matrix_multiply (cairo_matrix_t *result, const cairo_matrix_t *a, const cairo_matrix_t *b);
void
cairo_matrix_multiply (cairo_matrix_t *result,
const cairo_matrix_t *a,
const cairo_matrix_t *b);
cairo_status_t
void
cairo_matrix_transform_distance (cairo_matrix_t *matrix, double *dx, double *dy);
cairo_status_t
void
cairo_matrix_transform_point (cairo_matrix_t *matrix, double *x, double *y);
/**
@ -1068,6 +1093,8 @@ typedef cairo_status_t (*cairo_write_func_t) (void *closure,
#define cairo_init_clip cairo_init_clip_DEPRECATED_BY_cairo_reset_clip
#define cairo_surface_create_for_image cairo_surface_create_for_image_DEPRECATED_BY_cairo_image_surface_create_for_data
#define cairo_default_matrix cairo_default_matrix_DEPRECATED_BY_cairo_identity_matrix
#define cairo_matrix_set_affine cairo_matrix_set_affine_DEPRECTATED_BY_cairo_matrix_init
#define cairo_matrix_set_identity cairo_matrix_set_identity_DEPRECATED_BY_cairo_matrix_init_identity
#else /* CAIRO_API_SHAKEUP_FLAG_DAY */
@ -1085,7 +1112,6 @@ typedef cairo_status_t (*cairo_write_func_t) (void *closure,
#define cairo_current_line_cap cairo_get_line_cap
#define cairo_current_line_join cairo_get_line_join
#define cairo_current_miter_limit cairo_get_miter_limit
#define cairo_current_matrix cairo_get_matrix
#define cairo_current_target_surface cairo_get_target_surface
#define cairo_get_status cairo_status
#define cairo_get_status_string cairo_status_string
@ -1097,6 +1123,8 @@ typedef cairo_status_t (*cairo_write_func_t) (void *closure,
#define cairo_init_clip cairo_reset_clip
#define cairo_surface_create_for_image cairo_image_surface_create_for_data
#define cairo_default_matrix cairo_identity_matrix
#define cairo_matrix_set_affine cairo_matrix_init
#define cairo_matrix_set_identity cairo_matrix_init_identity
#endif /* CAIRO_API_SHAKEUP_FLAG_DAY */

View file

@ -630,10 +630,6 @@ typedef struct _cairo_surface_backend {
int num_glyphs);
} cairo_surface_backend_t;
struct _cairo_matrix {
double m[3][2];
};
typedef struct _cairo_format_masks {
int bpp;
unsigned long alpha_mask;
@ -956,8 +952,11 @@ _cairo_gstate_set_miter_limit (cairo_gstate_t *gstate, double limit);
cairo_private double
_cairo_gstate_get_miter_limit (cairo_gstate_t *gstate);
cairo_private cairo_matrix_t
_cairo_gstate_get_matrix (cairo_gstate_t *gstate);
cairo_private void
_cairo_gstate_get_matrix (cairo_gstate_t *gstate, cairo_matrix_t *matrix);
_cairo_gstate_current_matrix (cairo_gstate_t *gstate, cairo_matrix_t *matrix);
cairo_private cairo_status_t
_cairo_gstate_translate (cairo_gstate_t *gstate, double tx, double ty);
@ -1564,32 +1563,14 @@ _cairo_spline_fini (cairo_spline_t *spline);
/* cairo_matrix.c */
cairo_private void
_cairo_matrix_init (cairo_matrix_t *matrix);
cairo_private void
_cairo_matrix_fini (cairo_matrix_t *matrix);
cairo_private cairo_status_t
_cairo_matrix_set_translate (cairo_matrix_t *matrix,
double tx, double ty);
cairo_private cairo_status_t
_cairo_matrix_set_scale (cairo_matrix_t *matrix,
double sx, double sy);
cairo_private cairo_status_t
_cairo_matrix_set_rotate (cairo_matrix_t *matrix,
double angle);
cairo_private cairo_status_t
_cairo_matrix_transform_bounding_box (cairo_matrix_t *matrix,
double *x, double *y,
double *width, double *height);
cairo_private cairo_status_t
cairo_private void
_cairo_matrix_compute_determinant (cairo_matrix_t *matrix, double *det);
cairo_private cairo_status_t
cairo_private void
_cairo_matrix_compute_eigen_values (cairo_matrix_t *matrix, double *lambda1, double *lambda2);
cairo_private cairo_status_t
@ -1758,8 +1739,11 @@ slim_hidden_proto(cairo_matrix_copy)
slim_hidden_proto(cairo_matrix_invert)
slim_hidden_proto(cairo_matrix_multiply)
slim_hidden_proto(cairo_matrix_scale)
slim_hidden_proto(cairo_matrix_set_affine)
slim_hidden_proto(cairo_matrix_set_identity)
slim_hidden_proto(cairo_matrix_init)
slim_hidden_proto(cairo_matrix_init_identity)
slim_hidden_proto(cairo_matrix_init_translate)
slim_hidden_proto(cairo_matrix_init_scale)
slim_hidden_proto(cairo_matrix_init_rotate)
slim_hidden_proto(cairo_matrix_transform_distance)
slim_hidden_proto(cairo_matrix_transform_point)
slim_hidden_proto(cairo_move_to)

View file

@ -16,6 +16,7 @@ path-data
pixman-rotate
text-cache-crash
text-rotate
transforms
user-data
*-out.png
*-diff.png

View file

@ -13,6 +13,7 @@ path-data \
pixman-rotate \
text-cache-crash \
text-rotate \
transforms \
user-data
# And all new tests go here too. I really don't like having to repeat
@ -29,7 +30,8 @@ coverage-ref.png \
clip-twice-ref.png \
path-data-ref.png \
pixman-rotate-ref.png \
romedalen.png
romedalen.png \
transforms-ref.png
# Once we can draw the text-rotate.c test case correctly, we should
# create and add text-rotate-ref.png to the list of reference PNGs.
@ -86,6 +88,7 @@ path_data_LDADD = $(LDADDS)
pixman_rotate_LDADD = $(LDADDS)
text_cache_crash_LDADD = $(LDADDS)
text_rotate_LDADD = $(LDADDS)
transforms_LDADD = $(LDADDS)
user_data_LDADD = $(LDADDS)
noinst_PROGRAMS = imagediff

BIN
test/transforms-ref.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 302 B

111
test/transforms.c Normal file
View file

@ -0,0 +1,111 @@
/*
* Copyright © 2005 Red Hat, Inc.
*
* Permission to use, copy, modify, distribute, and sell this software
* and its documentation for any purpose is hereby granted without
* fee, provided that the above copyright notice appear in all copies
* and that both that copyright notice and this permission notice
* appear in supporting documentation, and that the name of
* Red Hat, Inc. not be used in advertising or publicity pertaining to
* distribution of the software without specific, written prior
* permission. Red Hat, Inc. makes no representations about the
* suitability of this software for any purpose. It is provided "as
* is" without express or implied warranty.
*
* RED HAT, INC. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS
* SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
* FITNESS, IN NO EVENT SHALL RED HAT, INC. BE LIABLE FOR ANY SPECIAL,
* INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
* RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
* OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR
* IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*
* Author: Carl Worth <cworth@cworth.org>
*/
#include "cairo-test.h"
#define WIDTH 45
#define HEIGHT 30
cairo_test_t test = {
"transforms",
"Test various transformations.",
WIDTH, HEIGHT
};
static void
draw_L_shape (cairo_t *cr)
{
cairo_move_to (cr, 0, 0);
cairo_rel_line_to (cr, 0, 10);
cairo_rel_line_to (cr, 5, 0);
cairo_save (cr);
cairo_default_matrix (cr);
cairo_set_line_width (cr, 2.0);
cairo_stroke (cr);
cairo_restore (cr);
}
static cairo_test_status_t
draw (cairo_t *cr, int width, int height)
{
cairo_translate (cr, 5, 5);
draw_L_shape (cr);
cairo_translate (cr, 10, 0);
cairo_save (cr);
{
cairo_scale (cr, 2, 2);
draw_L_shape (cr);
}
cairo_restore (cr);
cairo_translate (cr, 15, 0);
cairo_save (cr);
{
cairo_rotate (cr, M_PI / 2.0);
draw_L_shape (cr);
}
cairo_restore (cr);
cairo_translate (cr, 5, 0);
cairo_save (cr);
{
cairo_matrix_t skew_y = {
1, -1,
0, 1,
0, 0
};
cairo_transform (cr, &skew_y);
draw_L_shape (cr);
}
cairo_restore (cr);
cairo_translate (cr, 5, 10);
cairo_save (cr);
{
cairo_matrix_t skew_x = {
1.0, 0.0,
-0.5, 1.0,
0.0, 0.0
};
cairo_transform (cr, &skew_x);
draw_L_shape (cr);
}
cairo_restore (cr);
return CAIRO_TEST_SUCCESS;
}
int
main (void)
{
return cairo_test (&test, draw);
}