diff --git a/src/cairo-default-context.c b/src/cairo-default-context.c index 078135b2c..89642447a 100644 --- a/src/cairo-default-context.c +++ b/src/cairo-default-context.c @@ -189,9 +189,9 @@ _cairo_default_context_push_group (void *abstract_cr, cairo_content_t content) parent_surface->device_transform.x0 - extents.x, parent_surface->device_transform.y0 - extents.y); - _cairo_surface_set_device_scale (group_surface, - parent_surface->device_transform.xx, - parent_surface->device_transform.yy); + cairo_surface_set_device_scale (group_surface, + parent_surface->device_transform.xx, + parent_surface->device_transform.yy); /* If we have a current path, we need to adjust it to compensate for * the device offset just applied. */ diff --git a/src/cairo-paginated-surface.c b/src/cairo-paginated-surface.c index fe9ccee63..68e4e0e34 100644 --- a/src/cairo-paginated-surface.c +++ b/src/cairo-paginated-surface.c @@ -308,7 +308,7 @@ _paint_fallback_image (cairo_paginated_surface_t *surface, image = _cairo_paginated_surface_create_image_surface (surface, ceil (width * x_scale), ceil (height * y_scale)); - _cairo_surface_set_device_scale (image, x_scale, y_scale); + cairo_surface_set_device_scale (image, x_scale, y_scale); /* set_device_offset just sets the x0/y0 components of the matrix; * so we have to do the scaling manually. */ cairo_surface_set_device_offset (image, -x*x_scale, -y*y_scale); diff --git a/src/cairo-surface-subsurface.c b/src/cairo-surface-subsurface.c index 712c0fe9c..0efb96396 100644 --- a/src/cairo-surface-subsurface.c +++ b/src/cairo-surface-subsurface.c @@ -500,9 +500,9 @@ cairo_surface_create_for_rectangle (cairo_surface_t *target, surface->snapshot = NULL; - _cairo_surface_set_device_scale (&surface->base, - target->device_transform.xx, - target->device_transform.yy); + cairo_surface_set_device_scale (&surface->base, + target->device_transform.xx, + target->device_transform.yy); return &surface->base; } @@ -542,9 +542,9 @@ _cairo_surface_create_for_rectangle_int (cairo_surface_t *target, surface->snapshot = NULL; - _cairo_surface_set_device_scale (&surface->base, - target->device_transform.xx, - target->device_transform.yy); + cairo_surface_set_device_scale (&surface->base, + target->device_transform.xx, + target->device_transform.yy); return &surface->base; } diff --git a/src/cairo-surface.c b/src/cairo-surface.c index 79b2f2e30..f07a0f6ca 100644 --- a/src/cairo-surface.c +++ b/src/cairo-surface.c @@ -1624,26 +1624,28 @@ cairo_surface_mark_dirty_rectangle (cairo_surface_t *surface, slim_hidden_def (cairo_surface_mark_dirty_rectangle); /** - * _cairo_surface_set_device_scale: + * cairo_surface_set_device_scale: * @surface: a #cairo_surface_t * @sx: a scale factor in the X direction * @sy: a scale factor in the Y direction * - * Private function for setting an extra scale factor to affect all - * drawing to a surface. This is used, for example, when replaying a - * recording surface to an image fallback intended for an eventual - * vector-oriented backend. Since the recording surface will record - * coordinates in one backend space, but the image fallback uses a - * different backend space, (differing by the fallback resolution - * scale factors), we need a scale factor correction. + * Sets an scale that is multiplied to the device coordinates determined + * by the CTM when drawing to @surface. One common use for this is to + * render to very high resolution display devices at a scale factor, so + * that code that assumes 1 pixel will be a certain size will still work. + * Setting a transformation via cairo_translate() isn't + * sufficient to do this, since functions like + * cairo_device_to_user() will expose the hidden scale. * - * Caution: Not all places we use device transform correctly handle - * both a translate and a scale. An audit would be nice. + * Note that the scale affects drawing to the surface as well as + * using the surface in a source pattern. + * + * Since: 1.14 **/ void -_cairo_surface_set_device_scale (cairo_surface_t *surface, - double sx, - double sy) +cairo_surface_set_device_scale (cairo_surface_t *surface, + double sx, + double sy) { cairo_status_t status; @@ -1675,6 +1677,30 @@ _cairo_surface_set_device_scale (cairo_surface_t *surface, _cairo_observers_notify (&surface->device_transform_observers, surface); } +slim_hidden_def (cairo_surface_set_device_scale); + +/** + * cairo_surface_get_device_scale: + * @surface: a #cairo_surface_t + * @x_scale: the scale in the X direction, in device units + * @y_scale: the scale in the Y direction, in device units + * + * This function returns the previous device offset set by + * cairo_surface_set_device_scale(). + * + * Since: 1.14 + **/ +void +cairo_surface_get_device_scale (cairo_surface_t *surface, + double *x_scale, + double *y_scale) +{ + if (x_scale) + *x_scale = surface->device_transform.xx; + if (y_scale) + *y_scale = surface->device_transform.yy; +} +slim_hidden_def (cairo_surface_get_device_scale); /** * cairo_surface_set_device_offset: diff --git a/src/cairo.h b/src/cairo.h index a2f5aa37e..de3512619 100644 --- a/src/cairo.h +++ b/src/cairo.h @@ -2455,6 +2455,16 @@ cairo_surface_mark_dirty_rectangle (cairo_surface_t *surface, int width, int height); +cairo_public void +cairo_surface_set_device_scale (cairo_surface_t *surface, + double x_scale, + double y_scale); + +cairo_public void +cairo_surface_get_device_scale (cairo_surface_t *surface, + double *x_scale, + double *y_scale); + cairo_public void cairo_surface_set_device_offset (cairo_surface_t *surface, double x_offset, diff --git a/src/cairoint.h b/src/cairoint.h index 861e2f712..84e602648 100644 --- a/src/cairoint.h +++ b/src/cairoint.h @@ -1420,11 +1420,6 @@ cairo_private_no_warn cairo_bool_t _cairo_surface_get_extents (cairo_surface_t *surface, cairo_rectangle_int_t *extents); -cairo_private void -_cairo_surface_set_device_scale (cairo_surface_t *surface, - double sx, - double sy); - cairo_private cairo_bool_t _cairo_surface_has_device_transform (cairo_surface_t *surface) cairo_pure; @@ -1955,6 +1950,7 @@ slim_hidden_proto (cairo_surface_destroy); slim_hidden_proto (cairo_surface_finish); slim_hidden_proto (cairo_surface_flush); slim_hidden_proto (cairo_surface_get_device_offset); +slim_hidden_proto (cairo_surface_get_device_scale); slim_hidden_proto (cairo_surface_get_font_options); slim_hidden_proto (cairo_surface_get_mime_data); slim_hidden_proto (cairo_surface_has_show_text_glyphs); @@ -1962,6 +1958,7 @@ slim_hidden_proto (cairo_surface_mark_dirty); slim_hidden_proto (cairo_surface_mark_dirty_rectangle); slim_hidden_proto_no_warn (cairo_surface_reference); slim_hidden_proto (cairo_surface_set_device_offset); +slim_hidden_proto (cairo_surface_set_device_scale); slim_hidden_proto (cairo_surface_set_fallback_resolution); slim_hidden_proto (cairo_surface_set_mime_data); slim_hidden_proto (cairo_surface_show_page);