3

I have a simple GTK3 GUI with a treeview and treestore. I need to filter the column with data3 string and show only data3 row. But it also hides data3 row. Because parent row of the data3 column is also hidden.

It works when I use return model[iter][2] == "data2" instead of return model[iter][2] == "data3".

All of the rows could be viewed by commenting out this line: filter1.set_visible_func(filter1_func)

How could I fix this?

Simplified code:

import gi
gi.require_version('Gtk', '3.0')
from gi.repository import Gtk, GLib

builder = Gtk.Builder()
builder.add_from_file('test.glade')
builder.get_objects()
window1 = builder.get_object('window1')
treeview1 = builder.get_object('treeview1')

class Signals:
    def on_window1_destroy(self, widget):
        Gtk.main_quit()

def filter1_func(model, iter, data):
    return model[iter][2] == "data3"

list_data = [["text1", "data1", "data2"], ["text2", "data1", "data2"], ["text3", "data1", "data3"]]

treestore1 = Gtk.TreeStore(str, str, str)
piter1 = treestore1.append(None, list_data[0])
piter2 = treestore1.append(piter1, list_data[1])
piter3 = treestore1.append(piter1, list_data[2])

treeview1.set_model(treestore1)
filter1 = treestore1.filter_new()
filter1.set_visible_func(filter1_func)
filter1.refilter()

for i, column_title in enumerate(["col1", "col2", "col3"]):
    renderer = Gtk.CellRendererText()
    column = Gtk.TreeViewColumn(column_title, renderer, text=i)
    treeview1.append_column(column)

treeview1.set_model(filter1)
treeview1.expand_all()

builder.connect_signals(Signals())
window1.show_all()
Gtk.main()
demirod
  • 81
  • 15
  • As far as I know, there is no way to throw away parents and leave children. Neither in GTK, nor in Qt. Invisible parent means invisibility for all children. The first thing I can offer is quite obvious: come to terms with parent's visibility:) The second is to flatten your model. The second is to have both TreeStore and ListStore and dynamically update view's model when filtering is applied by user. The fourth would be much more difficult: subclass GtkTreeModel which would provide a *list* or *tree* of items if filtering is set or not set respectively. – Alexander Dmitriev Mar 18 '21 at 16:08
  • @Alexander Dmitriev, There is an example (at the end of the page) suggested in the first answer by oduncu90 user. But I am not a programmer and not very good at Python programming. It is a complicated example for me. It works when I excute the hole code in the example. I do not know it is in which way you offered. – demirod Mar 18 '21 at 16:18
  • Oh, that may be essential. Gtk has `ListStore` and `TreeStore`. Trees have hierarchy: a row can have child nodes, which can also have child nodes. List is, well, a list of items, all of them are at the same level, no parents, no children. If the look of that *Treeview filter demo* is ok for your data set, just use it and your code will work fine. – Alexander Dmitriev Mar 18 '21 at 21:07
  • By the way, TreeStore *can* be used like ListStore, if none of the items have parent nodes. This call: `piter2 = treestore1.append(piter1...)` makes a new row, which parent is `piter1`. – Alexander Dmitriev Mar 18 '21 at 21:11

1 Answers1

1

Have you tried the method in the last example of the link?

A treeview with a liststore is used in the example and treeview is updated with a function with a liststore filter. You may try modifying the code for your need (treeview with treestore).

Note: It is for liststore. I do not know if it works for a treeview with liststore. You may try updating your treeview with treestore by updating the entire model, but this may be computationally expensive.