[gtk+/wip/window-scales: 81/84] GtkIconHelper: Add support for cairo_pattern_t
- From: Alexander Larsson <alexl src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gtk+/wip/window-scales: 81/84] GtkIconHelper: Add support for cairo_pattern_t
- Date: Wed, 26 Jun 2013 15:11:42 +0000 (UTC)
commit 428e94ceefa46fda34937b730d1a59f229abd50c
Author: Alexander Larsson <alexl redhat com>
Date: Wed Jun 26 16:33:15 2013 +0200
GtkIconHelper: Add support for cairo_pattern_t
gtk/gtkiconhelper.c | 116 +++++++++++++++++++++++++++++++++++++++++++++++++-
gtk/gtkimage.h | 5 ++-
2 files changed, 117 insertions(+), 4 deletions(-)
---
diff --git a/gtk/gtkiconhelper.c b/gtk/gtkiconhelper.c
index 40ab0a5..ad07621 100644
--- a/gtk/gtkiconhelper.c
+++ b/gtk/gtkiconhelper.c
@@ -36,6 +36,7 @@ struct _GtkIconHelperPrivate {
GtkIconSet *icon_set;
gchar *icon_name;
gchar *stock_id;
+ cairo_pattern_t *orig_pattern;
GtkIconSize icon_size;
gint pixel_size;
@@ -62,6 +63,12 @@ _gtk_icon_helper_clear (GtkIconHelper *self)
g_clear_object (&self->priv->rendered_pixbuf);
g_clear_object (&self->priv->window);
+ if (self->priv->orig_pattern)
+ {
+ cairo_pattern_destroy (self->priv->orig_pattern);
+ self->priv->orig_pattern = NULL;
+ }
+
if (self->priv->rendered_pattern)
{
cairo_pattern_destroy (self->priv->rendered_pattern);
@@ -134,6 +141,7 @@ _gtk_icon_helper_init (GtkIconHelper *self)
self->priv->icon_size = GTK_ICON_SIZE_INVALID;
self->priv->pixel_size = -1;
self->priv->last_rendered_state = GTK_STATE_FLAG_NORMAL;
+ self->priv->orig_pixbuf_scale = 1;
}
static void
@@ -314,6 +322,63 @@ ensure_pixbuf_for_icon_set (GtkIconHelper *self,
}
static void
+get_pattern_size (GtkIconHelper *self,
+ GtkStyleContext *context,
+ cairo_pattern_t *pattern,
+ int *width,
+ int *height)
+{
+ cairo_surface_t *surface;
+
+ if(!cairo_pattern_get_surface (self->priv->rendered_pattern,
+ &surface) &&
+ cairo_surface_get_type (surface) == CAIRO_SURFACE_TYPE_IMAGE)
+ {
+ cairo_matrix_t matrix;
+
+ /* Assume any set scaling is icon scale */
+ cairo_pattern_get_matrix (self->priv->rendered_pattern, &matrix);
+ *width =
+ ceil (cairo_image_surface_get_width (surface) / matrix.xx);
+ *height =
+ ceil (cairo_image_surface_get_height (surface) / matrix.yy);
+ }
+ else
+ ensure_icon_size (self, context, width, height);
+}
+
+static void
+ensure_pixbuf_from_pattern (GtkIconHelper *self,
+ GtkStyleContext *context)
+{
+ cairo_surface_t *surface;
+ gint width, height;
+ cairo_t *cr;
+
+
+ if (!check_invalidate_pixbuf (self, context))
+ return;
+
+ if (self->priv->rendered_pixbuf)
+ return;
+
+ get_pattern_size (self, context, self->priv->orig_pattern, &width, &height);
+
+ surface = cairo_image_surface_create (CAIRO_FORMAT_ARGB32,
+ width, height);
+
+ cr = cairo_create (surface);
+ cairo_set_source (cr, self->priv->orig_pattern);
+ cairo_paint (cr);
+ cairo_destroy (cr);
+
+ self->priv->rendered_pixbuf =
+ gdk_pixbuf_get_from_surface (surface, 0, 0, width, height);
+
+ cairo_surface_destroy (surface);
+}
+
+static void
ensure_pixbuf_at_size (GtkIconHelper *self,
GtkStyleContext *context)
{
@@ -368,6 +433,10 @@ _gtk_icon_helper_ensure_pixbuf (GtkIconHelper *self,
switch (self->priv->storage_type)
{
+ case GTK_IMAGE_PATTERN:
+ ensure_pixbuf_from_pattern (self, context);
+ break;
+
case GTK_IMAGE_PIXBUF:
ensure_pixbuf_at_size (self, context);
break;
@@ -447,8 +516,26 @@ check_invalidate_pattern (GtkIconHelper *self,
}
static void
-ensure_pattern_at_size (GtkIconHelper *self,
- GtkStyleContext *context)
+ensure_pattern_from_pattern (GtkIconHelper *self,
+ GtkStyleContext *context)
+{
+ if (!check_invalidate_pattern (self, context))
+ return;
+
+ if (self->priv->rendered_pattern)
+ return;
+
+ self->priv->rendered_pattern =
+ cairo_pattern_reference (self->priv->orig_pattern);
+
+ get_pattern_size (self, context, self->priv->orig_pattern,
+ &self->priv->rendered_pattern_width,
+ &self->priv->rendered_pattern_height);
+}
+
+static void
+ensure_pattern_from_pixbuf (GtkIconHelper *self,
+ GtkStyleContext *context)
{
gint width, height;
GdkPixbuf *pixbuf;
@@ -656,8 +743,12 @@ _gtk_icon_helper_ensure_pattern (GtkIconHelper *self,
switch (self->priv->storage_type)
{
+ case GTK_IMAGE_PATTERN:
+ ensure_pattern_from_pattern (self, context);
+ break;
+
case GTK_IMAGE_PIXBUF:
- ensure_pattern_at_size (self, context);
+ ensure_pattern_from_pixbuf (self, context);
break;
case GTK_IMAGE_STOCK:
@@ -799,6 +890,19 @@ _gtk_icon_helper_set_animation (GtkIconHelper *self,
}
void
+_gtk_icon_helper_set_pattern (GtkIconHelper *self,
+ cairo_pattern_t *pattern)
+{
+ _gtk_icon_helper_clear (self);
+
+ if (pattern != NULL)
+ {
+ self->priv->storage_type = GTK_IMAGE_PATTERN;
+ self->priv->orig_pattern = cairo_pattern_reference (pattern);
+ }
+}
+
+void
_gtk_icon_helper_set_stock_id (GtkIconHelper *self,
const gchar *stock_id,
GtkIconSize icon_size)
@@ -895,6 +999,12 @@ _gtk_icon_helper_peek_icon_set (GtkIconHelper *self)
return self->priv->icon_set;
}
+cairo_pattern_t *
+_gtk_icon_helper_peek_pattern (GtkIconHelper *self)
+{
+ return self->priv->orig_pattern;
+}
+
const gchar *
_gtk_icon_helper_get_stock_id (GtkIconHelper *self)
{
diff --git a/gtk/gtkimage.h b/gtk/gtkimage.h
index 4174f5a..66d586e 100644
--- a/gtk/gtkimage.h
+++ b/gtk/gtkimage.h
@@ -60,6 +60,8 @@ typedef struct _GtkImageClass GtkImageClass;
* This image type was added in GTK+ 2.6
* @GTK_IMAGE_GICON: the widget contains a #GIcon.
* This image type was added in GTK+ 2.14
+ * @GTK_IMAGE_PATTERN: the widget contains a #cairo_pattern_t.
+ * This image type was added in GTK+ 3.10
*
* Describes the image data representation used by a #GtkImage. If you
* want to get the image from the widget, you can only get the
@@ -77,7 +79,8 @@ typedef enum
GTK_IMAGE_ICON_SET,
GTK_IMAGE_ANIMATION,
GTK_IMAGE_ICON_NAME,
- GTK_IMAGE_GICON
+ GTK_IMAGE_GICON,
+ GTK_IMAGE_PATTERN
} GtkImageType;
/**
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]