third_party/cairo/src/cairo-pattern.c
void
_cairo_pattern_sampled_area (const cairo_pattern_t *pattern,
			     const cairo_rectangle_int_t *extents,
			     cairo_rectangle_int_t *sample)
{
    double x1, x2, y1, y2;
    double padx, pady;

    /* Assume filters are interpolating, which means identity
       cannot change the image */
    if (_cairo_matrix_is_identity (&pattern->matrix)) {
	*sample = *extents;
	return;
    }

    /* Transform the centers of the corner pixels */
    x1 = extents->x + 0.5;
    y1 = extents->y + 0.5;
    x2 = x1 + (extents->width - 1);
    y2 = y1 + (extents->height - 1);
    _cairo_matrix_transform_bounding_box (&pattern->matrix,
					  &x1, &y1, &x2, &y2,
					  NULL);

    /* How far away from center will it actually sample?
     * This is the distance from a transformed pixel center to the
     * furthest sample of reasonable size.
     */
    switch (pattern->filter) {
    case CAIRO_FILTER_NEAREST:
    case CAIRO_FILTER_FAST:
	/* Correct value is zero, but when the sample is on an integer
	 * it is unknown if the backend will sample the pixel to the
	 * left or right. This value makes it include both possible pixels.
	 */
	padx = pady = 0.004;
	break;
    case CAIRO_FILTER_BILINEAR:
    case CAIRO_FILTER_GAUSSIAN:
    default:
	/* Correct value is .5 */
	padx = pady = 0.495;
	break;
    case CAIRO_FILTER_GOOD:
	/* Correct value is max(width,1)*.5 */
	padx = _cairo_hypot (pattern->matrix.xx, pattern->matrix.xy);
	if (padx <= 1.0) padx = 0.495;
	else if (padx >= 16.0) padx = 7.92;
	else padx *= 0.495;
	pady = _cairo_hypot (pattern->matrix.yx, pattern->matrix.yy);
	if (pady <= 1.0) pady = 0.495;
	else if (pady >= 16.0) pady = 7.92;
	else pady *= 0.495;
	break;
    case CAIRO_FILTER_BEST:
	/* Correct value is width*2 */
	padx = _cairo_hypot (pattern->matrix.xx, pattern->matrix.xy) * 1.98;
	if (padx > 7.92) padx = 7.92;
	pady = _cairo_hypot (pattern->matrix.yx, pattern->matrix.yy) * 1.98;
	if (pady > 7.92) pady = 7.92;
	break;
    }

    /* round furthest samples to edge of pixels */
    x1 = floor (x1 - padx);
    if (x1 < CAIRO_RECT_INT_MIN) x1 = CAIRO_RECT_INT_MIN;
    sample->x = x1;

    y1 = floor (y1 - pady);
    if (y1 < CAIRO_RECT_INT_MIN) y1 = CAIRO_RECT_INT_MIN;
    sample->y = y1;

    x2 = floor (x2 + padx) + 1.0;
    if (x2 > CAIRO_RECT_INT_MAX) x2 = CAIRO_RECT_INT_MAX;
    sample->width = x2 - x1;

    y2 = floor (y2 + pady) + 1.0;
    if (y2 > CAIRO_RECT_INT_MAX) y2 = CAIRO_RECT_INT_MAX;
    sample->height = y2 - y1;
}
/**
 * _cairo_pattern_sampled_area:
 *
 * Return region of @pattern that will be sampled to fill @extents,
 * based on the transformation and filter.
 *
 * This does not include pixels that are mulitiplied by values very
 * close to zero by the ends of filters. This is so that transforms
 * that should be the identity or 90 degree rotations do not expand
 * the source unexpectedly.
 *
 * XXX: We don't actually have any way of querying the backend for
 *      the filter radius, so we just guess base on what we know that
 *      backends do currently (see bug #10508)
 **/
Return region of @pattern that will be sampled to fill @extents,
based on the transformation and filter.

This does not include pixels that are mulitiplied by values very
close to zero by the ends of filters. This is so that transforms
that should be the identity or 90 degree rotations do not expand
the source unexpectedly.

