[gtk/wip/otte/listview: 49/58] listview: Expose GtkListItemFactory APIs



commit ef78af5621e08ec1cf1b9f925f5384fba4dd8711
Author: Benjamin Otte <otte redhat com>
Date:   Wed Oct 9 00:07:07 2019 +0200

    listview: Expose GtkListItemFactory APIs
    
    Due to the many different ways to set factories, it makes sense to
    expose them as custom objects.
    
    This makes the actual APIs for the list widgets simpler, because they
    can just have a regular "factory" property.
    
    As a convenience function, gtk_list_view_new_with_factory() was added
    to make this whole approach easy to use from C.

 demos/gtk-demo/awardview.c                         |   6 +-
 demos/gtk-demo/listview_weather.c                  |   9 +-
 docs/reference/gtk/gtk4-sections.txt               |   3 +
 gtk/gtk.h                                          |   3 +
 gtk/gtkbuilderlistitemfactory.c                    |   3 +-
 ...actoryprivate.h => gtkbuilderlistitemfactory.h} |  10 +-
 gtk/gtkfunctionslistitemfactory.c                  |   3 +-
 ...toryprivate.h => gtkfunctionslistitemfactory.h} |  38 ++++++-
 gtk/gtklistitem.h                                  |  28 -----
 gtk/gtklistitemfactory.h                           |  48 ++++++++
 gtk/gtklistitemfactoryprivate.h                    |  19 +---
 gtk/gtklistview.c                                  | 123 ++++++++++++++-------
 gtk/gtklistview.h                                  |  16 +--
 gtk/gtktypes.h                                     |   1 +
 gtk/meson.build                                    |   3 +
 tests/testlistview-animating.c                     |   9 +-
 tests/testlistview.c                               |  10 +-
 17 files changed, 217 insertions(+), 115 deletions(-)
---
diff --git a/demos/gtk-demo/awardview.c b/demos/gtk-demo/awardview.c
index ebf1794672..3303460add 100644
--- a/demos/gtk-demo/awardview.c
+++ b/demos/gtk-demo/awardview.c
@@ -53,15 +53,15 @@ do_awardview (GtkWidget *do_widget)
       sw = gtk_scrolled_window_new (NULL, NULL);
       gtk_container_add (GTK_CONTAINER (window), sw);
 
-      listview = gtk_list_view_new ();
 #if 0
+      listview = gtk_list_view_new ();
       gtk_list_view_set_functions (GTK_LIST_VIEW (listview),
                                    create_listitem,
                                    bind_listitem,
                                    NULL, NULL);
 #else
-      gtk_list_view_set_factory_from_resource (GTK_LIST_VIEW (listview),
-                                               "/awardview/awardlistitem.ui");
+      listview = gtk_list_view_new_with_factory (
+          gtk_builder_list_item_factory_new_from_resource ("/awardview/awardlistitem.ui"));
 #endif
       list = gtk_award_get_list ();
       gtk_list_view_set_model (GTK_LIST_VIEW (listview), list);
diff --git a/demos/gtk-demo/listview_weather.c b/demos/gtk-demo/listview_weather.c
index 3574f57369..e7fe3b508d 100644
--- a/demos/gtk-demo/listview_weather.c
+++ b/demos/gtk-demo/listview_weather.c
@@ -292,13 +292,12 @@ do_listview_weather (GtkWidget *do_widget)
       sw = gtk_scrolled_window_new (NULL, NULL);
       gtk_container_add (GTK_CONTAINER (window), sw);
     
-      listview = gtk_list_view_new ();
+      listview = gtk_list_view_new_with_factory (
+        gtk_functions_list_item_factory_new (setup_widget,
+                                             bind_widget,
+                                             NULL, NULL));
       gtk_orientable_set_orientation (GTK_ORIENTABLE (listview), GTK_ORIENTATION_HORIZONTAL);
       gtk_list_view_set_show_separators (GTK_LIST_VIEW (listview), TRUE);
