From 8217b2f74c9db38d7a64ce41eeb6c9659aae1ceb Mon Sep 17 00:00:00 2001 From: Krzysztof Kosi??ski Date: Mon, 12 Jul 2010 21:57:46 +0200 Subject: Gaussian blur (bzr r9508.1.15) --- src/display/cairo-utils.cpp | 72 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 72 insertions(+) (limited to 'src/display/cairo-utils.cpp') diff --git a/src/display/cairo-utils.cpp b/src/display/cairo-utils.cpp index bb401dc87..a063a62bb 100644 --- a/src/display/cairo-utils.cpp +++ b/src/display/cairo-utils.cpp @@ -329,6 +329,78 @@ ink_cairo_set_source_argb32_pixbuf(cairo_t *ct, GdkPixbuf *pb, double x, double cairo_surface_destroy(pbs); } +/** @brief Create an exact copy of a surface. + * Creates a surface that has the same type, content type, dimensions and contents + * as the specified surface. */ +cairo_surface_t * +ink_cairo_surface_copy(cairo_surface_t *s) +{ + cairo_surface_t *ns = ink_cairo_surface_create_identical(s); + + cairo_t *ct = cairo_create(ns); + cairo_set_source_surface(ct, s, 0, 0); + cairo_set_operator(ct, CAIRO_OPERATOR_SOURCE); + cairo_paint(ct); + cairo_destroy(ct); + + return ns; +} + +/** @brief Create a surface that differs only in pixel content. + * Creates a surface that has the same type, content type and dimensions + * as the specified surface. Pixel contents are not copied. */ +cairo_surface_t * +ink_cairo_surface_create_identical(cairo_surface_t *s) +{ + cairo_surface_t *ns = cairo_surface_create_similar(s, cairo_surface_get_content(s), + ink_cairo_surface_get_width(s), ink_cairo_surface_get_height(s)); + return ns; +} + +/** @brief Extract the alpha channel into a new surface. + * Creates a surface with a content type of CAIRO_CONTENT_ALPHA that contains + * the alpha values of pixels from @a s. */ +cairo_surface_t * +ink_cairo_extract_alpha(cairo_surface_t *s) +{ + cairo_surface_t *alpha = cairo_surface_create_similar(s, CAIRO_CONTENT_ALPHA, + ink_cairo_surface_get_width(s), ink_cairo_surface_get_height(s)); + + cairo_t *ct = cairo_create(alpha); + cairo_set_source_surface(ct, s, 0, 0); + cairo_set_operator(ct, CAIRO_OPERATOR_SOURCE); + cairo_paint(ct); + cairo_destroy(ct); + + return alpha; +} + +cairo_surface_t * +ink_cairo_surface_unshare(cairo_surface_t *s) +{ + if (cairo_surface_get_reference_count(s) > 1) { + return ink_cairo_surface_copy(s); + } else { + cairo_surface_reference(s); + return s; + } +} + +int +ink_cairo_surface_get_width(cairo_surface_t *surface) +{ + // For now only image surface is handled. + // Later add others, e.g. cairo-gl + assert(cairo_surface_get_type(surface) == CAIRO_SURFACE_TYPE_IMAGE); + return cairo_image_surface_get_width(surface); +} +int +ink_cairo_surface_get_height(cairo_surface_t *surface) +{ + assert(cairo_surface_get_type(surface) == CAIRO_SURFACE_TYPE_IMAGE); + return cairo_image_surface_get_height(surface); +} + // taken from Cairo sources static inline guint32 premul_alpha(guint32 color, guint32 alpha) { -- cgit v1.2.3