From 40f8eca926b3b72be804b2ed45ea629108327de0 Mon Sep 17 00:00:00 2001 From: Owen W. Taylor Date: Mon, 7 Apr 2008 16:05:18 -0400 Subject: [PATCH] Fix acquiring outside of source bounds Restrict the area we acquire from the source image to the bounds of the source image, even when we have an identity matrix. (Fixes regression from changes from #15349) --- src/cairo-pattern.c | 41 ++++++++++++++++++++++------------------- 1 files changed, 22 insertions(+), 19 deletions(-) diff --git a/src/cairo-pattern.c b/src/cairo-pattern.c index 097fc39..3d975f0 100644 --- a/src/cairo-pattern.c +++ b/src/cairo-pattern.c @@ -1675,6 +1675,7 @@ _cairo_pattern_acquire_surface_for_surface (cairo_surface_pattern_t *pattern, else { cairo_rectangle_int_t extents; + cairo_rectangle_int_t sampled_area; status = _cairo_surface_get_extents (pattern->surface, &extents); if (status) return status; @@ -1684,16 +1685,18 @@ _cairo_pattern_acquire_surface_for_surface (cairo_surface_pattern_t *pattern, * This is relied on in the svg backend. */ if (attr->extend == CAIRO_EXTEND_REPEAT || (width == (unsigned int) -1 && height == (unsigned int) -1)) { - x = extents.x; - y = extents.y; - width = extents.width; - height = extents.height; + sampled_area = extents; } else { /* Otherwise, we first transform the rectangle to the * coordinate space of the source surface so that we can * clone only that portion of the surface that will be * read. */ - if (! _cairo_matrix_is_identity (&attr->matrix)) { + if (_cairo_matrix_is_identity (&attr->matrix)) { + sampled_area.x = x; + sampled_area.y = y; + sampled_area.width = width; + sampled_area.height = height; + } else { double x1 = x; double y1 = y; double x2 = x + width; @@ -1704,27 +1707,27 @@ _cairo_pattern_acquire_surface_for_surface (cairo_surface_pattern_t *pattern, &x1, &y1, &x2, &y2, &is_tight); - /* The transform_bounding_box call may have resulted - * in a region larger than the surface, but we never - * want to clone more than the surface itself, (we - * know we're not repeating at this point due to the - * above. - * - * XXX: The one padding here is to account for filter + /* XXX: The one padding here is to account for filter * radius. It's a workaround right now, until we get a * proper fix. (see bug #10508) */ - x = MAX (0, floor (x1) - 1); - y = MAX (0, floor (y1) - 1); - width = MIN (extents.width, ceil (x2) + 1) - x; - height = MIN (extents.height, ceil (y2) + 1) - y; + sampled_area.x = floor (x1) - 1; + sampled_area.y = floor (y1) - 1; + sampled_area.width = ceil (x2) + 1 - sampled_area.x; + sampled_area.height = ceil (y2) + 1 - sampled_area.y; } - x += tx; - y += ty; + sampled_area.x += tx; + sampled_area.y += ty; + + /* Never acquire a larger area than the source itself + */ + _cairo_rectangle_intersect(&sampled_area, &extents); } status = _cairo_surface_clone_similar (dst, pattern->surface, - x, y, width, height, out); + sampled_area.x, sampled_area.y, + sampled_area.width, sampled_area.height, + out); } return status; -- 1.5.4.5