From 1e8c9c87a020db396c8c87dd8c4dd746146e9058 Mon Sep 17 00:00:00 2001 From: Michael Zucci Date: Thu, 6 Jul 2000 12:32:55 +0000 Subject: Well, delete, expunge, appear broken, it sorts (initially) at least now. * message-thread.c (sort_thread): sort messages based on date for the initial sort order. (thread_messages_free): Implement. (message_list_init): set the root node invisible afterall. (message_list_set_search): Clear the old tree before putting in a new one. svn path=/trunk/; revision=3922 --- mail/ChangeLog | 7 ++++ mail/mail-ops.c | 3 +- mail/message-list.c | 12 +++++-- mail/message-thread.c | 96 ++++++++++++++++++++++++++++++++++++++++++++------- 4 files changed, 101 insertions(+), 17 deletions(-) (limited to 'mail') diff --git a/mail/ChangeLog b/mail/ChangeLog index 0df4e1ac6f..bf099dac12 100644 --- a/mail/ChangeLog +++ b/mail/ChangeLog @@ -1,5 +1,9 @@ 2000-07-06 Not Zed + * message-thread.c (sort_thread): sort messages based on date for + the initial sort order. + (thread_messages_free): Implement. + * message-list.c (message_list_init_header): Setup the subject renderer to a tree in tree mode. (on_cursor_change_cmd): For a tree model, map the view row to the @@ -12,6 +16,9 @@ (ml_tree_is_cell_editable): Maps tree node to data row, and calls the equivalent table callback (message_list_init_renderers): Setup the tree renderer if needed. + (message_list_init): set the root node invisible afterall. + (message_list_set_search): Clear the old tree before putting in a + new one. * message-list.h: Add a tree renderer to render list, and tree_view indicator. diff --git a/mail/mail-ops.c b/mail/mail-ops.c index 069d74c2d7..a8f60d1f6a 100644 --- a/mail/mail-ops.c +++ b/mail/mail-ops.c @@ -702,7 +702,8 @@ delete_msg (GtkWidget *button, gpointer user_data) /* Move the cursor down a row... FIXME: should skip other * deleted messages. FIXME: this implementation is a bit - * questionable + * questionable. FIXME: this behaviour is very annoying + * too. */ e_table_set_cursor_row (E_TABLE (ml->etable), cursor + 1); } diff --git a/mail/message-list.c b/mail/message-list.c index 799b2aeab5..f12fec302b 100644 --- a/mail/message-list.c +++ b/mail/message-list.c @@ -787,8 +787,7 @@ message_list_init (GtkObject *object) ml_tree_set_value_at, ml_tree_is_cell_editable, message_list); - /* setting this seems to upset the display, not sure. It should be set though */ - /*e_tree_model_root_node_set_visible((ETableModel *)message_list->table_model, FALSE); */ + e_tree_model_root_node_set_visible((ETreeModel *)message_list->table_model, FALSE); } else { message_list->table_model = e_table_simple_new ( ml_col_count, ml_row_count, ml_value_at, @@ -1059,7 +1058,13 @@ message_list_set_search (MessageList *message_list, const char *search) if (message_list->is_tree_view) { struct _container *head; + /* clear the old list */ + if (message_list->tree_root) + e_tree_model_node_remove((ETreeModel *)message_list->table_model, message_list->tree_root); + + /* thread the new */ head = thread_messages((CamelMessageInfo **)message_list->summary_table->pdata, message_list->summary_table->len); + /* and populate ... */ message_list->tree_root = e_tree_model_node_insert((ETreeModel *)message_list->table_model, NULL, 0, message_list); e_tree_model_node_set_expanded((ETreeModel *)message_list->table_model, message_list->tree_root, TRUE); build_tree(message_list, message_list->tree_root, head); @@ -1092,8 +1097,9 @@ message_changed (CamelFolder *f, const char *uid, MessageList *message_list) int row; row = get_message_row (message_list, uid); - if (row != -1) + if (row != -1) { e_table_model_row_changed (message_list->table_model, row); + } } void diff --git a/mail/message-thread.c b/mail/message-thread.c index 008982e8db..780735bd9e 100644 --- a/mail/message-thread.c +++ b/mail/message-thread.c @@ -28,6 +28,7 @@ #include #include #include +#include #include "message-thread.h" @@ -44,10 +45,11 @@ container_add_child(struct _container *node, struct _container *child) child->parent = node; } +#if 0 static void container_unparent_child(struct _container *child) { - struct _container *c, *p = NULL, *last, *node; + struct _container *c, *node; /* are we unparented? */ if (child->parent == NULL) { @@ -71,11 +73,12 @@ container_unparent_child(struct _container *child) printf("DAMN, we shouldn't be here!\n"); } +#endif static void container_parent_child(struct _container *parent, struct _container *child) { - struct _container *c, *p = NULL, *last, *node; + struct _container *c, *node; /* are we already the right parent? */ if (child->parent == parent) @@ -109,7 +112,7 @@ container_parent_child(struct _container *parent, struct _container *child) static void prune_empty(struct _container **cp) { - struct _container *child, *next, *nextc, *c, *lastc; + struct _container *child, *next, *c, *lastc; /* yes, this is intentional */ lastc = (struct _container *)cp; @@ -149,7 +152,6 @@ static void hashloop(void *key, void *value, void *data) { struct _container *c = value; - char *keystr = key; struct _container *tail = data; if (c->parent == NULL) { @@ -181,7 +183,6 @@ get_root_subject(struct _container *c, int *re) } if (s != NULL) { while (*s) { - char cc; while (isspace(*s)) s++; if (s[0] == 0) @@ -189,7 +190,7 @@ get_root_subject(struct _container *c, int *re) if ((s[0] == 'r' || s[0]=='R') && (s[1] == 'e' || s[1]=='E')) { p = s+2; - while (ispunct(*p) || isdigit(*p) && *p != ':') + while (ispunct(*p) || (isdigit(*p) && (*p != ':'))) p++; if (*p==':') { *re = TRUE; @@ -227,8 +228,6 @@ group_root_set(struct _container **cp) { GHashTable *subject_table = g_hash_table_new(g_str_hash, g_str_equal); struct _container *c, *clast, *scan, *container; - char *s; - int re; /* gather subject lines */ d(printf("gathering subject lines\n")); @@ -309,7 +308,6 @@ int dump_tree(struct _container *c, int depth) { char *p; - struct _container *child; int count=0; p = alloca(depth*2+1); @@ -330,17 +328,88 @@ dump_tree(struct _container *c, int depth) return count; } -void thread_messages_free(struct _container *head) +void thread_messages_free(struct _container *c) { - printf("FIXME: Free message thread structure\n"); + struct _container *n; + + return; + + /* FIXME: ok, for some reason this doesn't work .. investigate later ... */ + + while (c) { + n = c->next; + if (c->child) + thread_messages_free(c->child); /* free's children first */ + g_free(c); + c = n; + } +} + +static int +sort_node(const void *a, const void *b) +{ + const struct _container *a1 = ((struct _container **)a)[0]; + const struct _container *b1 = ((struct _container **)b)[0]; + + /* if we have no message, it must be a dummy node, which + also means it must have a child, just use that as the + sort data (close enough?) */ + if (a1->message == NULL) + a1 = a1->child; + if (b1->message == NULL) + b1 = b1->child; + if (a1->message->date_sent == b1->message->date_sent) + return 0; + if (a1->message->date_sent < b1->message->date_sent) + return 1; + else + return -1; +} + +static void +sort_thread(struct _container **cp) +{ + struct _container *c, *head, **carray; + int size=0; + + c = *cp; + while (c) { + /* sort the children while we're at it */ + if (c->child) + sort_thread(&c->child); + size++; + c = c->next; + } + if (size<2) + return; + carray = alloca(size*sizeof(struct _container *)); + c = *cp; + size=0; + while (c) { + carray[size] = c; + c = c->next; + size++; + } + qsort(carray, size, sizeof(struct _container *), sort_node); + size--; + head = carray[size]; + head->next = NULL; + size--; + do { + c = carray[size]; + c->next = head; + head = c; + size--; + } while (size>=0); + *cp = head; } struct _container * thread_messages(CamelMessageInfo **messages, int count) { GHashTable *id_table; - int i, msgs; - struct _container *c, *p, *child, *head, *scan, *container; + int i; + struct _container *c, *p, *child, *head, *container; struct _header_references *ref; id_table = g_hash_table_new(g_str_hash, g_str_equal); @@ -411,6 +480,7 @@ thread_messages(CamelMessageInfo **messages, int count) printf("%d count, %d msgs initially, %d items in tree\n", count, msgs, i); #endif + sort_thread(&head); return head; } -- cgit v1.2.3