-      gtk_list_view_set_functions (GTK_LIST_VIEW (listview),
-                                   setup_widget,
-                                   bind_widget,
-                                   NULL, NULL);
       model = create_weather_model ();
       selection = G_LIST_MODEL (gtk_no_selection_new (model));
       gtk_list_view_set_model (GTK_LIST_VIEW (listview), selection);
diff --git a/docs/reference/gtk/gtk4-sections.txt b/docs/reference/gtk/gtk4-sections.txt
index a16dd96e12..5c7f4bed2b 100644
--- a/docs/reference/gtk/gtk4-sections.txt
+++ b/docs/reference/gtk/gtk4-sections.txt
@@ -518,6 +518,9 @@ gtk_list_item_get_type
 <TITLE>GtkListView</TITLE>
 GtkListView
 gtk_list_view_new
+gtk_list_view_new_with_factory
+gtk_list_view_set_factory
+gtk_list_view_get_factory
 gtk_list_view_set_model
 gtk_list_view_get_model
 gtk_list_view_set_show_separators
diff --git a/gtk/gtk.h b/gtk/gtk.h
index 7a5c5ad113..9676872c3c 100644
--- a/gtk/gtk.h
+++ b/gtk/gtk.h
@@ -55,6 +55,7 @@
 #include <gtk/gtkbox.h>
 #include <gtk/gtkbuildable.h>
 #include <gtk/gtkbuilder.h>
+#include <gtk/gtkbuilderlistitemfactory.h>
 #include <gtk/gtkbutton.h>
 #include <gtk/gtkcalendar.h>
 #include <gtk/gtkcellarea.h>
@@ -122,6 +123,7 @@
 #include <gtk/gtkfontchooserdialog.h>
 #include <gtk/gtkfontchooserwidget.h>
 #include <gtk/gtkframe.h>
+#include <gtk/gtkfunctionslistitemfactory.h>
 #include <gtk/gtkgesture.h>
 #include <gtk/gtkgestureclick.h>
 #include <gtk/gtkgesturedrag.h>
@@ -151,6 +153,7 @@
 #include <gtk/gtklinkbutton.h>
 #include <gtk/gtklistbox.h>
 #include <gtk/gtklistitem.h>
+#include <gtk/gtklistitemfactory.h>
 #include <gtk/gtkliststore.h>
 #include <gtk/gtklistview.h>
 #include <gtk/gtklockbutton.h>
diff --git a/gtk/gtkbuilderlistitemfactory.c b/gtk/gtkbuilderlistitemfactory.c
index b4c90554d1..4ff667cab1 100644
--- a/gtk/gtkbuilderlistitemfactory.c
+++ b/gtk/gtkbuilderlistitemfactory.c
@@ -19,9 +19,10 @@
 
 #include "config.h"
 
-#include "gtkbuilderlistitemfactoryprivate.h"
+#include "gtkbuilderlistitemfactory.h"
 
 #include "gtkbuilder.h"
+#include "gtklistitemfactoryprivate.h"
 #include "gtklistitemprivate.h"
 
 struct _GtkBuilderListItemFactory
diff --git a/gtk/gtkbuilderlistitemfactoryprivate.h b/gtk/gtkbuilderlistitemfactory.h
similarity index 90%
rename from gtk/gtkbuilderlistitemfactoryprivate.h
rename to gtk/gtkbuilderlistitemfactory.h
index b2cbf1b918..f0459e44d5 100644
--- a/gtk/gtkbuilderlistitemfactoryprivate.h
+++ b/gtk/gtkbuilderlistitemfactory.h
@@ -17,11 +17,14 @@
  * Authors: Benjamin Otte <otte gnome org>
  */
 
-
 #ifndef __GTK_BUILDER_LIST_ITEM_FACTORY_H__
 #define __GTK_BUILDER_LIST_ITEM_FACTORY_H__
 
-#include "gtklistitemfactoryprivate.h"
+#if !defined (__GTK_H_INSIDE__) && !defined (GTK_COMPILATION)
+#error "Only <gtk/gtk.h> can be included directly."
+#endif
+
+#include <gtk/gtklistitemfactory.h>
 
 G_BEGIN_DECLS
 
