Re: Model/view ideas for GtkListBox/GtkFlowBox

Hey Alex,

I've been playing with this idea myself, have a look at this github
repo[0], don't pay too much attention to the ListView widget, I'm
pretty much replicating Gtk.ListBox for the sake of understanding how
to implement such widget.
I am trying to experiement with a "scalable" approach where you can
have a large data set and a bound set of allocated widgets necessary
to display in the scrolledwindow (and also to avoid new widget
allocations while you scroll). Some people think this is a bit of an
overkill so I don't want to get too deep into this discussion while
it's still an experiment.

There is one thing that I'd like to discuss about the API that I
designed there and it is the notion of the RowDelegate, which is an
interface that requires GtkBin and points to a specific index (or row)
of a GObjectSet (Data.List in the source).

The idea here is that the application developer would implement this
interface and stuff it with whatever he wants, he would be responsible
for updating the contents if the data "pointed" by the index changes
or if the row itself changes. Then you pass your new class as an
argument when you create a new ListBox and ListBox does the index
binding itself and he can automatically create/destroy/move items by
reacting to changes in the model.

Let me know your thoughts.


2013/10/23 Alexander Larsson <alexl redhat com>:
More and more gnome apps are migrating to GtkListBox rather than
GtkTreeView for lists, and we now have GtkFlowBox that replaces
GtkIconView. These are nice for smaller lists, but with larger lists
they are a bit heavy. We may want to look at optimizing whatever is
possible, but at some point it makes sense to have a model/view split
that allows us to have large models without having each item in the
model be instantiated as a widget, both for performance reasons
and ease of use.

I've been thinking of ways to do this, and had plans to implement
this, but atm I'm busy working on a side project, so I don't have time
for this atm. I thought I'd write up a braindump of my ideas so that
maybe someone else can look at it, or at least it won't be losts.

So, the general idea is that we have a model, and we create and update
row widgets from the model based on some kind of template. The new
GtkBuilder class templates is an excellent example of how this could
work. We then create widgets as needed as they are scrolled into (or
near) view. One obvious problem with this is that we don't know the
height of the rows until we have widgets for them, so the listbox
probably has to be changed to implement GtkScrollable and do scrolling
based on row-nr and average height rather than exact offsets.

The model itself is a set of GObjects, where the data in the model is
stored as GObject properties. This is very flexible, in that we have
names (no more column nr shit) for the data that is easy to map to
properties (like GBinding, possibly with some transform function) in
the row widget template, as well as to generic sorting/filtering
functions. Property notification makes incremental updates
possible. The GProperty work being done will make it very simple to
create such model objects, and make property lookups very
efficient. Then we need to add a GObjectSet interface that has signals
for when objects are added and removed to the set, which would be used
as the model itself, but also as a property type for recursive models
(i.e. trees).

View updates on a model like this can be pretty efficient. We connect
to the added/removed signals on the set and keep track of the items
(and per-view info like selection status) in the view in a sorted &
filtered GSequence, then we connect to notify on all the model
elements and whenever we get it we look up the GParamSpec to see how
it affects the model (i.e. are we filtering/sorting/showing the
changed property). If anything is affected we flag things in the view
and request and update on the frame clock, so that we can minimally
update the view structure and any visible widgets at most once per

I believe we should also have some sort property caches in the view
objects. For instance any sort by string we should be monitoring
changes to the corresponding property and keep a g_utf8_collate_key()
or g_utf8_collate_key_for_filename() key up to date for fast
comparisons. That should easily integrate with the update cycle above.

We should also allow sorting based on object relationships. For
instance, if we had a "GObject *parent" property that could be used to
create a tree view if the view supported specifying that a child
should be sorted directly after its parent. You can event do more
complex structures like the twitter-style "expand in-reply-to/replies
before/after a tweet".

gtk-devel-list mailing list
gtk-devel-list gnome org

Alberto Ruiz

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