[cairo-commit] 3 commits - src/cairo-pdf-surface.c
src/cairo-ps-surface.c test/.gitignore test/Makefile.am
test/surface-pattern.c test/surface-pattern-scale-down.c
test/surface-pattern-scale-down-pdf-argb32-ref.png
test/surface-pattern-scale-down-ps-argb32-ref.png
test/surface-pattern-scale-down-ref.png
test/surface-pattern-scale-up.c
test/surface-pattern-scale-up-pdf-argb32-ref.png
test/surface-pattern-scale-up-ps-argb32-ref.png
test/surface-pattern-scale-up-ref.png
Behdad Esfahbod
behdad at kemper.freedesktop.org
Tue Feb 27 16:31:44 PST 2007
src/cairo-pdf-surface.c | 36 ++++-------
src/cairo-ps-surface.c | 43 ++++++++-----
test/.gitignore | 2
test/Makefile.am | 2
test/surface-pattern-scale-down-pdf-argb32-ref.png |binary
test/surface-pattern-scale-down-ps-argb32-ref.png |binary
test/surface-pattern-scale-down-ref.png |binary
test/surface-pattern-scale-down.c | 68 +++++++++++++++++++++
test/surface-pattern-scale-up-pdf-argb32-ref.png |binary
test/surface-pattern-scale-up-ps-argb32-ref.png |binary
test/surface-pattern-scale-up-ref.png |binary
test/surface-pattern-scale-up.c | 68 +++++++++++++++++++++
test/surface-pattern.c | 3
13 files changed, 184 insertions(+), 38 deletions(-)
New commits:
diff-tree 153465bfe5346b9e1ebdbd4f794bd11868ee7458 (from e2ce27db302a185e6e80ead699c01e43921939ca)
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Tue Feb 27 19:28:37 2007 -0500
[test] Add ref images for new tests
diff --git a/test/surface-pattern-scale-down-pdf-argb32-ref.png b/test/surface-pattern-scale-down-pdf-argb32-ref.png
new file mode 100644
index 0000000..9f27687
Binary files /dev/null and b/test/surface-pattern-scale-down-pdf-argb32-ref.png differ
diff --git a/test/surface-pattern-scale-down-ps-argb32-ref.png b/test/surface-pattern-scale-down-ps-argb32-ref.png
new file mode 100644
index 0000000..1f0b3e0
Binary files /dev/null and b/test/surface-pattern-scale-down-ps-argb32-ref.png differ
diff --git a/test/surface-pattern-scale-down-ref.png b/test/surface-pattern-scale-down-ref.png
new file mode 100644
index 0000000..b7255ef
Binary files /dev/null and b/test/surface-pattern-scale-down-ref.png differ
diff --git a/test/surface-pattern-scale-down.c b/test/surface-pattern-scale-down.c
index db5b861..314f852 100644
--- a/test/surface-pattern-scale-down.c
+++ b/test/surface-pattern-scale-down.c
@@ -21,8 +21,7 @@ draw (cairo_t *cr, int width, int height
int surface_size = 300;
cairo_set_source_rgb (cr, 0, 0, 0);
- cairo_rectangle (cr, 0, 0, SIZE, SIZE);
- cairo_fill (cr);
+ cairo_paint (cr);
/* Create an image surface with my favorite four colors in each
* quadrant. */
diff --git a/test/surface-pattern-scale-up-pdf-argb32-ref.png b/test/surface-pattern-scale-up-pdf-argb32-ref.png
new file mode 100644
index 0000000..c277a0f
Binary files /dev/null and b/test/surface-pattern-scale-up-pdf-argb32-ref.png differ
diff --git a/test/surface-pattern-scale-up-ps-argb32-ref.png b/test/surface-pattern-scale-up-ps-argb32-ref.png
new file mode 100644
index 0000000..dc9f8d2
Binary files /dev/null and b/test/surface-pattern-scale-up-ps-argb32-ref.png differ
diff --git a/test/surface-pattern-scale-up-ref.png b/test/surface-pattern-scale-up-ref.png
new file mode 100644
index 0000000..32d7bdf
Binary files /dev/null and b/test/surface-pattern-scale-up-ref.png differ
diff --git a/test/surface-pattern-scale-up.c b/test/surface-pattern-scale-up.c
index 921e1a3..d1f0e41 100644
--- a/test/surface-pattern-scale-up.c
+++ b/test/surface-pattern-scale-up.c
@@ -21,8 +21,7 @@ draw (cairo_t *cr, int width, int height
int surface_size = 6;
cairo_set_source_rgb (cr, 0, 0, 0);
- cairo_rectangle (cr, 0, 0, SIZE, SIZE);
- cairo_fill (cr);
+ cairo_paint (cr);
/* Create an image surface with my favorite four colors in each
* quadrant. */
diff --git a/test/surface-pattern.c b/test/surface-pattern.c
index 42aca27..51b638d 100644
--- a/test/surface-pattern.c
+++ b/test/surface-pattern.c
@@ -21,8 +21,7 @@ draw (cairo_t *cr, int width, int height
int surface_size = 6;
cairo_set_source_rgb (cr, 0, 0, 0);
- cairo_rectangle (cr, 0, 0, SIZE, SIZE);
- cairo_fill (cr);
+ cairo_paint (cr);
/* Create an image surface with my favorite four colors in each
* quadrant. */
diff-tree e2ce27db302a185e6e80ead699c01e43921939ca (from de0a6522b00822305fa5a0e32c4821628425ebdc)
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Tue Feb 27 18:47:47 2007 -0500
[PS/PDF] Fix xstep/ystep values for CAIRO_EXTEND_NONE
This fixes the fallback-resolution test, as well as the two of
surface-pattern-scale-up and surface-pattern-scale-down.
diff --git a/src/cairo-pdf-surface.c b/src/cairo-pdf-surface.c
index 3b8830d..938a4f0 100644
--- a/src/cairo-pdf-surface.c
+++ b/src/cairo-pdf-surface.c
@@ -878,7 +878,7 @@ emit_surface_pattern (cairo_pdf_surface_
cairo_pdf_resource_t alpha, image_resource = {0}; /* squelch bogus compiler warning */
cairo_matrix_t cairo_p2d, pdf_p2d;
cairo_extend_t extend = cairo_pattern_get_extend (&pattern->base);
- int xstep, ystep;
+ double xstep, ystep;
cairo_rectangle_int16_t surface_extents;
/* XXX: Should do something clever here for PDF source surfaces ? */
@@ -905,36 +905,30 @@ emit_surface_pattern (cairo_pdf_surface_
switch (extend) {
case CAIRO_EXTEND_NONE:
{
- /* In PDF, (as far as I can tell), all patterns are
+ /* In PS/PDF, (as far as I can tell), all patterns are
* repeating. So we support cairo's EXTEND_NONE semantics
* by setting the repeat step size to a size large enough
* to guarantee that no more than a single occurrence will
* be visible.
*
- * First, map the pattern's extents through the inverse
- * pattern matrix to compute the device-space bounds of
- * the desired single occurrence. Then consider the bounds
- * of (the union of this rectangle with the target surface
- * extents). If the repeat size is larger than the
- * diagonal of the bounds of the union, then it is
- * guaranteed to never repeat visibly.
+ * First, map the surface extents into pattern space (since
+ * xstep and ystep are in pattern space). Then use an upper
+ * bound on the length of the diagonal of the pattern image
+ * and the surface as repeat size. This guarantees to never
+ * repeat visibly.
*/
double x1 = 0.0, y1 = 0.0;
- double x2 = image->width, y2 = image->height;
- cairo_matrix_t surface_to_device = pattern->base.matrix;
- cairo_matrix_invert (&surface_to_device);
- _cairo_matrix_transform_bounding_box (&surface_to_device,
+ double x2 = surface->width, y2 = surface->height;
+ _cairo_matrix_transform_bounding_box (&pattern->base.matrix,
&x1, &y1, &x2, &y2,
NULL);
+
/* Rather than computing precise bounds of the union, just
* add the surface extents unconditionally. We only
* required an answer that's large enough, we don't really
- * care if it's not as tight as possible. */
- x1 = MAX (fabs(x1), fabs(x2)) + surface_extents.width;
- y1 = MAX (fabs(y1), fabs(y2)) + surface_extents.height;
- /* Similarly, don't bother computing the square root to
- * determine the length of the final diagonal. */
- xstep = ystep = _cairo_lround (ceil (x1 + y1));
+ * care if it's not as tight as possible.*/
+ xstep = ystep = ceil ((x2 - x1) + (y2 - y1) +
+ image->width + image->height);
}
break;
case CAIRO_EXTEND_REPEAT:
@@ -991,8 +985,8 @@ emit_surface_pattern (cairo_pdf_surface_
stream = _cairo_pdf_surface_open_stream (surface,
FALSE,
" /BBox [0 0 %d %d]\r\n"
- " /XStep %d\r\n"
- " /YStep %d\r\n"
+ " /XStep %f\r\n"
+ " /YStep %f\r\n"
" /PatternType 1\r\n"
" /TilingType 1\r\n"
" /PaintType 1\r\n"
diff --git a/src/cairo-ps-surface.c b/src/cairo-ps-surface.c
index b55900c..ac07395 100644
--- a/src/cairo-ps-surface.c
+++ b/src/cairo-ps-surface.c
@@ -1704,7 +1704,7 @@ emit_surface_pattern (cairo_ps_surface_t
cairo_surface_pattern_t *pattern)
{
double bbox_width, bbox_height;
- int xstep, ystep;
+ double xstep, ystep;
cairo_matrix_t inverse = pattern->base.matrix;
cairo_matrix_invert (&inverse);
@@ -1732,22 +1732,35 @@ emit_surface_pattern (cairo_ps_surface_t
bbox_width = image->width;
bbox_height = image->height;
- /* In PostScript, (as far as I can tell), all patterns are
- * repeating. So we support cairo's EXTEND_NONE semantics by
- * setting the repeat step size to the larger of the image size
- * and the extents of the destination surface. That way we
- * guarantee the pattern will not repeat.
- */
switch (pattern->base.extend) {
case CAIRO_EXTEND_NONE:
- /* XXX We may need to update this to something like the code
- * that is in PDF. The point is, xstep/ystep are in pattern
- * space, not device space, so surface->width/height do not
- * make much sense. But most of the time patterns scale up,
- * not down, so this is less of a problem. */
- xstep = MAX (image->width, surface->width);
- ystep = MAX (image->height, surface->height);
+ {
+ /* In PS/PDF, (as far as I can tell), all patterns are
+ * repeating. So we support cairo's EXTEND_NONE semantics
+ * by setting the repeat step size to a size large enough
+ * to guarantee that no more than a single occurrence will
+ * be visible.
+ *
+ * First, map the surface extents into pattern space (since
+ * xstep and ystep are in pattern space). Then use an upper
+ * bound on the length of the diagonal of the pattern image
+ * and the surface as repeat size. This guarantees to never
+ * repeat visibly.
+ */
+ double x1 = 0.0, y1 = 0.0;
+ double x2 = surface->width, y2 = surface->height;
+ _cairo_matrix_transform_bounding_box (&pattern->base.matrix,
+ &x1, &y1, &x2, &y2,
+ NULL);
+
+ /* Rather than computing precise bounds of the union, just
+ * add the surface extents unconditionally. We only
+ * required an answer that's large enough, we don't really
+ * care if it's not as tight as possible.*/
+ xstep = ystep = ceil ((x2 - x1) + (y2 - y1) +
+ image->width + image->height);
break;
+ }
case CAIRO_EXTEND_REPEAT:
case CAIRO_EXTEND_REFLECT:
xstep = image->width;
@@ -1773,7 +1786,7 @@ emit_surface_pattern (cairo_ps_surface_t
" /BBox [0 0 %f %f]\n",
bbox_width, bbox_height);
_cairo_output_stream_printf (surface->stream,
- " /XStep %d /YStep %d\n",
+ " /XStep %f /YStep %f\n",
xstep, ystep);
_cairo_output_stream_printf (surface->stream,
" /PaintProc { MyPattern } bind\n"
diff-tree de0a6522b00822305fa5a0e32c4821628425ebdc (from 4c1d788219ae62bb9e8a7723d5a73d70eb42e69a)
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Tue Feb 27 17:33:17 2007 -0500
[test] Add tests that show xstep/ystep failures in PS/PDF backends
with surface patterns. One test scaled the pattern up, another scales
down. We observe that both PS and PDF are broken when scaling down.
This is the reason that PDF is failing in the fallback-resolution test
too.
diff --git a/test/.gitignore b/test/.gitignore
index 6918015..7cbb8bc 100644
--- a/test/.gitignore
+++ b/test/.gitignore
@@ -123,6 +123,8 @@ source-clip-scale
source-surface-scale-paint
surface-finish-twice
surface-pattern
+surface-pattern-scale-down
+surface-pattern-scale-up
text-antialias-gray
text-antialias-none
text-antialias-subpixel
diff --git a/test/Makefile.am b/test/Makefile.am
index 162f607..1d1a796 100644
--- a/test/Makefile.am
+++ b/test/Makefile.am
@@ -89,6 +89,8 @@ source-clip-scale \
source-surface-scale-paint \
surface-finish-twice \
surface-pattern \
+surface-pattern-scale-down \
+surface-pattern-scale-up \
text-antialias-gray \
text-antialias-none \
text-antialias-subpixel \
diff --git a/test/surface-pattern-scale-down.c b/test/surface-pattern-scale-down.c
new file mode 100644
index 0000000..db5b861
--- /dev/null
+++ b/test/surface-pattern-scale-down.c
@@ -0,0 +1,69 @@
+#include <math.h>
+#include "cairo-test.h"
+#include <stdio.h>
+
+#define SIZE 200
+
+static cairo_test_draw_function_t draw;
+
+cairo_test_t test = {
+ "surface-pattern-scale-down",
+ "Test scaled-down transformed not-repeated surface patterns",
+ SIZE, SIZE,
+ draw
+};
+
+static cairo_test_status_t
+draw (cairo_t *cr, int width, int height)
+{
+ cairo_surface_t *surface;
+ cairo_t * cr_surface;
+ int surface_size = 300;
+
+ cairo_set_source_rgb (cr, 0, 0, 0);
+ cairo_rectangle (cr, 0, 0, SIZE, SIZE);
+ cairo_fill (cr);
+
+ /* Create an image surface with my favorite four colors in each
+ * quadrant. */
+ surface = cairo_image_surface_create (CAIRO_FORMAT_RGB24,
+ surface_size, surface_size);
+ cr_surface = cairo_create (surface);
+ cairo_set_source_rgb (cr_surface, 1, 1, 1);
+ cairo_rectangle (cr_surface,
+ 0, 0,
+ surface_size / 2, surface_size / 2);
+ cairo_fill (cr_surface);
+ cairo_set_source_rgb (cr_surface, 1, 0, 0);
+ cairo_rectangle (cr_surface,
+ surface_size / 2, 0,
+ surface_size / 2, surface_size / 2);
+ cairo_fill (cr_surface);
+ cairo_set_source_rgb (cr_surface, 0, 1, 0);
+ cairo_rectangle (cr_surface,
+ 0, surface_size / 2,
+ surface_size / 2, surface_size / 2);
+ cairo_fill (cr_surface);
+ cairo_set_source_rgb (cr_surface, 0, 0, 1);
+ cairo_rectangle (cr_surface,
+ surface_size / 2, surface_size / 2,
+ surface_size / 2, surface_size / 2);
+ cairo_fill (cr_surface);
+ cairo_destroy (cr_surface);
+
+ cairo_scale (cr, 0.2, 0.2);
+ cairo_rotate (cr, 1.);
+ cairo_set_source_surface (cr, surface, 225, -225);
+ cairo_surface_destroy (surface);
+
+ cairo_pattern_set_extend (cairo_get_source (cr), CAIRO_EXTEND_NONE);
+ cairo_paint (cr);
+
+ return CAIRO_TEST_SUCCESS;
+}
+
+int
+main (void)
+{
+ return cairo_test (&test);
+}
diff --git a/test/surface-pattern-scale-up.c b/test/surface-pattern-scale-up.c
new file mode 100644
index 0000000..921e1a3
--- /dev/null
+++ b/test/surface-pattern-scale-up.c
@@ -0,0 +1,69 @@
+#include <math.h>
+#include "cairo-test.h"
+#include <stdio.h>
+
+#define SIZE 100
+
+static cairo_test_draw_function_t draw;
+
+cairo_test_t test = {
+ "surface-pattern-scale-up",
+ "Test scaled-up transformed not-repeated surface patterns",
+ SIZE, SIZE,
+ draw
+};
+
+static cairo_test_status_t
+draw (cairo_t *cr, int width, int height)
+{
+ cairo_surface_t *surface;
+ cairo_t * cr_surface;
+ int surface_size = 6;
+
+ cairo_set_source_rgb (cr, 0, 0, 0);
+ cairo_rectangle (cr, 0, 0, SIZE, SIZE);
+ cairo_fill (cr);
+
+ /* Create an image surface with my favorite four colors in each
+ * quadrant. */
+ surface = cairo_image_surface_create (CAIRO_FORMAT_RGB24,
+ surface_size, surface_size);
+ cr_surface = cairo_create (surface);
+ cairo_set_source_rgb (cr_surface, 1, 1, 1);
+ cairo_rectangle (cr_surface,
+ 0, 0,
+ surface_size / 2, surface_size / 2);
+ cairo_fill (cr_surface);
+ cairo_set_source_rgb (cr_surface, 1, 0, 0);
+ cairo_rectangle (cr_surface,
+ surface_size / 2, 0,
+ surface_size / 2, surface_size / 2);
+ cairo_fill (cr_surface);
+ cairo_set_source_rgb (cr_surface, 0, 1, 0);
+ cairo_rectangle (cr_surface,
+ 0, surface_size / 2,
+ surface_size / 2, surface_size / 2);
+ cairo_fill (cr_surface);
+ cairo_set_source_rgb (cr_surface, 0, 0, 1);
+ cairo_rectangle (cr_surface,
+ surface_size / 2, surface_size / 2,
+ surface_size / 2, surface_size / 2);
+ cairo_fill (cr_surface);
+ cairo_destroy (cr_surface);
+
+ cairo_scale (cr, 10, 10);
+ cairo_rotate (cr, 1.);
+ cairo_set_source_surface (cr, surface, 4, -4.5);
+ cairo_surface_destroy (surface);
+
+ cairo_pattern_set_extend (cairo_get_source (cr), CAIRO_EXTEND_NONE);
+ cairo_paint (cr);
+
+ return CAIRO_TEST_SUCCESS;
+}
+
+int
+main (void)
+{
+ return cairo_test (&test);
+}
More information about the cairo-commit
mailing list