aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorhiro <hiro@ee746299-78ed-0310-b773-934348b2243d>2005-03-28 10:50:42 +0000
committerhiro <hiro@ee746299-78ed-0310-b773-934348b2243d>2005-03-28 10:50:42 +0000
commit78ffc1ed2c6fbf42feabfb348d746b5a36be3db8 (patch)
treea75543612f2088840dd905ddd09e94c02208a982
parentd0c14090a0d5e74834fabd896406bfe2cd212449 (diff)
improved the thread creation.
git-svn-id: svn://sylpheed.sraoss.jp/sylpheed/trunk@190 ee746299-78ed-0310-b773-934348b2243d
-rw-r--r--ChangeLog10
-rw-r--r--ChangeLog.ja10
-rw-r--r--src/defs.h2
-rw-r--r--src/procheader.c9
-rw-r--r--src/procmsg.c74
-rw-r--r--src/procmsg.h2
-rw-r--r--src/summaryview.c10
-rw-r--r--src/utils.c15
-rw-r--r--src/utils.h2
9 files changed, 114 insertions, 20 deletions
diff --git a/ChangeLog b/ChangeLog
index 6dc1600f..4b6fecdc 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,15 @@
2005-03-28
+ * src/utils.[ch]: references_list_prepend(): new.
+ * src/procmsg.[ch]
+ src/procheader.c
+ src/summaryview.c: modified the thread creation so that it looks up
+ every message-id in References header if the real parent message is
+ not found (thanks to Alfons).
+ * src/defs.h: upped the cache version.
+
+2005-03-28
+
* src/foldersel.c: reimplemented folder selection dialog using
GtkTreeView (thanks to Alfons).
* src/stock_pixmap.[ch]: stock_pixbuf_gdk(): new. It generates
diff --git a/ChangeLog.ja b/ChangeLog.ja
index 62085dfc..95ffd928 100644
--- a/ChangeLog.ja
+++ b/ChangeLog.ja
@@ -1,5 +1,15 @@
2005-03-28
+ * src/utils.[ch]: references_list_prepend(): 新規。
+ * src/procmsg.[ch]
+ src/procheader.c
+ src/summaryview.c: スレッドの生成処理を、実際の親メッセージが
+ 見つからなかった場合は References ヘッダの全てのメッセージ ID
+ を検索するように修正(Alfons さん thanks)。
+ * src/defs.h: キャッシュバージョンを増加。
+
+2005-03-28
+
* src/foldersel.c: フォルダ選択ダイアログを GtkTreeView を使用して
再実装(Alfons さん thanks)。
* src/stock_pixmap.[ch]: stock_pixbuf_gdk(): 新規。 xpm から GdkPixbuf
diff --git a/src/defs.h b/src/defs.h
index 7ad89e37..00392b40 100644
--- a/src/defs.h
+++ b/src/defs.h
@@ -63,7 +63,7 @@
#define FOLDER_LIST "folderlist.xml"
#define CACHE_FILE ".sylpheed_cache"
#define MARK_FILE ".sylpheed_mark"
-#define CACHE_VERSION 0x20
+#define CACHE_VERSION 0x21
#define MARK_VERSION 2
#define DEFAULT_SIGNATURE ".signature"
diff --git a/src/procheader.c b/src/procheader.c
index 442d5aea..62047aa5 100644
--- a/src/procheader.c
+++ b/src/procheader.c
@@ -504,7 +504,7 @@ MsgInfo *procheader_parse_stream(FILE *fp, MsgFlags flags, gboolean full)
MsgInfo *msginfo;
gchar buf[BUFFSIZE];
gchar *reference = NULL;
- gchar *p;
+ gchar *p, *q;
gchar *hp;
HeaderEntry *hentry;
gint hnum;
@@ -520,6 +520,7 @@ MsgInfo *procheader_parse_stream(FILE *fp, MsgFlags flags, gboolean full)
msginfo = g_new0(MsgInfo, 1);
msginfo->flags = flags;
+ msginfo->references = NULL;
msginfo->inreplyto = NULL;
while ((hnum = procheader_get_one_field(buf, sizeof(buf), fp, hentry))
@@ -567,6 +568,12 @@ MsgInfo *procheader_parse_stream(FILE *fp, MsgFlags flags, gboolean full)
msginfo->msgid = g_strdup(hp);
break;
case H_REFERENCES:
+ msginfo->references =
+ references_list_prepend(msginfo->references,
+ hp);
+ if (msginfo->references && !reference)
+ reference = g_strdup((gchar *)msginfo->references->data);
+ break;
case H_IN_REPLY_TO:
if (!reference) {
eliminate_parenthesis(hp, '(', ')');
diff --git a/src/procmsg.c b/src/procmsg.c
index 93a474ab..4ff70aec 100644
--- a/src/procmsg.c
+++ b/src/procmsg.c
@@ -1,6 +1,6 @@
/*
* Sylpheed -- a GTK+ based, lightweight, and fast e-mail client
- * Copyright (C) 1999-2004 Hiroyuki Yamamoto
+ * Copyright (C) 1999-2005 Hiroyuki Yamamoto
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -202,6 +202,7 @@ GSList *procmsg_read_cache(FolderItem *item, gboolean scan_file)
MsgFlags default_flags;
gchar file_buf[BUFFSIZE];
guint32 num;
+ guint refnum;
FolderType type;
g_return_val_if_fail(item != NULL, NULL);
@@ -258,6 +259,18 @@ GSList *procmsg_read_cache(FolderItem *item, gboolean scan_file)
READ_CACHE_DATA(msginfo->msgid, fp);
READ_CACHE_DATA(msginfo->inreplyto, fp);
+ READ_CACHE_DATA_INT(refnum, fp);
+ for (; refnum != 0; refnum--) {
+ gchar *ref;
+
+ READ_CACHE_DATA(ref, fp);
+ msginfo->references =
+ g_slist_prepend(msginfo->references, ref);
+ }
+ if (msginfo->references)
+ msginfo->references =
+ g_slist_reverse(msginfo->references);
+
MSG_SET_PERM_FLAGS(msginfo->flags, default_flags.perm_flags);
MSG_SET_TMP_FLAGS(msginfo->flags, default_flags.tmp_flags);
@@ -444,6 +457,7 @@ void procmsg_msg_list_free(GSList *mlist)
void procmsg_write_cache(MsgInfo *msginfo, FILE *fp)
{
MsgTmpFlags flags = msginfo->flags.tmp_flags & MSG_CACHED_FLAG_MASK;
+ GSList *cur;
WRITE_CACHE_DATA_INT(msginfo->msgnum, fp);
WRITE_CACHE_DATA_INT(msginfo->size, fp);
@@ -460,6 +474,11 @@ void procmsg_write_cache(MsgInfo *msginfo, FILE *fp)
WRITE_CACHE_DATA(msginfo->subject, fp);
WRITE_CACHE_DATA(msginfo->msgid, fp);
WRITE_CACHE_DATA(msginfo->inreplyto, fp);
+
+ WRITE_CACHE_DATA_INT(g_slist_length(msginfo->references), fp);
+ for (cur = msginfo->references; cur != NULL; cur = cur->next) {
+ WRITE_CACHE_DATA((gchar *)cur->data, fp);
+ }
}
void procmsg_write_flags(MsgInfo *msginfo, FILE *fp)
@@ -682,8 +701,8 @@ static FILE *procmsg_open_data_file(const gchar *file, guint version,
setvbuf(fp, buf, _IOFBF, buf_size);
if (fread(&data_ver, sizeof(data_ver), 1, fp) != 1 ||
version != data_ver) {
- debug_print("Mark/Cache version is different (%u != %u). "
- "Discarding it.\n", data_ver, version);
+ g_message("Mark/Cache version is different (%u != %u). "
+ "Discarding it.\n", data_ver, version);
fclose(fp);
fp = NULL;
}
@@ -753,19 +772,29 @@ GNode *procmsg_get_thread_tree(GSList *mlist)
GHashTable *table;
MsgInfo *msginfo;
const gchar *msgid;
+ GSList *reflist;
root = g_node_new(NULL);
table = g_hash_table_new(g_str_hash, g_str_equal);
for (; mlist != NULL; mlist = mlist->next) {
msginfo = (MsgInfo *)mlist->data;
- parent = root;
+ parent = NULL;
- if (msginfo->inreplyto) {
+ if (msginfo->inreplyto)
parent = g_hash_table_lookup(table, msginfo->inreplyto);
- if (parent == NULL)
- parent = root;
+
+ if (!parent && msginfo->references) {
+ for (reflist = msginfo->references;
+ reflist != NULL; reflist = reflist->next)
+ if ((parent = g_hash_table_lookup
+ (table, reflist->data)) != NULL)
+ break;
}
+
+ if (parent == NULL)
+ parent = root;
+
node = g_node_insert_data_before
(parent, parent == root ? parent->children : NULL,
msginfo);
@@ -778,16 +807,26 @@ GNode *procmsg_get_thread_tree(GSList *mlist)
for (node = root->children; node != NULL; ) {
next = node->next;
msginfo = (MsgInfo *)node->data;
- if (msginfo->inreplyto) {
+ parent = NULL;
+
+ if (msginfo->inreplyto)
parent = g_hash_table_lookup(table, msginfo->inreplyto);
- /* node should not be the parent, and node should not
- be an ancestor of parent (circular reference) */
- if (parent && parent != node &&
- !g_node_is_ancestor(node, parent)) {
- g_node_unlink(node);
- g_node_insert_before
- (parent, parent->children, node);
- }
+
+ if (!parent && msginfo->references) {
+ for (reflist = msginfo->references;
+ reflist != NULL; reflist = reflist->next)
+ if ((parent = g_hash_table_lookup
+ (table, reflist->data)) != NULL)
+ break;
+ }
+
+ /* node should not be the parent, and node should not
+ be an ancestor of parent (circular reference) */
+ if (parent && parent != node &&
+ !g_node_is_ancestor(node, parent)) {
+ g_node_unlink(node);
+ g_node_insert_before
+ (parent, parent->children, node);
}
node = next;
}
@@ -1448,6 +1487,9 @@ void procmsg_msginfo_free(MsgInfo *msginfo)
g_free(msginfo->msgid);
g_free(msginfo->inreplyto);
+ slist_free_strings(msginfo->references);
+ g_slist_free(msginfo->references);
+
g_free(msginfo->file_path);
g_free(msginfo->plaintext_file);
diff --git a/src/procmsg.h b/src/procmsg.h
index 2a718baf..18138bf2 100644
--- a/src/procmsg.h
+++ b/src/procmsg.h
@@ -181,6 +181,8 @@ struct _MsgInfo
gchar *msgid;
gchar *inreplyto;
+ GSList *references;
+
FolderItem *folder;
FolderItem *to_folder;
diff --git a/src/summaryview.c b/src/summaryview.c
index f0c4ef43..eecb703a 100644
--- a/src/summaryview.c
+++ b/src/summaryview.c
@@ -3031,6 +3031,7 @@ void summary_thread_build(SummaryView *summaryview)
GtkCTreeNode *next;
GtkCTreeNode *parent;
MsgInfo *msginfo;
+ GSList *reflist;
summary_lock(summaryview);
@@ -3051,6 +3052,15 @@ void summary_thread_build(SummaryView *summaryview)
if (msginfo && msginfo->inreplyto) {
parent = g_hash_table_lookup(summaryview->msgid_table,
msginfo->inreplyto);
+ if (!parent && msginfo->references) {
+ for (reflist = msginfo->references;
+ reflist != NULL; reflist = reflist->next)
+ if ((parent = g_hash_table_lookup
+ (summaryview->msgid_table,
+ reflist->data)))
+ break;
+ }
+
if (parent && parent != node) {
gtk_ctree_move(ctree, node, parent, NULL);
gtk_ctree_expand(ctree, node);
diff --git a/src/utils.c b/src/utils.c
index 5d65c418..ed067a6f 100644
--- a/src/utils.c
+++ b/src/utils.c
@@ -883,7 +883,7 @@ GSList *address_list_append(GSList *addr_list, const gchar *str)
return addr_list;
}
-GSList *references_list_append(GSList *msgid_list, const gchar *str)
+GSList *references_list_prepend(GSList *msgid_list, const gchar *str)
{
const gchar *strp;
@@ -903,7 +903,7 @@ GSList *references_list_append(GSList *msgid_list, const gchar *str)
msgid = g_strndup(start + 1, end - start - 1);
g_strstrip(msgid);
if (*msgid)
- msgid_list = g_slist_append(msgid_list, msgid);
+ msgid_list = g_slist_prepend(msgid_list, msgid);
else
g_free(msgid);
@@ -913,6 +913,17 @@ GSList *references_list_append(GSList *msgid_list, const gchar *str)
return msgid_list;
}
+GSList *references_list_append(GSList *msgid_list, const gchar *str)
+{
+ GSList *list;
+
+ list = references_list_prepend(NULL, str);
+ list = g_slist_reverse(list);
+ msgid_list = g_slist_concat(msgid_list, list);
+
+ return msgid_list;
+}
+
GSList *newsgroup_list_append(GSList *group_list, const gchar *str)
{
gchar *work;
diff --git a/src/utils.h b/src/utils.h
index 0d8e827d..d2ef3348 100644
--- a/src/utils.h
+++ b/src/utils.h
@@ -273,6 +273,8 @@ void extract_list_id_str (gchar *str);
GSList *address_list_append (GSList *addr_list,
const gchar *str);
+GSList *references_list_prepend (GSList *msgid_list,
+ const gchar *str);
GSList *references_list_append (GSList *msgid_list,
const gchar *str);
GSList *newsgroup_list_append (GSList *group_list,