treelistmodel: Fix handling of collapsed nodes

When we collapse a node, we clear out the children,
but we were not disconnecting the signal handler on
the child listmodel, leading to bad outcomes when
that model is persistent and changing.

Fixes: #4595
This commit is contained in:
Matthias Clasen 2022-08-24 08:20:33 -04:00 committed by Mat
parent 083d023b6b
commit d21112a3ce

View File

@ -436,6 +436,20 @@ gtk_tree_list_model_items_changed_cb (GListModel *model,
static void gtk_tree_list_row_destroy (GtkTreeListRow *row);
static void
gtk_tree_list_model_clear_node_children (TreeNode *node)
{
if (node->model)
{
g_signal_handlers_disconnect_by_func (node->model,
gtk_tree_list_model_items_changed_cb,
node);
g_clear_object (&node->model);
}
g_clear_pointer (&node->children, gtk_rb_tree_unref);
}
static void
gtk_tree_list_model_clear_node (gpointer data)
{
@ -444,15 +458,7 @@ gtk_tree_list_model_clear_node (gpointer data)
if (node->row)
gtk_tree_list_row_destroy (node->row);
if (node->model)
{
g_signal_handlers_disconnect_by_func (node->model,
gtk_tree_list_model_items_changed_cb,
node);
g_object_unref (node->model);
}
if (node->children)
gtk_rb_tree_unref (node->children);
gtk_tree_list_model_clear_node_children (node);
}
static void
@ -547,8 +553,7 @@ gtk_tree_list_model_collapse_node (GtkTreeListModel *self,
n_items = tree_node_get_n_children (node);
g_clear_pointer (&node->children, gtk_rb_tree_unref);
g_clear_object (&node->model);
gtk_tree_list_model_clear_node_children (node);
tree_node_mark_dirty (node);