From 4530d0cf3f799917a8a497c27446f0fbc76c2e63 Mon Sep 17 00:00:00 2001 From: Christoph Hohmann Date: Tue, 18 Mar 2003 18:24:34 +0000 Subject: [PATCH] 0.8.11claws26 * src/folder.[ch] * src/imap.c * src/procmsg.[ch] rewrite flag handling for folders --- ChangeLog.claws | 9 ++- configure.ac | 2 +- src/folder.c | 20 +++++- src/folder.h | 20 +++--- src/imap.c | 58 +++++++++++++++++- src/procmsg.c | 160 +++++++++++++++++------------------------------- src/procmsg.h | 13 ++-- 7 files changed, 158 insertions(+), 124 deletions(-) diff --git a/ChangeLog.claws b/ChangeLog.claws index 148e2bfb2..5cbcf0263 100644 --- a/ChangeLog.claws +++ b/ChangeLog.claws @@ -1,4 +1,11 @@ -2003-03-17 [christoph] 0.8.11claws25 +2003-03-18 [christoph] 0.8.11claws26 + + * src/folder.[ch] + * src/imap.c + * src/procmsg.[ch] + rewrite flag handling for folders + +2003-03-18 [christoph] 0.8.11claws25 * src/folder.c * src/procmsg.c diff --git a/configure.ac b/configure.ac index 697d30aba..9085441a3 100644 --- a/configure.ac +++ b/configure.ac @@ -11,7 +11,7 @@ MINOR_VERSION=8 MICRO_VERSION=11 INTERFACE_AGE=0 BINARY_AGE=0 -EXTRA_VERSION=claws25 +EXTRA_VERSION=claws26 VERSION=$MAJOR_VERSION.$MINOR_VERSION.$MICRO_VERSION$EXTRA_VERSION dnl set $target diff --git a/src/folder.c b/src/folder.c index 66d77d435..f0a074e11 100644 --- a/src/folder.c +++ b/src/folder.c @@ -1223,13 +1223,15 @@ gint folder_item_scan(FolderItem *item) MsgInfo *msginfo; msginfo = elem->data; - if (MSG_IS_NEW(msginfo->flags) && !MSG_IS_IGNORE_THREAD(msginfo->flags)) + if (MSG_IS_NEW(msginfo->flags)) newcnt++; - if (MSG_IS_UNREAD(msginfo->flags) && !MSG_IS_IGNORE_THREAD(msginfo->flags)) + if (MSG_IS_UNREAD(msginfo->flags)) unreadcnt++; if (MSG_IS_UNREAD(msginfo->flags) && procmsg_msg_has_marked_parent(msginfo)) unreadmarkedcnt++; - if (!MSG_IS_IGNORE_THREAD(msginfo->flags) && procmsg_msg_has_flagged_parent(msginfo, MSG_IGNORE_THREAD)) { + if (MSG_IS_IGNORE_THREAD(msginfo->flags) && (MSG_IS_NEW(msginfo->flags) || MSG_IS_UNREAD(msginfo->flags))) + procmsg_msginfo_unset_flags(msginfo, MSG_NEW | MSG_UNREAD, 0); + if (procmsg_msg_has_flagged_parent(msginfo, MSG_IGNORE_THREAD)) { procmsg_msginfo_unset_flags(msginfo, MSG_NEW | MSG_UNREAD, 0); procmsg_msginfo_set_flags(msginfo, MSG_IGNORE_THREAD, 0); } @@ -2117,6 +2119,18 @@ gint folder_item_remove_all_msg(FolderItem *item) return result; } +void folder_item_change_msg_flags(FolderItem *item, MsgInfo *msginfo, MsgPermFlags newflags) +{ + g_return_if_fail(item != NULL); + g_return_if_fail(msginfo != NULL); + + if (item->folder->class->change_flags != NULL) { + item->folder->class->change_flags(item->folder, item, msginfo, newflags); + } else { + msginfo->flags.perm_flags = newflags; + } +} + gboolean folder_item_is_msg_changed(FolderItem *item, MsgInfo *msginfo) { Folder *folder; diff --git a/src/folder.h b/src/folder.h index 7ea413cef..9c9b06299 100644 --- a/src/folder.h +++ b/src/folder.h @@ -33,13 +33,6 @@ typedef struct _MaildirFolder MaildirFolder; typedef struct _FolderItem FolderItem; typedef struct _FolderItemUpdateData FolderItemUpdateData; -#include "prefs_folder_item.h" - -#include "prefs_account.h" -#include "session.h" -#include "procmsg.h" -#include "msgcache.h" - #define FOLDER(obj) ((Folder *)obj) #define FOLDER_TYPE(obj) (FOLDER(obj)->class->type) @@ -126,6 +119,13 @@ typedef void (*FolderDestroyNotify) (Folder *folder, typedef void (*FolderItemFunc) (FolderItem *item, gpointer data); +#include "prefs_folder_item.h" + +#include "prefs_account.h" +#include "session.h" +#include "procmsg.h" +#include "msgcache.h" + struct _Folder { FolderClass *class; @@ -228,7 +228,8 @@ struct _FolderClass MsgInfo *msginfo); void (*change_flags) (Folder *folder, FolderItem *item, - MsgInfo *info); + MsgInfo *msginfo, + MsgPermFlags newflags); }; struct _LocalFolder @@ -416,6 +417,9 @@ gint folder_item_remove_msg (FolderItem *item, gint folder_item_remove_msgs (FolderItem *item, GSList *msglist); gint folder_item_remove_all_msg (FolderItem *item); +void folder_item_change_msg_flags (FolderItem *item, + MsgInfo *msginfo, + MsgPermFlags newflags); gboolean folder_item_is_msg_changed (FolderItem *item, MsgInfo *msginfo); gchar *folder_item_get_cache_file (FolderItem *item); diff --git a/src/imap.c b/src/imap.c index e722ab5dd..cc877b3b7 100644 --- a/src/imap.c +++ b/src/imap.c @@ -295,6 +295,10 @@ MsgInfo *imap_get_msginfo (Folder *folder, gint num); gboolean imap_check_msgnum_validity (Folder *folder, FolderItem *item); +void imap_change_flags (Folder *folder, + FolderItem *item, + MsgInfo *msginfo, + MsgPermFlags newflags); FolderClass imap_class = { @@ -333,7 +337,7 @@ FolderClass imap_class = imap_remove_msgs, imap_remove_all_msg, imap_is_msg_changed, - NULL, + imap_change_flags, }; FolderClass *imap_get_class() @@ -3597,3 +3601,55 @@ gboolean imap_check_msgnum_validity(Folder *folder, FolderItem *_item) return FALSE; } + +void imap_change_flags(Folder *folder, FolderItem *item, MsgInfo *msginfo, MsgPermFlags newflags) +{ + IMAPSession *session; + IMAPFlags flags_set = 0, flags_unset = 0; + gint ok = IMAP_SUCCESS; + + g_return_if_fail(folder != NULL); + g_return_if_fail(folder->class == &imap_class); + g_return_if_fail(item != NULL); + g_return_if_fail(item->folder == folder); + g_return_if_fail(msginfo != NULL); + g_return_if_fail(msginfo->folder == item); + + session = imap_session_get(folder); + if (!session) return; + + if ((ok = imap_select(session, IMAP_FOLDER(folder), msginfo->folder->path, + NULL, NULL, NULL, NULL)) != IMAP_SUCCESS) + return; + + if (!MSG_IS_MARKED(msginfo->flags) && (newflags & MSG_MARKED)) + flags_set |= IMAP_FLAG_FLAGGED; + if ( MSG_IS_MARKED(msginfo->flags) && !(newflags & MSG_MARKED)) + flags_unset |= IMAP_FLAG_FLAGGED; + + if (!MSG_IS_UNREAD(msginfo->flags) && (newflags & MSG_UNREAD)) + flags_unset |= IMAP_FLAG_SEEN; + if ( MSG_IS_UNREAD(msginfo->flags) && !(newflags & MSG_UNREAD)) + flags_set |= IMAP_FLAG_SEEN; + + if (!MSG_IS_REPLIED(msginfo->flags) && (newflags & MSG_REPLIED)) + flags_set |= IMAP_FLAG_ANSWERED; + if ( MSG_IS_REPLIED(msginfo->flags) && !(newflags & MSG_REPLIED)) + flags_set |= IMAP_FLAG_ANSWERED; + + if (flags_set) { + ok = imap_set_message_flags(session, msginfo->msgnum, + msginfo->msgnum, flags_set, TRUE); + if (ok != IMAP_SUCCESS) return; + } + + if (flags_unset) { + ok = imap_set_message_flags(session, msginfo->msgnum, + msginfo->msgnum, flags_unset, FALSE); + if (ok != IMAP_SUCCESS) return; + } + + msginfo->flags.perm_flags = newflags; + + return; +} diff --git a/src/procmsg.c b/src/procmsg.c index 306bdcd4d..1f8207069 100644 --- a/src/procmsg.c +++ b/src/procmsg.c @@ -39,7 +39,6 @@ #endif #include "alertpanel.h" #include "news.h" -#include "imap.h" #include "hooks.h" #include "msgcache.h" @@ -738,7 +737,7 @@ void procmsg_msginfo_free(MsgInfo *msginfo) if (msginfo->refcnt > 0) return; - debug_print("freeing msginfo %d is %s\n", msginfo->msgnum, msginfo->folder ? msginfo->folder->path : "(nil)"); + debug_print("freeing msginfo %d in %s\n", msginfo->msgnum, msginfo->folder ? msginfo->folder->path : "(nil)"); if (msginfo->to_folder) { msginfo->to_folder->op_count--; @@ -1058,142 +1057,97 @@ gint procmsg_send_message_queue(const gchar *file) return (newsval != 0 ? newsval : mailval); } -#define CHANGE_FLAGS(msginfo) \ -{ \ -if (msginfo->folder->folder->class->change_flags != NULL) \ -msginfo->folder->folder->class->change_flags(msginfo->folder->folder, \ - msginfo->folder, \ - msginfo); \ -} - -void procmsg_msginfo_set_flags(MsgInfo *msginfo, MsgPermFlags perm_flags, MsgTmpFlags tmp_flags) +static void update_folder_msg_counts(FolderItem *item, MsgInfo *msginfo, MsgPermFlags old) { - FolderItem *item; - MsgInfoUpdate msginfo_update; - - g_return_if_fail(msginfo != NULL); - item = msginfo->folder; - g_return_if_fail(item != NULL); - - debug_print("Setting flags for message %d in folder %s\n", msginfo->msgnum, item->path); + MsgPermFlags new = msginfo->flags.perm_flags; - /* if new flag is set */ - if ((perm_flags & MSG_NEW) && !MSG_IS_NEW(msginfo->flags) && - !MSG_IS_IGNORE_THREAD(msginfo->flags)) { + /* NEW flag */ + if (!(old & MSG_NEW) && (new & MSG_NEW)) { item->new++; } - /* if unread flag is set */ - if ((perm_flags & MSG_UNREAD) && !MSG_IS_UNREAD(msginfo->flags) && - !MSG_IS_IGNORE_THREAD(msginfo->flags)) { + if ((old & MSG_NEW) && !(new & MSG_NEW)) { + item->new--; + } + + /* UNREAD flag */ + if (!(old & MSG_UNREAD) && (new & MSG_UNREAD)) { item->unread++; + if (procmsg_msg_has_marked_parent(msginfo)) + item->unreadmarked++; } - if (!MSG_IS_UNREAD(msginfo->flags) &&(perm_flags & MSG_UNREAD) - && procmsg_msg_has_marked_parent(msginfo)) { - item->unreadmarked++; + if ((old & MSG_UNREAD) && !(new & MSG_UNREAD)) { + item->unread--; + if (procmsg_msg_has_marked_parent(msginfo)) + item->unreadmarked--; } - if (!MSG_IS_MARKED(msginfo->flags) && (perm_flags & MSG_MARKED)) { + /* MARK flag */ + if (!(old & MSG_MARKED) && (new & MSG_MARKED)) { procmsg_update_unread_children(msginfo, TRUE); } + if ((old & MSG_MARKED) && !(new & MSG_MARKED)) { + procmsg_update_unread_children(msginfo, FALSE); + } +} - /* if ignore thread flag is set */ - if ((perm_flags & MSG_IGNORE_THREAD) && !MSG_IS_IGNORE_THREAD(msginfo->flags)) { - if (MSG_IS_NEW(msginfo->flags) || (perm_flags & MSG_NEW)) { - item->new--; - } - if (MSG_IS_UNREAD(msginfo->flags) || (perm_flags & MSG_UNREAD)) { - item->unread--; - } - if ((perm_flags & MSG_UNREAD) || (MSG_IS_UNREAD(msginfo->flags) - && procmsg_msg_has_marked_parent(msginfo))) { - item->unreadmarked--; - } - if ((perm_flags & MSG_MARKED) || (MSG_IS_MARKED(msginfo->flags) - && !MSG_IS_IGNORE_THREAD(msginfo->flags))) { - procmsg_update_unread_children(msginfo, FALSE); - } +void procmsg_msginfo_set_flags(MsgInfo *msginfo, MsgPermFlags perm_flags, MsgTmpFlags tmp_flags) +{ + FolderItem *item; + MsgInfoUpdate msginfo_update; + MsgPermFlags perm_flags_new, perm_flags_old; - } + g_return_if_fail(msginfo != NULL); + item = msginfo->folder; + g_return_if_fail(item != NULL); + + debug_print("Setting flags for message %d in folder %s\n", msginfo->msgnum, item->path); - if (FOLDER_TYPE(msginfo->folder->folder) == F_IMAP) - imap_msg_set_perm_flags(msginfo, perm_flags); + /* Perm Flags handling */ + perm_flags_old = msginfo->flags.perm_flags; + perm_flags_new = msginfo->flags.perm_flags | perm_flags; + if ((perm_flags & MSG_IGNORE_THREAD) || (perm_flags_old & MSG_IGNORE_THREAD)) { + perm_flags_new &= ~(MSG_NEW | MSG_UNREAD); + } - msginfo->flags.perm_flags |= perm_flags; - msginfo->flags.tmp_flags |= tmp_flags; + if (perm_flags_old != perm_flags_new) { + folder_item_change_msg_flags(msginfo->folder, msginfo, perm_flags_new); - msginfo_update.msginfo = msginfo; - hooks_invoke(MSGINFO_UPDATE_HOOKLIST, &msginfo_update); - folder_item_update(msginfo->folder, F_ITEM_UPDATE_MSGCNT); + update_folder_msg_counts(item, msginfo, perm_flags_old); - CHANGE_FLAGS(msginfo); + msginfo_update.msginfo = msginfo; + hooks_invoke(MSGINFO_UPDATE_HOOKLIST, &msginfo_update); + folder_item_update(msginfo->folder, F_ITEM_UPDATE_MSGCNT); + } } void procmsg_msginfo_unset_flags(MsgInfo *msginfo, MsgPermFlags perm_flags, MsgTmpFlags tmp_flags) { FolderItem *item; MsgInfoUpdate msginfo_update; + MsgPermFlags perm_flags_new, perm_flags_old; g_return_if_fail(msginfo != NULL); item = msginfo->folder; - g_return_if_fail(item != NULL); + g_return_if_fail(item != NULL); debug_print("Unsetting flags for message %d in folder %s\n", msginfo->msgnum, item->path); - /* if new flag is unset */ - if ((perm_flags & MSG_NEW) && MSG_IS_NEW(msginfo->flags) && - !MSG_IS_IGNORE_THREAD(msginfo->flags)) { - item->new--; - } - - /* if unread flag is unset */ - if ((perm_flags & MSG_UNREAD) && MSG_IS_UNREAD(msginfo->flags) && - !MSG_IS_IGNORE_THREAD(msginfo->flags)) { - item->unread--; - } + /* Perm Flags handling */ + perm_flags_old = msginfo->flags.perm_flags; + perm_flags_new = msginfo->flags.perm_flags & ~perm_flags; - if (MSG_IS_UNREAD(msginfo->flags) && (perm_flags & MSG_UNREAD) - && !MSG_IS_IGNORE_THREAD(msginfo->flags) - && procmsg_msg_has_marked_parent(msginfo)) { - item->unreadmarked--; - } + if (perm_flags_old != perm_flags_new) { + folder_item_change_msg_flags(msginfo->folder, msginfo, perm_flags_new); - if (MSG_IS_MARKED(msginfo->flags) && (perm_flags & MSG_MARKED) - && !MSG_IS_IGNORE_THREAD(msginfo->flags)) { - procmsg_update_unread_children(msginfo, FALSE); - } - - /* if ignore thread flag is unset */ - if ((perm_flags & MSG_IGNORE_THREAD) && MSG_IS_IGNORE_THREAD(msginfo->flags)) { - if (MSG_IS_NEW(msginfo->flags) && !(perm_flags & MSG_NEW)) { - item->new++; - } - if (MSG_IS_UNREAD(msginfo->flags) && !(perm_flags & MSG_UNREAD)) { - item->unread++; - } - if (MSG_IS_UNREAD(msginfo->flags) && !(perm_flags & MSG_UNREAD) - && procmsg_msg_has_marked_parent(msginfo)) { - item->unreadmarked++; - } - if (MSG_IS_MARKED(msginfo->flags) && !(perm_flags & MSG_MARKED)) { - procmsg_update_unread_children(msginfo, TRUE); - } + update_folder_msg_counts(item, msginfo, perm_flags_old); + msginfo_update.msginfo = msginfo; + hooks_invoke(MSGINFO_UPDATE_HOOKLIST, &msginfo_update); + folder_item_update(msginfo->folder, F_ITEM_UPDATE_MSGCNT); } - - if (FOLDER_TYPE(msginfo->folder->folder) == F_IMAP) - imap_msg_unset_perm_flags(msginfo, perm_flags); - - msginfo->flags.perm_flags &= ~perm_flags; - msginfo->flags.tmp_flags &= ~tmp_flags; - - msginfo_update.msginfo = msginfo; - hooks_invoke(MSGINFO_UPDATE_HOOKLIST, &msginfo_update); - folder_item_update(msginfo->folder, F_ITEM_UPDATE_MSGCNT); - - CHANGE_FLAGS(msginfo); } /*! diff --git a/src/procmsg.h b/src/procmsg.h index ba70b7d5d..98cefd569 100644 --- a/src/procmsg.h +++ b/src/procmsg.h @@ -32,9 +32,7 @@ typedef struct _MsgInfo MsgInfo; typedef struct _MsgFlags MsgFlags; - -#include "folder.h" -#include "procmime.h" +typedef struct _MsgInfoUpdate MsgInfoUpdate; typedef enum { @@ -143,6 +141,11 @@ typedef enum #define MSG_IS_IGNORE_THREAD(msg) (((msg).perm_flags & MSG_IGNORE_THREAD) != 0) #define MSG_IS_RETRCPT_PENDING(msg) (((msg).perm_flags & MSG_RETRCPT_PENDING) != 0) +#define MSGINFO_UPDATE_HOOKLIST "msginfo_update" + +#include "folder.h" +#include "procmime.h" + struct _MsgFlags { MsgPermFlags perm_flags; @@ -191,10 +194,6 @@ struct _MsgInfo guint decryption_failed : 1; }; -#define MSGINFO_UPDATE_HOOKLIST "msginfo_update" - -typedef struct _MsgInfoUpdate MsgInfoUpdate; - struct _MsgInfoUpdate { MsgInfo *msginfo; }; -- 2.25.1