[gtk+] GtkImage: Drop support for storing pixbufs
- From: Alexander Larsson <alexl src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gtk+] GtkImage: Drop support for storing pixbufs
- Date: Mon, 23 Oct 2017 13:28:42 +0000 (UTC)
commit 2b194089dd525b74c532fdd95c0ab654ac88d295
Author: Alexander Larsson <alexl redhat com>
Date: Mon Oct 23 14:47:50 2017 +0200
GtkImage: Drop support for storing pixbufs
This drops the pixbuf property and the pixbuf getters. We keep
gtk_image_new/set_from_pixbuf, but these are small helpers that
immediately convert to a surface, and there is no way to later get
back the pixbuf you passed in.
The from file/resource codepaths are also changed to load a surface
instead of a pixbuf.
demos/gtk-demo/images.c | 11 +---
demos/gtk-demo/main.c | 2 +-
docs/reference/gtk/gtk4-sections.txt | 1 -
gtk/a11y/gtkimageaccessible.c | 12 ++--
gtk/gtkimage.c | 105 ++++++++++++++--------------------
gtk/gtkimage.h | 7 +-
gtk/gtktoolbutton.c | 35 +++++++----
tests/testimage.c | 17 +++---
8 files changed, 85 insertions(+), 105 deletions(-)
---
diff --git a/demos/gtk-demo/images.c b/demos/gtk-demo/images.c
index c80f5f2..bf0618a 100644
--- a/demos/gtk-demo/images.c
+++ b/demos/gtk-demo/images.c
@@ -54,17 +54,8 @@ progressive_updated_callback (GdkPixbufLoader *loader,
image = GTK_WIDGET (data);
- /* We know the pixbuf inside the GtkImage has changed, but the image
- * itself doesn't know this; so give it a hint by setting the pixbuf
- * again. Queuing a redraw used to be sufficient, but nowadays GtkImage
- * uses GtkIconHelper which caches the pixbuf state and will just redraw
- * from the cache.
- */
-
- pixbuf = gtk_image_get_pixbuf (GTK_IMAGE (image));
- g_object_ref (pixbuf);
+ pixbuf = gdk_pixbuf_loader_get_pixbuf (loader);
gtk_image_set_from_pixbuf (GTK_IMAGE (image), pixbuf);
- g_object_unref (pixbuf);
}
static gint
diff --git a/demos/gtk-demo/main.c b/demos/gtk-demo/main.c
index d0cca8c..49f368b 100644
--- a/demos/gtk-demo/main.c
+++ b/demos/gtk-demo/main.c
@@ -556,7 +556,7 @@ add_data_tab (const gchar *demoname)
resource_name = g_strconcat (resource_dir, "/", resources[i], NULL);
widget = gtk_image_new_from_resource (resource_name);
- if (gtk_image_get_pixbuf (GTK_IMAGE (widget)) == NULL &&
+ if (gtk_image_get_surface (GTK_IMAGE (widget)) == NULL &&
gtk_image_get_animation (GTK_IMAGE (widget)) == NULL)
{
GBytes *bytes;
diff --git a/docs/reference/gtk/gtk4-sections.txt b/docs/reference/gtk/gtk4-sections.txt
index 186dea7..683f3b3 100644
--- a/docs/reference/gtk/gtk4-sections.txt
+++ b/docs/reference/gtk/gtk4-sections.txt
@@ -1486,7 +1486,6 @@ GtkIconViewPrivate
<TITLE>GtkImage</TITLE>
GtkImage
GtkImageType
-gtk_image_get_pixbuf
gtk_image_get_surface
gtk_image_get_animation
gtk_image_get_icon_name
diff --git a/gtk/a11y/gtkimageaccessible.c b/gtk/a11y/gtkimageaccessible.c
index 7c394d0..edf2003 100644
--- a/gtk/a11y/gtkimageaccessible.c
+++ b/gtk/a11y/gtkimageaccessible.c
@@ -270,13 +270,13 @@ gtk_image_accessible_get_image_size (AtkImage *image,
image_type = gtk_image_get_storage_type (gtk_image);
switch (image_type)
{
- case GTK_IMAGE_PIXBUF:
+ case GTK_IMAGE_SURFACE:
{
- GdkPixbuf *pixbuf;
+ cairo_surface_t *surface;
- pixbuf = gtk_image_get_pixbuf (gtk_image);
- *height = gdk_pixbuf_get_height (pixbuf);
- *width = gdk_pixbuf_get_width (pixbuf);
+ surface = gtk_image_get_surface (gtk_image);
+ *height = cairo_image_surface_get_height (surface);
+ *width = cairo_image_surface_get_width (surface);
break;
}
case GTK_IMAGE_ICON_NAME:
@@ -298,7 +298,7 @@ gtk_image_accessible_get_image_size (AtkImage *image,
break;
}
case GTK_IMAGE_EMPTY:
- case GTK_IMAGE_SURFACE:
+ case GTK_IMAGE_PIXBUF:
default:
{
*height = -1;
diff --git a/gtk/gtkimage.c b/gtk/gtkimage.c
index d0e65f7..b94f960 100644
--- a/gtk/gtkimage.c
+++ b/gtk/gtkimage.c
@@ -84,8 +84,8 @@ struct _GtkImagePrivate
float baseline_align;
- gchar *filename; /* Only used with GTK_IMAGE_ANIMATION, GTK_IMAGE_PIXBUF */
- gchar *resource_path; /* Only used with GTK_IMAGE_PIXBUF */
+ gchar *filename; /* Only used with GTK_IMAGE_ANIMATION, GTK_IMAGE_SURFACE */
+ gchar *resource_path; /* Only used with GTK_IMAGE_SURFACE */
};
@@ -121,7 +121,6 @@ static void gtk_image_get_property (GObject *object,
enum
{
PROP_0,
- PROP_PIXBUF,
PROP_SURFACE,
PROP_FILE,
PROP_ICON_SIZE,
@@ -146,7 +145,7 @@ gtk_image_class_init (GtkImageClass *class)
GtkWidgetClass *widget_class;
gobject_class = G_OBJECT_CLASS (class);
-
+
gobject_class->set_property = gtk_image_set_property;
gobject_class->get_property = gtk_image_get_property;
gobject_class->finalize = gtk_image_finalize;
@@ -159,13 +158,6 @@ gtk_image_class_init (GtkImageClass *class)
widget_class->unrealize = gtk_image_unrealize;
widget_class->style_updated = gtk_image_style_updated;
- image_props[PROP_PIXBUF] =
- g_param_spec_object ("pixbuf",
- P_("Pixbuf"),
- P_("A GdkPixbuf to display"),
- GDK_TYPE_PIXBUF,
- GTK_PARAM_READWRITE);
-
image_props[PROP_SURFACE] =
g_param_spec_boxed ("surface",
P_("Surface"),
@@ -330,9 +322,6 @@ gtk_image_set_property (GObject *object,
switch (prop_id)
{
- case PROP_PIXBUF:
- gtk_image_set_from_pixbuf (image, g_value_get_object (value));
- break;
case PROP_SURFACE:
gtk_image_set_from_surface (image, g_value_get_boxed (value));
break;
@@ -384,9 +373,6 @@ gtk_image_get_property (GObject *object,
switch (prop_id)
{
- case PROP_PIXBUF:
- g_value_set_object (value, _gtk_icon_helper_peek_pixbuf (&priv->icon_helper));
- break;
case PROP_SURFACE:
g_value_set_boxed (value, _gtk_icon_helper_peek_surface (&priv->icon_helper));
break;
@@ -438,7 +424,7 @@ gtk_image_get_property (GObject *object,
*
* If you need to detect failures to load the file, use
* gdk_pixbuf_new_from_file() to load the file yourself, then create
- * the #GtkImage from the pixbuf. (Or for animations, use
+ * the #GtkImage from the surface. (Or for animations, use
* gdk_pixbuf_animation_new_from_file()).
*
* The storage type (gtk_image_get_storage_type()) of the returned
@@ -504,7 +490,10 @@ gtk_image_new_from_resource (const gchar *resource_path)
* The #GtkImage does not assume a reference to the
* pixbuf; you still need to unref it if you own references.
* #GtkImage will add its own reference rather than adopting yours.
- *
+ *
+ * This is a helper for gtk_image_new_from_surface, and you can't
+ * get back the exact pixbuf once this is called, only a surface.
+ *
* Note that this function just creates an #GtkImage from the pixbuf. The
* #GtkImage created will not react to state changes. Should you want that,
* you should use gtk_image_new_from_icon_name().
@@ -767,17 +756,22 @@ gtk_image_set_from_file (GtkImage *image,
*/
if (gdk_pixbuf_animation_is_static_image (anim))
- gtk_image_set_from_pixbuf (image,
- gdk_pixbuf_animation_get_static_image (anim));
+ {
+ cairo_surface_t *surface = gdk_cairo_surface_create_from_pixbuf (gdk_pixbuf_animation_get_static_image
(anim),
+ scale_factor, _gtk_widget_get_window
(GTK_WIDGET (image)));
+ gtk_image_set_from_surface (image, surface);
+ cairo_surface_destroy (surface);
+ }
else
- gtk_image_set_from_animation (image, anim);
-
- _gtk_icon_helper_set_pixbuf_scale (&priv->icon_helper, scale_factor);
+ {
+ gtk_image_set_from_animation (image, anim);
+ _gtk_icon_helper_set_pixbuf_scale (&priv->icon_helper, scale_factor);
+ }
g_object_unref (anim);
priv->filename = g_strdup (filename);
-
+
g_object_thaw_notify (G_OBJECT (image));
}
@@ -858,11 +852,17 @@ gtk_image_set_from_resource (GtkImage *image,
}
if (gdk_pixbuf_animation_is_static_image (animation))
- gtk_image_set_from_pixbuf (image, gdk_pixbuf_animation_get_static_image (animation));
+ {
+ cairo_surface_t *surface = gdk_cairo_surface_create_from_pixbuf (gdk_pixbuf_animation_get_static_image
(animation),
+ scale_factor, _gtk_widget_get_window
(GTK_WIDGET (image)));
+ gtk_image_set_from_surface (image, surface);
+ cairo_surface_destroy (surface);
+ }
else
- gtk_image_set_from_animation (image, animation);
-
- _gtk_icon_helper_set_pixbuf_scale (&priv->icon_helper, scale_factor);
+ {
+ gtk_image_set_from_animation (image, animation);
+ _gtk_icon_helper_set_pixbuf_scale (&priv->icon_helper, scale_factor);
+ }
priv->resource_path = g_strdup (resource_path);
@@ -880,27 +880,29 @@ gtk_image_set_from_resource (GtkImage *image,
* @pixbuf: (allow-none): a #GdkPixbuf or %NULL
*
* See gtk_image_new_from_pixbuf() for details.
+ *
+ * Note: This is a helper for gtk_image_new_from_surface, and you can't
+ * get back the exact pixbuf once this is called, only a surface.
+ *
**/
void
gtk_image_set_from_pixbuf (GtkImage *image,
GdkPixbuf *pixbuf)
{
- GtkImagePrivate *priv = gtk_image_get_instance_private (image);
+ cairo_surface_t *surface = NULL;
g_return_if_fail (GTK_IS_IMAGE (image));
g_return_if_fail (pixbuf == NULL ||
GDK_IS_PIXBUF (pixbuf));
- g_object_freeze_notify (G_OBJECT (image));
-
- gtk_image_clear (image);
- if (pixbuf != NULL)
- _gtk_icon_helper_set_pixbuf (&priv->icon_helper, pixbuf);
+ if (pixbuf)
+ surface = gdk_cairo_surface_create_from_pixbuf (pixbuf, 1, gtk_widget_get_window (GTK_WIDGET (image)));
- g_object_notify_by_pspec (G_OBJECT (image), image_props[PROP_PIXBUF]);
+ gtk_image_set_from_surface (image, surface);
- g_object_thaw_notify (G_OBJECT (image));
+ if (surface)
+ cairo_surface_destroy (surface);
}
/**
@@ -1065,29 +1067,6 @@ gtk_image_get_storage_type (GtkImage *image)
}
/**
- * gtk_image_get_pixbuf:
- * @image: a #GtkImage
- *
- * Gets the #GdkPixbuf being displayed by the #GtkImage.
- * The storage type of the image must be %GTK_IMAGE_EMPTY or
- * %GTK_IMAGE_PIXBUF (see gtk_image_get_storage_type()).
- * The caller of this function does not own a reference to the
- * returned pixbuf.
- *
- * Returns: (nullable) (transfer none): the displayed pixbuf, or %NULL if
- * the image is empty
- **/
-GdkPixbuf*
-gtk_image_get_pixbuf (GtkImage *image)
-{
- GtkImagePrivate *priv = gtk_image_get_instance_private (image);
-
- g_return_val_if_fail (GTK_IS_IMAGE (image), NULL);
-
- return _gtk_icon_helper_peek_pixbuf (&priv->icon_helper);
-}
-
-/**
* gtk_image_get_surface:
* @image: a #GtkImage
*
@@ -1387,9 +1366,6 @@ gtk_image_notify_for_storage_type (GtkImage *image,
{
switch (storage_type)
{
- case GTK_IMAGE_PIXBUF:
- g_object_notify_by_pspec (G_OBJECT (image), image_props[PROP_PIXBUF]);
- break;
case GTK_IMAGE_ANIMATION:
g_object_notify_by_pspec (G_OBJECT (image), image_props[PROP_PIXBUF_ANIMATION]);
break;
@@ -1402,6 +1378,9 @@ gtk_image_notify_for_storage_type (GtkImage *image,
case GTK_IMAGE_SURFACE:
g_object_notify_by_pspec (G_OBJECT (image), image_props[PROP_SURFACE]);
break;
+ case GTK_IMAGE_PIXBUF:
+ g_warning ("pixbuf not supported");
+ break;
case GTK_IMAGE_EMPTY:
default:
break;
diff --git a/gtk/gtkimage.h b/gtk/gtkimage.h
index 52c5d49..79fc191 100644
--- a/gtk/gtkimage.h
+++ b/gtk/gtkimage.h
@@ -67,6 +67,10 @@ typedef struct _GtkImageClass GtkImageClass;
* call gtk_image_get_pixbuf(). For empty images, you can request any
* storage type (call any of the "get" functions), but they will all
* return %NULL values.
+ *
+ * Note: GTK_IMAGE_PIXBUF is not not supported as storage by GtkImage. Any
+ * pixbuf set on the GtkImage will be converted to a surface and can only
+ * be read back as a GTK_IMAGE_SURFACE.
*/
typedef enum
{
@@ -154,9 +158,6 @@ void gtk_image_set_pixel_size (GtkImage *image,
GDK_AVAILABLE_IN_ALL
GtkImageType gtk_image_get_storage_type (GtkImage *image);
-GDK_AVAILABLE_IN_ALL
-GdkPixbuf* gtk_image_get_pixbuf (GtkImage *image);
-
GDK_AVAILABLE_IN_3_94
cairo_surface_t *gtk_image_get_surface (GtkImage *image);
diff --git a/gtk/gtktoolbutton.c b/gtk/gtktoolbutton.c
index c94e1fd..a3c019e 100644
--- a/gtk/gtktoolbutton.c
+++ b/gtk/gtktoolbutton.c
@@ -723,21 +723,32 @@ clone_image_menu_size (GtkImage *image)
gtk_image_get_gicon (image, &icon, NULL);
return gtk_image_new_from_gicon (icon, GTK_ICON_SIZE_MENU);
}
- else if (storage_type == GTK_IMAGE_PIXBUF)
+ else if (storage_type == GTK_IMAGE_SURFACE)
{
gint width, height;
-
- if (gtk_icon_size_lookup (GTK_ICON_SIZE_MENU, &width, &height))
- {
- GdkPixbuf *src_pixbuf, *dest_pixbuf;
- GtkWidget *cloned_image;
- src_pixbuf = gtk_image_get_pixbuf (image);
- dest_pixbuf = gdk_pixbuf_scale_simple (src_pixbuf, width, height,
- GDK_INTERP_BILINEAR);
-
- cloned_image = gtk_image_new_from_pixbuf (dest_pixbuf);
- g_object_unref (dest_pixbuf);
+ if (gtk_icon_size_lookup (GTK_ICON_SIZE_MENU, &width, &height))
+ {
+ cairo_surface_t *src_surface, *dest_surface;
+ GtkWidget *cloned_image;
+ gint scale = gtk_widget_get_scale_factor (GTK_WIDGET (image));
+ cairo_t *cr;
+
+ src_surface = gtk_image_get_surface (image);
+ dest_surface =
+ gdk_window_create_similar_image_surface (gtk_widget_get_window (GTK_WIDGET(image)),
+ CAIRO_FORMAT_ARGB32,
+ width * scale, height * scale, scale);
+ cr = cairo_create (dest_surface);
+ cairo_set_source_surface (cr, src_surface, 0, 0);
+ cairo_scale (cr,
+ width / cairo_image_surface_get_width (src_surface),
+ height / cairo_image_surface_get_height (src_surface));
+ cairo_paint (cr);
+ cairo_destroy (cr);
+
+ cloned_image = gtk_image_new_from_surface (dest_surface);
+ cairo_surface_destroy (dest_surface);
return cloned_image;
}
diff --git a/tests/testimage.c b/tests/testimage.c
index aa33374..a9be868 100644
--- a/tests/testimage.c
+++ b/tests/testimage.c
@@ -40,9 +40,9 @@ drag_data_get (GtkWidget *widget,
{
GtkWidget *image = GTK_WIDGET (data);
- GdkPixbuf *pixbuf = gtk_image_get_pixbuf (GTK_IMAGE (image));
+ cairo_surface_t *surface = gtk_image_get_surface (GTK_IMAGE (image));
- gtk_selection_data_set_pixbuf (selection_data, pixbuf);
+ gtk_selection_data_set_surface (selection_data, surface);
}
static void
@@ -56,15 +56,14 @@ drag_data_received (GtkWidget *widget,
gpointer data)
{
GtkWidget *image = GTK_WIDGET (data);
-
- GdkPixbuf *pixbuf;
+ cairo_surface_t *surface;
if (gtk_selection_data_get_length (selection_data) < 0)
return;
- pixbuf = gtk_selection_data_get_pixbuf (selection_data);
+ surface = gtk_selection_data_get_surface (selection_data);
- gtk_image_set_from_pixbuf (GTK_IMAGE (image), pixbuf);
+ gtk_image_set_from_surface (GTK_IMAGE (image), surface);
}
static gboolean
@@ -81,7 +80,7 @@ main (int argc, char **argv)
GtkWidget *window, *grid;
GtkWidget *label, *image;
GtkIconTheme *theme;
- GdkPixbuf *pixbuf;
+ cairo_surface_t *surface;
gchar *icon_name = "help-browser";
gchar *anim_filename = NULL;
GIcon *icon;
@@ -111,8 +110,8 @@ main (int argc, char **argv)
gtk_grid_attach (GTK_GRID (grid), label, 0, 1, 1, 1);
theme = gtk_icon_theme_get_default ();
- pixbuf = gtk_icon_theme_load_icon (theme, icon_name, 48, 0, NULL);
- image = gtk_image_new_from_pixbuf (pixbuf);
+ surface = gtk_icon_theme_load_surface (theme, icon_name, 48, gtk_widget_get_scale_factor (window),
gtk_widget_get_window (window), 0, NULL);
+ image = gtk_image_new_from_surface (surface);
gtk_grid_attach (GTK_GRID (grid), image, 2, 1, 1, 1);
gtk_drag_source_set (image, GDK_BUTTON1_MASK,
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]