@@ -35,9 +38,12 @@ G_BEGIN_DECLS
 typedef struct _GtkBuilderListItemFactory GtkBuilderListItemFactory;
 typedef struct _GtkBuilderListItemFactoryClass GtkBuilderListItemFactoryClass;
 
+GDK_AVAILABLE_IN_ALL
 GType                   gtk_builder_list_item_factory_get_type          (void) G_GNUC_CONST;
 
+GDK_AVAILABLE_IN_ALL
 GtkListItemFactory *    gtk_builder_list_item_factory_new_from_bytes    (GBytes         *bytes);
+GDK_AVAILABLE_IN_ALL
 GtkListItemFactory *    gtk_builder_list_item_factory_new_from_resource (const char     *resource_path);
 
 
diff --git a/gtk/gtkfunctionslistitemfactory.c b/gtk/gtkfunctionslistitemfactory.c
index 6841a2a36b..6b7c2814b9 100644
--- a/gtk/gtkfunctionslistitemfactory.c
+++ b/gtk/gtkfunctionslistitemfactory.c
@@ -19,8 +19,9 @@
 
 #include "config.h"
 
-#include "gtkfunctionslistitemfactoryprivate.h"
+#include "gtkfunctionslistitemfactory.h"
 
+#include "gtklistitemfactoryprivate.h"
 #include "gtklistitemprivate.h"
 
 struct _GtkFunctionsListItemFactory
diff --git a/gtk/gtkfunctionslistitemfactoryprivate.h b/gtk/gtkfunctionslistitemfactory.h
similarity index 68%
rename from gtk/gtkfunctionslistitemfactoryprivate.h
rename to gtk/gtkfunctionslistitemfactory.h
index aeac050a28..116ef52af9 100644
--- a/gtk/gtkfunctionslistitemfactoryprivate.h
+++ b/gtk/gtkfunctionslistitemfactory.h
@@ -17,11 +17,15 @@
  * Authors: Benjamin Otte <otte gnome org>
  */
 
-
 #ifndef __GTK_FUNCTIONS_LIST_ITEM_FACTORY_H__
 #define __GTK_FUNCTIONS_LIST_ITEM_FACTORY_H__
 
-#include "gtklistitemfactoryprivate.h"
+#if !defined (__GTK_H_INSIDE__) && !defined (GTK_COMPILATION)
+#error "Only <gtk/gtk.h> can be included directly."
+#endif
+
+#include <gtk/gtklistitemfactory.h>
+#include <gtk/gtklistitem.h>
 
 G_BEGIN_DECLS
 
@@ -35,8 +39,38 @@ G_BEGIN_DECLS
 typedef struct _GtkFunctionsListItemFactory GtkFunctionsListItemFactory;
 typedef struct _GtkFunctionsListItemFactoryClass GtkFunctionsListItemFactoryClass;
 
+/**
+ * GtkListItemSetupFunc:
+ * @item: the #GtkListItem to set up
+ * @user_data: (closure): user data
+ *
+ * Called whenever a new list item needs to be setup for managing a row in
+ * the list.
+ *
+ * At this point, the list item is not bound yet, so gtk_list_item_get_item()
+ * will return %NULL.
+ * The list item will later be bound to an item via the #GtkListItemBindFunc.
+ */
+typedef void (* GtkListItemSetupFunc) (GtkListItem *item, gpointer user_data);
+
+/**
+ * GtkListItemBindFunc:
+ * @item: the #GtkListItem to bind
+ * @user_data: (closure): user data
+ *
+ * Binds a#GtkListItem previously set up via a #GtkListItemSetupFunc to
+ * an @item.
+ *
+ * Rebinding a @item to different @items is supported as well as
+ * unbinding it by setting @item to %NULL.
+ */
+typedef void (* GtkListItemBindFunc) (GtkListItem *item,
+                                      gpointer   user_data);
+
+GDK_AVAILABLE_IN_ALL
 GType                   gtk_functions_list_item_factory_get_type (void) G_GNUC_CONST;
 
