[gtk+/wip/window-scales] gtk: Use cairo surfaces rather than patterns for icons



commit 17e8846bf903f932a9ea886ec85c7e719d5c3af4
Author: Alexander Larsson <alexl redhat com>
Date:   Tue Jul 2 22:28:06 2013 +0200

    gtk: Use cairo surfaces rather than patterns for icons
    
    cairo_pattern_t were used because they also support scaling
    via the pattern matrix. However, patterns are not a great fit
    for icons as they are potentially unbounded (i.e. for gradients).
    So we switch to surfaces, using the device_scale for scaling.

 gtk/gtkcellrendererpixbuf.c |   24 +++---
 gtk/gtkfilechooserbutton.c  |  121 ++++++-----------------
 gtk/gtkfilechooserbutton.ui |    4 +-
 gtk/gtkfilechooserdefault.c |   19 +---
 gtk/gtkiconfactory.c        |   21 ++---
 gtk/gtkiconhelper.c         |  230 ++++++++++++++++++++-----------------------
 gtk/gtkiconhelperprivate.h  |    6 +-
 gtk/gtkimage.c              |   54 +++++-----
 gtk/gtkimage.h              |   10 +-
 gtk/gtkpathbar.c            |   58 ++++-------
 gtk/gtkstylecontext.c       |   16 ++--
 gtk/gtkstylecontext.h       |    4 +-
 gtk/gtkthemingengine.c      |   14 +--
 gtk/gtkthemingengine.h      |    6 +-
 14 files changed, 239 insertions(+), 348 deletions(-)
