[evolution] Custom mail account order reset on an account add or remove
- From: Milan Crha <mcrha src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [evolution] Custom mail account order reset on an account add or remove
- Date: Tue, 20 May 2014 10:15:45 +0000 (UTC)
commit fd688bf25fc58455ae58a3f9d5754aab5af1e74c
Author: Milan Crha <mcrha redhat com>
Date: Tue May 20 12:12:44 2014 +0200
Custom mail account order reset on an account add or remove
It was quite discouraging to change order of mail accounts when it
reset to default sort order when a new account had been added or
an old removed. Rather than reset the order, the Evolution should
adapt the account count change properly, same as sort newly added
accounts by the default sort function.
mail/e-mail-account-store.c | 121 ++++++++++++++++++++++++++++++++-----------
1 files changed, 91 insertions(+), 30 deletions(-)
---
diff --git a/mail/e-mail-account-store.c b/mail/e-mail-account-store.c
index 2a6439c..70c7cf3 100644
--- a/mail/e-mail-account-store.c
+++ b/mail/e-mail-account-store.c
@@ -125,7 +125,7 @@ mail_account_store_get_iter (EMailAccountStore *store,
static gint
mail_account_store_default_compare (CamelService *service_a,
CamelService *service_b,
- EMailAccountStore *store)
+ gpointer user_data)
{
const gchar *display_name_a;
const gchar *display_name_b;
@@ -160,6 +160,29 @@ mail_account_store_default_compare (CamelService *service_a,
return g_utf8_collate (display_name_a, display_name_b);
}
+static gint
+mail_account_store_get_defailt_index (EMailAccountStore *store,
+ CamelService *service)
+{
+ GQueue *current_order;
+ gint intended_position;
+
+ g_return_val_if_fail (E_IS_MAIL_ACCOUNT_STORE (store), -1);
+ g_return_val_if_fail (CAMEL_IS_SERVICE (service), -1);
+
+ current_order = g_queue_new ();
+ e_mail_account_store_queue_services (store, current_order);
+
+ g_queue_insert_sorted (current_order, service,
+ (GCompareDataFunc) mail_account_store_default_compare, NULL);
+
+ intended_position = g_queue_index (current_order, service);
+
+ g_queue_free (current_order);
+
+ return intended_position;
+}
+
static void
mail_account_store_update_row (EMailAccountStore *store,
CamelService *service,
@@ -1115,10 +1138,10 @@ e_mail_account_store_add_service (EMailAccountStore *store,
ESourceRegistry *registry;
ESource *collection;
ESource *source;
- GtkTreeIter iter;
- const gchar *filename;
+ GtkTreeIter iter, sibling;
const gchar *icon_name = NULL;
const gchar *uid;
+ gint intended_position;
gboolean builtin;
gboolean enabled;
gboolean online_account = FALSE;
@@ -1181,19 +1204,12 @@ e_mail_account_store_add_service (EMailAccountStore *store,
g_object_unref (source);
- /* Where do we insert new services now that accounts can be
- * reordered? This is just a simple policy I came up with.
- * It's certainly subject to debate and tweaking.
- *
- * Always insert new services in row 0 initially. Then test
- * for the presence of the sort order file. If present, the
- * user has messed around with the ordering so leave the new
- * service at row 0. If not present, services are sorted in
- * their default order. So re-apply the default order using
- * e_mail_account_store_reorder_services(store, NULL) so the
- * new service moves to its proper default position. */
-
- gtk_list_store_prepend (GTK_LIST_STORE (store), &iter);
+ intended_position = mail_account_store_get_defailt_index (store, service);
+ if (intended_position >= 0 &&
+ gtk_tree_model_iter_nth_child (GTK_TREE_MODEL (store), &sibling, NULL, intended_position))
+ gtk_list_store_insert_before (GTK_LIST_STORE (store), &iter, &sibling);
+ else
+ gtk_list_store_prepend (GTK_LIST_STORE (store), &iter);
gtk_list_store_set (
GTK_LIST_STORE (store), &iter,
@@ -1218,11 +1234,6 @@ e_mail_account_store_add_service (EMailAccountStore *store,
g_signal_emit (store, signals[SERVICE_ENABLED], 0, service);
else
g_signal_emit (store, signals[SERVICE_DISABLED], 0, service);
-
- filename = store->priv->sort_order_filename;
-
- if (!g_file_test (filename, G_FILE_TEST_EXISTS))
- e_mail_account_store_reorder_services (store, NULL);
}
void
@@ -1425,6 +1436,56 @@ e_mail_account_store_have_enabled_service (EMailAccountStore *store,
return found;
}
+static GQueue *
+mail_account_store_ensure_all_services_in_queue (GQueue *current_order,
+ GQueue *ordered_services)
+{
+ GHashTable *known_services;
+ GHashTableIter iter;
+ gpointer key, value;
+ GQueue *use_order;
+ GList *link;
+
+ g_return_val_if_fail (current_order != NULL, NULL);
+ g_return_val_if_fail (ordered_services != NULL, NULL);
+
+ known_services = g_hash_table_new (g_str_hash, g_str_equal);
+
+ for (link = g_queue_peek_head_link (current_order); link != NULL; link = g_list_next (link)) {
+ CamelService *service = link->data;
+
+ if (!service)
+ continue;
+
+ g_hash_table_insert (known_services, (gpointer) camel_service_get_uid (service), service);
+ }
+
+ use_order = g_queue_new ();
+
+ for (link = g_queue_peek_head_link (ordered_services); link != NULL; link = g_list_next (link)) {
+ CamelService *service = link->data, *found;
+
+ if (!service)
+ continue;
+
+ found = g_hash_table_lookup (known_services, camel_service_get_uid (service));
+ if (found) {
+ g_hash_table_remove (known_services, camel_service_get_uid (found));
+ g_queue_push_tail (use_order, found);
+ }
+ }
+
+ g_hash_table_iter_init (&iter, known_services);
+ while (g_hash_table_iter_next (&iter, &key, &value)) {
+ g_queue_insert_sorted (use_order, value, (GCompareDataFunc)
+ mail_account_store_default_compare, NULL);
+ }
+
+ g_hash_table_destroy (known_services);
+
+ return use_order;
+}
+
void
e_mail_account_store_reorder_services (EMailAccountStore *store,
GQueue *ordered_services)
@@ -1447,13 +1508,6 @@ e_mail_account_store_reorder_services (EMailAccountStore *store,
if (ordered_services != NULL && g_queue_is_empty (ordered_services))
ordered_services = NULL;
- /* If the length of the custom ordering disagrees with the
- * number of rows in the store, revert to default ordering. */
- if (ordered_services != NULL) {
- if (g_queue_get_length (ordered_services) != n_children)
- ordered_services = NULL;
- }
-
use_default_order = (ordered_services == NULL);
/* Build a queue of CamelServices in the order they appear in
@@ -1468,7 +1522,11 @@ e_mail_account_store_reorder_services (EMailAccountStore *store,
g_queue_sort (
default_order, (GCompareDataFunc)
- mail_account_store_default_compare, store);
+ mail_account_store_default_compare, NULL);
+
+ ordered_services = default_order;
+ } else {
+ default_order = mail_account_store_ensure_all_services_in_queue (current_order,
ordered_services);
ordered_services = default_order;
}
@@ -1488,7 +1546,8 @@ e_mail_account_store_reorder_services (EMailAccountStore *store,
old_pos = g_queue_link_index (current_order, matching_link);
matching_link->data = NULL;
- new_order[new_pos++] = old_pos;
+ if (new_pos < n_children)
+ new_order[new_pos++] = old_pos;
}
if (new_pos == n_children) {
@@ -1496,6 +1555,8 @@ e_mail_account_store_reorder_services (EMailAccountStore *store,
g_signal_emit (
store, signals[SERVICES_REORDERED], 0,
use_default_order);
+ } else {
+ g_warn_if_reached ();
}
g_free (new_order);
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]