+GDK_AVAILABLE_IN_ALL
 GtkListItemFactory *    gtk_functions_list_item_factory_new     (GtkListItemSetupFunc    setup_func,
                                                                  GtkListItemBindFunc     bind_func,
                                                                  gpointer                user_data,
diff --git a/gtk/gtklistitem.h b/gtk/gtklistitem.h
index ec92653e23..a783b8af56 100644
--- a/gtk/gtklistitem.h
+++ b/gtk/gtklistitem.h
@@ -31,34 +31,6 @@ G_BEGIN_DECLS
 GDK_AVAILABLE_IN_ALL
 G_DECLARE_FINAL_TYPE (GtkListItem, gtk_list_item, GTK, LIST_ITEM, GtkBin)
 
-/**
- * GtkListItemSetupFunc:
- * @item: the #GtkListItem to set up
- * @user_data: (closure): user data
- *
- * Called whenever a new list item needs to be setup for managing a row in
- * the list.
- *
- * At this point, the list item is not bound yet, so gtk_list_item_get_item()
- * will return %NULL.
- * The list item will later be bound to an item via the #GtkListItemBindFunc.
- */
-typedef void (* GtkListItemSetupFunc) (GtkListItem *item, gpointer user_data);
-
-/**
- * GtkListItemBindFunc:
- * @item: the #GtkListItem to bind
- * @user_data: (closure): user data
- *
- * Binds a#GtkListItem previously set up via a #GtkListItemSetupFunc to
- * an @item.
- *
- * Rebinding a @item to different @items is supported as well as
- * unbinding it by setting @item to %NULL.
- */
-typedef void (* GtkListItemBindFunc) (GtkListItem *item,
-                                      gpointer   user_data);
-
 #define GTK_TYPE_LIST_ITEM         (gtk_list_item_get_type ())
 
 GDK_AVAILABLE_IN_ALL
diff --git a/gtk/gtklistitemfactory.h b/gtk/gtklistitemfactory.h
new file mode 100644
index 0000000000..629beb66fb
--- /dev/null
+++ b/gtk/gtklistitemfactory.h
@@ -0,0 +1,48 @@
+/*
+ * Copyright © 2019 Benjamin Otte
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * Authors: Benjamin Otte <otte gnome org>
+ */
+
+#ifndef __GTK_LIST_ITEM_FACTORY_H__
+#define __GTK_LIST_ITEM_FACTORY_H__
+
+#if !defined (__GTK_H_INSIDE__) && !defined (GTK_COMPILATION)
+#error "Only <gtk/gtk.h> can be included directly."
+#endif
+
+typedef struct _GtkListItemFactoryClass GtkListItemFactoryClass;
+
+#include <gdk/gdk.h>
+#include <gtk/gtktypes.h>
+
+G_BEGIN_DECLS
+
+#define GTK_TYPE_LIST_ITEM_FACTORY         (gtk_list_item_factory_get_type ())
+#define GTK_LIST_ITEM_FACTORY(o)           (G_TYPE_CHECK_INSTANCE_CAST ((o), GTK_TYPE_LIST_ITEM_FACTORY, 
GtkListItemFactory))
+#define GTK_LIST_ITEM_FACTORY_CLASS(k)     (G_TYPE_CHECK_CLASS_CAST ((k), GTK_TYPE_LIST_ITEM_FACTORY, 
GtkListItemFactoryClass))
+#define GTK_IS_LIST_ITEM_FACTORY(o)        (G_TYPE_CHECK_INSTANCE_TYPE ((o), GTK_TYPE_LIST_ITEM_FACTORY))
+#define GTK_IS_LIST_ITEM_FACTORY_CLASS(k)  (G_TYPE_CHECK_CLASS_TYPE ((k), GTK_TYPE_LIST_ITEM_FACTORY))
+#define GTK_LIST_ITEM_FACTORY_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), GTK_TYPE_LIST_ITEM_FACTORY, 
GtkListItemFactoryClass))
+
+
+GDK_AVAILABLE_IN_ALL
+GType        gtk_list_item_factory_get_type       (void) G_GNUC_CONST;
+
+
+G_END_DECLS
+
+#endif /* __GTK_LIST_ITEM_FACTORY_H__ */
diff --git a/gtk/gtklistitemfactoryprivate.h b/gtk/gtklistitemfactoryprivate.h
index dc32429dd2..d948db5ede 100644
--- a/gtk/gtklistitemfactoryprivate.h
+++ b/gtk/gtklistitemfactoryprivate.h
@@ -18,24 +18,15 @@
  */
 
 