---
diff --git a/gtk/gtkcellrendererpixbuf.c b/gtk/gtkcellrendererpixbuf.c
index 22c9991..e6a8f53 100644
--- a/gtk/gtkcellrendererpixbuf.c
+++ b/gtk/gtkcellrendererpixbuf.c
@@ -75,7 +75,7 @@ enum {
   PROP_PIXBUF,
   PROP_PIXBUF_EXPANDER_OPEN,
   PROP_PIXBUF_EXPANDER_CLOSED,
-  PROP_PATTERN,
+  PROP_SURFACE,
   PROP_STOCK_ID,
   PROP_STOCK_SIZE,
   PROP_STOCK_DETAIL,
@@ -171,11 +171,11 @@ gtk_cell_renderer_pixbuf_class_init (GtkCellRendererPixbufClass *class)
                                                        GDK_TYPE_PIXBUF,
                                                        GTK_PARAM_READWRITE));
   g_object_class_install_property (object_class,
-                                  PROP_PATTERN,
-                                  g_param_spec_boxed ("pattern",
-                                                      P_("pattern"),
-                                                      P_("The pattern to render"),
-                                                      CAIRO_GOBJECT_TYPE_PATTERN,
+                                  PROP_SURFACE,
+                                  g_param_spec_boxed ("surface",
+                                                      P_("surface"),
+                                                      P_("The surface to render"),
+                                                      CAIRO_GOBJECT_TYPE_SURFACE,
                                                       GTK_PARAM_READWRITE));
 
   /**
@@ -288,8 +288,8 @@ gtk_cell_renderer_pixbuf_get_property (GObject        *object,
     case PROP_PIXBUF_EXPANDER_CLOSED:
       g_value_set_object (value, priv->pixbuf_expander_closed);
       break;
-    case PROP_PATTERN:
-      g_value_set_boxed (value, _gtk_icon_helper_peek_pattern (priv->icon_helper));
+    case PROP_SURFACE:
+      g_value_set_boxed (value, _gtk_icon_helper_peek_surface (priv->icon_helper));
       break;
     case PROP_STOCK_ID:
       g_value_set_string (value, _gtk_icon_helper_get_stock_id (priv->icon_helper));
@@ -323,8 +323,8 @@ gtk_cell_renderer_pixbuf_reset (GtkCellRendererPixbuf *cellpixbuf)
 
   switch (storage_type)
     {
-    case GTK_IMAGE_PATTERN:
-      g_object_notify (G_OBJECT (cellpixbuf), "pattern");
+    case GTK_IMAGE_SURFACE:
+      g_object_notify (G_OBJECT (cellpixbuf), "surface");
       break;
     case GTK_IMAGE_PIXBUF:
       g_object_notify (G_OBJECT (cellpixbuf), "pixbuf");
@@ -371,9 +371,9 @@ gtk_cell_renderer_pixbuf_set_property (GObject      *object,
         g_object_unref (priv->pixbuf_expander_closed);
       priv->pixbuf_expander_closed = (GdkPixbuf*) g_value_dup_object (value);
       break;
-    case PROP_PATTERN:
+    case PROP_SURFACE:
       gtk_cell_renderer_pixbuf_reset (cellpixbuf);
-      _gtk_icon_helper_set_pattern (priv->icon_helper, g_value_get_boxed (value));
+      _gtk_icon_helper_set_surface (priv->icon_helper, g_value_get_boxed (value));
       break;
     case PROP_STOCK_ID:
       gtk_cell_renderer_pixbuf_reset (cellpixbuf);
diff --git a/gtk/gtkfilechooserbutton.c b/gtk/gtkfilechooserbutton.c
index a32c47f..c69870e 100644
--- a/gtk/gtkfilechooserbutton.c
+++ b/gtk/gtkfilechooserbutton.c
@@ -1321,7 +1321,6 @@ change_icon_theme_get_info_cb (GCancellable *cancellable,
                               gpointer      user_data)
 {
   gboolean cancelled = g_cancellable_is_cancelled (cancellable);
-  cairo_pattern_t *pattern = NULL;
   cairo_surface_t *surface;
   struct ChangeIconThemeData *data = user_data;
 
@@ -1335,13 +1334,8 @@ change_icon_theme_get_info_cb (GCancellable *cancellable,
     goto out;
 
   surface = _gtk_file_info_render_icon (info, GTK_WIDGET (data->button), data->button->priv->icon_size);
-  if (surface)
-    {
-      pattern = cairo_pattern_create_for_surface (surface);
-      cairo_surface_destroy (surface);
-    }
 
-  if (pattern)
+  if (surface)
     {
       gint width = 0;
       GtkTreeIter iter;
@@ -1356,14 +1350,14 @@ change_icon_theme_get_info_cb (GCancellable *cancellable,
           gtk_tree_path_free (path);
 
           gtk_list_store_set (GTK_LIST_STORE (data->button->priv->model), &iter,
-                             ICON_COLUMN, pattern,
+                             ICON_COLUMN, surface,
                              -1);
 
           g_object_set (data->button->priv->icon_cell,
                        "width", width,
                        NULL);
         }
-      cairo_pattern_destroy (pattern);
+      cairo_surface_destroy (surface);
     }
 
 out:
@@ -1405,7 +1399,6 @@ change_icon_theme (GtkFileChooserButton *button)
   do
     {
       cairo_surface_t *surface = NULL;
-      cairo_pattern_t *pattern = NULL;
       gchar type;
       gpointer data;
 
@@ -1442,7 +1435,7 @@ change_icon_theme (GtkFileChooserButton *button)
                                               info);
                  button->priv->change_icon_theme_cancellables =
                    g_slist_append (button->priv->change_icon_theme_cancellables, cancellable);
-                 pattern = NULL;
+                 surface = NULL;
                }
              else
                 {
@@ -1456,8 +1449,6 @@ change_icon_theme (GtkFileChooserButton *button)
                                                          gtk_widget_get_scale_factor (GTK_WIDGET (button)),
                                                          gtk_widget_get_window (GTK_WIDGET (button)),
                                                          0, NULL);
-                  pattern = cairo_pattern_create_for_surface (surface);
-                  cairo_surface_destroy (surface);
                 }
            }
          break;
@@ -1468,11 +1459,6 @@ change_icon_theme (GtkFileChooserButton *button)
                                                              GTK_WIDGET (button),
                                                              priv->icon_size,
                                                              NULL);
-              if (surface)
-                {
-                  pattern = cairo_pattern_create_for_surface (surface);
-                  cairo_surface_destroy (surface);
-                }
             }
 
          break;
@@ -1481,15 +1467,15 @@ change_icon_theme (GtkFileChooserButton *button)
          break;
        }
 
-      if (pattern)
+      if (surface)
        width = MAX (width, priv->icon_size);
 
       gtk_list_store_set (GTK_LIST_STORE (priv->model), &iter,
-                         ICON_COLUMN, pattern,
+                         ICON_COLUMN, surface,
                          -1);
 
-      if (pattern)
-       cairo_pattern_destroy (pattern);
+      if (surface)
+       cairo_surface_destroy (surface);
     }
   while (gtk_tree_model_iter_next (priv->model, &iter));
 
@@ -1548,7 +1534,6 @@ set_info_get_info_cb (GCancellable *cancellable,
                      gpointer      callback_data)
 {
   gboolean cancelled = g_cancellable_is_cancelled (cancellable);
-  cairo_pattern_t *pattern = NULL;
   cairo_surface_t *surface;
   GtkTreePath *path;
   GtkTreeIter iter;
@@ -1584,11 +1569,6 @@ set_info_get_info_cb (GCancellable *cancellable,
     goto out;
 
   surface = _gtk_file_info_render_icon (info, GTK_WIDGET (data->button), data->button->priv->icon_size);
-  if (surface)
-    {
-      pattern = cairo_pattern_create_for_surface (surface);
-      cairo_surface_destroy (surface);
-    }
 
   if (!data->label)
     data->label = g_strdup (g_file_info_get_display_name (info));
@@ -1596,13 +1576,13 @@ set_info_get_info_cb (GCancellable *cancellable,
   is_folder = _gtk_file_info_consider_as_directory (info);
 
   gtk_list_store_set (GTK_LIST_STORE (data->button->priv->model), &iter,
-                     ICON_COLUMN, pattern,
+                     ICON_COLUMN, surface,
                      DISPLAY_NAME_COLUMN, data->label,
                      IS_FOLDER_COLUMN, is_folder,
                      -1);
 
-  if (pattern)
-    cairo_pattern_destroy (pattern);
+  if (surface)
+    cairo_surface_destroy (surface);
 
 out:
   g_object_unref (data->button);
@@ -1744,7 +1724,6 @@ model_add_special_get_info_cb (GCancellable *cancellable,
   gboolean cancelled = g_cancellable_is_cancelled (cancellable);
   GtkTreeIter iter;
   GtkTreePath *path;
-  cairo_pattern_t *pattern = NULL;
   cairo_surface_t *surface;
   GCancellable *model_cancellable = NULL;
   struct ChangeIconThemeData *data = user_data;
@@ -1778,16 +1757,10 @@ model_add_special_get_info_cb (GCancellable *cancellable,
   surface = _gtk_file_info_render_icon (info, GTK_WIDGET (data->button), data->button->priv->icon_size);
   if (surface)
     {
-      pattern = cairo_pattern_create_for_surface (surface);
-      cairo_surface_destroy (surface);
-    }
-
-  if (pattern)
-    {
       gtk_list_store_set (GTK_LIST_STORE (data->button->priv->model), &iter,
-                         ICON_COLUMN, pattern,
+                         ICON_COLUMN, surface,
                          -1);
-      cairo_pattern_destroy (pattern);
+      cairo_surface_destroy (surface);
     }
 
   gtk_tree_model_get (data->button->priv->model, &iter,
@@ -1915,7 +1888,6 @@ model_add_volumes (GtkFileChooserButton *button,
     {
       GtkFileSystemVolume *volume;
       GtkTreeIter iter;
-      cairo_pattern_t *pattern = NULL;
       cairo_surface_t *surface;
       gchar *display_name;
 
@@ -1945,24 +1917,19 @@ model_add_volumes (GtkFileChooserButton *button,
                                                      GTK_WIDGET (button),
                                                      button->priv->icon_size,
                                                      NULL);
-      if (surface)
-        {
-          pattern = cairo_pattern_create_for_surface (surface);
-          cairo_surface_destroy (surface);
-        }
       display_name = _gtk_file_system_volume_get_display_name (volume);
 
       gtk_list_store_insert (store, &iter, pos);
       gtk_list_store_set (store, &iter,
-                          ICON_COLUMN, pattern,
+                          ICON_COLUMN, surface,
                           DISPLAY_NAME_COLUMN, display_name,
                           TYPE_COLUMN, ROW_TYPE_VOLUME,
                           DATA_COLUMN, _gtk_file_system_volume_ref (volume),
                           IS_FOLDER_COLUMN, TRUE,
                           -1);
 
-      if (pattern)
-        cairo_pattern_destroy (pattern);
+      if (surface)
+        cairo_surface_destroy (surface);
       g_free (display_name);
 
       button->priv->n_volumes++;
@@ -2011,7 +1978,6 @@ model_add_bookmarks (GtkFileChooserButton *button,
        {
          gchar *label;
          GtkIconTheme *icon_theme;
-         cairo_pattern_t *pattern = NULL;
          cairo_surface_t *surface = NULL;
 
          if (local_only)
@@ -2032,12 +1998,10 @@ model_add_bookmarks (GtkFileChooserButton *button,
                                                 gtk_widget_get_scale_factor (GTK_WIDGET (button)),
                                                 gtk_widget_get_window (GTK_WIDGET (button)),
                                                 0, NULL);
-          pattern = cairo_pattern_create_for_surface (surface);
-          cairo_surface_destroy (surface);
 
          gtk_list_store_insert (store, &iter, pos);
          gtk_list_store_set (store, &iter,
-                             ICON_COLUMN, pattern,
+                             ICON_COLUMN, surface,
                              DISPLAY_NAME_COLUMN, label,
                              TYPE_COLUMN, ROW_TYPE_BOOKMARK,
                              DATA_COLUMN, g_object_ref (file),
@@ -2045,8 +2009,8 @@ model_add_bookmarks (GtkFileChooserButton *button,
                              -1);
 
          g_free (label);
-         if (pattern)
-           cairo_pattern_destroy (pattern);
+         if (surface)
+           cairo_surface_destroy (surface);
        }
 
       button->priv->n_bookmarks++;
@@ -2124,7 +2088,6 @@ model_update_current_folder (GtkFileChooserButton *button,
     {
       gchar *label;
       GtkIconTheme *icon_theme;
-      cairo_pattern_t *pattern = NULL;
       cairo_surface_t *surface;
 
       /* Don't call get_info for remote paths to avoid latency and
@@ -2150,14 +2113,9 @@ model_update_current_folder (GtkFileChooserButton *button,
                                                 gtk_widget_get_scale_factor (GTK_WIDGET (button)),
                                                 gtk_widget_get_window (GTK_WIDGET (button)),
                                                 0, NULL);
-      if (surface)
-        {
-          pattern = cairo_pattern_create_for_surface (surface);
-          cairo_surface_destroy (surface);
-        }
 
       gtk_list_store_set (store, &iter,
-                         ICON_COLUMN, pattern,
+                         ICON_COLUMN, surface,
                          DISPLAY_NAME_COLUMN, label,
                          TYPE_COLUMN, ROW_TYPE_CURRENT_FOLDER,
                          DATA_COLUMN, g_object_ref (file),
@@ -2165,8 +2123,8 @@ model_update_current_folder (GtkFileChooserButton *button,
                          -1);
 
       g_free (label);
-      if (pattern)
-       cairo_pattern_destroy (pattern);
+      if (surface)
+       cairo_surface_destroy (surface);
     }
 }
 
@@ -2502,7 +2460,6 @@ update_label_get_info_cb (GCancellable *cancellable,
                          gpointer      data)
 {
   gboolean cancelled = g_cancellable_is_cancelled (cancellable);
-  cairo_pattern_t *pattern = NULL;
   cairo_surface_t *surface;
   GtkFileChooserButton *button = data;
   GtkFileChooserButtonPrivate *priv = button->priv;
@@ -2518,15 +2475,9 @@ update_label_get_info_cb (GCancellable *cancellable,
   gtk_label_set_text (GTK_LABEL (priv->label), g_file_info_get_display_name (info));
 
   surface = _gtk_file_info_render_icon (info, GTK_WIDGET (priv->image), priv->icon_size);
+  gtk_image_set_from_surface (GTK_IMAGE (priv->image), surface);
   if (surface)
-    {
-      pattern = cairo_pattern_create_for_surface (surface);
-      cairo_surface_destroy (surface);
-    }
-
-  gtk_image_set_from_pattern (GTK_IMAGE (priv->image), pattern);
-  if (pattern)
-    cairo_pattern_destroy (pattern);
+    cairo_surface_destroy (surface);
 
 out:
   emit_selection_changed_if_changing_selection (button);
@@ -2566,7 +2517,6 @@ update_label_and_image (GtkFileChooserButton *button)
           base_file = _gtk_file_system_volume_get_root (volume);
           if (base_file && g_file_equal (base_file, file))
             {
-              cairo_pattern_t *pattern = NULL;
               cairo_surface_t *surface;
 
               label_text = _gtk_file_system_volume_get_display_name (volume);
@@ -2574,15 +2524,9 @@ update_label_and_image (GtkFileChooserButton *button)
                                                             GTK_WIDGET (button),
                                                             priv->icon_size,
                                                             NULL);
+              gtk_image_set_from_surface (GTK_IMAGE (priv->image), surface);
               if (surface)
-                {
-                  pattern = cairo_pattern_create_for_surface (surface);
-                  cairo_surface_destroy (surface);
-                }
-
-              gtk_image_set_from_pattern (GTK_IMAGE (priv->image), pattern);
-              if (pattern)
-                cairo_pattern_destroy (pattern);
+                cairo_surface_destroy (surface);
             }
 
           if (base_file)
@@ -2607,7 +2551,6 @@ update_label_and_image (GtkFileChooserButton *button)
         }
       else
         {
-          cairo_pattern_t *pattern = NULL;
           cairo_surface_t *surface;
 
           label_text = _gtk_bookmarks_manager_get_bookmark_label (button->priv->bookmarks_manager, file);
@@ -2617,15 +2560,9 @@ update_label_and_image (GtkFileChooserButton *button)
                                                 gtk_widget_get_scale_factor (GTK_WIDGET (button)),
                                                 gtk_widget_get_window (GTK_WIDGET (button)),
                                                 0, NULL);
+          gtk_image_set_from_surface (GTK_IMAGE (priv->image), surface);
           if (surface)
-            {
-              pattern = cairo_pattern_create_for_surface (surface);
-              cairo_surface_destroy (surface);
-            }
-
-          gtk_image_set_from_pattern (GTK_IMAGE (priv->image), pattern);
-          if (pattern)
-            cairo_pattern_destroy (pattern);
+            cairo_surface_destroy (surface);
 
          done_changing_selection = TRUE;
         }
@@ -2649,7 +2586,7 @@ out:
   else
     {
       gtk_label_set_text (GTK_LABEL (priv->label), _(FALLBACK_DISPLAY_NAME));
-      gtk_image_set_from_pattern (GTK_IMAGE (priv->image), NULL);
+      gtk_image_set_from_surface (GTK_IMAGE (priv->image), NULL);
     }
 
   if (done_changing_selection)
diff --git a/gtk/gtkfilechooserbutton.ui b/gtk/gtkfilechooserbutton.ui
index 03ad204..4004dcc 100644
--- a/gtk/gtkfilechooserbutton.ui
+++ b/gtk/gtkfilechooserbutton.ui
@@ -84,7 +84,7 @@
         <child>
           <object class="GtkCellRendererPixbuf" id="icon_cell"/>
           <attributes>
-            <attribute name="pattern">0</attribute>
+            <attribute name="surface">0</attribute>
           </attributes>
         </child>
         <child>
@@ -104,7 +104,7 @@
   <object class="GtkListStore" id="model">
     <columns>
       <!-- column-name icon -->
-      <column type="CairoPattern"/>
+      <column type="CairoSurface"/>
       <!-- column-name display-name -->
       <column type="gchararray"/>
       <!-- column-name type -->
diff --git a/gtk/gtkfilechooserdefault.c b/gtk/gtkfilechooserdefault.c
index faa605f..d1e4cea 100644
--- a/gtk/gtkfilechooserdefault.c
+++ b/gtk/gtkfilechooserdefault.c
@@ -365,7 +365,7 @@ enum {
   MODEL_COL_NAME_COLLATED,
   MODEL_COL_IS_FOLDER,
   MODEL_COL_IS_SENSITIVE,
-  MODEL_COL_PATTERN,
+  MODEL_COL_SURFACE,
   MODEL_COL_SIZE_TEXT,
   MODEL_COL_MTIME_TEXT,
   MODEL_COL_ELLIPSIZE,
@@ -382,7 +382,7 @@ enum {
        G_TYPE_STRING,            /* MODEL_COL_NAME_COLLATED */ \
        G_TYPE_BOOLEAN,           /* MODEL_COL_IS_FOLDER */     \
        G_TYPE_BOOLEAN,           /* MODEL_COL_IS_SENSITIVE */  \
-       CAIRO_GOBJECT_TYPE_PATTERN,  /* MODEL_COL_PATTERN */    \
+       CAIRO_GOBJECT_TYPE_SURFACE,  /* MODEL_COL_SURFACE */    \
        G_TYPE_STRING,            /* MODEL_COL_SIZE_TEXT */     \
        G_TYPE_STRING,            /* MODEL_COL_MTIME_TEXT */    \
        PANGO_TYPE_ELLIPSIZE_MODE /* MODEL_COL_ELLIPSIZE */
@@ -3133,7 +3133,7 @@ change_icon_theme (GtkFileChooserDefault *impl)
   set_icon_cell_renderer_fixed_size (impl);
 
   if (priv->browse_files_model)
-    _gtk_file_system_model_clear_cache (priv->browse_files_model, MODEL_COL_PATTERN);
+    _gtk_file_system_model_clear_cache (priv->browse_files_model, MODEL_COL_SURFACE);
   gtk_widget_queue_resize (priv->browse_files_tree_view);
 
   profile_end ("end", NULL);
@@ -4153,19 +4153,12 @@ file_system_model_set (GtkFileSystemModel *model,
       else
         g_value_set_boolean (value, TRUE);
       break;
-    case MODEL_COL_PATTERN:
+    case MODEL_COL_SURFACE:
       if (info)
         {
           if (g_file_info_has_attribute (info, G_FILE_ATTRIBUTE_STANDARD_ICON))
             {
-             cairo_pattern_t *pattern = NULL;
-             cairo_surface_t *surface = _gtk_file_info_render_icon (info, GTK_WIDGET (impl), 
priv->icon_size);
-             if (surface)
-               {
-                 pattern = cairo_pattern_create_for_surface (surface);
-                 cairo_surface_destroy (surface);
-               }
-              g_value_take_boxed (value, pattern);
+              g_value_take_boxed (value, _gtk_file_info_render_icon (info, GTK_WIDGET (impl), 
priv->icon_size));
             }
           else
             {
@@ -7077,7 +7070,7 @@ update_cell_renderer_attributes (GtkFileChooserDefault *impl)
       if (GTK_IS_CELL_RENDERER_PIXBUF (renderer))
         {
           gtk_tree_view_column_set_attributes (column, renderer, 
-                                               "pattern", MODEL_COL_PATTERN,
+                                               "surface", MODEL_COL_SURFACE,
                                                NULL);
         }
       else
diff --git a/gtk/gtkiconfactory.c b/gtk/gtkiconfactory.c
index 7fcb777..ab65682 100644
--- a/gtk/gtkiconfactory.c
+++ b/gtk/gtkiconfactory.c
@@ -1582,7 +1582,7 @@ gtk_icon_set_render_icon_pixbuf (GtkIconSet        *icon_set,
 }
 
 /**
- * gtk_icon_set_render_icon_pattern:
+ * gtk_icon_set_render_icon_surface:
  * @icon_set: a #GtkIconSet
  * @context: a #GtkStyleContext
  * @size: (type int): icon size. A size of (GtkIconSize)-1
@@ -1591,18 +1591,18 @@ gtk_icon_set_render_icon_pixbuf (GtkIconSet        *icon_set,
  * @for_window: (allow-none): #GdkWindow to optimize drawing for, or %NULL
  *
  * Renders an icon using gtk_render_icon_pixbuf() and converts it to a
- * cairo pattern. 
+ * cairo surface. 
  *
  * This function never returns %NULL; if the icon can't be rendered
  * (perhaps because an image file fails to load), a default "missing
  * image" icon will be returned instead.
  *
- * Return value: (transfer full): a #cairo_pattern_t to be displayed
+ * Return value: (transfer full): a #cairo_surface_t to be displayed
  *
  * Since: 3.10
  */
-cairo_pattern_t *
-gtk_icon_set_render_icon_pattern  (GtkIconSet      *icon_set,
+cairo_surface_t *
+gtk_icon_set_render_icon_surface  (GtkIconSet      *icon_set,
                                   GtkStyleContext *context,
                                   GtkIconSize      size,
                                   gint             scale,
@@ -1610,20 +1610,13 @@ gtk_icon_set_render_icon_pattern  (GtkIconSet      *icon_set,
 {
   GdkPixbuf *pixbuf;
   cairo_surface_t *surface;
-  cairo_pattern_t *pattern;
-  cairo_matrix_t matrix;
 
   pixbuf = gtk_icon_set_render_icon_pixbuf_for_scale (icon_set, context, size, scale);
 
-  surface = gdk_cairo_surface_create_from_pixbuf (pixbuf, 1, for_window);
+  surface = gdk_cairo_surface_create_from_pixbuf (pixbuf, scale, for_window);
   g_object_unref (pixbuf);
-  pattern = cairo_pattern_create_for_surface (surface);
-  cairo_surface_destroy (surface);
 
-  cairo_matrix_init_scale (&matrix, scale, scale);
-  cairo_pattern_set_matrix (pattern, &matrix);
-
-  return pattern;
+  return surface;
 }
 
 /**
diff --git a/gtk/gtkiconhelper.c b/gtk/gtkiconhelper.c
index 99af81d..56cb97c 100644
--- a/gtk/gtkiconhelper.c
+++ b/gtk/gtkiconhelper.c
@@ -36,7 +36,7 @@ struct _GtkIconHelperPrivate {
   GtkIconSet *icon_set;
   gchar *icon_name;
   gchar *stock_id;
-  cairo_pattern_t *orig_pattern;
+  cairo_surface_t *orig_surface;
 
   GtkIconSize icon_size;
   gint pixel_size;
@@ -47,11 +47,11 @@ struct _GtkIconHelperPrivate {
   GdkPixbuf *rendered_pixbuf;
   GtkStateFlags last_rendered_state;
 
-  cairo_pattern_t *rendered_pattern;
-  gint rendered_pattern_width;
-  gint rendered_pattern_height;
-  GtkStateFlags last_pattern_state;
-  gint last_pattern_scale;
+  cairo_surface_t *rendered_surface;
+  gint rendered_surface_width;
+  gint rendered_surface_height;
+  GtkStateFlags last_surface_state;
+  gint last_surface_scale;
 };
 
 void
@@ -63,16 +63,16 @@ _gtk_icon_helper_clear (GtkIconHelper *self)
   g_clear_object (&self->priv->rendered_pixbuf);
   g_clear_object (&self->priv->window);
 
-  if (self->priv->orig_pattern)
+  if (self->priv->orig_surface)
     {
-      cairo_pattern_destroy (self->priv->orig_pattern);
-      self->priv->orig_pattern = NULL;
+      cairo_surface_destroy (self->priv->orig_surface);
+      self->priv->orig_surface = NULL;
     }
 
-  if (self->priv->rendered_pattern)
+  if (self->priv->rendered_surface)
     {
-      cairo_pattern_destroy (self->priv->rendered_pattern);
-      self->priv->rendered_pattern = NULL;
+      cairo_surface_destroy (self->priv->rendered_surface);
+      self->priv->rendered_surface = NULL;
     }
 
   if (self->priv->icon_set != NULL)
@@ -92,8 +92,8 @@ _gtk_icon_helper_clear (GtkIconHelper *self)
   self->priv->storage_type = GTK_IMAGE_EMPTY;
   self->priv->icon_size = GTK_ICON_SIZE_INVALID;
   self->priv->last_rendered_state = GTK_STATE_FLAG_NORMAL;
-  self->priv->last_pattern_state = GTK_STATE_FLAG_NORMAL;
-  self->priv->last_pattern_scale = 0;
+  self->priv->last_surface_state = GTK_STATE_FLAG_NORMAL;
+  self->priv->last_surface_scale = 0;
 }
 
 void
@@ -325,33 +325,34 @@ ensure_pixbuf_for_icon_set (GtkIconHelper *self,
 }
 
 static void
-get_pattern_size (GtkIconHelper   *self,
+get_surface_size (GtkIconHelper   *self,
                  GtkStyleContext *context,
-                 cairo_pattern_t *pattern,
+                 cairo_surface_t *surface,
                  int *width,
                  int *height)
 {
-  cairo_surface_t *surface;
+  double x_scale, y_scale;
 
-  if(!cairo_pattern_get_surface (self->priv->rendered_pattern,
-                                &surface) &&
-     cairo_surface_get_type (surface) == CAIRO_SURFACE_TYPE_IMAGE)
+  if (cairo_surface_get_type (surface) == CAIRO_SURFACE_TYPE_IMAGE)
     {
-      cairo_matrix_t matrix;
+      x_scale = y_scale = 1;
+
+#ifdef HAVE_CAIRO_SURFACE_SET_DEVICE_SCALE
+      cairo_surface_get_device_scale (surface, &x_scale, &y_scale);
+#endif
 
       /* 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);
+       ceil (cairo_image_surface_get_width (surface) / x_scale);
       *height =
-       ceil (cairo_image_surface_get_height (surface) / matrix.yy);
+       ceil (cairo_image_surface_get_height (surface) / y_scale);
     }
   else
     ensure_icon_size (self, context, width, height);
 }
 
 static void
-ensure_pixbuf_from_pattern (GtkIconHelper   *self,
+ensure_pixbuf_from_surface (GtkIconHelper   *self,
                            GtkStyleContext *context)
 {
   cairo_surface_t *surface;
@@ -365,13 +366,13 @@ ensure_pixbuf_from_pattern (GtkIconHelper   *self,
   if (self->priv->rendered_pixbuf)
     return;
 
-  get_pattern_size (self, context, self->priv->orig_pattern, &width, &height);
+  get_surface_size (self, context, self->priv->orig_surface, &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_set_source_surface (cr, self->priv->orig_surface, 0, 0);
   cairo_paint (cr);
   cairo_destroy (cr);
 
@@ -436,8 +437,8 @@ _gtk_icon_helper_ensure_pixbuf (GtkIconHelper *self,
 
   switch (self->priv->storage_type)
     {
-    case GTK_IMAGE_PATTERN:
-      ensure_pixbuf_from_pattern (self, context);
+    case GTK_IMAGE_SURFACE:
+      ensure_pixbuf_from_surface (self, context);
       break;
 
     case GTK_IMAGE_PIXBUF:
@@ -496,7 +497,7 @@ get_scale_factor (GtkIconHelper *self,
 }
 
 static gboolean
-check_invalidate_pattern (GtkIconHelper *self,
+check_invalidate_surface (GtkIconHelper *self,
                          GtkStyleContext *context)
 {
   GtkStateFlags state;
@@ -505,53 +506,51 @@ check_invalidate_pattern (GtkIconHelper *self,
   state = gtk_style_context_get_state (context);
   scale = get_scale_factor (self, context);
 
-  if ((self->priv->rendered_pattern != NULL) &&
-      (self->priv->last_pattern_state == state) &&
-      (self->priv->last_pattern_scale == scale))
+  if ((self->priv->rendered_surface != NULL) &&
+      (self->priv->last_surface_state == state) &&
+      (self->priv->last_surface_scale == scale))
     return FALSE;
 
-  self->priv->last_pattern_state = state;
-  self->priv->last_pattern_scale = scale;
+  self->priv->last_surface_state = state;
+  self->priv->last_surface_scale = scale;
 
-  if (self->priv->rendered_pattern)
-    cairo_pattern_destroy (self->priv->rendered_pattern);
-  self->priv->rendered_pattern = NULL;
+  if (self->priv->rendered_surface)
+    cairo_surface_destroy (self->priv->rendered_surface);
+  self->priv->rendered_surface = NULL;
 
   return TRUE;
 }
 
 static void
-ensure_pattern_from_pattern (GtkIconHelper   *self,
+ensure_surface_from_surface (GtkIconHelper   *self,
                             GtkStyleContext *context)
 {
-  if (!check_invalidate_pattern (self, context))
+  if (!check_invalidate_surface (self, context))
     return;
 
-  if (self->priv->rendered_pattern)
+  if (self->priv->rendered_surface)
     return;
 
-  self->priv->rendered_pattern =
-    cairo_pattern_reference (self->priv->orig_pattern);
+  self->priv->rendered_surface =
+    cairo_surface_reference (self->priv->orig_surface);
 
-  get_pattern_size (self, context, self->priv->orig_pattern,
-                   &self->priv->rendered_pattern_width,
-                   &self->priv->rendered_pattern_height);
+  get_surface_size (self, context, self->priv->orig_surface,
+                   &self->priv->rendered_surface_width,
+                   &self->priv->rendered_surface_height);
 }
 
 static void
-ensure_pattern_from_pixbuf (GtkIconHelper   *self,
+ensure_surface_from_pixbuf (GtkIconHelper   *self,
                            GtkStyleContext *context)
 {
   gint width, height;
   GdkPixbuf *pixbuf;
-  cairo_surface_t *surface;
-  cairo_matrix_t matrix;
   int scale;
 
-  if (!check_invalidate_pattern (self, context))
+  if (!check_invalidate_surface (self, context))
     return;
 
-  if (self->priv->rendered_pattern)
+  if (self->priv->rendered_surface)
     return;
 
   scale = get_scale_factor (self, context);
@@ -585,59 +584,45 @@ ensure_pattern_from_pixbuf (GtkIconHelper   *self,
       scale = self->priv->orig_pixbuf_scale;
     }
 
-  self->priv->rendered_pattern_width = (gdk_pixbuf_get_width (pixbuf) + scale - 1) / scale;
-  self->priv->rendered_pattern_height = (gdk_pixbuf_get_height (pixbuf) + scale - 1) / scale;
+  self->priv->rendered_surface_width = (gdk_pixbuf_get_width (pixbuf) + scale - 1) / scale;
+  self->priv->rendered_surface_height = (gdk_pixbuf_get_height (pixbuf) + scale - 1) / scale;
 
-  surface = gdk_cairo_surface_create_from_pixbuf (pixbuf, 1, self->priv->window);
+  self->priv->rendered_surface = gdk_cairo_surface_create_from_pixbuf (pixbuf, scale, self->priv->window);
   g_object_unref (pixbuf);
-  self->priv->rendered_pattern = cairo_pattern_create_for_surface (surface);
-  cairo_surface_destroy (surface);
-
-  cairo_matrix_init_scale (&matrix, scale, scale);
-  cairo_pattern_set_matrix (self->priv->rendered_pattern, &matrix);
 }
 
 static void
-ensure_pattern_for_icon_set (GtkIconHelper *self,
+ensure_surface_for_icon_set (GtkIconHelper *self,
                             GtkStyleContext *context,
                             GtkIconSet *icon_set)
 {
-  cairo_surface_t *surface;
   gint scale;
 
-  if (!check_invalidate_pattern (self, context))
+  if (!check_invalidate_surface (self, context))
     return;
 
   scale = get_scale_factor (self, context);
 
-  self->priv->rendered_pattern =
-    gtk_icon_set_render_icon_pattern (icon_set, context, self->priv->icon_size,
+  self->priv->rendered_surface =
+    gtk_icon_set_render_icon_surface (icon_set, context, 
+                                     self->priv->icon_size,
                                      scale, self->priv->window);
 
-  if (self->priv->rendered_pattern &&
-      !cairo_pattern_get_surface (self->priv->rendered_pattern,
-                                 &surface))
-    {
-      cairo_matrix_t matrix;
-      cairo_pattern_get_matrix (self->priv->rendered_pattern, &matrix);
-      self->priv->rendered_pattern_width =
-       ceil (cairo_image_surface_get_width (surface) / matrix.xx);
-      self->priv->rendered_pattern_height =
-       ceil (cairo_image_surface_get_height (surface) / matrix.yy);
-    }
+  if (self->priv->rendered_surface)
+    get_surface_size (self, context, self->priv->rendered_surface, 
+                     &self->priv->rendered_surface_width, 
+                     &self->priv->rendered_surface_height);
 }
 
 static void
-ensure_stated_pattern_from_info (GtkIconHelper *self,
+ensure_stated_surface_from_info (GtkIconHelper *self,
                                 GtkStyleContext *context,
                                 GtkIconInfo *info,
                                 int scale)
 {
   GdkPixbuf *destination = NULL;
   cairo_surface_t *surface;
-  cairo_pattern_t *pattern;
   gboolean symbolic;
-  cairo_matrix_t matrix;
 
   symbolic = FALSE;
 
@@ -682,23 +667,22 @@ ensure_stated_pattern_from_info (GtkIconHelper *self,
       destination = rendered;
     }
 
-  pattern = NULL;
+  surface = NULL;
   if (destination)
     {
-      surface = gdk_cairo_surface_create_from_pixbuf (destination, 1, self->priv->window);
-      pattern = cairo_pattern_create_for_surface (surface);
-      cairo_matrix_init_scale (&matrix, scale, scale);
-      cairo_pattern_set_matrix (pattern, &matrix);
+      surface = gdk_cairo_surface_create_from_pixbuf (destination, scale, self->priv->window);
 
-      self->priv->rendered_pattern_width = (gdk_pixbuf_get_width (destination) + scale - 1) / scale;
-      self->priv->rendered_pattern_height = (gdk_pixbuf_get_height (destination) + scale - 1) / scale;
+      self->priv->rendered_surface_width = 
+       (gdk_pixbuf_get_width (destination) + scale - 1) / scale;
+      self->priv->rendered_surface_height = 
+       (gdk_pixbuf_get_height (destination) + scale - 1) / scale;
     }
 
-  self->priv->rendered_pattern = pattern;
+  self->priv->rendered_surface = surface;
 }
 
 static void
-ensure_pattern_for_icon_name_or_gicon (GtkIconHelper *self,
+ensure_surface_for_icon_name_or_gicon (GtkIconHelper *self,
                                       GtkStyleContext *context)
 {
   GtkIconTheme *icon_theme;
@@ -706,7 +690,7 @@ ensure_pattern_for_icon_name_or_gicon (GtkIconHelper *self,
   GtkIconInfo *info;
   GtkIconLookupFlags flags;
 
-  if (!check_invalidate_pattern (self, context))
+  if (!check_invalidate_surface (self, context))
     return;
 
   icon_theme = gtk_icon_theme_get_default ();
@@ -737,59 +721,59 @@ ensure_pattern_for_icon_name_or_gicon (GtkIconHelper *self,
       return;
     }
 
-  ensure_stated_pattern_from_info (self, context, info, scale);
+  ensure_stated_surface_from_info (self, context, info, scale);
 
   if (info)
     g_object_unref (info);
 }
 
-cairo_pattern_t *
-_gtk_icon_helper_ensure_pattern (GtkIconHelper *self,
+cairo_surface_t *
+_gtk_icon_helper_ensure_surface (GtkIconHelper *self,
                                 GtkStyleContext *context)
 {
-  cairo_pattern_t *pattern = NULL;
+  cairo_surface_t *surface = NULL;
   GtkIconSet *icon_set;
 
   switch (self->priv->storage_type)
     {
-    case GTK_IMAGE_PATTERN:
-      ensure_pattern_from_pattern (self, context);
+    case GTK_IMAGE_SURFACE:
+      ensure_surface_from_surface (self, context);
       break;
 
     case GTK_IMAGE_PIXBUF:
-      ensure_pattern_from_pixbuf (self, context);
+      ensure_surface_from_pixbuf (self, context);
       break;
 
     case GTK_IMAGE_STOCK:
       icon_set = gtk_style_context_lookup_icon_set (context, self->priv->stock_id);
       if (icon_set != NULL)
-       ensure_pattern_for_icon_set (self, context, icon_set);
+       ensure_surface_for_icon_set (self, context, icon_set);
       else
-       pattern = NULL;
+       surface = NULL;
       break;
 
     case GTK_IMAGE_ICON_SET:
       icon_set = self->priv->icon_set;
-      ensure_pattern_for_icon_set (self, context, icon_set);
+      ensure_surface_for_icon_set (self, context, icon_set);
       break;
 
     case GTK_IMAGE_ICON_NAME:
     case GTK_IMAGE_GICON:
-      ensure_pattern_for_icon_name_or_gicon (self, context);
+      ensure_surface_for_icon_name_or_gicon (self, context);
       break;
 
     case GTK_IMAGE_ANIMATION:
     case GTK_IMAGE_EMPTY:
     default:
-      pattern = NULL;
+      surface = NULL;
       break;
     }
 
-  if (pattern == NULL &&
-      self->priv->rendered_pattern != NULL)
-    pattern = cairo_pattern_reference (self->priv->rendered_pattern);
+  if (surface == NULL &&
+      self->priv->rendered_surface != NULL)
+    surface = cairo_surface_reference (self->priv->rendered_surface);
 
-  return pattern;
+  return surface;
 }
 
 void
@@ -798,17 +782,17 @@ _gtk_icon_helper_get_size (GtkIconHelper *self,
                            gint *width_out,
                            gint *height_out)
 {
-  cairo_pattern_t *pattern;
+  cairo_surface_t *surface;
   gint width, height;
 
   width = height = 0;
-  pattern = _gtk_icon_helper_ensure_pattern (self, context);
+  surface = _gtk_icon_helper_ensure_surface (self, context);
 
-  if (pattern != NULL)
+  if (surface != NULL)
     {
-      width = self->priv->rendered_pattern_width;
-      height = self->priv->rendered_pattern_height;
-      cairo_pattern_destroy (pattern);
+      width = self->priv->rendered_surface_width;
+      height = self->priv->rendered_surface_height;
+      cairo_surface_destroy (surface);
     }
   else if (self->priv->storage_type == GTK_IMAGE_ANIMATION)
     {
@@ -901,15 +885,15 @@ _gtk_icon_helper_set_animation (GtkIconHelper *self,
 }
 
 void 
-_gtk_icon_helper_set_pattern (GtkIconHelper *self,
-                             cairo_pattern_t *pattern)
+_gtk_icon_helper_set_surface (GtkIconHelper *self,
+                             cairo_surface_t *surface)
 {
   _gtk_icon_helper_clear (self);
 
-  if (pattern != NULL)
+  if (surface != NULL)
     {
-      self->priv->storage_type = GTK_IMAGE_PATTERN;
-      self->priv->orig_pattern = cairo_pattern_reference (pattern);
+      self->priv->storage_type = GTK_IMAGE_SURFACE;
+      self->priv->orig_surface = cairo_surface_reference (surface);
     }
 }
 
@@ -1010,10 +994,10 @@ _gtk_icon_helper_peek_icon_set (GtkIconHelper *self)
   return self->priv->icon_set;
 }
 
-cairo_pattern_t *
-_gtk_icon_helper_peek_pattern (GtkIconHelper *self)
+cairo_surface_t *
+_gtk_icon_helper_peek_surface (GtkIconHelper *self)
 {
-  return self->priv->orig_pattern;
+  return self->priv->orig_surface;
 }
 
 const gchar *
@@ -1041,13 +1025,13 @@ _gtk_icon_helper_draw (GtkIconHelper *self,
                        gdouble x,
                        gdouble y)
 {
-  cairo_pattern_t *pattern;
+  cairo_surface_t *surface;
 
-  pattern = _gtk_icon_helper_ensure_pattern (self, context);
-  if (pattern != NULL)
+  surface = _gtk_icon_helper_ensure_surface (self, context);
+  if (surface != NULL)
     {
-      gtk_render_icon_pattern (context, cr, pattern, x, y);
-      cairo_pattern_destroy (pattern);
+      gtk_render_icon_surface (context, cr, surface, x, y);
+      cairo_surface_destroy (surface);
     }
 }
 
diff --git a/gtk/gtkiconhelperprivate.h b/gtk/gtkiconhelperprivate.h
index fcee95e..e7136ac 100644
--- a/gtk/gtkiconhelperprivate.h
+++ b/gtk/gtkiconhelperprivate.h
@@ -95,8 +95,8 @@ void _gtk_icon_helper_set_icon_name (GtkIconHelper *self,
 void _gtk_icon_helper_set_stock_id (GtkIconHelper *self,
                                     const gchar *stock_id,
                                     GtkIconSize icon_size);
-void _gtk_icon_helper_set_pattern (GtkIconHelper *self,
-                                  cairo_pattern_t *pattern);
+void _gtk_icon_helper_set_surface (GtkIconHelper *self,
+                                  cairo_surface_t *surface);
 
 void _gtk_icon_helper_set_icon_size (GtkIconHelper *self,
                                      GtkIconSize icon_size);
@@ -114,7 +114,7 @@ GdkPixbuf *_gtk_icon_helper_peek_pixbuf (GtkIconHelper *self);
 GIcon *_gtk_icon_helper_peek_gicon (GtkIconHelper *self);
 GtkIconSet *_gtk_icon_helper_peek_icon_set (GtkIconHelper *self);
 GdkPixbufAnimation *_gtk_icon_helper_peek_animation (GtkIconHelper *self);
-cairo_pattern_t *_gtk_icon_helper_peek_pattern (GtkIconHelper *self);
+cairo_surface_t *_gtk_icon_helper_peek_surface (GtkIconHelper *self);
 
 const gchar *_gtk_icon_helper_get_stock_id (GtkIconHelper *self);
 const gchar *_gtk_icon_helper_get_icon_name (GtkIconHelper *self);
diff --git a/gtk/gtkimage.c b/gtk/gtkimage.c
index 0373114..bffdb73 100644
--- a/gtk/gtkimage.c
+++ b/gtk/gtkimage.c
@@ -186,7 +186,7 @@ enum
 {
   PROP_0,
   PROP_PIXBUF,
-  PROP_PATTERN,
+  PROP_SURFACE,
   PROP_FILE,
   PROP_STOCK,
   PROP_ICON_SET,
@@ -234,11 +234,11 @@ gtk_image_class_init (GtkImageClass *class)
                                                         GTK_PARAM_READWRITE));
 
   g_object_class_install_property (gobject_class,
-                                   PROP_PATTERN,
-                                   g_param_spec_boxed ("pattern",
-                                                      P_("Pattern"),
-                                                      P_("A cairo_pattern_t to display"),
-                                                      CAIRO_GOBJECT_TYPE_PATTERN,
+                                   PROP_SURFACE,
+                                   g_param_spec_boxed ("surface",
+                                                      P_("Surface"),
+                                                      P_("A cairo_surface_t to display"),
+                                                      CAIRO_GOBJECT_TYPE_SURFACE,
                                                       GTK_PARAM_READWRITE));
 
   g_object_class_install_property (gobject_class,
@@ -440,8 +440,8 @@ gtk_image_set_property (GObject      *object,
       gtk_image_set_from_pixbuf (image,
                                  g_value_get_object (value));
       break;
-    case PROP_PATTERN:
-      gtk_image_set_from_pattern (image,
+    case PROP_SURFACE:
+      gtk_image_set_from_surface (image,
                                  g_value_get_boxed (value));
       break;
     case PROP_FILE:
@@ -505,8 +505,8 @@ gtk_image_get_property (GObject     *object,
     case PROP_PIXBUF:
       g_value_set_object (value, _gtk_icon_helper_peek_pixbuf (priv->icon_helper));
       break;
-    case PROP_PATTERN:
-      g_value_set_boxed (value, _gtk_icon_helper_peek_pattern (priv->icon_helper));
+    case PROP_SURFACE:
+      g_value_set_boxed (value, _gtk_icon_helper_peek_surface (priv->icon_helper));
       break;
     case PROP_FILE:
       g_value_set_string (value, priv->filename);
@@ -650,24 +650,24 @@ gtk_image_new_from_pixbuf (GdkPixbuf *pixbuf)
 }
 
 /**
- * gtk_image_new_from_pattern:
- * @pattern: (allow-none): a #cairo_pattern_t, or %NULL
+ * gtk_image_new_from_surface:
+ * @surface: (allow-none): a #cairo_surface_t, or %NULL
  *
- * Creates a new #GtkImage displaying @pattern.
+ * Creates a new #GtkImage displaying @surface.
  * The #GtkImage does not assume a reference to the
- * pattern; you still need to unref it if you own references.
+ * surface; you still need to unref it if you own references.
  * #GtkImage will add its own reference rather than adopting yours.
  * 
  * Return value: a new #GtkImage
  **/
 GtkWidget*
-gtk_image_new_from_pattern (cairo_pattern_t *pattern)
+gtk_image_new_from_surface (cairo_surface_t *surface)
 {
   GtkImage *image;
 
   image = g_object_new (GTK_TYPE_IMAGE, NULL);
 
-  gtk_image_set_from_pattern (image, pattern);
+  gtk_image_set_from_surface (image, surface);
 
   return GTK_WIDGET (image);  
 }
@@ -1169,17 +1169,17 @@ gtk_image_set_from_gicon  (GtkImage       *image,
 }
 
 /**
- * gtk_image_set_from_pattern:
+ * gtk_image_set_from_surface:
  * @image: a #GtkImage
- * @pattern: a cairo_pattern_t
+ * @surface: a cairo_surface_t
  *
- * See gtk_image_new_from_pattern() for details.
+ * See gtk_image_new_from_surface() for details.
  * 
  * Since: 3.10
  **/
 void
-gtk_image_set_from_pattern (GtkImage       *image,
-                           cairo_pattern_t *pattern)
+gtk_image_set_from_surface (GtkImage       *image,
+                           cairo_surface_t *surface)
 {
   GtkImagePrivate *priv;
 
@@ -1189,18 +1189,18 @@ gtk_image_set_from_pattern (GtkImage       *image,
 
   g_object_freeze_notify (G_OBJECT (image));
 
-  if (pattern)
-    cairo_pattern_reference (pattern);
+  if (surface)
+    cairo_surface_reference (surface);
 
   gtk_image_clear (image);
 
-  if (pattern)
+  if (surface)
     {
-      _gtk_icon_helper_set_pattern (priv->icon_helper, pattern);
-      cairo_pattern_destroy (pattern);
+      _gtk_icon_helper_set_surface (priv->icon_helper, surface);
+      cairo_surface_destroy (surface);
     }
 
-  g_object_notify (G_OBJECT (image), "pattern");
+  g_object_notify (G_OBJECT (image), "surface");
   
   g_object_thaw_notify (G_OBJECT (image));
 }
diff --git a/gtk/gtkimage.h b/gtk/gtkimage.h
index e48d4d1..a7fede0 100644
--- a/gtk/gtkimage.h
+++ b/gtk/gtkimage.h
@@ -60,7 +60,7 @@ 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.
+ * @GTK_IMAGE_SURFACE: the widget contains a #cairo_surface_t.
  *  This image type was added in GTK+ 3.10
  *
  * Describes the image data representation used by a #GtkImage. If you
@@ -80,7 +80,7 @@ typedef enum
   GTK_IMAGE_ANIMATION,
   GTK_IMAGE_ICON_NAME,
   GTK_IMAGE_GICON,
-  GTK_IMAGE_PATTERN
+  GTK_IMAGE_SURFACE
 } GtkImageType;
 
 /**
@@ -134,7 +134,7 @@ GDK_AVAILABLE_IN_ALL
 GtkWidget* gtk_image_new_from_gicon     (GIcon           *icon,
                                         GtkIconSize      size);
 GDK_AVAILABLE_IN_3_10
-GtkWidget* gtk_image_new_from_pattern   (cairo_pattern_t *pattern);
+GtkWidget* gtk_image_new_from_surface   (cairo_surface_t *surface);
 
 GDK_AVAILABLE_IN_ALL
 void gtk_image_clear              (GtkImage        *image);
@@ -167,8 +167,8 @@ void gtk_image_set_from_gicon     (GtkImage        *image,
                                   GIcon           *icon,
                                   GtkIconSize      size);
 GDK_AVAILABLE_IN_3_10
-void gtk_image_set_from_pattern   (GtkImage        *image,
-                                  cairo_pattern_t *pattern);
+void gtk_image_set_from_surface   (GtkImage        *image,
+                                  cairo_surface_t *surface);
 GDK_AVAILABLE_IN_ALL
 void gtk_image_set_pixel_size     (GtkImage        *image,
                                   gint             pixel_size);
diff --git a/gtk/gtkpathbar.c b/gtk/gtkpathbar.c
index 51135a2..a00a4a4 100644
--- a/gtk/gtkpathbar.c
+++ b/gtk/gtkpathbar.c
@@ -46,9 +46,9 @@ struct _GtkPathBarPrivate
 
   GCancellable *get_info_cancellable;
 
-  cairo_pattern_t *root_icon;
-  cairo_pattern_t *home_icon;
-  cairo_pattern_t *desktop_icon;
+  cairo_surface_t *root_icon;
+  cairo_surface_t *home_icon;
+  cairo_surface_t *desktop_icon;
 
   GdkWindow *event_window;
 
@@ -293,11 +293,11 @@ gtk_path_bar_finalize (GObject *object)
     g_object_unref (path_bar->priv->desktop_file);
 
   if (path_bar->priv->root_icon)
-    cairo_pattern_destroy (path_bar->priv->root_icon);
+    cairo_surface_destroy (path_bar->priv->root_icon);
   if (path_bar->priv->home_icon)
-    cairo_pattern_destroy (path_bar->priv->home_icon);
+    cairo_surface_destroy (path_bar->priv->home_icon);
   if (path_bar->priv->desktop_icon)
-    cairo_pattern_destroy (path_bar->priv->desktop_icon);
+    cairo_surface_destroy (path_bar->priv->desktop_icon);
 
   if (path_bar->priv->file_system)
     g_object_unref (path_bar->priv->file_system);
@@ -1238,17 +1238,17 @@ reload_icons (GtkPathBar *path_bar)
 
   if (path_bar->priv->root_icon)
     {
-      cairo_pattern_destroy (path_bar->priv->root_icon);
+      cairo_surface_destroy (path_bar->priv->root_icon);
       path_bar->priv->root_icon = NULL;
     }
   if (path_bar->priv->home_icon)
     {
-      cairo_pattern_destroy (path_bar->priv->home_icon);
+      cairo_surface_destroy (path_bar->priv->home_icon);
       path_bar->priv->home_icon = NULL;
     }
   if (path_bar->priv->desktop_icon)
     {
-      cairo_pattern_destroy (path_bar->priv->desktop_icon);
+      cairo_surface_destroy (path_bar->priv->desktop_icon);
       path_bar->priv->desktop_icon = NULL;
     }
 
@@ -1375,7 +1375,6 @@ set_button_image_get_info_cb (GCancellable *cancellable,
                              gpointer      user_data)
 {
   gboolean cancelled = g_cancellable_is_cancelled (cancellable);
-  cairo_pattern_t *pattern = NULL;
   cairo_surface_t *surface;
   struct SetButtonImageData *data = user_data;
 
@@ -1395,27 +1394,22 @@ set_button_image_get_info_cb (GCancellable *cancellable,
 
   surface = _gtk_file_info_render_icon (info, GTK_WIDGET (data->path_bar),
                                       data->path_bar->priv->icon_size);
-  if (surface)
-    {
-      pattern = cairo_pattern_create_for_surface (surface);
-      cairo_surface_destroy (surface);
-    }
-  gtk_image_set_from_pattern (GTK_IMAGE (data->button_data->image), pattern);
+  gtk_image_set_from_surface (GTK_IMAGE (data->button_data->image), surface);
 
   switch (data->button_data->type)
     {
       case HOME_BUTTON:
        if (data->path_bar->priv->home_icon)
-         cairo_pattern_destroy (pattern);
+         cairo_surface_destroy (surface);
        else
-         data->path_bar->priv->home_icon = pattern;
+         data->path_bar->priv->home_icon = surface;
        break;
 
       case DESKTOP_BUTTON:
        if (data->path_bar->priv->desktop_icon)
-         cairo_pattern_destroy (pattern);
+         cairo_surface_destroy (surface);
        else
-         data->path_bar->priv->desktop_icon = pattern;
+         data->path_bar->priv->desktop_icon = surface;
        break;
 
       default:
@@ -1433,8 +1427,6 @@ set_button_image (GtkPathBar *path_bar,
 {
   GtkFileSystemVolume *volume;
   struct SetButtonImageData *data;
-  cairo_pattern_t *pattern = NULL;
-  cairo_surface_t *surface;
 
   switch (button_data->type)
     {
@@ -1442,7 +1434,7 @@ set_button_image (GtkPathBar *path_bar,
 
       if (path_bar->priv->root_icon != NULL)
         {
-          gtk_image_set_from_pattern (GTK_IMAGE (button_data->image), path_bar->priv->root_icon);
+          gtk_image_set_from_surface (GTK_IMAGE (button_data->image), path_bar->priv->root_icon);
          break;
        }
 
@@ -1450,25 +1442,19 @@ set_button_image (GtkPathBar *path_bar,
       if (volume == NULL)
        return;
 
-      surface = _gtk_file_system_volume_render_icon (volume,
-                                                     GTK_WIDGET (path_bar),
-                                                     path_bar->priv->icon_size,
-                                                     NULL);
-      if (surface)
-        {
-          pattern = cairo_pattern_create_for_surface (surface);
-          cairo_surface_destroy (surface);
-        }
-      path_bar->priv->root_icon = pattern;
+      path_bar->priv->root_icon = _gtk_file_system_volume_render_icon (volume,
+                                                                      GTK_WIDGET (path_bar),
+                                                                      path_bar->priv->icon_size,
+                                                                      NULL);
       _gtk_file_system_volume_unref (volume);
 
-      gtk_image_set_from_pattern (GTK_IMAGE (button_data->image), path_bar->priv->root_icon);
+      gtk_image_set_from_surface (GTK_IMAGE (button_data->image), path_bar->priv->root_icon);
       break;
 
     case HOME_BUTTON:
       if (path_bar->priv->home_icon != NULL)
         {
-         gtk_image_set_from_pattern (GTK_IMAGE (button_data->image), path_bar->priv->home_icon);
+         gtk_image_set_from_surface (GTK_IMAGE (button_data->image), path_bar->priv->home_icon);
          break;
        }
 
@@ -1490,7 +1476,7 @@ set_button_image (GtkPathBar *path_bar,
     case DESKTOP_BUTTON:
       if (path_bar->priv->desktop_icon != NULL)
         {
-         gtk_image_set_from_pattern (GTK_IMAGE (button_data->image), path_bar->priv->desktop_icon);
+         gtk_image_set_from_surface (GTK_IMAGE (button_data->image), path_bar->priv->desktop_icon);
          break;
        }
 
diff --git a/gtk/gtkstylecontext.c b/gtk/gtkstylecontext.c
index 0bb4fed..d70aa56 100644
--- a/gtk/gtkstylecontext.c
+++ b/gtk/gtkstylecontext.c
@@ -4513,21 +4513,21 @@ gtk_render_icon (GtkStyleContext *context,
 }
 
 /**
- * gtk_render_icon_pattern:
+ * gtk_render_icon_surface:
  * @context: a #GtkStyleContext
  * @cr: a #cairo_t
- * @pattern: a #cairo_pattern_t containing the icon to draw
- * @x: X position for the @pixbuf
- * @y: Y position for the @pixbuf
+ * @surface: a #cairo_surface_t containing the icon to draw
+ * @x: X position for the @icon
+ * @y: Y position for the @incon
  *
- * Renders the icon in @pixbuf at the specified @x and @y coordinates.
+ * Renders the icon in @surface at the specified @x and @y coordinates.
  *
  * Since: 3.10
  **/
 void
-gtk_render_icon_pattern (GtkStyleContext *context,
+gtk_render_icon_surface (GtkStyleContext *context,
                         cairo_t         *cr,
-                        cairo_pattern_t *pattern,
+                        cairo_surface_t *surface,
                         gdouble          x,
                         gdouble          y)
 {
@@ -4543,7 +4543,7 @@ gtk_render_icon_pattern (GtkStyleContext *context,
   cairo_save (cr);
 
   _gtk_theming_engine_set_context (engine, context);
-  engine_class->render_icon_pattern (engine, cr, pattern, x, y);
+  engine_class->render_icon_surface (engine, cr, surface, x, y);
 
   cairo_restore (cr);
 }
diff --git a/gtk/gtkstylecontext.h b/gtk/gtkstylecontext.h
index 69d347a..59012ed 100644
--- a/gtk/gtkstylecontext.h
+++ b/gtk/gtkstylecontext.h
@@ -1098,9 +1098,9 @@ void        gtk_render_icon        (GtkStyleContext     *context,
                                     gdouble              x,
                                     gdouble              y);
 GDK_AVAILABLE_IN_3_10
-void        gtk_render_icon_pattern (GtkStyleContext    *context,
+void        gtk_render_icon_surface (GtkStyleContext    *context,
                                     cairo_t            *cr,
-                                    cairo_pattern_t    *pattern,
+                                    cairo_surface_t    *surface,
                                     gdouble             x,
                                     gdouble             y);
 GDK_AVAILABLE_IN_3_4
diff --git a/gtk/gtkthemingengine.c b/gtk/gtkthemingengine.c
index 3946032..006afe7 100644
--- a/gtk/gtkthemingengine.c
+++ b/gtk/gtkthemingengine.c
@@ -182,9 +182,9 @@ static void gtk_theming_engine_render_icon (GtkThemingEngine *engine,
                                            GdkPixbuf *pixbuf,
                                             gdouble x,
                                             gdouble y);
-static void gtk_theming_engine_render_icon_pattern (GtkThemingEngine *engine,
+static void gtk_theming_engine_render_icon_surface (GtkThemingEngine *engine,
                                                    cairo_t *cr,
-                                                   cairo_pattern_t *pattern,
+                                                   cairo_surface_t *surface,
                                                    gdouble x,
                                                    gdouble y);
 
@@ -244,7 +244,7 @@ gtk_theming_engine_class_init (GtkThemingEngineClass *klass)
   klass->render_handle = gtk_theming_engine_render_handle;
   klass->render_activity = gtk_theming_engine_render_activity;
   klass->render_icon_pixbuf = gtk_theming_engine_render_icon_pixbuf;
-  klass->render_icon_pattern = gtk_theming_engine_render_icon_pattern;
+  klass->render_icon_surface = gtk_theming_engine_render_icon_surface;
 
   /**
    * GtkThemingEngine:name:
@@ -2798,17 +2798,15 @@ gtk_theming_engine_render_icon (GtkThemingEngine *engine,
 }
 
 static void
-gtk_theming_engine_render_icon_pattern (GtkThemingEngine *engine,
+gtk_theming_engine_render_icon_surface (GtkThemingEngine *engine,
                                        cairo_t *cr,
-                                       cairo_pattern_t *pattern,
+                                       cairo_surface_t *surface,
                                        gdouble x,
                                        gdouble y)
 {
   cairo_save (cr);
 
-  cairo_translate (cr, x, y);
-  cairo_set_source (cr, pattern);
-
+  cairo_set_source_surface (cr, surface, x, y);
 
   _gtk_css_shadows_value_paint_icon (_gtk_theming_engine_peek_property (engine, 
GTK_CSS_PROPERTY_ICON_SHADOW), cr);
 
diff --git a/gtk/gtkthemingengine.h b/gtk/gtkthemingengine.h
index 3e05f16..f75464a 100644
--- a/gtk/gtkthemingengine.h
+++ b/gtk/gtkthemingengine.h
@@ -70,7 +70,7 @@ struct _GtkThemingEngine
  *                   or #GtkProgressBar.
  * @render_icon_pixbuf: Renders an icon as a #GdkPixbuf.
  * @render_icon: Renders an icon given as a #GdkPixbuf.
- * @render_icon_pattern: Renders an icon given as a #cairo_pattern_t.
+ * @render_icon_surface: Renders an icon given as a #cairo_surface_t.
  *
  * Base class for theming engines.
  */
@@ -175,9 +175,9 @@ struct _GtkThemingEngineClass
                        GdkPixbuf        *pixbuf,
                         gdouble           x,
                         gdouble           y);
-  void (* render_icon_pattern) (GtkThemingEngine *engine,
+  void (* render_icon_surface) (GtkThemingEngine *engine,
                                cairo_t          *cr,
-                               cairo_pattern_t  *pattern,
+                               cairo_surface_t  *surface,
                                gdouble           x,
                                gdouble           y);
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]