Thu Nov 2 14:38:54 2006 John Ellis <johne@verizon.net>
authorJohn Ellis <johne@verizon.net>
Thu, 2 Nov 2006 19:45:18 +0000 (19:45 +0000)
committerJohn Ellis <johne@verizon.net>
Thu, 2 Nov 2006 19:45:18 +0000 (19:45 +0000)
        * view_file_list.c: Fix slow re-sort when updating list by clearing the
        list and adding items in the new order instead of simply moving them.
        Fixes bug #1451200.

ChangeLog
src/view_file_list.c

index 54a1ebf..9c31310 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+Thu Nov  2 14:38:54 2006  John Ellis  <johne@verizon.net>
+
+       * view_file_list.c: Fix slow re-sort when updating list by clearing the
+       list and adding items in the new order instead of simply moving them.
+       Fixes bug #1451200.
+
 Thu Nov  2 06:46:14 2006  John Ellis  <johne@verizon.net>
 
        * po/eo.po: Add Esperanto translation,
index 10f58bb..0995fe7 100644 (file)
@@ -734,10 +734,23 @@ static gboolean vflist_select_cb(GtkTreeSelection *selection, GtkTreeModel *stor
  *-----------------------------------------------------------------------------
  */
 
+static gboolean vflist_dummy_select_cb(GtkTreeSelection *selection, GtkTreeModel *store, GtkTreePath *tpath,
+                                       gboolean path_currently_selected, gpointer data)
+{
+       return TRUE;
+}
+
 void vflist_sort_set(ViewFileList *vfl, SortType type, gint ascend)
 {
+       GtkTreeModel *model;
        GtkListStore *store;
        GList *work;
+       GtkTreeSelection *selection;
+       GtkTreePath *tpath;
+       GtkTreeIter iter;
+       GList *select_list;
+       FileData *cursor_fd = NULL;
+       gint single_select;
 
        if (vfl->sort_method == type && vfl->sort_ascend == ascend) return;
 
@@ -748,9 +761,12 @@ void vflist_sort_set(ViewFileList *vfl, SortType type, gint ascend)
 
        vfl->list = filelist_sort(vfl->list, vfl->sort_method, vfl->sort_ascend);
 
+       /* now reorder the treeview, maintaining current selection */
+
+#if 0
+       /* this is simpler, but much slower */
        store = GTK_LIST_STORE(gtk_tree_view_get_model(GTK_TREE_VIEW(vfl->listview)));
 
-       /* reorder the treeview, maintaining current selection */
        work = g_list_last(vfl->list);
        while (work)
                {
@@ -765,6 +781,87 @@ void vflist_sort_set(ViewFileList *vfl, SortType type, gint ascend)
 
                work = work->prev;
                }
+#endif
+
+       selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(vfl->listview));
+
+       gtk_tree_selection_set_select_function(selection, vflist_dummy_select_cb, vfl, NULL);
+
+       select_list = gtk_tree_selection_get_selected_rows(selection, &model);
+       work = select_list;
+       while (work)
+               {
+               FileData *fd;
+
+               tpath = work->data;
+               gtk_tree_model_get_iter(model, &iter, tpath);
+               gtk_tree_model_get(model, &iter, FILE_COLUMN_POINTER, &fd, -1);
+               gtk_tree_path_free(tpath);
+
+               work->data = fd;
+               work = work->next;
+               }
+
+       select_list = filelist_sort(select_list, vfl->sort_method, vfl->sort_ascend);
+
+       gtk_tree_view_get_cursor(GTK_TREE_VIEW(vfl->listview), &tpath, NULL);
+       if (tpath)
+               {
+               if (gtk_tree_model_get_iter(model, &iter, tpath))
+                       {
+                       gtk_tree_model_get(model, &iter, FILE_COLUMN_POINTER, &cursor_fd, -1);
+                       }
+               gtk_tree_path_free(tpath);
+               }
+
+       single_select = (select_list && !select_list->next);
+       if (single_select) cursor_fd = select_list->data;
+
+       store = GTK_LIST_STORE(model);
+       gtk_list_store_clear(store);
+
+       work = vfl->list;
+       while (work)
+               {
+               FileData *fd;
+               gchar *size;
+
+               fd = work->data;
+               size = text_from_size(fd->size);
+               gtk_list_store_append(store, &iter);
+               gtk_list_store_set(store, &iter, FILE_COLUMN_POINTER, fd,
+                                                FILE_COLUMN_THUMB, (vfl->thumbs_enabled) ? fd->pixbuf : NULL,
+                                                FILE_COLUMN_NAME, fd->name,
+                                                FILE_COLUMN_SIZE, size,
+                                                FILE_COLUMN_DATE, text_from_time(fd->date),
+                                                FILE_COLUMN_COLOR, FALSE, -1);
+               g_free(size);
+
+               if (select_list && select_list->data == fd)
+                       {
+                       select_list = g_list_remove(select_list, fd);
+                       gtk_tree_selection_select_iter(selection, &iter);
+                       }
+
+               work = work->next;
+               }
+
+       g_list_free(select_list);
+
+       if (cursor_fd &&
+           vflist_find_row(vfl, cursor_fd, &iter) >= 0)
+               {
+               if (single_select)
+                       {
+                       vflist_move_cursor(vfl, &iter);
+                       }
+               else
+                       {
+                       tree_view_row_make_visible(GTK_TREE_VIEW(vfl->listview), &iter, TRUE);
+                       }
+               }
+
+       gtk_tree_selection_set_select_function(selection, vflist_select_cb, vfl, NULL);
 }
 
 /*