-#ifndef __GTK_LIST_ITEM_FACTORY_H__
-#define __GTK_LIST_ITEM_FACTORY_H__
+#ifndef __GTK_LIST_ITEM_FACTORY_PRIVATE_H__
+#define __GTK_LIST_ITEM_FACTORY_PRIVATE_H__
 
 #include <gtk/gtklistitem.h>
+#include <gtk/gtklistitemfactory.h>
 #include <gtk/gtklistview.h>
 
 G_BEGIN_DECLS
 
-#define GTK_TYPE_LIST_ITEM_FACTORY         (gtk_list_item_factory_get_type ())
-#define GTK_LIST_ITEM_FACTORY(o)           (G_TYPE_CHECK_INSTANCE_CAST ((o), GTK_TYPE_LIST_ITEM_FACTORY, 
GtkListItemFactory))
-#define GTK_LIST_ITEM_FACTORY_CLASS(k)     (G_TYPE_CHECK_CLASS_CAST ((k), GTK_TYPE_LIST_ITEM_FACTORY, 
GtkListItemFactoryClass))
-#define GTK_IS_LIST_ITEM_FACTORY(o)        (G_TYPE_CHECK_INSTANCE_TYPE ((o), GTK_TYPE_LIST_ITEM_FACTORY))
-#define GTK_IS_LIST_ITEM_FACTORY_CLASS(k)  (G_TYPE_CHECK_CLASS_TYPE ((k), GTK_TYPE_LIST_ITEM_FACTORY))
-#define GTK_LIST_ITEM_FACTORY_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), GTK_TYPE_LIST_ITEM_FACTORY, 
GtkListItemFactoryClass))
-
-typedef struct _GtkListItemFactory GtkListItemFactory;
-typedef struct _GtkListItemFactoryClass GtkListItemFactoryClass;
-
 struct _GtkListItemFactory
 {
   GObject parent_instance;
@@ -74,8 +65,6 @@ struct _GtkListItemFactoryClass
                                                                  GtkListItem            *list_item);
 };
 
