From b4c81288e4c8490f1f6d2f8d738ff7649839385d Mon Sep 17 00:00:00 2001 From: Owen Taylor Date: Thu, 27 Mar 2003 00:10:25 +0000 Subject: [PATCH] Finish monitoring, add a TODO, fill in details in README, fix some missing finalization chainups --- gtk/gtkfilesystem.c | 16 +-- gtk/gtkfilesystem.h | 10 +- gtk/gtkfilesystemmodel.c | 294 +++++++++++++++++++++++++++++++-------- gtk/gtkfilesystemunix.c | 10 ++ 4 files changed, 257 insertions(+), 73 deletions(-) diff --git a/gtk/gtkfilesystem.c b/gtk/gtkfilesystem.c index aea65740f..1ec3cf29a 100644 --- a/gtk/gtkfilesystem.c +++ b/gtk/gtkfilesystem.c @@ -518,22 +518,22 @@ gtk_file_folder_base_init (gpointer g_class) g_cclosure_marshal_VOID__POINTER, G_TYPE_NONE, 1, G_TYPE_POINTER); - g_signal_new ("file_changed", + g_signal_new ("files_changed", iface_type, G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (GtkFileFolderIface, file_changed), + G_STRUCT_OFFSET (GtkFileFolderIface, files_changed), NULL, NULL, - g_cclosure_marshal_VOID__STRING, + g_cclosure_marshal_VOID__POINTER, G_TYPE_NONE, 1, - G_TYPE_STRING); - g_signal_new ("file_removed", + G_TYPE_POINTER); + g_signal_new ("files_removed", iface_type, G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (GtkFileFolderIface, file_removed), + G_STRUCT_OFFSET (GtkFileFolderIface, files_removed), NULL, NULL, - g_cclosure_marshal_VOID__STRING, + g_cclosure_marshal_VOID__POINTER, G_TYPE_NONE, 1, - G_TYPE_STRING); + G_TYPE_POINTER); initialized = TRUE; } diff --git a/gtk/gtkfilesystem.h b/gtk/gtkfilesystem.h index ad388aa6e..791cbd671 100644 --- a/gtk/gtkfilesystem.h +++ b/gtk/gtkfilesystem.h @@ -200,13 +200,13 @@ struct _GtkFileFolderIface /* Signals */ - void (*deleted) (GtkFileFolder *monitor); + void (*deleted) (GtkFileFolder *monitor); void (*files_added) (GtkFileFolder *monitor, GSList *uris); - void (*file_changed) (GtkFileFolder *monitor, - const gchar *uri); - void (*file_removed) (GtkFileFolder *monitor, - const gchar *uri); + void (*files_changed) (GtkFileFolder *monitor, + GSList *uris); + void (*files_removed) (GtkFileFolder *monitor, + GSList *uris); }; GType gtk_file_folder_get_type (void); diff --git a/gtk/gtkfilesystemmodel.c b/gtk/gtkfilesystemmodel.c index 45db4db30..284738bea 100644 --- a/gtk/gtkfilesystemmodel.c +++ b/gtk/gtkfilesystemmodel.c @@ -44,9 +44,6 @@ struct _GtkFileSystemModel FileModelNode *roots; GtkFileFolder *root_folder; - GSource *dummy_idle; - GSList *dummy_idle_nodes; - gushort max_depth; guint show_hidden : 1; @@ -132,29 +129,29 @@ static void file_model_node_clear (GtkFileSystemModel *mode static FileModelNode * file_model_node_get_children (GtkFileSystemModel *model, FileModelNode *node); -static void deleted_callback (GtkFileFolder *folder, - FileModelNode *node); -static void files_added_callback (GtkFileFolder *folder, - GSList *uris, - FileModelNode *node); -static void file_changed_callback (GtkFileFolder *folder, - const gchar *uri, - FileModelNode *node); -static void file_removed_callback (GtkFileFolder *folder, - const gchar *uri, - FileModelNode *node); - -static void root_deleted_callback (GtkFileFolder *folder, - GtkFileSystemModel *model); +static void deleted_callback (GtkFileFolder *folder, + FileModelNode *node); +static void files_added_callback (GtkFileFolder *folder, + GSList *uris, + FileModelNode *node); +static void files_changed_callback (GtkFileFolder *folder, + GSList *uris, + FileModelNode *node); +static void files_removed_callback (GtkFileFolder *folder, + GSList *uris, + FileModelNode *node); + +static void root_deleted_callback (GtkFileFolder *folder, + GtkFileSystemModel *model); static void root_files_added_callback (GtkFileFolder *folder, GSList *uris, GtkFileSystemModel *model); -static void root_file_changed_callback (GtkFileFolder *folder, - const gchar *uri, - GtkFileSystemModel *model); -static void root_file_removed_callback (GtkFileFolder *folder, - const gchar *uri, - GtkFileSystemModel *model); +static void root_files_changed_callback (GtkFileFolder *folder, + GSList *uris, + GtkFileSystemModel *model); +static void root_files_removed_callback (GtkFileFolder *folder, + GSList *uris, + GtkFileSystemModel *model); GType _gtk_file_system_model_get_type (void) @@ -589,10 +586,10 @@ _gtk_file_system_model_new (GtkFileSystem *file_system, G_CALLBACK (root_deleted_callback), model); g_signal_connect (model->root_folder, "files_added", G_CALLBACK (root_files_added_callback), model); - g_signal_connect (model->root_folder, "file_changed", - G_CALLBACK (root_file_changed_callback), model); - g_signal_connect (model->root_folder, "file_removed", - G_CALLBACK (root_file_removed_callback), model); + g_signal_connect (model->root_folder, "files_changed", + G_CALLBACK (root_files_changed_callback), model); + g_signal_connect (model->root_folder, "files_removed", + G_CALLBACK (root_files_removed_callback), model); } } else @@ -981,7 +978,7 @@ file_model_node_get_info (GtkFileSystemModel *model, if (node->is_dummy) { node->info = gtk_file_info_new (); - gtk_file_info_set_display_name (node->info, "Loading..."); + gtk_file_info_set_display_name (node->info, "(Empty)"); } else if (node->parent || model->root_folder) { @@ -1115,10 +1112,10 @@ file_model_node_get_children (GtkFileSystemModel *model, G_CALLBACK (deleted_callback), node); g_signal_connect (node->folder, "files_added", G_CALLBACK (files_added_callback), node); - g_signal_connect (node->folder, "file_changed", - G_CALLBACK (file_changed_callback), node); - g_signal_connect (node->folder, "file_removed", - G_CALLBACK (file_removed_callback), node); + g_signal_connect (node->folder, "files_changed", + G_CALLBACK (files_changed_callback), node); + g_signal_connect (node->folder, "files_removed", + G_CALLBACK (files_removed_callback), node); g_object_set_data (G_OBJECT (node->folder), "model-node", node); } @@ -1143,17 +1140,12 @@ file_model_node_get_children (GtkFileSystemModel *model, return node->children; } -static void -deleted_callback (GtkFileFolder *folder, - FileModelNode *node) -{ -} - static void do_files_added (GtkFileSystemModel *model, FileModelNode *parent_node, GSList *uris) { + GtkTreeModel *tree_model = GTK_TREE_MODEL (model); FileModelNode *children; FileModelNode *prev = NULL; GtkTreeIter iter; @@ -1167,7 +1159,7 @@ do_files_added (GtkFileSystemModel *model, if (parent_node) { iter.user_data = parent_node; - path = gtk_tree_model_get_path (GTK_TREE_MODEL (model), &iter); + path = gtk_tree_model_get_path (tree_model, &iter); children = parent_node->children; } else @@ -1229,8 +1221,6 @@ do_files_added (GtkFileSystemModel *model, if (new->is_visible) { - GtkTreeModel *tree_model = GTK_TREE_MODEL (model); - iter.user_data = new; path = gtk_tree_model_get_path (tree_model, &iter); gtk_tree_model_row_inserted (tree_model, path, &iter); @@ -1251,7 +1241,7 @@ do_files_added (GtkFileSystemModel *model, gtk_tree_path_up (dummy_path); gtk_tree_path_down (dummy_path); - gtk_tree_model_row_deleted (tree_model, path); + gtk_tree_model_row_deleted (tree_model, dummy_path); gtk_tree_path_free (dummy_path); } @@ -1264,6 +1254,186 @@ do_files_added (GtkFileSystemModel *model, g_slist_free (sorted_uris); } +static void +do_files_changed (GtkFileSystemModel *model, + FileModelNode *parent_node, + GSList *uris) +{ + GtkTreeModel *tree_model = GTK_TREE_MODEL (model); + FileModelNode *children; + FileModelNode *prev = NULL; + GtkTreeIter iter; + GtkTreePath *path; + GSList *sorted_uris; + GSList *tmp_list; + + sorted_uris = g_slist_copy (uris); + sorted_uris = g_slist_sort (sorted_uris, (GCompareFunc)strcmp); + + if (parent_node) + { + iter.user_data = parent_node; + path = gtk_tree_model_get_path (tree_model, &iter); + children = parent_node->children; + } + else + { + path = gtk_tree_path_new (); + children = model->roots; + } + + gtk_tree_path_down (path); + + if (parent_node && parent_node->has_dummy) + { + prev = children; + children = children->next; + gtk_tree_path_next (path); + } + + for (tmp_list = sorted_uris; tmp_list; tmp_list = tmp_list->next) + { + const gchar *uri = tmp_list->data; + + while (children && strcmp (children->uri, uri) < 0) + { + prev = children; + if (children->is_visible) + gtk_tree_path_next (path); + + children = children->next; + } + + if (children && strcmp (children->uri, uri) == 0) + { + gtk_tree_model_row_changed (tree_model, path, &iter); + } + else + { + /* Shouldn't happen */ + } + } + + gtk_tree_path_free (path); + g_slist_free (sorted_uris); +} + +static void +do_files_removed (GtkFileSystemModel *model, + FileModelNode *parent_node, + GSList *uris) +{ + GtkTreeModel *tree_model = GTK_TREE_MODEL (model); + FileModelNode *children; + FileModelNode *prev = NULL; + GtkTreeIter iter; + GtkTreePath *path; + GSList *sorted_uris; + GSList *tmp_list; + FileModelNode *tmp_child; + gint n_visible; + + sorted_uris = g_slist_copy (uris); + sorted_uris = g_slist_sort (sorted_uris, (GCompareFunc)strcmp); + + if (parent_node) + { + iter.user_data = parent_node; + path = gtk_tree_model_get_path (tree_model, &iter); + children = parent_node->children; + } + else + { + path = gtk_tree_path_new (); + children = model->roots; + } + + /* Count the number of currently visible children, so that + * can catch when we need to insert a dummy node. + */ + n_visible = 0; + for (tmp_child = children; tmp_child; tmp_child = tmp_child->next) + { + if (tmp_child->is_visible) + n_visible++; + } + + gtk_tree_path_down (path); + + if (parent_node && parent_node->has_dummy) + { + prev = children; + children = children->next; + gtk_tree_path_next (path); + } + + for (tmp_list = sorted_uris; tmp_list; tmp_list = tmp_list->next) + { + const gchar *uri = tmp_list->data; + + while (children && strcmp (children->uri, uri) < 0) + { + prev = children; + if (children->is_visible) + gtk_tree_path_next (path); + + children = children->next; + } + + if (children && strcmp (children->uri, uri) == 0) + { + FileModelNode *next = children->next; + + if (children->is_visible) + n_visible--; + + if (n_visible == 0) + { + FileModelNode *dummy = file_model_node_new (model, "***dummy***"); + dummy->is_visible = TRUE; + dummy->parent = parent_node; + dummy->is_dummy = TRUE; + + parent_node->children = dummy; + parent_node->has_dummy = TRUE; + + iter.user_data = dummy; + gtk_tree_model_row_inserted (tree_model, path, &iter); + gtk_tree_path_next (path); + + prev = dummy; + } + + if (prev) + prev->next = next; + else if (parent_node) + parent_node->children = next; + else + model->roots = next; + + if (children->is_visible) + gtk_tree_model_row_deleted (tree_model, path); + + file_model_node_free (children); + + children = next; + } + else + { + /* Shouldn't happen */ + } + } + + gtk_tree_path_free (path); + g_slist_free (sorted_uris); +} + +static void +deleted_callback (GtkFileFolder *folder, + FileModelNode *node) +{ +} + static void files_added_callback (GtkFileFolder *folder, GSList *uris, @@ -1273,45 +1443,49 @@ files_added_callback (GtkFileFolder *folder, } static void -root_files_added_callback (GtkFileFolder *folder, - GSList *uris, - GtkFileSystemModel *model) +files_changed_callback (GtkFileFolder *folder, + GSList *uris, + FileModelNode *node) { - do_files_added (model, NULL, uris); + do_files_changed (node->model, node, uris); } static void -file_changed_callback (GtkFileFolder *folder, - const gchar *uri, - FileModelNode *node) +files_removed_callback (GtkFileFolder *folder, + GSList *uris, + FileModelNode *node) { + do_files_removed (node->model, node, uris); } static void -file_removed_callback (GtkFileFolder *folder, - const gchar *uri, - FileModelNode *node) +root_deleted_callback (GtkFileFolder *folder, + GtkFileSystemModel *model) { } static void -root_deleted_callback (GtkFileFolder *folder, - GtkFileSystemModel *model) +root_files_added_callback (GtkFileFolder *folder, + GSList *uris, + GtkFileSystemModel *model) { + do_files_added (model, NULL, uris); } static void -root_file_changed_callback (GtkFileFolder *folder, - const gchar *uri, - GtkFileSystemModel *model) +root_files_changed_callback (GtkFileFolder *folder, + GSList *uris, + GtkFileSystemModel *model) { + do_files_changed (model, NULL, uris); } static void -root_file_removed_callback (GtkFileFolder *folder, - const gchar *uri, - GtkFileSystemModel *model) +root_files_removed_callback (GtkFileFolder *folder, + GSList *uris, + GtkFileSystemModel *model) { + do_files_removed (model, NULL, uris); } diff --git a/gtk/gtkfilesystemunix.c b/gtk/gtkfilesystemunix.c index 34e173dc3..94797a2fd 100644 --- a/gtk/gtkfilesystemunix.c +++ b/gtk/gtkfilesystemunix.c @@ -66,6 +66,9 @@ struct _GtkFileFolderUnix gchar *filename; }; +GObjectClass *system_parent_class; +GObjectClass *folder_parent_class; + static void gtk_file_system_unix_class_init (GtkFileSystemUnixClass *class); static void gtk_file_system_unix_iface_init (GtkFileSystemIface *iface); static void gtk_file_system_unix_init (GtkFileSystemUnix *impl); @@ -179,6 +182,8 @@ static void gtk_file_system_unix_class_init (GtkFileSystemUnixClass *class) { GObjectClass *gobject_class = G_OBJECT_CLASS (class); + + system_parent_class = g_type_class_peek_parent (class); gobject_class->finalize = gtk_file_system_unix_finalize; } @@ -203,6 +208,7 @@ gtk_file_system_unix_init (GtkFileSystemUnix *system_unix) static void gtk_file_system_unix_finalize (GObject *object) { + system_parent_class->finalize (object); } static GSList * @@ -529,6 +535,8 @@ gtk_file_folder_unix_class_init (GtkFileFolderUnixClass *class) { GObjectClass *gobject_class = G_OBJECT_CLASS (class); + folder_parent_class = g_type_class_peek_parent (class); + gobject_class->finalize = gtk_file_folder_unix_finalize; } @@ -550,6 +558,8 @@ gtk_file_folder_unix_finalize (GObject *object) GtkFileFolderUnix *folder_unix = GTK_FILE_FOLDER_UNIX (object); g_free (folder_unix->filename); + + folder_parent_class->finalize (object); } static GtkFileInfo * -- 2.43.2