We don't actually have any way of querying the backend for
the filter radius, so we just guess base on what we know that
backends do currently
Return region of @pattern that will be sampled to fill @extents based on the transformation and filter . This does not include pixels that are mulitiplied by values very close to zero by the ends of filters . This is so that transforms that should be the identity or 90 degree rotations do not expand the source unexpectedly . We don ' t actually have any way of querying the backend for the filter radius so we just guess base on what we know that backends do currently
void
_cairo_pattern_sampled_area (const cairo_pattern_t *pattern,
			     const cairo_rectangle_int_t *extents,
			     cairo_rectangle_int_t *sample)
{
    double x1, x2, y1, y2;
    double padx, pady;
    if (_cairo_matrix_is_identity (&pattern->matrix)) {
	*sample = *extents;
	return;
    }
    x1 = extents->x + 0.5;
    y1 = extents->y + 0.5;
    x2 = x1 + (extents->width - 1);
    y2 = y1 + (extents->height - 1);
    _cairo_matrix_transform_bounding_box (&pattern->matrix,
					  &x1, &y1, &x2, &y2,
					  NULL);
    switch (pattern->filter) {
    case CAIRO_FILTER_NEAREST:
    case CAIRO_FILTER_FAST:
	padx = pady = 0.004;
	break;
    case CAIRO_FILTER_BILINEAR:
    case CAIRO_FILTER_GAUSSIAN:
    default:
	padx = pady = 0.495;
	break;
    case CAIRO_FILTER_GOOD:
	padx = _cairo_hypot (pattern->matrix.xx, pattern->matrix.xy);
	if (padx <= 1.0) padx = 0.495;
	else if (padx >= 16.0) padx = 7.92;
	else padx *= 0.495;
	pady = _cairo_hypot (pattern->matrix.yx, pattern->matrix.yy);
	if (pady <= 1.0) pady = 0.495;
	else if (pady >= 16.0) pady = 7.92;
	else pady *= 0.495;
	break;
    case CAIRO_FILTER_BEST:
	padx = _cairo_hypot (pattern->matrix.xx, pattern->matrix.xy) * 1.98;
	if (padx > 7.92) padx = 7.92;
	pady = _cairo_hypot (pattern->matrix.yx, pattern->matrix.yy) * 1.98;
	if (pady > 7.92) pady = 7.92;
	break;
    }
    x1 = floor (x1 - padx);
    if (x1 < CAIRO_RECT_INT_MIN) x1 = CAIRO_RECT_INT_MIN;
    sample->x = x1;
    y1 = floor (y1 - pady);
    if (y1 < CAIRO_RECT_INT_MIN) y1 = CAIRO_RECT_INT_MIN;
    sample->y = y1;
    x2 = floor (x2 + padx) + 1.0;
    if (x2 > CAIRO_RECT_INT_MAX) x2 = CAIRO_RECT_INT_MAX;
    sample->width = x2 - x1;
    y2 = floor (y2 + pady) + 1.0;
    if (y2 > CAIRO_RECT_INT_MAX) y2 = CAIRO_RECT_INT_MAX;
    sample->height = y2 - y1;
}
void _cairo_pattern_sampled_area ( const cairo_pattern_t * pattern , const cairo_rectangle_int_t * extents , cairo_rectangle_int_t * sample ) { double x1 , x2 , y1 , y2 ; double padx , pady ; if ( _cairo_matrix_is_identity ( & pattern -> matrix ) ) { * sample = * extents ; return ; } x1 = extents -> x + 0.5 ; y1 = extents -> y + 0.5 ; x2 = x1 + ( extents -> width - 1 ) ; y2 = y1 + ( extents -> height - 1 ) ; _cairo_matrix_transform_bounding_box ( & pattern -> matrix , & x1 , & y1 , & x2 , & y2 , NULL ) ; switch ( pattern -> filter ) { case CAIRO_FILTER_NEAREST : case CAIRO_FILTER_FAST : padx = pady = 0.004 ; break ; case CAIRO_FILTER_BILINEAR : case CAIRO_FILTER_GAUSSIAN : default : padx = pady = 0.495 ; break ; case CAIRO_FILTER_GOOD : padx = _cairo_hypot ( pattern -> matrix . xx , pattern -> matrix . xy ) ; if ( padx <= 1.0 ) padx = 0.495 ; else if ( padx >= 16.0 ) padx = 7.92 ; else padx *= 0.495 ; pady = _cairo_hypot ( pattern -> matrix . yx , pattern -> matrix . yy ) ; if ( pady <= 1.0 ) pady = 0.495 ; else if ( pady >= 16.0 ) pady = 7.92 ; else pady *= 0.495 ; break ; case CAIRO_FILTER_BEST : padx = _cairo_hypot ( pattern -> matrix . xx , pattern -> matrix . xy ) * 1.98 ; if ( padx > 7.92 ) padx = 7.92 ; pady = _cairo_hypot ( pattern -> matrix . yx , pattern -> matrix . yy ) * 1.98 ; if ( pady > 7.92 ) pady = 7.92 ; break ; } x1 = floor ( x1 - padx ) ; if ( x1 < CAIRO_RECT_INT_MIN ) x1 = CAIRO_RECT_INT_MIN ; sample -> x = x1 ; y1 = floor ( y1 - pady ) ; if ( y1 < CAIRO_RECT_INT_MIN ) y1 = CAIRO_RECT_INT_MIN ; sample -> y = y1 ; x2 = floor ( x2 + padx ) + 1.0 ; if ( x2 > CAIRO_RECT_INT_MAX ) x2 = CAIRO_RECT_INT_MAX ; sample -> width = x2 - x1 ; y2 = floor ( y2 + pady ) + 1.0 ; if ( y2 > CAIRO_RECT_INT_MAX ) y2 = CAIRO_RECT_INT_MAX ; sample -> height = y2 - y1 ; }
_cairo_pattern_sampled_area:
 Return region of @pattern that will be sampled to fill @extents,
 based on the transformation and filter.
_cairo_pattern_sampled_area : Return region of @pattern that will be sampled to fill @extents based on the transformation and filter .
/* Assume filters are interpolating, which means identity
       cannot change the image */ /* Transform the centers of the corner pixels */ /* How far away from center will it actually sample?
     * This is the distance from a transformed pixel center to the
     * furthest sample of reasonable size.
     */ /* Correct value is zero, but when the sample is on an integer
	 * it is unknown if the backend will sample the pixel to the
	 * left or right. This value makes it include both possible pixels.
	 */ /* Correct value is .5 */ /* Correct value is max(width,1)*.5 */ /* Correct value is width*2 */ /* round furthest samples to edge of pixels */