-GType                   gtk_list_item_factory_get_type          (void) G_GNUC_CONST;
-
 void                    gtk_list_item_factory_setup             (GtkListItemFactory     *self,
                                                                  GtkListItem            *list_item);
 void                    gtk_list_item_factory_teardown          (GtkListItemFactory     *self,
@@ -101,4 +90,4 @@ void                    gtk_list_item_factory_unbind            (GtkListItemFact
 
 G_END_DECLS
 
-#endif /* __GTK_LIST_ITEM_FACTORY_H__ */
+#endif /* __GTK_LIST_ITEM_FACTORY_PRIVATE_H__ */
diff --git a/gtk/gtklistview.c b/gtk/gtklistview.c
index 45124e90da..5e8093b607 100644
--- a/gtk/gtklistview.c
+++ b/gtk/gtklistview.c
@@ -22,8 +22,6 @@
 #include "gtklistview.h"
 
 #include "gtkadjustment.h"
-#include "gtkbuilderlistitemfactoryprivate.h"
-#include "gtkfunctionslistitemfactoryprivate.h"
 #include "gtkintl.h"
 #include "gtklistitemmanagerprivate.h"
 #include "gtkorientableprivate.h"
@@ -91,6 +89,7 @@ struct _ListRowAugment
 enum
 {
   PROP_0,
+  PROP_FACTORY,
   PROP_HADJUSTMENT,
   PROP_HSCROLL_POLICY,
   PROP_MODEL,
@@ -636,6 +635,10 @@ gtk_list_view_get_property (GObject    *object,
 
   switch (property_id)
     {
+    case PROP_FACTORY:
+      g_value_set_object (value, gtk_list_item_manager_get_factory (self->item_manager));
+      break;
+
     case PROP_HADJUSTMENT:
       g_value_set_object (value, self->adjustment[GTK_ORIENTATION_HORIZONTAL]);
       break;
@@ -720,6 +723,10 @@ gtk_list_view_set_property (GObject      *object,
 
   switch (property_id)
     {
+    case PROP_FACTORY:
+      gtk_list_view_set_factory (self, g_value_get_object (value));
+      break;
+
     case PROP_HADJUSTMENT:
       gtk_list_view_set_adjustment (self, GTK_ORIENTATION_HORIZONTAL, g_value_get_object (value));
       break;
@@ -911,6 +918,18 @@ gtk_list_view_class_init (GtkListViewClass *klass)
       g_param_spec_override ("vscroll-policy",
                              g_object_interface_find_property (iface, "vscroll-policy"));
 
+  /**
+   * GtkListView:factory:
+   *
+   * Factory for populating list items
+   */
+  properties[PROP_FACTORY] =
+    g_param_spec_object ("factory",
+                         P_("Factory"),
+                         P_("Factory for populating list items"),
+                         GTK_TYPE_LIST_ITEM_FACTORY,
+                         G_PARAM_READWRITE | G_PARAM_EXPLICIT_NOTIFY | G_PARAM_STATIC_STRINGS);
+
   /**
    * GtkListView:model:
    *
@@ -990,8 +1009,9 @@ gtk_list_view_init (GtkListView *self)
  *
  * Creates a new empty #GtkListView.
  *
- * You most likely want to call gtk_list_view_set_model() to set
- * a model and then set up a way to map its items to widgets next.
+ * You most likely want to call gtk_list_view_set_factory() to
+ * set up a way to map its items to widgets and gtk_list_view_set_model()
+ * to set a model to provide items next.
  *
  * Returns: a new #GtkListView
  **/
@@ -1001,6 +1021,41 @@ gtk_list_view_new (void)
   return g_object_new (GTK_TYPE_LIST_VIEW, NULL);
 }
 
+/**
+ * gtk_list_view_new_with_factory:
+ * @factory: (transfer full): The factory to populate items with
+ *
+ * Creates a new #GtkListView that uses the given @factory for
+ * mapping items to widgets.
+ *
+ * You most likely want to call gtk_list_view_set_model() to set
+ * a model next.
+ *
+ * The function takes ownership of the
+ * argument, so you can write code like
+ * ```
+ *   list_view = gtk_list_view_new_with_factory (
+ *     gtk_builder_list_item_factory_newfrom_resource ("/resource.ui"));
+ * ```
+ *
+ * Returns: a new #GtkListView using the given @factory
+ **/
+GtkWidget *
+gtk_list_view_new_with_factory (GtkListItemFactory *factory)
+{
+  GtkWidget *result;
+
+  g_return_val_if_fail (GTK_IS_LIST_ITEM_FACTORY (factory), NULL);
+
+  result = g_object_new (GTK_TYPE_LIST_VIEW,
+                         "factory", factory,
+                         NULL);
+
+  g_object_unref (factory);
+
+  return result;
+}
+
 /**
  * gtk_list_view_get_model:
  * @self: a #GtkListView
@@ -1063,50 +1118,42 @@ gtk_list_view_set_model (GtkListView *self,
   g_object_notify_by_pspec (G_OBJECT (self), properties[PROP_MODEL]);
 }
 
-void
-gtk_list_view_set_functions (GtkListView          *self,
-                             GtkListItemSetupFunc  setup_func,
-                             GtkListItemBindFunc   bind_func,
-                             gpointer              user_data,
-                             GDestroyNotify        user_destroy)
+/**
+ * gtk_list_view_get_factory:
+ * @self: a #GtkListView
+ *
+ * Gets the factory that's currently used to populate list items.
+ *
+ * Returns: (nullable) (transfer none): The factory in use
+ **/
+GtkListItemFactory *
+gtk_list_view_get_factory (GtkListView *self)
 {
-  GtkListItemFactory *factory;
-
-  g_return_if_fail (GTK_IS_LIST_VIEW (self));
-  g_return_if_fail (setup_func || bind_func);
-  g_return_if_fail (user_data != NULL || user_destroy == NULL);
+  g_return_val_if_fail (GTK_IS_LIST_VIEW (self), NULL);
 
-  factory = gtk_functions_list_item_factory_new (setup_func, bind_func, user_data, user_destroy);
-  gtk_list_item_manager_set_factory (self->item_manager, factory);
-  g_object_unref (factory);
+  return gtk_list_item_manager_get_factory (self->item_manager);
 }
 
+/**
+ * gtk_list_view_set_factory:
+ * @self: a #GtkListView
+ * @factory: (allow-none) (transfer none): the factory to use or %NULL for none
+ *
+ * Sets the #GtkListItemFactory to use for populating list items.
+ **/
 void
-gtk_list_view_set_factory_from_bytes (GtkListView *self,
-                                      GBytes      *bytes)
+gtk_list_view_set_factory (GtkListView        *self,
+                           GtkListItemFactory *factory)
 {
-  GtkListItemFactory *factory;
-
   g_return_if_fail (GTK_IS_LIST_VIEW (self));
-  g_return_if_fail (bytes != NULL);
+  g_return_if_fail (factory == NULL || GTK_LIST_ITEM_FACTORY (factory));
 
-  factory = gtk_builder_list_item_factory_new_from_bytes (bytes);
-  gtk_list_item_manager_set_factory (self->item_manager, factory);
-  g_object_unref (factory);
-}
-
-void
-gtk_list_view_set_factory_from_resource (GtkListView *self,
-                                         const char  *resource_path)
-{
-  GtkListItemFactory *factory;
-
-  g_return_if_fail (GTK_IS_LIST_VIEW (self));
-  g_return_if_fail (resource_path != NULL);
+  if (factory == gtk_list_item_manager_get_factory (self->item_manager))
+    return;
 
-  factory = gtk_builder_list_item_factory_new_from_resource (resource_path);
   gtk_list_item_manager_set_factory (self->item_manager, factory);
-  g_object_unref (factory);
+
+  g_object_notify_by_pspec (G_OBJECT (self), properties[PROP_FACTORY]);
 }
 
 /**
diff --git a/gtk/gtklistview.h b/gtk/gtklistview.h
index f953c360ab..205cf8e9aa 100644
--- a/gtk/gtklistview.h
+++ b/gtk/gtklistview.h
@@ -36,6 +36,8 @@ G_DECLARE_FINAL_TYPE (GtkListView, gtk_list_view, GTK, LIST_VIEW, GtkWidget)
 
 GDK_AVAILABLE_IN_ALL
 GtkWidget *     gtk_list_view_new                               (void);
+GDK_AVAILABLE_IN_ALL
+GtkWidget *     gtk_list_view_new_with_factory                  (GtkListItemFactory     *factory);
 
 GDK_AVAILABLE_IN_ALL
 GListModel *    gtk_list_view_get_model                         (GtkListView            *self);
@@ -43,17 +45,11 @@ GDK_AVAILABLE_IN_ALL
 void            gtk_list_view_set_model                         (GtkListView            *self,
                                                                  GListModel             *model);
 GDK_AVAILABLE_IN_ALL
-void            gtk_list_view_set_functions                     (GtkListView            *self,
-                                                                 GtkListItemSetupFunc    setup_func,
-                                                                 GtkListItemBindFunc     bind_func,
-                                                                 gpointer                user_data,
-                                                                 GDestroyNotify          user_destroy);
-GDK_AVAILABLE_IN_ALL
-void            gtk_list_view_set_factory_from_bytes            (GtkListView            *self,
-                                                                 GBytes                 *bytes);
+void            gtk_list_view_set_factory                       (GtkListView            *self,
+                                                                 GtkListItemFactory     *factory);
 GDK_AVAILABLE_IN_ALL
-void            gtk_list_view_set_factory_from_resource         (GtkListView            *self,
-                                                                 const char             *resource_path);
+GtkListItemFactory *
+                gtk_list_view_get_factory                       (GtkListView            *self);
 
 GDK_AVAILABLE_IN_ALL
 void            gtk_list_view_set_show_separators               (GtkListView            *self,
diff --git a/gtk/gtktypes.h b/gtk/gtktypes.h
index 2798bd1b02..1f0438ed80 100644
--- a/gtk/gtktypes.h
+++ b/gtk/gtktypes.h
@@ -39,6 +39,7 @@ typedef struct _GtkClipboard         GtkClipboard;
 typedef struct _GtkEventController     GtkEventController;
 typedef struct _GtkGesture             GtkGesture;
 typedef struct _GtkLayoutManager       GtkLayoutManager;
+typedef struct _GtkListItemFactory     GtkListItemFactory;
 typedef struct _GtkNative              GtkNative;
 typedef struct _GtkRequisition        GtkRequisition;
 typedef struct _GtkRoot               GtkRoot;
diff --git a/gtk/meson.build b/gtk/meson.build
index a6900f9a7c..c12427f27d 100644
--- a/gtk/meson.build
+++ b/gtk/meson.build
@@ -450,6 +450,7 @@ gtk_public_headers = files([
   'gtkboxlayout.h',
   'gtkbuildable.h',
   'gtkbuilder.h',
+  'gtkbuilderlistitemfactory.h',
   'gtkbutton.h',
   'gtkcalendar.h',
   'gtkcenterbox.h',
@@ -518,6 +519,7 @@ gtk_public_headers = files([
   'gtkfontchooserdialog.h',
   'gtkfontchooserwidget.h',
   'gtkframe.h',
+  'gtkfunctionslistitemfactory.h',
   'gtkgesture.h',
   'gtkgesturedrag.h',
   'gtkgesturelongpress.h',
@@ -548,6 +550,7 @@ gtk_public_headers = files([
   'gtklinkbutton.h',
   'gtklistbox.h',
   'gtklistitem.h',
+  'gtklistitemfactory.h',
   'gtkliststore.h',
   'gtklistview.h',
   'gtklockbutton.h',
diff --git a/tests/testlistview-animating.c b/tests/testlistview-animating.c
index 9f17996814..223ba458bb 100644
--- a/tests/testlistview-animating.c
+++ b/tests/testlistview-animating.c
@@ -153,11 +153,10 @@ main (int   argc,
   gtk_widget_set_vexpand (sw, TRUE);
   gtk_container_add (GTK_CONTAINER (vbox), sw);
 
-  listview = gtk_list_view_new ();
-  gtk_list_view_set_functions (GTK_LIST_VIEW (listview),
-                               setup_list_item,
-                               NULL,
-                               NULL, NULL);
+  listview = gtk_list_view_new_with_factory (
+    gtk_functions_list_item_factory_new (setup_list_item,
+                                         NULL,
+                                         NULL, NULL));
   gtk_container_add (GTK_CONTAINER (sw), listview);
 
   vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 4);
diff --git a/tests/testlistview.c b/tests/testlistview.c
index 8b530c6f57..2b7ef0a470 100644
--- a/tests/testlistview.c
+++ b/tests/testlistview.c
@@ -601,6 +601,7 @@ update_statusbar (GtkStatusbar *statusbar)
       g_string_append_printf (string, " (%u directories remaining)", active + g_slist_length (pending));
       result = G_SOURCE_CONTINUE;
     }
+      result = G_SOURCE_CONTINUE;
 
   gtk_statusbar_push (statusbar, 0, string->str);
   g_free (string->str);
@@ -654,11 +655,10 @@ main (int argc, char *argv[])
   gtk_search_entry_set_key_capture_widget (GTK_SEARCH_ENTRY (search_entry), sw);
   gtk_container_add (GTK_CONTAINER (vbox), sw);
 
-  listview = gtk_list_view_new ();
-  gtk_list_view_set_functions (GTK_LIST_VIEW (listview),
-                               setup_widget,
-                               NULL,
-                               NULL, NULL);
+  listview = gtk_list_view_new_with_factory (
+    gtk_functions_list_item_factory_new (setup_widget,
+                                         NULL,
+                                         NULL, NULL));
   gtk_container_add (GTK_CONTAINER (sw), listview);
 
   if (argc > 1)


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