[cairo] Pixman sampling coordinates

Bertram Felgenhauer bertram.felgenhauer at googlemail.com
Wed Jan 23 09:27:14 PST 2008


Carl Worth wrote:
> On Tue, 22 Jan 2008 16:12:33 -0800, Carl Worth wrote:
> > just to reduce the amount of #ifdefing. But I am quite glad to see
> > that you added a comment there explaining why this adjustment isn't
> > necessary for the case of other values of N_BITS.
> >
> > I'll just do that in a separate commit after pushing this series.
> 
> I've pushed the series and I did that little change. So pixman should
> be all set as far as this bug now.

Nice.

I have a fix for the rotate-image-surface-paint testcase now.

It's basically what I proposed in the previous mail, but streamlined
slightly, so no new arguments to _cairo_matrix_to_pixman_matrix
are needed. It uses the origin of the pattern as the anchor.

    git-fetch git://people.freedesktop.org/~inte/cairo pixman-transform-rounding
    http://gitweb.freedesktop.org/?p=users/inte/cairo.git;a=shortlog;h=pixman-transform-rounding

This requires a trivial patch to pixman; the pixman_transform_point_3d
function wasn't properly exported.

    git-fetch git://people.freedesktop.org/~inte/pixman missing-export
    http://gitweb.freedesktop.org/?p=users/inte/pixman.git;a=shortlog;h=missing-export

Bertram
-------------- next part --------------
commit 5a0b15d2c9b5e9ef3aed1f01e8ea28a3f2c36216
Author: Bertram Felgenhauer <int-e at gmx.de>
Date:   Wed Jan 23 18:02:02 2008 +0100

    anchor pattern transformations at the pattern origin
    This keeps the rounding errors due to the conversion to 16.16 fixed point
    numbers small and improves cairo's translation invariance.

diff --git a/src/cairo-matrix.c b/src/cairo-matrix.c
index d534826..589566d 100644
--- a/src/cairo-matrix.c
+++ b/src/cairo-matrix.c
@@ -753,6 +753,10 @@ _cairo_matrix_to_pixman_matrix (const cairo_matrix_t	*matrix,
         *pixman_transform = pixman_identity_transform;
     }
     else {
+        cairo_matrix_t inv = *matrix;
+        double x = 0, y = 0;
+        pixman_vector_t vector;
+
         pixman_transform->matrix[0][0] = _cairo_fixed_16_16_from_double (matrix->xx);
         pixman_transform->matrix[0][1] = _cairo_fixed_16_16_from_double (matrix->xy);
         pixman_transform->matrix[0][2] = _cairo_fixed_16_16_from_double (matrix->x0);
@@ -764,5 +768,24 @@ _cairo_matrix_to_pixman_matrix (const cairo_matrix_t	*matrix,
         pixman_transform->matrix[2][0] = 0;
         pixman_transform->matrix[2][1] = 0;
         pixman_transform->matrix[2][2] = 1 << 16;
+
+        if (cairo_matrix_invert (&inv) != CAIRO_STATUS_SUCCESS)
+            return;
+
+        /* find the device space coordinate that maps to (0, 0) */
+        cairo_matrix_transform_point (&inv, &x, &y);
+
+        /* transform the resulting device space coordinate back
+         * to the pattern space, using pixman's transform */
+        vector.vector[0] = _cairo_fixed_16_16_from_double (x);
+        vector.vector[1] = _cairo_fixed_16_16_from_double (y);
+        vector.vector[2] = 1 << 16;
+
+        if (!pixman_transform_point_3d (pixman_transform, &vector))
+            return;
+
+        /* and compensate for the resulting error */
+        pixman_transform->matrix[0][2] -= vector.vector[0];
+        pixman_transform->matrix[1][2] -= vector.vector[1];
     }
 }
-------------- next part --------------
commit 787cc57c7cb36a3b7eff836dd979d08cf7861e29
Author: Bertram Felgenhauer <int-e at gmx.de>
Date:   Wed Jan 23 16:08:48 2008 +0100

    export pixman_transform_point_3d function

diff --git a/pixman/pixman.h b/pixman/pixman.h
index 2fd3133..2965acd 100644
--- a/pixman/pixman.h
+++ b/pixman/pixman.h
@@ -165,6 +165,7 @@ struct pixman_transform
     pixman_fixed_t	matrix[3][3];
 };
 
+PIXMAN_EXPORT
 pixman_bool_t pixman_transform_point_3d (pixman_transform_t *transform,
 					 pixman_vector_t    *vector);
 


More information about the cairo mailing list