Remove more markup from translatable strings
[claws.git] / src / summaryview.c
index ca66a76ed31d31b86237bf97f5897bcae6dfa99b..e47a02fec10b25017c3394f40bf7ba06fc3ffc6c 100644 (file)
@@ -1,6 +1,6 @@
 /*
- * Sylpheed -- a GTK+ based, lightweight, and fast e-mail client
- * Copyright (C) 1999-2009 Hiroyuki Yamamoto and the Claws Mail team
+ * Claws Mail -- a GTK+ based, lightweight, and fast e-mail client
+ * Copyright (C) 1999-2015 the Claws Mail team
  *
  * 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
@@ -14,7 +14,6 @@
  *
  * You should have received a copy of the GNU General Public License
  * along with this program. If not, see <http://www.gnu.org/licenses/>.
- * 
  */
 
 #include "defs.h"
@@ -36,6 +35,7 @@
 #include "folderview.h"
 #include "summaryview.h"
 #include "messageview.h"
+#include "mimeview.h"
 #include "foldersel.h"
 #include "procmsg.h"
 #include "procheader.h"
 #include "colorlabel.h"
 #include "inc.h"
 #include "imap.h"
-#include "addressbook.h"
+#ifndef USE_NEW_ADDRBOOK
+       #include "addressbook.h"
+#else
+       #include "addressbook-dbus.h"
+       #include "addressadd.h"
+#endif
 #include "addr_compl.h"
 #include "folder_item_prefs.h"
 #include "filtering.h"
 #include "partial_download.h"
 #include "tags.h"
 #include "timing.h"
-#include "gedit-print.h"
 #include "log.h"
 #include "edittags.h"
 #include "manual.h"
+#include "manage_window.h"
+#include "avatars.h"
 
 #define SUMMARY_COL_MARK_WIDTH         10
 #define SUMMARY_COL_STATUS_WIDTH       13
@@ -98,6 +104,7 @@ static GdkPixbuf *newxpm;
 static GdkPixbuf *unreadxpm;
 static GdkPixbuf *repliedxpm;
 static GdkPixbuf *forwardedxpm;
+static GdkPixbuf *repliedandforwardedxpm;
 static GdkPixbuf *ignorethreadxpm;
 static GdkPixbuf *watchthreadxpm;
 static GdkPixbuf *lockedxpm;
@@ -122,10 +129,9 @@ guint summary_get_msgnum           (SummaryView            *summaryview,
                                         GtkCMCTreeNode         *node);
 
 
-static void summary_set_hide_read_msgs_menu (SummaryView *summaryview,
-                                            guint action);
-static void summary_set_hide_del_msgs_menu (SummaryView *summaryview,
-                                            guint action);
+static void summary_set_hide_menu (SummaryView *summaryview,
+                                  const gchar *menu_item,
+                                  guint action);
 
 static GtkCMCTreeNode *summary_find_prev_msg
                                        (SummaryView            *summaryview,
@@ -385,6 +391,7 @@ static gint summary_cmp_by_tags             (GtkCMCList             *clist,
 
 static void quicksearch_execute_cb     (QuickSearch    *quicksearch,
                                         gpointer        data);
+
 static void tog_searchbar_cb           (GtkWidget      *w,
                                         gpointer        data);
 
@@ -399,10 +406,11 @@ static void summary_set_colorlabel_color (GtkCMCTree              *ctree,
                                   guint                 labelcolor);
 static void summary_thread_build(SummaryView *summaryview);
 
-GtkTargetEntry summary_drag_types[2] =
+GtkTargetEntry summary_drag_types[3] =
 {
        {"text/uri-list", 0, TARGET_MAIL_URI_LIST},
-       {"claws-mail/internal", GTK_TARGET_SAME_APP, TARGET_DUMMY}
+       {"claws-mail/internal", GTK_TARGET_SAME_APP, TARGET_DUMMY},
+       {"claws-mail/msg-path-list", 0, TARGET_MAIL_CM_PATH_LIST},
 };
 
 #define DO_ACTION(name, act) {                                         \
@@ -452,6 +460,14 @@ void summary_thaw(SummaryView *summaryview)
                gtk_cmclist_thaw(GTK_CMCLIST(summaryview->ctree));
 }
 
+void summary_thaw_with_status(SummaryView *summaryview)
+{
+       if (summaryview) {
+               summary_status_show(summaryview);
+               gtk_cmclist_thaw(GTK_CMCLIST(summaryview->ctree));
+       }
+}
+
 void summary_grab_focus(SummaryView *summaryview)
 {
        if (summaryview)
@@ -512,14 +528,10 @@ SummaryView *summary_create(MainWindow *mainwin)
        GtkWidget *toggle_arrow;
        GtkWidget *toggle_search;
        QuickSearch *quicksearch;
-       CLAWS_TIP_DECL();
 
        debug_print("Creating summary view...\n");
        summaryview = g_new0(SummaryView, 1);
 
-#if !(GTK_CHECK_VERSION(2,12,0))
-       summaryview->tooltips = tips;
-#endif
 #define SUMMARY_VBOX_SPACING 3
        vbox = gtk_vbox_new(FALSE, SUMMARY_VBOX_SPACING);
        
@@ -539,6 +551,7 @@ SummaryView *summary_create(MainWindow *mainwin)
        toggle_search = gtk_toggle_button_new();
        gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(toggle_search),
                                     prefs_common.show_searchbar);
+       gtkut_widget_set_can_focus(toggle_search, FALSE);
        gtk_widget_show(toggle_search);
 
        CLAWS_SET_TIP(toggle_search, _("Toggle quick search bar"));
@@ -693,15 +706,17 @@ SummaryView *summary_create(MainWindow *mainwin)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "Separator1", "Message/Mark/---", GTK_UI_MANAGER_SEPARATOR)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "MarkUnread", "Message/Mark/MarkUnread", GTK_UI_MANAGER_MENUITEM)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "MarkRead", "Message/Mark/MarkRead", GTK_UI_MANAGER_MENUITEM)
+       MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "Separator2", "Message/Mark/---", GTK_UI_MANAGER_SEPARATOR)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "MarkAllRead", "Message/Mark/MarkAllRead", GTK_UI_MANAGER_MENUITEM)
+       MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "Separator3", "Message/Mark/---", GTK_UI_MANAGER_SEPARATOR)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "IgnoreThread", "Message/Mark/IgnoreThread", GTK_UI_MANAGER_MENUITEM)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "UnignoreThread", "Message/Mark/UnignoreThread", GTK_UI_MANAGER_MENUITEM)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "WatchThread", "Message/Mark/WatchThread", GTK_UI_MANAGER_MENUITEM)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "UnwatchThread", "Message/Mark/UnwatchThread", GTK_UI_MANAGER_MENUITEM)
-       MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "Separator2", "Message/Mark/---", GTK_UI_MANAGER_SEPARATOR)
+       MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "Separator4", "Message/Mark/---", GTK_UI_MANAGER_SEPARATOR)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "MarkSpam", "Message/Mark/MarkSpam", GTK_UI_MANAGER_MENUITEM)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "MarkHam", "Message/Mark/MarkHam", GTK_UI_MANAGER_MENUITEM)
-       MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "Separator3", "Message/Mark/---", GTK_UI_MANAGER_SEPARATOR)
+       MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "Separator5", "Message/Mark/---", GTK_UI_MANAGER_SEPARATOR)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "Lock", "Message/Mark/Lock", GTK_UI_MANAGER_MENUITEM)
        MENUITEM_ADDUI_MANAGER(mainwin->ui_manager, "/Menus/SummaryViewPopup/Mark", "Unlock", "Message/Mark/Unlock", GTK_UI_MANAGER_MENUITEM)
 
@@ -759,7 +774,7 @@ SummaryView *summary_create(MainWindow *mainwin)
                                summary_update_folder_hook,
                                (gpointer) summaryview);
 
-       summaryview->target_list = gtk_target_list_new(summary_drag_types, 2);
+       summaryview->target_list = gtk_target_list_new(summary_drag_types, 3);
 
        summaryview->quicksearch = quicksearch;
 
@@ -790,8 +805,10 @@ void summary_relayout(SummaryView *summaryview)
        g_object_ref(summaryview->hbox_l);
        g_object_ref(summaryview->statlabel_msgs);
        
-       gtkut_container_remove(GTK_CONTAINER(summaryview->hbox_l->parent), summaryview->hbox_l);
-       gtkut_container_remove(GTK_CONTAINER(summaryview->statlabel_msgs->parent), summaryview->statlabel_msgs);
+       gtkut_container_remove(GTK_CONTAINER(
+               gtk_widget_get_parent(summaryview->hbox_l)), summaryview->hbox_l);
+       gtkut_container_remove(GTK_CONTAINER(
+               gtk_widget_get_parent(summaryview->statlabel_msgs)), summaryview->statlabel_msgs);
 
        switch (prefs_common.layout_mode) {
        case NORMAL_LAYOUT:
@@ -875,7 +892,7 @@ static void summary_set_fonts(SummaryView *summaryview)
        if (prefs_common.derive_from_normal_font || !SMALL_FONT) {
                font_desc = pango_font_description_new();
                size = pango_font_description_get_size
-                       (summaryview->ctree->style->font_desc);
+                       (gtk_widget_get_style(summaryview->ctree)->font_desc);
                pango_font_description_set_size(font_desc, size * PANGO_SCALE_SMALL);
        } else {
                font_desc = pango_font_description_from_string(SMALL_FONT);
@@ -927,6 +944,8 @@ void summary_init(SummaryView *summaryview)
                         &repliedxpm);
        stock_pixbuf_gdk(summaryview->ctree, STOCK_PIXMAP_FORWARDED,
                         &forwardedxpm);
+       stock_pixbuf_gdk(summaryview->ctree, STOCK_PIXMAP_REPLIED_AND_FORWARDED,
+                        &repliedandforwardedxpm);
        stock_pixbuf_gdk(summaryview->ctree, STOCK_PIXMAP_CLIP,
                         &clipxpm);
        stock_pixbuf_gdk(summaryview->ctree, STOCK_PIXMAP_LOCKED,
@@ -973,9 +992,7 @@ void summary_init(SummaryView *summaryview)
        summaryview->sort_type = SORT_ASCENDING;
 
        /* Init summaryview extra data */
-#ifndef G_OS_WIN32
        summaryview->simplify_subject_preg = NULL;
-#endif
        summary_clear_list(summaryview);
        summary_set_column_titles(summaryview);
        summary_colorlabel_menu_create(summaryview, FALSE);
@@ -1002,7 +1019,7 @@ static void summary_switch_from_to(SummaryView *summaryview, FolderItem *item)
        SummaryColumnState *col_state = summaryview->col_state;
        GtkCMCTree *ctree = GTK_CMCTREE(summaryview->ctree);
        
-       if (!item || (prefs_common.layout_mode == VERTICAL_LAYOUT && prefs_common.two_line_vert) )
+       if (!item || ((prefs_common.layout_mode == VERTICAL_LAYOUT || prefs_common.layout_mode == SMALL_LAYOUT) && prefs_common.two_line_vert) )
                return;
        if (FOLDER_SHOWS_TO_HDR(item))
                show_to = TRUE;
@@ -1052,16 +1069,101 @@ static void summary_switch_from_to(SummaryView *summaryview, FolderItem *item)
        summary_set_column_titles(summaryview);
 }
 
-static gboolean summaryview_quicksearch_recurse(gpointer data)
+static void summaryview_reset_recursive_folder_match(SummaryView *summaryview)
 {
-       SummaryView *summaryview = (SummaryView *)data;
+       GSList *cur;
+
+       for (cur = summaryview->recursive_matched_folders; cur != NULL; cur = cur->next) {
+               folderview_update_search_icon(cur->data, FALSE);
+       }
+
+       g_slist_free(summaryview->recursive_matched_folders);
+       summaryview->recursive_matched_folders = NULL;
+       summaryview->search_root_folder = NULL;
+}
+
+static gboolean summaryview_quicksearch_recursive_progress(gpointer data, guint at, guint matched, guint total)
+{
+       QuickSearch *search = (QuickSearch*) data;
+       gint interval = quicksearch_is_fast(search) ? 5000 : 100;
+
+       statusbar_progress_all(at, total, interval);
+       if (at % interval == 0)
+               GTK_EVENTS_FLUSH();
+
+       if (matched > 0)
+               return FALSE;
+
+       return TRUE;
+}
+
+static void summaryview_quicksearch_recurse_step(SummaryView *summaryview, FolderItem *item)
+{
+       MsgInfoList *msgs = NULL;
+       gboolean result = TRUE;
+
+       statusbar_print_all(_("Searching in %s... \n"),
+               item->path ? item->path : "(null)");
+       folder_item_update_freeze();
+
+       quicksearch_set_on_progress_cb(summaryview->quicksearch, summaryview_quicksearch_recursive_progress, summaryview->quicksearch);
+       if (!quicksearch_run_on_folder(summaryview->quicksearch, item, &msgs))
+               result = FALSE;
+
+       result = result && msgs != NULL;
+
+       if (msgs != NULL)
+               procmsg_msg_list_free(msgs);
+
+       folder_item_update_thaw();
+       statusbar_progress_all(0, 0, 0);
+       statusbar_pop_all();
+
+       if (result) {
+               summaryview->recursive_matched_folders = g_slist_prepend(
+                               summaryview->recursive_matched_folders, item);
+       
+               folderview_update_search_icon(item, TRUE);
+       }
+}
+
+static void summaryview_quicksearch_search_subfolders(SummaryView *summaryview, FolderItem *folder_item)
+{
+       FolderItem *cur = NULL;
+       GNode *node = folder_item->node->children;
+
+       if (!prefs_common.summary_quicksearch_recurse
+                       || !quicksearch_has_sat_predicate(summaryview->quicksearch)
+                       || quicksearch_is_in_typing(summaryview->quicksearch))
+               return;
+
+       for (; node != NULL; node = node->next) {
+               if (!quicksearch_has_sat_predicate(summaryview->quicksearch))
+                       return;
+
+               cur = FOLDER_ITEM(node->data);
+               summaryview_quicksearch_recurse_step(summaryview, cur);
+               if (cur->node->children)
+                       summaryview_quicksearch_search_subfolders(summaryview, cur);
+       }
+}
+
+static void summaryview_quicksearch_recurse(SummaryView *summaryview)
+{
+       if (!prefs_common.summary_quicksearch_recurse
+               || !quicksearch_has_sat_predicate(summaryview->quicksearch)
+               || summaryview->folder_item == NULL) {
+               return;
+       }
+
        main_window_cursor_wait(summaryview->mainwin);
-       quicksearch_reset_cur_folder_item(summaryview->quicksearch);
-       quicksearch_search_subfolders(summaryview->quicksearch, 
-                             summaryview->folderview,
-                             summaryview->folder_item);
+
+       summaryview_reset_recursive_folder_match(summaryview);
+       summaryview->search_root_folder = summaryview->folder_item;
+
+       summaryview_quicksearch_search_subfolders(summaryview, summaryview->folder_item);
+       
        main_window_cursor_normal(summaryview->mainwin);
-       return FALSE;
 }
 
 static gboolean summary_check_consistency(FolderItem *item, GSList *mlist)
@@ -1109,6 +1211,20 @@ static gboolean summary_check_consistency(FolderItem *item, GSList *mlist)
        return TRUE;
 }
 
+gboolean summaryview_search_root_progress(gpointer data, guint at, guint matched, guint total)
+{
+       SummaryView *summaryview = (SummaryView*) data;
+
+       gint interval = quicksearch_is_fast(summaryview->quicksearch) ? 5000 : 100;
+       
+       statusbar_progress_all(at, total, interval);
+
+       if (at % interval == 0)
+               GTK_EVENTS_FLUSH();
+
+       return TRUE;
+}
+
 gboolean summary_show(SummaryView *summaryview, FolderItem *item)
 {
        GtkCMCTree *ctree = GTK_CMCTREE(summaryview->ctree);
@@ -1127,7 +1243,6 @@ gboolean summary_show(SummaryView *summaryview, FolderItem *item)
        if (!summaryview->mainwin)
                return FALSE;
        START_TIMING("");
-       summaryview->last_displayed = NULL;
        summary_switch_from_to(summaryview, item);
 
        inc_lock();
@@ -1154,8 +1269,8 @@ gboolean summary_show(SummaryView *summaryview, FolderItem *item)
        }
        if (!prefs_common.summary_quicksearch_sticky
         && (!prefs_common.summary_quicksearch_recurse
-         || !quicksearch_is_active(summaryview->quicksearch)
-         || (item && !quicksearch_is_in_subfolder(summaryview->quicksearch, item)))
+         || !quicksearch_has_sat_predicate(summaryview->quicksearch)
+         || (item && !folder_is_child_of(item, summaryview->search_root_folder)))
         && !quicksearch_is_running(summaryview->quicksearch)
         && !is_refresh) {
                quicksearch_set(summaryview->quicksearch, prefs_common.summary_quicksearch_type, "");
@@ -1192,7 +1307,7 @@ gboolean summary_show(SummaryView *summaryview, FolderItem *item)
                        END_TIMING();
                        return FALSE;
                }
-               if (changed || !quicksearch_is_active(summaryview->quicksearch))
+               if (changed || !quicksearch_has_sat_predicate(summaryview->quicksearch))
                        folder_update_op_count();
        }
        
@@ -1208,23 +1323,15 @@ gboolean summary_show(SummaryView *summaryview, FolderItem *item)
                                (item && item->path)?item->path:"(null)",
                                item?folder_item_parent(item):0x0,
                                item?item->no_select:FALSE);
-               summary_set_hide_read_msgs_menu(summaryview, FALSE);
-               summary_set_hide_del_msgs_menu(summaryview, FALSE);
+               summary_set_hide_menu(summaryview, "/Menu/View/HideReadMessages", FALSE);
+               summary_set_hide_menu(summaryview, "/Menu/View/HideDelMessages", FALSE);
+               summary_set_hide_menu(summaryview, "/Menu/View/HideReadThreads", FALSE);
                summary_clear_all(summaryview);
                summaryview->folder_item = item;
                summary_thaw(summaryview);
                summary_unlock(summaryview);
                inc_unlock();
-               if (item && quicksearch_is_running(summaryview->quicksearch)) {
-                       main_window_cursor_wait(summaryview->mainwin);
-                       quicksearch_reset_cur_folder_item(summaryview->quicksearch);
-                       if (quicksearch_is_active(summaryview->quicksearch))
-                               quicksearch_search_subfolders(summaryview->quicksearch, 
-                                             summaryview->folderview,
-                                             summaryview->folder_item);
-                       main_window_cursor_normal(summaryview->mainwin);
-               }       
-               END_TIMING();           
+               END_TIMING();
                return TRUE;
        }
        g_free(buf);
@@ -1250,12 +1357,51 @@ gboolean summary_show(SummaryView *summaryview, FolderItem *item)
                mlist = folder_item_get_msg_list(item);
        }
 
-       if ((summaryview->folder_item->hide_read_msgs || summaryview->folder_item->hide_del_msgs) &&
-           quicksearch_is_active(summaryview->quicksearch) == FALSE) {
+       if (quicksearch_has_sat_predicate(summaryview->quicksearch)) {
+               procmsg_msg_list_free(mlist);
+               mlist = NULL;
+
+               START_TIMING("quicksearch");
+
+               statusbar_print_all(_("Searching in %s... \n"), 
+                       summaryview->folder_item->path ? 
+                       summaryview->folder_item->path : "(null)");
+
+               folder_item_update_freeze();
+
+               quicksearch_set_on_progress_cb(summaryview->quicksearch, summaryview_search_root_progress, summaryview);
+               quicksearch_run_on_folder(summaryview->quicksearch, summaryview->folder_item, &mlist);
+
+               folder_item_update_thaw();
+               statusbar_progress_all(0, 0, 0);
+               statusbar_pop_all();
+
+               if (!quicksearch_has_sat_predicate(summaryview->quicksearch)) {
+                       debug_print("search cancelled!\n");
+                       summary_thaw(summaryview);
+                       STATUSBAR_POP(summaryview->mainwin);
+                       main_window_cursor_normal(summaryview->mainwin);
+                       summary_unlock(summaryview);
+                       inc_unlock();
+                       summary_show(summaryview, summaryview->folder_item);
+                       END_TIMING();
+                       return FALSE;
+               }
+               END_TIMING();
+       }
+
+       if ((summaryview->folder_item->hide_read_msgs
+             || summaryview->folder_item->hide_del_msgs
+             || summaryview->folder_item->hide_read_threads) &&
+           quicksearch_has_sat_predicate(summaryview->quicksearch) == FALSE) {
                GSList *not_killed;
                
-               summary_set_hide_read_msgs_menu(summaryview, summaryview->folder_item->hide_read_msgs);
-               summary_set_hide_del_msgs_menu(summaryview, summaryview->folder_item->hide_del_msgs);
+               summary_set_hide_menu(summaryview, "/Menu/View/HideReadMessages",
+                                               summaryview->folder_item->hide_read_msgs);
+               summary_set_hide_menu(summaryview, "/Menu/View/HideDelMessages",
+                                               summaryview->folder_item->hide_del_msgs);
+               summary_set_hide_menu(summaryview, "/Menu/View/HideReadThreads",
+                                               summaryview->folder_item->hide_read_threads);
                not_killed = NULL;
                for(cur = mlist ; cur != NULL && cur->data != NULL ; cur = g_slist_next(cur)) {
                        MsgInfo * msginfo = (MsgInfo *) cur->data;
@@ -1288,54 +1434,12 @@ gboolean summary_show(SummaryView *summaryview, FolderItem *item)
                g_slist_free(mlist);
                mlist = not_killed;
        } else {
-               summary_set_hide_read_msgs_menu(summaryview, FALSE);
-               summary_set_hide_del_msgs_menu(summaryview, FALSE);
-       }
-
-       if (quicksearch_is_active(summaryview->quicksearch)) {
-               GSList *not_killed;
-               gint interval = quicksearch_is_fast(summaryview->quicksearch) ? 5000:100;
-               START_TIMING("quicksearch");
-               gint num = 0, total = summaryview->folder_item->total_msgs;
-               statusbar_print_all(_("Searching in %s... \n"), 
-                       summaryview->folder_item->path ? 
-                       summaryview->folder_item->path : "(null)");
-               not_killed = NULL;
-               folder_item_update_freeze();
-               for (cur = mlist ; cur != NULL && cur->data != NULL ; cur = g_slist_next(cur)) {
-                       MsgInfo * msginfo = (MsgInfo *) cur->data;
-
-                       statusbar_progress_all(num++,total, interval);
-
-                       if (!msginfo->hidden && quicksearch_match(summaryview->quicksearch, msginfo))
-                               not_killed = g_slist_prepend(not_killed, msginfo);
-                       else
-                               procmsg_msginfo_free(msginfo);
-                       if (num % interval == 0)
-                               GTK_EVENTS_FLUSH();
-                       if (!quicksearch_is_active(summaryview->quicksearch)) {
-                               break;
-                       }
-               }
-               folder_item_update_thaw();
-               statusbar_progress_all(0,0,0);
-               statusbar_pop_all();
-               
-               hidden_removed = TRUE;
-               if (!quicksearch_is_active(summaryview->quicksearch)) {
-                       debug_print("search cancelled!\n");
-                       summary_thaw(summaryview);
-                       STATUSBAR_POP(summaryview->mainwin);
-                       main_window_cursor_normal(summaryview->mainwin);
-                       summary_unlock(summaryview);
-                       inc_unlock();
-                       summary_show(summaryview, summaryview->folder_item);
-                       END_TIMING();
-                       return FALSE;
-               }
-               g_slist_free(mlist);
-               mlist = not_killed;
-               END_TIMING();
+               summary_set_hide_menu(summaryview, "/Menu/View/HideReadMessages",
+                                               FALSE);
+               summary_set_hide_menu(summaryview, "/Menu/View/HideDelMessages",
+                                               FALSE);
+               summary_set_hide_menu(summaryview, "/Menu/View/HideReadThreads",
+                                               FALSE);
        }
 
        if (!hidden_removed) {
@@ -1362,16 +1466,8 @@ gboolean summary_show(SummaryView *summaryview, FolderItem *item)
 
        g_slist_free(mlist);
 
-       if (quicksearch_is_active(summaryview->quicksearch) &&
-           quicksearch_is_running(summaryview->quicksearch)) {
-               /* only scan subfolders when quicksearch changed,
-                * not when search is the same and folder changed */
-               g_timeout_add(100, summaryview_quicksearch_recurse, summaryview);
-       }
-
        if (is_refresh) {
                if (!quicksearch_is_in_typing(summaryview->quicksearch)) {
-                       summaryview->last_displayed = summaryview->displayed;
                        summaryview->displayed =
                                summary_find_msg_by_msgnum(summaryview,
                                                           displayed_msgnum);
@@ -1496,6 +1592,12 @@ gboolean summary_show(SummaryView *summaryview, FolderItem *item)
 
 #undef CURRENTLY_DISPLAYED
 
+static void summary_cancel_mark_read_timeout(SummaryView *summaryview) {
+       if (summaryview->mark_as_read_timeout_tag != 0) {
+               g_source_remove(summaryview->mark_as_read_timeout_tag);
+               summaryview->mark_as_read_timeout_tag = 0;
+       }
+}
 
 void summary_clear_list(SummaryView *summaryview)
 {
@@ -1512,6 +1614,8 @@ void summary_clear_list(SummaryView *summaryview)
                summaryview->folder_item = NULL;
        }
 
+       summary_cancel_mark_read_timeout(summaryview);
+
        summaryview->display_msg = FALSE;
 
        summaryview->selected = NULL;
@@ -1618,72 +1722,83 @@ GSList *summary_get_selected_msg_list(SummaryView *summaryview)
 
 void summary_set_menu_sensitive(SummaryView *summaryview)
 {
-       SensitiveCond state;
+       SensitiveCondMask state;
        gboolean sensitive;
        gint i;
 
-       static const struct {
-               gchar *const entry;
-               SensitiveCond cond;
-       } entry[] = {
-               {"Menus/SummaryViewPopup/Reply"                 , M_HAVE_ACCOUNT|M_TARGET_EXIST},
+#define N_ENTRIES 38
+       static struct {
+               const gchar *entry;
+               SensitiveCondMask cond;
+       } entry[N_ENTRIES];
+
+       i = 0;
+#define FILL_TABLE(entry_str, ...) \
+do { \
+       entry[i].entry = (const gchar *) entry_str; entry[i++].cond = main_window_get_mask(__VA_ARGS__, -1); \
+} while (0)
+
+       FILL_TABLE("Menus/SummaryViewPopup/Reply", M_HAVE_ACCOUNT, M_TARGET_EXIST);
 #ifndef GENERIC_UMPC
-               {"Menus/SummaryViewPopup/ReplyTo"                       , M_HAVE_ACCOUNT|M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/ReplyTo/All"           , M_HAVE_ACCOUNT|M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/ReplyTo/Sender"             , M_HAVE_ACCOUNT|M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/ReplyTo/MailingList"       , M_HAVE_ACCOUNT|M_TARGET_EXIST},
+       FILL_TABLE("Menus/SummaryViewPopup/ReplyTo", M_HAVE_ACCOUNT, M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/ReplyTo/All", M_HAVE_ACCOUNT, M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/ReplyTo/Sender", M_HAVE_ACCOUNT, M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/ReplyTo/MailingList", M_HAVE_ACCOUNT, M_TARGET_EXIST);
 #endif
 
-               {"Menus/SummaryViewPopup/Forward"                       , M_HAVE_ACCOUNT|M_TARGET_EXIST},
+       FILL_TABLE("Menus/SummaryViewPopup/Forward", M_HAVE_ACCOUNT, M_TARGET_EXIST);
 #ifndef GENERIC_UMPC
-               {"Menus/SummaryViewPopup/ForwardAtt"    , M_HAVE_ACCOUNT|M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Redirect"                      , M_HAVE_ACCOUNT|M_TARGET_EXIST},
+       FILL_TABLE("Menus/SummaryViewPopup/ForwardAtt", M_HAVE_ACCOUNT, M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Redirect", M_HAVE_ACCOUNT, M_TARGET_EXIST);
 #endif
 
-               {"Menus/SummaryViewPopup/Move"                  , M_TARGET_EXIST|M_ALLOW_DELETE|M_NOT_NEWS},
-               {"Menus/SummaryViewPopup/Copy"                  , M_TARGET_EXIST|M_EXEC},
-               {"Menus/SummaryViewPopup/Trash"         , M_TARGET_EXIST|M_ALLOW_DELETE|M_NOT_NEWS},
+       FILL_TABLE("Menus/SummaryViewPopup/Move", M_TARGET_EXIST, M_ALLOW_DELETE, M_NOT_NEWS);
+       FILL_TABLE("Menus/SummaryViewPopup/Copy", M_TARGET_EXIST, M_EXEC);
+       FILL_TABLE("Menus/SummaryViewPopup/Trash", M_TARGET_EXIST, M_ALLOW_DELETE, M_NOT_NEWS, M_NOT_TRASH);
 #ifndef GENERIC_UMPC
-               {"Menus/SummaryViewPopup/Delete"                        , M_TARGET_EXIST|M_ALLOW_DELETE},
+       FILL_TABLE("Menus/SummaryViewPopup/Delete", M_TARGET_EXIST, M_ALLOW_DELETE);
 #endif
 
-               {"Menus/SummaryViewPopup/Mark"                  , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/Mark"             , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/Unmark"                   , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/MarkUnread"       , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/MarkRead"         , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/MarkAllRead"      , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/IgnoreThread"     , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/UnignoreThread"           , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/WatchThread"              , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/UnwatchThread"    , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/Unlock"                   , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/Lock"             , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Mark/MarkSpam"         , M_TARGET_EXIST|M_CAN_LEARN_SPAM},
-               {"Menus/SummaryViewPopup/Mark/MarkHam"          , M_TARGET_EXIST|M_CAN_LEARN_SPAM},
-               {"Menus/SummaryViewPopup/ColorLabel"                    , M_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/Tags"                  , M_TARGET_EXIST},
+       FILL_TABLE("Menus/SummaryViewPopup/Mark", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/Mark", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/Unmark", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/MarkUnread", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/MarkRead", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/MarkAllRead", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/IgnoreThread", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/UnignoreThread", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/WatchThread", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/UnwatchThread", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/Unlock", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/Lock", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/MarkSpam", M_TARGET_EXIST, M_CAN_LEARN_SPAM);
+       FILL_TABLE("Menus/SummaryViewPopup/Mark/MarkHam", M_TARGET_EXIST, M_CAN_LEARN_SPAM);
+       FILL_TABLE("Menus/SummaryViewPopup/ColorLabel", M_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/Tags", M_TARGET_EXIST);
 
 #ifndef GENERIC_UMPC
-               {"Menus/SummaryViewPopup/AddSenderToAB" , M_SINGLE_TARGET_EXIST},
+       FILL_TABLE("Menus/SummaryViewPopup/AddSenderToAB", M_SINGLE_TARGET_EXIST);
 #endif
-               {"Menus/SummaryViewPopup/CreateFilterRule"              , M_SINGLE_TARGET_EXIST|M_UNLOCKED},
+       FILL_TABLE("Menus/SummaryViewPopup/CreateFilterRule", M_SINGLE_TARGET_EXIST, M_UNLOCKED);
 #ifndef GENERIC_UMPC
-               {"Menus/SummaryViewPopup/CreateProcessingRule"  , M_SINGLE_TARGET_EXIST|M_UNLOCKED},
+       FILL_TABLE("Menus/SummaryViewPopup/CreateProcessingRule", M_SINGLE_TARGET_EXIST, M_UNLOCKED);
 #endif
 
-               {"Menus/SummaryViewPopup/View"                  , M_SINGLE_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/View/OpenNewWindow"     , M_SINGLE_TARGET_EXIST},
-               {"Menus/SummaryViewPopup/View/MessageSource"            , M_SINGLE_TARGET_EXIST},
+       FILL_TABLE("Menus/SummaryViewPopup/View", M_SINGLE_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/View/OpenNewWindow", M_SINGLE_TARGET_EXIST);
+       FILL_TABLE("Menus/SummaryViewPopup/View/MessageSource", M_SINGLE_TARGET_EXIST);
 #ifndef GENERIC_UMPC
-               {"Menus/SummaryViewPopup/View/AllHeaders"               , M_SINGLE_TARGET_EXIST},
+       FILL_TABLE("Menus/SummaryViewPopup/View/AllHeaders", M_SINGLE_TARGET_EXIST);
 #endif
-               {"Menus/SummaryViewPopup/SaveAs"                        , M_TARGET_EXIST},
+       FILL_TABLE("Menus/SummaryViewPopup/SaveAs", M_TARGET_EXIST);
 #ifndef GENERIC_UMPC
-               {"Menus/SummaryViewPopup/Print"                 , M_TARGET_EXIST},
+       FILL_TABLE("Menus/SummaryViewPopup/Print", M_TARGET_EXIST);
 #endif
-               {NULL, 0}
-       };
+       FILL_TABLE(NULL, -1);
+#undef FILL_TABLE
+       if (i != N_ENTRIES)
+               g_error("summaryview menu entry table size mismatch (%d/%d)", i, N_ENTRIES);
+#undef ENTRIES
 
        main_window_set_menu_sensitive(summaryview->mainwin);
 
@@ -1700,7 +1815,7 @@ void summary_set_menu_sensitive(SummaryView *summaryview)
        &&  summaryview->messageview->mimeview
        &&  summaryview->messageview->mimeview->textview)
                cm_toggle_menu_set_active_full(summaryview->mainwin->ui_manager, "Menus/SummaryViewPopup/View/AllHeaders",
-                       summaryview->messageview->mimeview->textview->show_all_headers);
+                       prefs_common.show_all_headers);
 #endif
        summary_unlock(summaryview);
 }
@@ -1792,15 +1907,11 @@ void summary_select_next_unread(SummaryView *summaryview)
                                                _("Internal error: unexpected value for prefs_common.next_unread_msg_dialog\n"));
                        }
 
-                       if (val == G_ALERTALTERNATE) {
-                               folderview_select_next_unread(summaryview->folderview, TRUE);
-                               return;
-                       } 
-                       else
-                               return;
-               } else
+                       if (val == G_ALERTALTERNATE)
+                               folderview_select_next_with_flag(summaryview->folderview, MSG_UNREAD, TRUE);
+               } else {
                        summary_select_node(summaryview, node, TRUE, FALSE);
-
+               }
        }
 }
 
@@ -1892,7 +2003,7 @@ void summary_select_next_new(SummaryView *summaryview)
                        }
 
                        if (val == G_ALERTALTERNATE) {
-                               folderview_select_next_new(summaryview->folderview);
+                               folderview_select_next_with_flag(summaryview->folderview, MSG_NEW, TRUE);
                                return;
                        } 
                        else
@@ -1971,7 +2082,7 @@ void summary_select_next_marked(SummaryView *summaryview)
                        }
 
                        if (val == G_ALERTALTERNATE) {
-                               folderview_select_next_marked(summaryview->folderview);
+                               folderview_select_next_with_flag(summaryview->folderview, MSG_MARKED, TRUE);
                                return;
                        } 
                        else
@@ -2032,12 +2143,6 @@ void summary_select_next_labeled(SummaryView *summaryview)
                summary_select_node(summaryview, node, TRUE, FALSE);
 }
 
-void summary_select_last_read(SummaryView *summaryview)
-{
-       if (summaryview->last_displayed)
-               summary_select_node(summaryview, summaryview->last_displayed, TRUE, FALSE);
-}
-
 void summary_select_parent(SummaryView *summaryview)
 {
        GtkCMCTreeNode *node = NULL;
@@ -2056,6 +2161,34 @@ void summary_select_by_msgnum(SummaryView *summaryview, guint msgnum)
        summary_select_node(summaryview, node, FALSE, TRUE);
 }
 
+void summary_display_by_msgnum(SummaryView *summaryview, guint msgnum)
+{
+       GtkCMCTreeNode *node;
+
+       node = summary_find_msg_by_msgnum(summaryview, msgnum);
+       summary_select_node(summaryview, node, TRUE, FALSE);
+}
+
+void summary_select_by_msg_list(SummaryView    *summaryview, GSList *msginfos)
+{
+       GtkCMCTree *ctree;
+       GSList *msgnum_list, *walk;
+       gboolean froze = FALSE;
+
+       ctree = GTK_CMCTREE(summaryview->ctree);
+
+       msgnum_list = procmsg_get_number_list_for_msgs(msginfos);
+
+       START_LONG_OPERATION(summaryview, FALSE);
+       for(walk = msgnum_list; walk; walk = walk->next) {
+               GtkCMCTreeNode *node;
+               node = summary_find_msg_by_msgnum(summaryview, GPOINTER_TO_UINT(walk->data));
+               gtk_cmctree_select(ctree, node);
+       }
+       END_LONG_OPERATION(summaryview);
+       g_slist_free(msgnum_list);
+}
+
 typedef struct _PostponedSelectData
 {
        GtkCMCTree *ctree;
@@ -2125,6 +2258,7 @@ void summary_select_node(SummaryView *summaryview, GtkCMCTreeNode *node,
        if (!summaryview->folder_item)
                return;
        if (node) {
+               summary_cancel_mark_read_timeout(summaryview);
                gtkut_ctree_expand_parent_all(ctree, node);
                if (do_refresh) {
                        summary_lock(summaryview);
@@ -2376,6 +2510,8 @@ static void summary_set_marks_func(GtkCMCTree *ctree, GtkCMCTreeNode *node,
 
        msginfo = gtk_cmctree_node_get_row_data(ctree, node);
 
+       cm_return_if_fail(msginfo != NULL);
+
        if (MSG_IS_DELETED(msginfo->flags))
                summaryview->deleted++;
 
@@ -2423,9 +2559,7 @@ static void summary_status_show(SummaryView *summaryview)
        goffset sel_size = 0, n_size = 0;
        MsgInfo *msginfo;
        gchar *name;
-#if GTK_CHECK_VERSION(2, 12, 0)
        gchar *tooltip;
-#endif
        
        if (!summaryview->folder_item) {
                gtk_label_set_text(GTK_LABEL(summaryview->statlabel_folder), "");
@@ -2448,7 +2582,8 @@ static void summary_status_show(SummaryView *summaryview)
        
        if (summaryview->folder_item->hide_read_msgs 
        || summaryview->folder_item->hide_del_msgs
-       || quicksearch_is_active(summaryview->quicksearch)) {
+       || summaryview->folder_item->hide_read_threads
+       || quicksearch_has_sat_predicate(summaryview->quicksearch)) {
                rowlist = GTK_CMCLIST(summaryview->ctree)->row_list;
                for (cur = rowlist; cur != NULL && cur->data != NULL; cur = cur->next) {
                        msginfo = gtk_cmctree_node_get_row_data
@@ -2517,10 +2652,7 @@ static void summary_status_show(SummaryView *summaryview)
 
        if (n_selected) {
                sel = g_strdup_printf(" (%s)", to_human_readable((goffset)sel_size));
-               if (n_selected == 1)
-                       itstr = g_strdup(_(" item selected"));
-               else
-                       itstr = g_strdup(_(" items selected"));
+               itstr = g_strdup_printf(ngettext(" item selected"," items selected", n_selected));
        } else {
                sel = g_strdup("");
                itstr = g_strdup("");
@@ -2545,27 +2677,32 @@ static void summary_status_show(SummaryView *summaryview)
 
                gtk_label_set_text(GTK_LABEL(summaryview->statlabel_msgs), str);
                g_free(str);
-#if GTK_CHECK_VERSION(2, 12, 0)
-               tooltip = g_strdup_printf(_("<b>Message summary</b>\n"
-                                           "<b>New:</b> %d\n"
-                                           "<b>Unread:</b> %d\n"
-                                           "<b>Total:</b> %d\n"
-                                           "<b>Size:</b> %s\n\n"
-                                           "<b>Marked:</b> %d\n"
-                                           "<b>Replied:</b> %d\n"
-                                           "<b>Forwarded:</b> %d\n"
-                                           "<b>Locked:</b> %d\n"
-                                           "<b>Ignored:</b> %d\n"
-                                           "<b>Watched:</b> %d"),
-                                             n_new, n_unread, n_total,
-                                             to_human_readable((goffset)n_size),
-                                             n_marked,n_replied,n_forwarded,
-                                             n_locked,n_ignored,n_watched);
+               tooltip = g_strdup_printf("<b>%s</b>\n"
+                                       "<b>%s</b> %d\n"
+                                       "<b>%s</b> %d\n"
+                                       "<b>%s</b> %d\n"
+                                       "<b>%s</b> %s\n\n"
+                                       "<b>%s</b> %d\n"
+                                       "<b>%s</b> %d\n"
+                                       "<b>%s</b> %d\n"
+                                       "<b>%s</b> %d\n"
+                                       "<b>%s</b> %d\n"
+                                       "<b>%s</b> %d",
+                                       _("Message summary"),
+                                       _("New:"), n_new,
+                                       _("Unread:"), n_unread,
+                                       _("Total:"), n_total,
+                                       _("Size:"), to_human_readable((goffset)n_size),
+                                       _("Marked:"), n_marked,
+                                       _("Replied:"), n_replied,
+                                       _("Forwarded:"), n_forwarded,
+                                       _("Locked:"), n_locked,
+                                       _("Ignored:"), n_ignored,
+                                       _("Watched:"), n_watched);
 
                gtk_widget_set_tooltip_markup(GTK_WIDGET(summaryview->statlabel_msgs),
                                            tooltip); 
                g_free(tooltip);
-#endif
        } else {
                gchar *ssize, *tsize;
                if (n_selected) {
@@ -2682,7 +2819,9 @@ static void summary_set_column_titles(SummaryView *summaryview)
                        gtk_box_pack_start(GTK_BOX(hbox), label,
                                           FALSE, FALSE, 0);
 
-               if (summaryview->sort_key == sort_by[type]) {
+               if (summaryview->sort_key == sort_by[type] ||
+                   (summaryview->sort_key == SORT_BY_THREAD_DATE &&
+                    sort_by[SORT_BY_DATE] && type == S_COL_DATE)) {
                        arrow = gtk_arrow_new
                                (summaryview->sort_type == SORT_ASCENDING
                                 ? GTK_ARROW_DOWN : GTK_ARROW_UP,
@@ -2704,7 +2843,7 @@ static void summary_set_column_titles(SummaryView *summaryview)
 void summary_reflect_tags_changes(SummaryView *summaryview)
 {
        GtkMenuShell *menu;
-       GList *cur;
+       GList *children, *cur;
        GtkCMCTreeNode *node;
        GtkCMCTree *ctree = GTK_CMCTREE(summaryview->ctree);
        gboolean froze = FALSE;
@@ -2715,9 +2854,11 @@ void summary_reflect_tags_changes(SummaryView *summaryview)
        cm_return_if_fail(menu != NULL);
 
        /* clear items. get item pointers. */
-       for (cur = menu->children; cur != NULL && cur->data != NULL; cur = cur->next) {
+       children = gtk_container_get_children(GTK_CONTAINER(menu));
+       for (cur = children; cur != NULL && cur->data != NULL; cur = cur->next) {
                gtk_menu_item_set_submenu(GTK_MENU_ITEM(cur->data), NULL);
        }
+       g_list_free(children);
        summary_tags_menu_create(summaryview, TRUE);
 
        START_LONG_OPERATION(summaryview, TRUE);
@@ -2809,11 +2950,9 @@ void summary_sort(SummaryView *summaryview,
                cmp_func = (GtkCMCListCompareFunc)summary_cmp_by_from;
                break;
        case SORT_BY_SUBJECT:
-#ifndef G_OS_WIN32
                if (summaryview->simplify_subject_preg)
                        cmp_func = (GtkCMCListCompareFunc)summary_cmp_by_simplified_subject;
                else
-#endif
                        cmp_func = (GtkCMCListCompareFunc)summary_cmp_by_subject;
                break;
        case SORT_BY_SCORE:
@@ -2897,6 +3036,30 @@ static void summary_find_thread_age(GNode *gnode)
        msginfo->thread_date = most_recent;
 }
 
+static gboolean summary_update_is_read(GNode *node, gpointer data)
+{
+       MsgInfo *msginfo = node->data;
+       gboolean *all_read = (gboolean *)data;
+
+       if (MSG_IS_UNREAD(msginfo->flags)) {
+               *all_read = FALSE;
+               return TRUE;
+       }
+       return FALSE;
+}      
+
+static gboolean summary_thread_is_read(GNode *gnode)
+{
+       MsgInfo *msginfo = (MsgInfo *)gnode->data;
+       gboolean all_read = TRUE;
+
+       if (!msginfo)
+               return all_read;
+
+       g_node_traverse(gnode, G_IN_ORDER, G_TRAVERSE_ALL, -1, summary_update_is_read, &all_read);
+    return all_read;
+}
+
 static gboolean summary_insert_gnode_func(GtkCMCTree *ctree, guint depth, GNode *gnode,
                                   GtkCMCTreeNode *cnode, gpointer data)
 {
@@ -2906,11 +3069,12 @@ static gboolean summary_insert_gnode_func(GtkCMCTree *ctree, guint depth, GNode
        gint *col_pos = summaryview->col_pos;
        const gchar *msgid = msginfo->msgid;
        GHashTable *msgid_table = summaryview->msgid_table;
-       gboolean vert = (prefs_common.layout_mode == VERTICAL_LAYOUT);
+       gboolean vert_layout = (prefs_common.layout_mode == VERTICAL_LAYOUT);
+       gboolean small_layout = (prefs_common.layout_mode == SMALL_LAYOUT);
 
        summary_set_header(summaryview, text, msginfo);
 
-       gtk_sctree_set_node_info(ctree, cnode, text[col_pos[S_COL_SUBJECT]], 2,
+       gtk_cmctree_set_node_info(ctree, cnode, text[col_pos[S_COL_SUBJECT]], 2,
                                NULL, NULL, FALSE, summaryview->threaded && !summaryview->thread_collapsed);
 #define SET_TEXT(col) {                                                \
        gtk_cmctree_node_set_text(ctree, cnode, col_pos[col],   \
@@ -2932,7 +3096,7 @@ static gboolean summary_insert_gnode_func(GtkCMCTree *ctree, guint depth, GNode
        if (summaryview->col_state[summaryview->col_pos[S_COL_TAGS]].visible)
                SET_TEXT(S_COL_TAGS);
 
-       if (vert && prefs_common.two_line_vert)
+       if ((vert_layout || small_layout) && prefs_common.two_line_vert)
                g_free(text[summaryview->col_pos[S_COL_SUBJECT]]);
 
 #undef SET_TEXT
@@ -2955,8 +3119,8 @@ static void summary_set_ctree_from_list(SummaryView *summaryview,
        GHashTable *msgid_table;
        GHashTable *subject_table = NULL;
        GSList * cur;
-       gboolean vert = (prefs_common.layout_mode == VERTICAL_LAYOUT);
-
+       gboolean vert_layout = (prefs_common.layout_mode == VERTICAL_LAYOUT);
+       gboolean small_layout = (prefs_common.layout_mode == SMALL_LAYOUT);
        START_TIMING("");
        
        if (!mlist) return;
@@ -2990,10 +3154,14 @@ static void summary_set_ctree_from_list(SummaryView *summaryview,
                
                for (gnode = root->children; gnode != NULL;
                     gnode = gnode->next) {
-                       summary_find_thread_age(gnode);
-                       node = gtk_sctree_insert_gnode
-                               (ctree, NULL, node, gnode,
-                                summary_insert_gnode_func, summaryview);
+            if (!summaryview->folder_item->hide_read_threads ||
+                    !summary_thread_is_read(gnode))
+            {
+                summary_find_thread_age(gnode);
+                node = gtk_sctree_insert_gnode
+                    (ctree, NULL, node, gnode,
+                     summary_insert_gnode_func, summaryview);
+            }
                }
 
                g_node_destroy(root);
@@ -3012,7 +3180,7 @@ static void summary_set_ctree_from_list(SummaryView *summaryview,
                                (ctree, NULL, node, text, 2,
                                 NULL, NULL,
                                 FALSE, FALSE);
-                       if (vert && prefs_common.two_line_vert)
+                       if ((vert_layout || small_layout) && prefs_common.two_line_vert)
                                g_free(text[summaryview->col_pos[S_COL_SUBJECT]]);
 
                        GTKUT_CTREE_NODE_SET_ROW_DATA(node, msginfo);
@@ -3110,14 +3278,11 @@ static inline void summary_set_header(SummaryView *summaryview, gchar *text[],
        gint *col_pos = summaryview->col_pos;
        gchar *from_text = NULL, *to_text = NULL, *tags_text = NULL;
        gboolean should_swap = FALSE;
-       gboolean vert = (prefs_common.layout_mode == VERTICAL_LAYOUT);
-#if GTK_CHECK_VERSION(2,12,0)
+       gboolean vert_layout = (prefs_common.layout_mode == VERTICAL_LAYOUT);
+       gboolean small_layout = (prefs_common.layout_mode == SMALL_LAYOUT);
        static const gchar *color_dim_rgb = NULL;
        if (!color_dim_rgb)
                color_dim_rgb = gdk_color_to_string(&summaryview->color_dim);
-#else
-       static const gchar *color_dim_rgb = "#888888";
-#endif
        text[col_pos[S_COL_FROM]]   = "";
        text[col_pos[S_COL_TO]]     = "";
        text[col_pos[S_COL_SUBJECT]]= "";
@@ -3158,7 +3323,7 @@ static inline void summary_set_header(SummaryView *summaryview, gchar *text[],
 
        /* slow! */
        if (summaryview->col_state[summaryview->col_pos[S_COL_DATE]].visible || 
-           (vert && prefs_common.two_line_vert)) {
+           ((vert_layout || small_layout) && prefs_common.two_line_vert)) {
                if (msginfo->date_t && msginfo->date_t > 0) {
                        procheader_date_get_localtime(date_modified,
                                                      sizeof(date_modified),
@@ -3186,9 +3351,16 @@ static inline void summary_set_header(SummaryView *summaryview, gchar *text[],
        }
 
        if (!prefs_common.use_addr_book) {
-               from_text = msginfo->fromname ? 
-                               msginfo->fromname :
-                               _("(No From)");
+               if (prefs_common.summary_from_show == SHOW_NAME)
+                       from_text = msginfo->fromname;
+               else if (prefs_common.summary_from_show == SHOW_BOTH)
+                       from_text = msginfo->from;
+               else {
+                       from_text = msginfo->from;
+                       extract_address(from_text);
+               }
+               if (!from_text)
+                       from_text = _("(No From)");
        } else {
                gchar *tmp = summary_complete_address(msginfo->from);
                if (tmp) {
@@ -3196,9 +3368,17 @@ static inline void summary_set_header(SummaryView *summaryview, gchar *text[],
                        g_free(tmp);
                        from_text = buf;
                } else {
-                       from_text = (msginfo->fromname) ?
-                                       msginfo->fromname: 
-                                       _("(No From)");
+                       if (prefs_common.summary_from_show == SHOW_NAME)
+                               from_text = msginfo->fromname;
+                       else if (prefs_common.summary_from_show == SHOW_BOTH)
+                               from_text = msginfo->from;
+                       else {
+                               from_text = msginfo->from;
+                               if (from_text)
+                                       extract_address(from_text);
+                       }
+                       if (!from_text)
+                               from_text = _("(No From)");
                }
        }
        
@@ -3222,31 +3402,33 @@ static inline void summary_set_header(SummaryView *summaryview, gchar *text[],
                                to_text = to_text ? to_text : _("(No From)");
                        }
                }
-               snprintf(tmp2, BUFFSIZE-1, "--> %s", to_text);
+               snprintf(tmp2, BUFFSIZE-1, "âžœ %s", to_text);
                tmp2[BUFFSIZE-1]='\0';
                text[col_pos[S_COL_FROM]] = tmp2;
        }
        
-#ifndef G_OS_WIN32
        if (summaryview->simplify_subject_preg != NULL)
                text[col_pos[S_COL_SUBJECT]] = msginfo->subject ? 
                        string_remove_match(tmp3, BUFFSIZE, msginfo->subject, 
                                        summaryview->simplify_subject_preg) : 
                        _("(No Subject)");
        else 
-#endif
                text[col_pos[S_COL_SUBJECT]] = msginfo->subject ? msginfo->subject :
                        _("(No Subject)");
-       if (vert && prefs_common.two_line_vert) {
+       if ((vert_layout || small_layout) && prefs_common.two_line_vert) {
                if (!FOLDER_SHOWS_TO_HDR(summaryview->folder_item)) {
-                       gchar *tmp = g_markup_printf_escaped(_("%s\n<span color='%s' style='italic'>From: %s, on %s</span>"),
+                       gchar *tmp = g_markup_printf_escaped(g_strconcat("%s\n",
+                                                                       "<span color='%s' style='italic'>",
+                                                                       _("From: %s, on %s"), "</span>", NULL),
                                        text[col_pos[S_COL_SUBJECT]],
                                        color_dim_rgb,
                                        text[col_pos[S_COL_FROM]],
                                        text[col_pos[S_COL_DATE]]);
                        text[col_pos[S_COL_SUBJECT]] = tmp;
                } else {
-                       gchar *tmp = g_markup_printf_escaped(_("%s\n<span color='%s' style='italic'>To: %s, on %s</span>"),
+                       gchar *tmp = g_markup_printf_escaped(g_strconcat("%s\n",
+                                                                        "<span color='%s' style='italic'>",
+                                                                       _("To: %s, on %s"), "</span>", NULL),
                                        text[col_pos[S_COL_SUBJECT]],
                                        color_dim_rgb,
                                        text[col_pos[S_COL_TO]],
@@ -3344,7 +3526,7 @@ gboolean defer_change(gpointer data)
                                chg->unset_flags, chg->unset_tmp_flags);
                        break;
                default:
-                       g_warning("shouldn't happen\n");
+                       g_warning("unknown change op");
                }
                g_free(chg);
        }
@@ -3376,14 +3558,18 @@ static int msginfo_mark_as_read_timeout(void *data)
        MarkAsReadData *mdata = (MarkAsReadData *)data;
        if (!mdata)
                return FALSE;
-       
+
+       summary_lock(mdata->summaryview);
        if (mdata->msginfo == summary_get_selected_msg(mdata->summaryview))
                msginfo_mark_as_read(mdata->summaryview, mdata->msginfo,
-                                    mdata->summaryview->selected); 
+                                    mdata->summaryview->selected);
+       procmsg_msginfo_free(mdata->msginfo);
 
-       g_free(mdata);
+       mdata->summaryview->mark_as_read_timeout_tag = 0;
+       summary_unlock(mdata->summaryview);
 
-       return FALSE;   
+       g_free(mdata);
+       return FALSE;
 }
 
 static void summary_display_msg_full(SummaryView *summaryview,
@@ -3395,7 +3581,8 @@ static void summary_display_msg_full(SummaryView *summaryview,
        gint val;
        START_TIMING("");
        if (!new_window) {
-               if (summaryview->displayed == row)
+               if (summaryview->displayed == row &&
+                   messageview_is_visible(summaryview->messageview))
                        return;
                else if (summaryview->messageview)
                        summaryview->messageview->filtered = FALSE;
@@ -3431,23 +3618,22 @@ static void summary_display_msg_full(SummaryView *summaryview,
                        else
                                gtkut_window_popup(summaryview->ext_messageview->window);
                        msgview = summaryview->ext_messageview;
-                       summaryview->last_displayed = summaryview->displayed;
                        summaryview->displayed = row;
                        val = messageview_show(msgview, msginfo, all_headers);
-                       if (GTK_CMCLIST(msgview->mimeview->ctree)->row_list == NULL)
+                       if (mimeview_tree_is_empty(msgview->mimeview))
                                gtk_widget_grab_focus(summaryview->ctree);
                        gtkut_ctree_node_move_if_on_the_edge(ctree, row,
                                GTK_CMCLIST(summaryview->ctree)->focus_row);
                } else {
                        msgview = summaryview->messageview;
-                       summaryview->last_displayed = summaryview->displayed;
                        summaryview->displayed = row;
-                       if (!messageview_is_visible(msgview)) {
+                       if (!messageview_is_visible(msgview) &&
+                           gtk_window_is_active(GTK_WINDOW(summaryview->mainwin->window))) {
                                main_window_toggle_message_view(summaryview->mainwin);
                                GTK_EVENTS_FLUSH();
                        }
                        val = messageview_show(msgview, msginfo, all_headers);
-                       if (GTK_CMCLIST(msgview->mimeview->ctree)->row_list == NULL)
+                       if (mimeview_tree_is_empty(msgview->mimeview))
                                gtk_widget_grab_focus(summaryview->ctree);
                        gtkut_ctree_node_move_if_on_the_edge(ctree, row,
                                GTK_CMCLIST(summaryview->ctree)->focus_row);
@@ -3459,14 +3645,12 @@ static void summary_display_msg_full(SummaryView *summaryview,
                    prefs_common.mark_as_read_delay) {
                        MarkAsReadData *data = g_new0(MarkAsReadData, 1);
                        data->summaryview = summaryview;
-                       data->msginfo = msginfo;
-#if GLIB_CHECK_VERSION(2,14,0)
-                       g_timeout_add_seconds(prefs_common.mark_as_read_delay,
-                               msginfo_mark_as_read_timeout, data);
-#else
-                       g_timeout_add(prefs_common.mark_as_read_delay * 1000,
-                               msginfo_mark_as_read_timeout, data);
-#endif
+                       data->msginfo = procmsg_msginfo_new_ref(msginfo);
+                       if (summaryview->mark_as_read_timeout_tag != 0)
+                               g_source_remove(summaryview->mark_as_read_timeout_tag);
+                       summaryview->mark_as_read_timeout_tag = 
+                               g_timeout_add_seconds(prefs_common.mark_as_read_delay,
+                                       msginfo_mark_as_read_timeout, data);
                } else if (new_window || !prefs_common.mark_as_read_on_new_window) {
                        msginfo_mark_as_read(summaryview, msginfo, row);
                }
@@ -3522,10 +3706,6 @@ void summary_view_source(SummaryView * summaryview)
        msginfo = gtk_cmctree_node_get_row_data(ctree, summaryview->selected);
        source_window_show_msg(srcwin, msginfo);
        source_window_show(srcwin);
-#ifdef MAEMO
-       maemo_window_full_screen_if_needed(GTK_WINDOW(srcwin->window));
-       maemo_connect_key_press_to_mainwindow(GTK_WINDOW(srcwin->window));
-#endif
 }
 
 void summary_reedit(SummaryView *summaryview)
@@ -3604,6 +3784,8 @@ void summary_toggle_view(SummaryView *summaryview)
 {
        if (prefs_common.layout_mode == SMALL_LAYOUT)
                return;
+       if (summary_is_locked(summaryview))
+               return;
        if (!messageview_is_visible(summaryview->messageview) &&
            summaryview->selected && summary_is_list(summaryview))
                summary_display_msg(summaryview,
@@ -3682,6 +3864,9 @@ static void summary_set_row_marks(SummaryView *summaryview, GtkCMCTreeNode *row)
        } else if (MSG_IS_UNREAD(flags)) {
                gtk_cmctree_node_set_pixbuf(ctree, row, col_pos[S_COL_STATUS],
                                          unreadxpm);
+       } else if (MSG_IS_REPLIED(flags) && MSG_IS_FORWARDED(flags)) {
+               gtk_cmctree_node_set_pixbuf(ctree, row, col_pos[S_COL_STATUS],
+                                         repliedandforwardedxpm);
        } else if (MSG_IS_REPLIED(flags)) {
                gtk_cmctree_node_set_pixbuf(ctree, row, col_pos[S_COL_STATUS],
                                          repliedxpm);
@@ -3717,13 +3902,24 @@ static void summary_set_row_marks(SummaryView *summaryview, GtkCMCTreeNode *row)
        } else if (MSG_IS_MOVE(flags)) {
                gtk_cmctree_node_set_pixbuf(ctree, row, col_pos[S_COL_MARK],
                                          movedxpm);
-               if (style)
-                       style = bold_marked_style;
-               else {
-                       style = small_marked_style;
-               }
+               if (!msginfo->to_folder ||
+                   !folder_has_parent_of_type(msginfo->to_folder, F_TRASH)) {
+                       if (style)
+                               style = bold_marked_style;
+                       else {
+                               style = small_marked_style;
+                       }
                        gtk_cmctree_node_set_foreground
                                (ctree, row, &summaryview->color_marked);
+               } else {
+                       if (style)
+                               style = bold_deleted_style;
+                       else {
+                               style = small_deleted_style;
+                       }
+                               gtk_cmctree_node_set_foreground
+                                       (ctree, row, &summaryview->color_dim);
+               }
        } else if (MSG_IS_COPY(flags)) {
                gtk_cmctree_node_set_pixbuf(ctree, row, col_pos[S_COL_MARK],
                                          copiedxpm);
@@ -3801,7 +3997,6 @@ static void summary_mark_row(SummaryView *summaryview, GtkCMCTreeNode *row)
 
 static void summary_lock_row(SummaryView *summaryview, GtkCMCTreeNode *row)
 {
-       gboolean changed = FALSE;
        GtkCMCTree *ctree = GTK_CMCTREE(summaryview->ctree);
        MsgInfo *msginfo;
 
@@ -3811,11 +4006,9 @@ static void summary_lock_row(SummaryView *summaryview, GtkCMCTreeNode *row)
                summaryview->deleted--;
        if (MSG_IS_MOVE(msginfo->flags)) {
                summaryview->moved--;
-               changed = TRUE;
        }
        if (MSG_IS_COPY(msginfo->flags)) {
                summaryview->copied--;
-               changed = TRUE;
        }
        procmsg_msginfo_set_to_folder(msginfo, NULL);
        summary_msginfo_change_flags(msginfo, MSG_LOCKED, 0, MSG_DELETED, 
@@ -3939,7 +4132,7 @@ void summary_mark_all_read(SummaryView *summaryview)
        if (prefs_common.ask_mark_all_read) {
                val = alertpanel_full(_("Mark all as read"),
                        _("Do you really want to mark all mails in this "
-                         "folder as read ?"), GTK_STOCK_NO, GTK_STOCK_YES, NULL,
+                         "folder as read?"), GTK_STOCK_NO, GTK_STOCK_YES, NULL,
                          TRUE, NULL, ALERT_QUESTION, G_ALERTDEFAULT);
 
                if ((val & ~G_ALERTDISABLE) != G_ALERTALTERNATE)
@@ -4199,6 +4392,8 @@ void summary_delete(SummaryView *summaryview)
        if (summary_is_locked(summaryview)) return;
 
        if (!summaryview->folder_item) return;
+       
+       START_LONG_OPERATION(summaryview, FALSE);
 
        if (!summaryview->folder_item->folder->account || summaryview->folder_item->folder->account->imap_use_trash) {
                if (!prefs_common.live_dangerously) {
@@ -4212,7 +4407,10 @@ void summary_delete(SummaryView *summaryview)
                                          buf,
                                          GTK_STOCK_CANCEL, "+"GTK_STOCK_DELETE, NULL);
                        g_free(buf);
-                       if (aval != G_ALERTALTERNATE) return;
+                       if (aval != G_ALERTALTERNATE) {
+                               END_LONG_OPERATION(summaryview);
+                               return;
+                       }
                }
        }
 
@@ -4229,7 +4427,6 @@ void summary_delete(SummaryView *summaryview)
 
        /* next code sets current row focus right. We need to find a row
         * that is not deleted. */
-       START_LONG_OPERATION(summaryview, FALSE);
        folder_item_set_batch(summaryview->folder_item, TRUE);
        for (cur = GTK_CMCLIST(ctree)->selection; cur != NULL && cur->data != NULL; cur = cur->next) {
                sel_last = GTK_CMCTREE_NODE(cur->data);
@@ -4238,10 +4435,15 @@ void summary_delete(SummaryView *summaryview)
        folder_item_set_batch(summaryview->folder_item, FALSE);
        END_LONG_OPERATION(summaryview);
 
-       node = summary_find_next_msg(summaryview, sel_last);
-       if (!node)
+       if (summaryview->sort_type == SORT_ASCENDING) {
+               node = summary_find_next_msg(summaryview, sel_last);
+               if (!node || prefs_common.next_on_delete == FALSE)
+                       node = summary_find_prev_msg(summaryview, sel_last);
+       } else {
                node = summary_find_prev_msg(summaryview, sel_last);
-
+               if (!node || prefs_common.next_on_delete == FALSE)
+                       node = summary_find_next_msg(summaryview, sel_last);
+       }
        summary_select_node(summaryview, node, prefs_common.always_show_msg, TRUE);
        
        if (prefs_common.immediate_exec || folder_has_parent_of_type(item, F_TRASH)) {
@@ -4396,9 +4598,16 @@ void summary_move_selected_to(SummaryView *summaryview, FolderItem *to_folder)
        if (prefs_common.immediate_exec) {
                summary_execute(summaryview);
        } else {
-               GtkCMCTreeNode *node = summary_find_next_msg(summaryview, sel_last);
-               if (!node)
+               GtkCMCTreeNode *node = NULL;
+               if (summaryview->sort_type == SORT_ASCENDING) {
+                       node = summary_find_next_msg(summaryview, sel_last);
+                       if (!node)
+                               node = summary_find_prev_msg(summaryview, sel_last);
+               } else {
                        node = summary_find_prev_msg(summaryview, sel_last);
+                       if (!node)
+                               node = summary_find_next_msg(summaryview, sel_last);
+               }
                summary_select_node(summaryview, node, summaryview->display_msg, TRUE);
                summary_status_show(summaryview);
        }
@@ -4419,8 +4628,7 @@ void summary_move_to(SummaryView *summaryview)
        if (!summaryview->folder_item ||
            FOLDER_TYPE(summaryview->folder_item->folder) == F_NEWS) return;
 
-       to_folder = foldersel_folder_sel(summaryview->folder_item->folder,
-                                        FOLDER_SEL_MOVE, NULL, FALSE);
+       to_folder = foldersel_folder_sel(NULL, FOLDER_SEL_MOVE, NULL, FALSE);
        summary_move_selected_to(summaryview, to_folder);
 }
 
@@ -4500,8 +4708,7 @@ void summary_copy_to(SummaryView *summaryview)
 
        if (!summaryview->folder_item) return;
 
-       to_folder = foldersel_folder_sel(summaryview->folder_item->folder,
-                                        FOLDER_SEL_COPY, NULL, FALSE);
+       to_folder = foldersel_folder_sel(NULL, FOLDER_SEL_COPY, NULL, FALSE);
        summary_copy_selected_to(summaryview, to_folder);
 }
 
@@ -4509,8 +4716,8 @@ void summary_add_address(SummaryView *summaryview)
 {
        MsgInfo *msginfo, *full_msginfo;
        gchar *from;
-       GtkWidget *image = NULL;
        GdkPixbuf *picture = NULL;
+       AvatarRender *avatarr;
 
        msginfo = gtk_cmctree_node_get_row_data(GTK_CMCTREE(summaryview->ctree),
                                              summaryview->selected);
@@ -4522,28 +4729,23 @@ void summary_add_address(SummaryView *summaryview)
        extract_address(from);
        
        full_msginfo = procmsg_msginfo_get_full_info(msginfo);
-       if (full_msginfo &&
-           full_msginfo->extradata &&
-           full_msginfo->extradata->face) {
-               image = face_get_from_header(full_msginfo->extradata->face);
-       } 
-#if HAVE_LIBCOMPFACE
-       else if (full_msginfo &&
-                full_msginfo->extradata &&
-                full_msginfo->extradata->xface) {
-               image = xface_get_from_header(full_msginfo->extradata->xface,
-                               &summaryview->ctree->style->white,
-                               summaryview->mainwin->window->window);  
-       }
-#endif
+
+       avatarr = avatars_avatarrender_new(full_msginfo);
+       hooks_invoke(AVATAR_IMAGE_RENDER_HOOKLIST, avatarr);
+
        procmsg_msginfo_free(full_msginfo);
-       if (image)
-               picture = gtk_image_get_pixbuf(GTK_IMAGE(image));
 
-       addressbook_add_contact(msginfo->fromname, from, NULL, picture);
+       if (avatarr->image)
+               picture = gtk_image_get_pixbuf(GTK_IMAGE(avatarr->image));
 
-       if (image)
-               gtk_widget_destroy(image);
+#ifndef USE_NEW_ADDRBOOK
+       addressbook_add_contact(msginfo->fromname, from, NULL, picture);
+#else
+       if (addressadd_selection(msginfo->fromname, from, NULL, picture)) {
+               debug_print( "addressbook_add_contact - added\n" );
+       }
+#endif
+       avatars_avatarrender_free(avatarr);
 }
 
 void summary_select_all(SummaryView *summaryview)
@@ -4564,7 +4766,8 @@ void summary_unselect_all(SummaryView *summaryview)
        summary_status_show(summaryview);
 }
 
-void summary_select_thread(SummaryView *summaryview, gboolean delete_thread)
+void summary_select_thread(SummaryView *summaryview, gboolean delete_thread,
+                          gboolean trash_thread)
 {
        GtkCMCTree *ctree = GTK_CMCTREE(summaryview->ctree);
        GtkCMCTreeNode *node = NULL;
@@ -4590,12 +4793,14 @@ void summary_select_thread(SummaryView *summaryview, gboolean delete_thread)
        g_list_free(copy);
        END_LONG_OPERATION(summaryview);
 
-       if (delete_thread) {
+       if (trash_thread) {
                if (FOLDER_TYPE(summaryview->folder_item->folder) == F_NEWS)
                        summary_delete(summaryview);
                else
                        summary_delete_trash(summaryview);
-       }
+       } else if (delete_thread)
+               summary_delete(summaryview);
+
        summary_status_show(summaryview);
 }
 
@@ -4617,6 +4822,9 @@ void summary_save_as(SummaryView *summaryview)
                Xstrdup_a(filename, msginfo->subject, return);
                subst_for_filename(filename);
        }
+
+       manage_window_focus_in(summaryview->window, NULL, NULL);
+
        if (filename && !g_utf8_validate(filename, -1, NULL)) {
                gchar *oldstr = filename;
                filename = conv_codeset_strdup(filename,
@@ -4675,12 +4883,6 @@ void summary_save_as(SummaryView *summaryview)
 void summary_print(SummaryView *summaryview)
 {
        GtkCMCList *clist = GTK_CMCLIST(summaryview->ctree);
-#if !defined(USE_GNOMEPRINT) && !GTK_CHECK_VERSION(2,10,0)
-       GtkCMCTree *ctree = GTK_CMCTREE(summaryview->ctree);
-       MsgInfo *msginfo;
-       gchar *cmdline = NULL;
-       gchar *p;
-#endif
        GList *cur;
        gchar *msg = g_strdup_printf(_("You are about to print %d "
                                       "messages, one by one. Do you "
@@ -4695,30 +4897,6 @@ void summary_print(SummaryView *summaryview)
        g_free(msg);
 
        if (clist->selection == NULL) return;
-#if !defined(USE_GNOMEPRINT) && !GTK_CHECK_VERSION(2,10,0)
-       cmdline = input_dialog(_("Print"),
-                              _("Enter the print command-line:\n"
-                                "('%s' will be replaced with file name)"),
-                              prefs_common.print_cmd);
-       if (!cmdline) return;
-       if (!(p = strchr(cmdline, '%')) || *(p + 1) != 's' ||
-           strchr(p + 2, '%')) {
-               alertpanel_error(_("Print command-line is invalid:\n'%s'"),
-                                cmdline);
-               g_free(cmdline);
-               return;
-       }
-       for (cur = clist->selection; 
-            cur != NULL && cur->data != NULL; 
-            cur = cur->next) {
-               msginfo = gtk_cmctree_node_get_row_data
-                       (ctree, GTK_CMCTREE_NODE(cur->data));
-               if (msginfo) 
-                       procmsg_print_message(msginfo, cmdline);
-       }
-
-       g_free(cmdline);
-#else
        for (cur = clist->selection; 
             cur != NULL && cur->data != NULL; 
             cur = cur->next) {
@@ -4736,7 +4914,6 @@ void summary_print(SummaryView *summaryview)
                messageview_print(msginfo, summaryview->messageview->all_headers,
                        sel_start, sel_end, partnum);
        }
-#endif
 }
 
 gboolean summary_execute(SummaryView *summaryview)
@@ -4771,6 +4948,7 @@ gboolean summary_execute(SummaryView *summaryview)
 
                if (node == summaryview->displayed) {
                        messageview_clear(summaryview->messageview);
+                       summary_cancel_mark_read_timeout(summaryview);
                        summaryview->displayed = NULL;
                }
                if (GTK_CMCTREE_ROW(node)->children != NULL) {
@@ -4791,10 +4969,15 @@ gboolean summary_execute(SummaryView *summaryview)
                if (!new_selected &&
                    gtkut_ctree_node_is_selected(ctree, node)) {
                        summary_unselect_all(summaryview);
-                       new_selected = summary_find_next_msg(summaryview, node);
-                       if (!new_selected)
-                               new_selected = summary_find_prev_msg
-                                       (summaryview, node);
+                       if (summaryview->sort_type == SORT_ASCENDING) {
+                               new_selected = summary_find_next_msg(summaryview, node);
+                               if (!new_selected)
+                                       new_selected = summary_find_prev_msg(summaryview, node);
+                       } else {
+                               new_selected = summary_find_prev_msg(summaryview, node);
+                               if (!new_selected)
+                                       new_selected = summary_find_next_msg(summaryview, node);
+                       }
                }
 
                gtk_sctree_remove_node((GtkSCTree *)ctree, node);
@@ -4871,6 +5054,7 @@ gboolean summary_expunge(SummaryView *summaryview)
 
                if (node == summaryview->displayed) {
                        messageview_clear(summaryview->messageview);
+                       summary_cancel_mark_read_timeout(summaryview);
                        summaryview->displayed = NULL;
                }
                if (GTK_CMCTREE_ROW(node)->children != NULL) {
@@ -5303,6 +5487,8 @@ static void summary_unthread_for_exec_func(GtkCMCTree *ctree, GtkCMCTreeNode *no
        if (node == summaryview->displayed)
                summaryview->displayed = NULL;
 
+       summary_cancel_mark_read_timeout(summaryview);
+       
        for (top_parent = node;
             GTK_CMCTREE_ROW(top_parent)->parent != NULL;
             top_parent = GTK_CMCTREE_ROW(top_parent)->parent)
@@ -5772,7 +5958,7 @@ static void summary_colorlabel_menu_item_activate_item_cb(GtkMenuItem *menu_item
        GtkMenuShell *menu;
        GtkCheckMenuItem **items;
        gint n;
-       GList *cur, *sel;
+       GList *children, *cur, *sel;
 
        summaryview = (SummaryView *)data;
        cm_return_if_fail(summaryview != NULL);
@@ -5792,7 +5978,8 @@ static void summary_colorlabel_menu_item_activate_item_cb(GtkMenuItem *menu_item
                          GINT_TO_POINTER(1));
 
        /* clear items. get item pointers. */
-       for (n = 0, cur = menu->children; cur != NULL && cur->data != NULL; cur = cur->next) {
+       children = gtk_container_get_children(GTK_CONTAINER(menu));
+       for (n = 0, cur = children; cur != NULL && cur->data != NULL; cur = cur->next) {
                if (GTK_IS_CHECK_MENU_ITEM(cur->data)) {
                        gtk_check_menu_item_set_active
                                (GTK_CHECK_MENU_ITEM(cur->data), FALSE);
@@ -5801,6 +5988,8 @@ static void summary_colorlabel_menu_item_activate_item_cb(GtkMenuItem *menu_item
                }
        }
 
+       g_list_free(children);
+
        if (n == (N_COLOR_LABELS + 1)) {
                /* iterate all messages and set the state of the appropriate
                 * items */
@@ -5813,13 +6002,13 @@ static void summary_colorlabel_menu_item_activate_item_cb(GtkMenuItem *menu_item
                                 GTK_CMCTREE_NODE(sel->data));
                        if (msginfo) {
                                clabel = MSG_GET_COLORLABEL_VALUE(msginfo->flags);
-                               if (!items[clabel]->active)
+                               if (!gtk_check_menu_item_get_active(items[clabel]))
                                        gtk_check_menu_item_set_active
                                                (items[clabel], TRUE);
                        }
                }
        } else
-               g_warning("invalid number of color elements (%d)\n", n);
+               g_warning("invalid number of color elements (%d)", n);
 
        /* reset "dont_toggle" state */
        g_object_set_data(G_OBJECT(menu), "dont_toggle",
@@ -5861,7 +6050,7 @@ static void summary_colorlabel_menu_create(SummaryView *summaryview, gboolean re
        accel_path = g_strdup_printf("<ClawsColorLabels>/None");
        gtk_menu_item_set_accel_path(GTK_MENU_ITEM(item), accel_path);
        g_free(accel_path);
-       gtk_accel_map_add_entry("<ClawsColorLabels>/None", GDK_0, GDK_CONTROL_MASK);
+       gtk_accel_map_add_entry("<ClawsColorLabels>/None", GDK_KEY_0, GDK_CONTROL_MASK);
 
        item = gtk_menu_item_new();
        gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
@@ -5881,7 +6070,7 @@ static void summary_colorlabel_menu_create(SummaryView *summaryview, gboolean re
                accel_path = g_strdup_printf("<ClawsColorLabels>/%d", i+1);
                gtk_menu_item_set_accel_path(GTK_MENU_ITEM(item), accel_path);
                if (i < 9)
-                       gtk_accel_map_add_entry(accel_path, GDK_1+i, GDK_CONTROL_MASK);
+                       gtk_accel_map_add_entry(accel_path, GDK_KEY_1+i, GDK_CONTROL_MASK);
                g_free(accel_path);
                g_signal_connect (gtk_ui_manager_get_accel_group(mainwindow_get_mainwindow()->ui_manager), 
                        "accel-changed", G_CALLBACK (mainwin_accel_changed_cb), item);
@@ -5896,7 +6085,7 @@ static void summary_tags_menu_item_activate_item_cb(GtkMenuItem *menu_item,
                                                          gpointer data)
 {
        GtkMenuShell *menu;
-       GList *cur;
+       GList *children, *cur;
        GList *sel;
        GHashTable *menu_table = g_hash_table_new_full(
                                        g_direct_hash,
@@ -5922,7 +6111,8 @@ static void summary_tags_menu_item_activate_item_cb(GtkMenuItem *menu_item,
                          GINT_TO_POINTER(1));
 
        /* clear items. get item pointers. */
-       for (cur = menu->children; cur != NULL && cur->data != NULL; cur = cur->next) {
+       children = gtk_container_get_children(GTK_CONTAINER(menu));
+       for (cur = children; cur != NULL && cur->data != NULL; cur = cur->next) {
                if (GTK_IS_CHECK_MENU_ITEM(cur->data)) {
                        gint id = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(cur->data),
                                "tag_id"));
@@ -5934,13 +6124,14 @@ static void summary_tags_menu_item_activate_item_cb(GtkMenuItem *menu_item,
                }
        }
 
+       g_list_free(children);
+
        /* iterate all messages and set the state of the appropriate
         * items */
        sel_len = 0;
        for (; sel != NULL; sel = sel->next) {
                MsgInfo *msginfo;
                GSList *tags = NULL;
-               gint id;
                GtkCheckMenuItem *item;
                msginfo = gtk_cmctree_node_get_row_data
                        (GTK_CMCTREE(summaryview->ctree),
@@ -5953,9 +6144,8 @@ static void summary_tags_menu_item_activate_item_cb(GtkMenuItem *menu_item,
 
                        for (; tags; tags = tags->next) {
                                gint num_checked = GPOINTER_TO_INT(g_hash_table_lookup(menu_allsel_table, tags->data));
-                               id = GPOINTER_TO_INT(tags->data);
                                item = g_hash_table_lookup(menu_table, GINT_TO_POINTER(tags->data));
-                               if (item && !item->active) {
+                               if (item && !gtk_check_menu_item_get_active(item)) {
                                        gtk_check_menu_item_set_active
                                                (item, TRUE);
                                }
@@ -5965,7 +6155,8 @@ static void summary_tags_menu_item_activate_item_cb(GtkMenuItem *menu_item,
                }
        }
 
-       for (cur = menu->children; cur != NULL && cur->data != NULL; cur = cur->next) {
+       children = gtk_container_get_children(GTK_CONTAINER(menu));
+       for (cur = children; cur != NULL && cur->data != NULL; cur = cur->next) {
                if (GTK_IS_CHECK_MENU_ITEM(cur->data)) {
                        gint id = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(cur->data),
                                "tag_id"));
@@ -5976,6 +6167,7 @@ static void summary_tags_menu_item_activate_item_cb(GtkMenuItem *menu_item,
                                gtk_check_menu_item_set_inconsistent(GTK_CHECK_MENU_ITEM(cur->data), FALSE);
                }
        }
+       g_list_free(children);
        g_hash_table_destroy(menu_table);
        g_hash_table_destroy(menu_allsel_table);
        /* reset "dont_toggle" state */
@@ -5985,13 +6177,11 @@ static void summary_tags_menu_item_activate_item_cb(GtkMenuItem *menu_item,
 
 void summaryview_destroy(SummaryView *summaryview)
 {
-#ifndef G_OS_WIN32
        if(summaryview->simplify_subject_preg) {
                regfree(summaryview->simplify_subject_preg);
                g_free(summaryview->simplify_subject_preg);
                summaryview->simplify_subject_preg = NULL;
        }
-#endif
 }
 static void summary_tags_menu_item_apply_tags_activate_cb(GtkWidget *widget,
                                                     gpointer data)
@@ -6020,7 +6210,7 @@ static gint summary_tag_cmp_list(gconstpointer a, gconstpointer b)
                return tag_b == NULL ? 0:1;
        
        if (tag_b == NULL)
-               return tag_a == NULL ? 0:1;
+               return 1;
 
        return g_utf8_collate(tag_a, tag_b);
 }
@@ -6105,7 +6295,7 @@ static gboolean summary_popup_menu(GtkWidget *widget, gpointer data)
        return TRUE;
 }
 
-#if GTK_CHECK_VERSION(2,12,0) && !GENERIC_UMPC
+#if !GENERIC_UMPC
 static gchar *summaryview_get_tooltip_text(SummaryView *summaryview, MsgInfo *info, gint column)
 {
        MsgFlags flags;
@@ -6126,6 +6316,8 @@ static gchar *summaryview_get_tooltip_text(SummaryView *summaryview, MsgInfo *in
                                return _("New");
                        } else if (MSG_IS_UNREAD(flags)) {
                                return _("Unread");
+                       } else if (MSG_IS_REPLIED(flags) && MSG_IS_FORWARDED(flags)) {
+                               return _("Replied but also forwarded - click to see reply");
                        } else if (MSG_IS_REPLIED(flags)) {
                                return _("Replied - click to see reply");
                        } else if (MSG_IS_FORWARDED(flags)) {
@@ -6185,8 +6377,8 @@ static gboolean tooltip_cb (GtkWidget  *widget,
        gchar *formatted = NULL;
        MsgInfo *info = NULL;
        GdkRectangle rect;
-       gboolean vert = (prefs_common.layout_mode == VERTICAL_LAYOUT);
-
+       gboolean vert_layout = (prefs_common.layout_mode == VERTICAL_LAYOUT);
+       gboolean small_layout = (prefs_common.layout_mode == SMALL_LAYOUT);
        if (!prefs_common.show_tooltips)
                return FALSE;
 
@@ -6224,10 +6416,10 @@ static gboolean tooltip_cb (GtkWidget  *widget,
        formatted = g_strdup(text);
        g_strstrip(formatted);
 
-       if (!vert)      
-               gtk_tooltip_set_text (tooltip, formatted);
-       else if (prefs_common.two_line_vert)
+       if ((vert_layout || small_layout) && prefs_common.two_line_vert)
                gtk_tooltip_set_markup (tooltip, formatted);
+       else 
+                       gtk_tooltip_set_text (tooltip, formatted);
        g_free(formatted);
        
        rect.x = x - 2;
@@ -6247,8 +6439,8 @@ static GtkWidget *summary_ctree_create(SummaryView *summaryview)
        gchar *titles[N_SUMMARY_COLS];
        SummaryColumnType type;
        gint pos;
-       gboolean vert = (prefs_common.layout_mode == VERTICAL_LAYOUT);
-
+       gboolean vert_layout = (prefs_common.layout_mode == VERTICAL_LAYOUT);
+       gboolean small_layout = (prefs_common.layout_mode == SMALL_LAYOUT);
        memset(titles, 0, sizeof(titles));
 
        col_state = prefs_summary_column_get_config();
@@ -6263,14 +6455,10 @@ static GtkWidget *summary_ctree_create(SummaryView *summaryview)
        ctree = gtk_sctree_new_with_titles
                (N_SUMMARY_COLS, col_pos[S_COL_SUBJECT], titles);
 
-       /* get normal row height */
-       gtk_cmclist_set_row_height(GTK_CMCLIST(ctree), 0);
-       normal_row_height = GTK_CMCLIST(ctree)->row_height;
-
        if (prefs_common.show_col_headers == FALSE)
                gtk_cmclist_column_titles_hide(GTK_CMCLIST(ctree));
 
-       gtk_cmclist_set_selection_mode(GTK_CMCLIST(ctree), GTK_SELECTION_EXTENDED);
+       gtk_cmclist_set_selection_mode(GTK_CMCLIST(ctree), GTK_SELECTION_MULTIPLE);
        gtk_cmclist_set_column_justification(GTK_CMCLIST(ctree), col_pos[S_COL_MARK],
                                           GTK_JUSTIFY_CENTER);
        gtk_cmclist_set_column_justification(GTK_CMCLIST(ctree), col_pos[S_COL_STATUS],
@@ -6310,15 +6498,9 @@ static GtkWidget *summary_ctree_create(SummaryView *summaryview)
        gtk_cmclist_set_column_width(GTK_CMCLIST(ctree), col_pos[S_COL_TAGS],
                                   prefs_common.summary_col_size[S_COL_TAGS]);
 
-       if (prefs_common.enable_dotted_lines) {
-               gtk_cmctree_set_line_style(GTK_CMCTREE(ctree), GTK_CMCTREE_LINES_DOTTED);
-               gtk_cmctree_set_expander_style(GTK_CMCTREE(ctree),
-                                    GTK_CMCTREE_EXPANDER_SQUARE);
-       } else {
-               gtk_cmctree_set_line_style(GTK_CMCTREE(ctree), GTK_CMCTREE_LINES_NONE);
-               gtk_cmctree_set_expander_style(GTK_CMCTREE(ctree),
-                                    GTK_CMCTREE_EXPANDER_TRIANGLE);
-       }
+       gtk_cmctree_set_line_style(GTK_CMCTREE(ctree), GTK_CMCTREE_LINES_NONE);
+       gtk_cmctree_set_expander_style(GTK_CMCTREE(ctree),
+                            GTK_CMCTREE_EXPANDER_TRIANGLE);
 
        gtk_sctree_set_stripes(GTK_SCTREE(ctree), prefs_common.use_stripes_in_summaries);
 
@@ -6326,11 +6508,11 @@ static GtkWidget *summary_ctree_create(SummaryView *summaryview)
        g_object_set_data(G_OBJECT(ctree), "summaryview", (gpointer)summaryview); 
 
        for (pos = 0; pos < N_SUMMARY_COLS; pos++) {
-               GTK_WIDGET_UNSET_FLAGS(GTK_CMCLIST(ctree)->column[pos].button,
-                                      GTK_CAN_FOCUS);
+               gtkut_widget_set_can_focus(GTK_CMCLIST(ctree)->column[pos].button,
+                                      FALSE);
                if (((pos == summaryview->col_pos[S_COL_FROM] && !FOLDER_SHOWS_TO_HDR(summaryview->folder_item)) ||
                     (pos == summaryview->col_pos[S_COL_TO] && FOLDER_SHOWS_TO_HDR(summaryview->folder_item)) ||
-                    pos == summaryview->col_pos[S_COL_DATE]) && vert &&
+                    pos == summaryview->col_pos[S_COL_DATE]) && (vert_layout || small_layout) &&
                            prefs_common.two_line_vert)
                        gtk_cmclist_set_column_visibility
                                (GTK_CMCLIST(ctree), pos, FALSE);
@@ -6339,7 +6521,7 @@ static GtkWidget *summary_ctree_create(SummaryView *summaryview)
                                (GTK_CMCLIST(ctree), pos, col_state[pos].visible);
        }
        if (prefs_common.two_line_vert)
-               gtk_sctree_set_use_markup(GTK_SCTREE(ctree), summaryview->col_pos[S_COL_SUBJECT], vert);
+               gtk_sctree_set_use_markup(GTK_SCTREE(ctree), summaryview->col_pos[S_COL_SUBJECT], vert_layout||small_layout);
 
        /* connect signal to the buttons for sorting */
 #define CLIST_BUTTON_SIGNAL_CONNECT(col, func) \
@@ -6371,15 +6553,8 @@ static GtkWidget *summary_ctree_create(SummaryView *summaryview)
        g_signal_connect(G_OBJECT(ctree), "button_press_event",
                         G_CALLBACK(summary_button_pressed),
                         summaryview);
-#ifndef MAEMO
        g_signal_connect(G_OBJECT(ctree), "popup-menu",
                         G_CALLBACK(summary_popup_menu), summaryview);
-#else
-       gtk_widget_tap_and_hold_setup(GTK_WIDGET(ctree), NULL, NULL,
-                       GTK_TAP_AND_HOLD_NONE | GTK_TAP_AND_HOLD_NO_INTERNALS);
-       g_signal_connect(G_OBJECT(ctree), "tap-and-hold",
-                        G_CALLBACK(summary_popup_menu), summaryview);
-#endif
        g_signal_connect(G_OBJECT(ctree), "button_release_event",
                         G_CALLBACK(summary_button_released),
                         summaryview);
@@ -6408,7 +6583,7 @@ static GtkWidget *summary_ctree_create(SummaryView *summaryview)
                         summaryview);
 
        gtk_drag_dest_set(ctree, GTK_DEST_DEFAULT_ALL & ~GTK_DEST_DEFAULT_HIGHLIGHT,
-                         summary_drag_types, 2,
+                         summary_drag_types, 3,
                          GDK_ACTION_MOVE | GDK_ACTION_COPY | GDK_ACTION_DEFAULT);
 
        g_signal_connect(G_OBJECT(ctree), "drag_data_received",
@@ -6419,7 +6594,7 @@ static GtkWidget *summary_ctree_create(SummaryView *summaryview)
                         G_CALLBACK(summary_drag_motion_cb),
                         summaryview);
 
-#if GTK_CHECK_VERSION(2,12,0) && !GENERIC_UMPC
+#if !GENERIC_UMPC
        g_object_set (G_OBJECT(ctree), "has-tooltip", TRUE, NULL);
        g_signal_connect(G_OBJECT(ctree), "query-tooltip", 
                         G_CALLBACK(tooltip_cb),
@@ -6457,17 +6632,18 @@ void summary_set_column_order(SummaryView *summaryview)
 
        summaryview->selected = summary_find_msg_by_msgnum(summaryview, selected_msgnum);
        summaryview->displayed = summary_find_msg_by_msgnum(summaryview, displayed_msgnum);
-       summaryview->last_displayed = summaryview->displayed;
        if (!summaryview->displayed)
                messageview_clear(summaryview->messageview);
        else
                summary_redisplay_msg(summaryview);
 
-       if (prefs_common.layout_mode == VERTICAL_LAYOUT &&
+       /* get normal row height */
+       gtk_cmclist_set_row_height(GTK_CMCLIST(ctree), 0);
+       normal_row_height = GTK_CMCLIST(ctree)->row_height;             
+               
+       if ((prefs_common.layout_mode == SMALL_LAYOUT || prefs_common.layout_mode == VERTICAL_LAYOUT) &&
            prefs_common.two_line_vert) {
                gtk_cmclist_set_row_height(GTK_CMCLIST(summaryview->ctree), 2*normal_row_height + 2);           
-       } else {
-               gtk_cmclist_set_row_height(GTK_CMCLIST(summaryview->ctree), 0);         
        }
 }
 
@@ -6505,11 +6681,8 @@ static gboolean summary_button_pressed(GtkWidget *ctree, GdkEventButton *event,
        if (!event) return FALSE;
 
        if (event->button == 3) {
-               summaryview->display_msg = messageview_is_visible(summaryview->messageview);
                /* right clicked */
                summary_set_menu_sensitive(summaryview);
-               cm_menu_set_sensitive_full(summaryview->mainwin->ui_manager, "Menus/SummaryViewPopup/Trash", 
-                       !folder_has_parent_of_type(summaryview->folder_item, F_TRASH) && summaryview->selected);
                gtk_menu_popup(GTK_MENU(summaryview->popupmenu), NULL, NULL,
                               NULL, NULL, event->button, event->time);
        } else if (event->button == 2) {
@@ -6542,15 +6715,19 @@ gboolean summary_pass_key_press_event(SummaryView *summaryview, GdkEventKey *eve
 #define BREAK_ON_MODIFIER_KEY() \
        if ((event->state & (GDK_MOD1_MASK|GDK_CONTROL_MASK)) != 0) break
 
+/* Copied from gtkcmclist.c, if it changes there, it has to change
+ * here as well. This is an ugly hack, there must be a better way to
+ * find out how much to move for page up/down. */
+#define CELL_SPACING 1
 static gboolean summary_key_pressed(GtkWidget *widget, GdkEventKey *event,
                                    SummaryView *summaryview)
 {
        GtkCMCTree *ctree = GTK_CMCTREE(widget);
        GtkCMCTreeNode *node;
        MessageView *messageview;
-       TextView *textview;
        GtkAdjustment *adj;
        gboolean mod_pressed;
+       gfloat row_align = 0;
 
        if (!event) 
                return TRUE;
@@ -6559,7 +6736,6 @@ static gboolean summary_key_pressed(GtkWidget *widget, GdkEventKey *event,
                return FALSE;
 
        messageview = summaryview->messageview;
-       textview = messageview->mimeview->textview;
 
        mod_pressed =
                ((event->state & (GDK_SHIFT_MASK|GDK_MOD1_MASK)) != 0);
@@ -6567,7 +6743,7 @@ static gboolean summary_key_pressed(GtkWidget *widget, GdkEventKey *event,
        if (summaryview->selected) {
                gboolean handled = FALSE;
                switch (event->keyval) {
-               case GDK_space:         /* Page down or go to the next */
+               case GDK_KEY_space:             /* Page down or go to the next */
                        handled = TRUE;
                        if (event->state & GDK_CONTROL_MASK) {
                                handled = FALSE;
@@ -6590,12 +6766,12 @@ static gboolean summary_key_pressed(GtkWidget *widget, GdkEventKey *event,
                                }                               
                        }
                        break;
-               case GDK_BackSpace:     /* Page up */
+               case GDK_KEY_BackSpace: /* Page up */
                        handled = TRUE;
                        mimeview_scroll_page(messageview->mimeview, TRUE);
                        break;
-               case GDK_Return:        /* Scroll up/down one line */
-               case GDK_KP_Enter:
+               case GDK_KEY_Return:    /* Scroll up/down one line */
+               case GDK_KEY_KP_Enter:
                        handled = TRUE;
                        if (summaryview->displayed != summaryview->selected) {
 #ifndef GENERIC_UMPC
@@ -6617,31 +6793,66 @@ static gboolean summary_key_pressed(GtkWidget *widget, GdkEventKey *event,
                return TRUE;
 
        switch (event->keyval) {
-       case GDK_Left:          /* Move focus */
+       case GDK_KEY_Left:              /* Move focus */
                adj = gtk_scrolled_window_get_hadjustment
                        (GTK_SCROLLED_WINDOW(summaryview->scrolledwin));
-               if (adj->lower != adj->value)
+               if (gtk_adjustment_get_lower(adj) != gtk_adjustment_get_value(adj))
                        break;
                /* FALLTHROUGH */       
-       case GDK_Escape:
+       case GDK_KEY_Escape:
                gtk_widget_grab_focus(summaryview->folderview->ctree);
                mainwindow_exit_folder(summaryview->mainwin);
                return TRUE;
-       case GDK_Home:
-       case GDK_End:
+       case GDK_KEY_Home: case GDK_KEY_KP_Home:
+       case GDK_KEY_End: case GDK_KEY_KP_End:
+       case GDK_KEY_Up: case GDK_KEY_KP_Up:
+       case GDK_KEY_Down: case GDK_KEY_KP_Down:
+       case GDK_KEY_Page_Up: case GDK_KEY_KP_Page_Up:
+       case GDK_KEY_Page_Down: case GDK_KEY_KP_Page_Down:
                if ((node = summaryview->selected) != NULL) {
                        GtkCMCTreeNode *next = NULL;
-                       next = (event->keyval == GDK_Home)
-                                       ? gtk_cmctree_node_nth(ctree, 0)
-                                       : gtk_cmctree_node_nth(ctree, 
-                                               g_list_length(GTK_CMCLIST(ctree)->row_list)-1);
+                       switch (event->keyval) {
+                               case GDK_KEY_Home: case GDK_KEY_KP_Home:
+                                       next = gtk_cmctree_node_nth(ctree, 0);
+                                       break;
+                               case GDK_KEY_End: case GDK_KEY_KP_End:
+                                       next = gtk_cmctree_node_nth(ctree,
+                                                       g_list_length(GTK_CMCLIST(ctree)->row_list)-1);
+                                       row_align = 1;
+                                       break;
+                               case GDK_KEY_Up: case GDK_KEY_KP_Up:
+                                       next = gtk_cmctree_node_nth(ctree,
+                                                       MAX(0, GTK_CMCLIST(ctree)->focus_row - 1));
+                                       break;
+                               case GDK_KEY_Down: case GDK_KEY_KP_Down:
+                                       next = gtk_cmctree_node_nth(ctree,
+                                                       MIN(GTK_CMCLIST(ctree)->focus_row + 1, GTK_CMCLIST(ctree)->rows));
+                                       row_align = 1;
+                                       break;
+                               case GDK_KEY_Page_Up: case GDK_KEY_KP_Page_Up:
+                                       next = gtk_cmctree_node_nth(ctree,
+                                                       MAX(0, GTK_CMCLIST(ctree)->focus_row -
+                                                               (2 * GTK_CMCLIST(ctree)->clist_window_height -
+                                                                GTK_CMCLIST(ctree)->row_height - CELL_SPACING) /
+                                                               (2 * (GTK_CMCLIST(ctree)->row_height + CELL_SPACING))));
+                                       break;
+                               case GDK_KEY_Page_Down: case GDK_KEY_KP_Page_Down:
+                                       next = gtk_cmctree_node_nth(ctree,
+                                                       MIN(GTK_CMCLIST(ctree)->rows - 1, GTK_CMCLIST(ctree)->focus_row +
+                                                               (2 * GTK_CMCLIST(ctree)->clist_window_height -
+                                                                GTK_CMCLIST(ctree)->row_height - CELL_SPACING) /
+                                                               (2 * (GTK_CMCLIST(ctree)->row_height + CELL_SPACING))));
+                                       row_align = 1;
+                                       break;
+                       }
+
                        if (next) {
                                gtk_sctree_select_with_state
                                        (GTK_SCTREE(ctree), next, (event->state & ~GDK_CONTROL_MASK) );
 
                                /* Deprecated - what are the non-deprecated equivalents? */
                                if (gtk_cmctree_node_is_visible(GTK_CMCTREE(ctree), next) != GTK_VISIBILITY_FULL)
-                                       gtk_cmctree_node_moveto(GTK_CMCTREE(ctree), next, 0, 0, 0);
+                                       gtk_cmctree_node_moveto(GTK_CMCTREE(ctree), next, 0, row_align, 0);
                                summaryview->selected = next;
                        }
                }
@@ -6659,34 +6870,26 @@ static gboolean summary_key_pressed(GtkWidget *widget, GdkEventKey *event,
        }
 
        switch (event->keyval) {
-       case GDK_Delete:
+       case GDK_KEY_Delete:
                BREAK_ON_MODIFIER_KEY();
                summary_delete_trash(summaryview);
                break;
-       case GDK_y:
-       case GDK_t:
-       case GDK_l:
-       case GDK_o:
-       case GDK_c:
-       case GDK_a:
-               if ((event->state & (GDK_MOD1_MASK|GDK_CONTROL_MASK)) == 0) {
-                       g_signal_stop_emission_by_name(G_OBJECT(widget), 
-                                       "key_press_event");
-                       mimeview_pass_key_press_event(messageview->mimeview,
-                                                     event);
-                       break;
-               }
        default:
                break;
        }
        return FALSE;
 }
+#undef CELL_SPACING
 
 static void quicksearch_execute_cb(QuickSearch *quicksearch, gpointer data)
 {
        SummaryView *summaryview = data;
 
-       summary_show(summaryview, summaryview->folder_item);
+       summaryview_reset_recursive_folder_match(summaryview);
+       if (summary_show(summaryview, summaryview->folder_item))
+               summaryview_quicksearch_recurse(summaryview);
+       else
+               summaryview_reset_recursive_folder_match(summaryview);
 }
 
 static void tog_searchbar_cb(GtkWidget *w, gpointer data)
@@ -6761,6 +6964,8 @@ static void summary_unselected(GtkCMCTree *ctree, GtkCMCTreeNode *row,
 static void summary_selected(GtkCMCTree *ctree, GtkCMCTreeNode *row,
                             gint column, SummaryView *summaryview)
 {
+       const GList *list, *cur;
+       MessageView *msgview;
        MsgInfo *msginfo;
        gboolean marked_unread = FALSE;
 
@@ -6852,6 +7057,17 @@ static void summary_selected(GtkCMCTree *ctree, GtkCMCTreeNode *row,
                break;
        }
 
+       list = messageview_get_msgview_list();
+       for (cur = list; cur != NULL; cur = cur->next) {
+               msgview = (MessageView *) cur->data;
+               
+               if (msgview->new_window && msgview->update_needed) {
+                       MsgInfo *new_msginfo = summary_get_selected_msg(summaryview);
+                       messageview_show(msgview, new_msginfo, msgview->all_headers);
+                       msgview->update_needed = FALSE;         
+               }
+       }
+
        if (summaryview->display_msg ||
            (prefs_common.always_show_msg &&
             messageview_is_visible(summaryview->messageview))) {
@@ -6964,7 +7180,10 @@ static void summary_size_clicked(GtkWidget *button, SummaryView *summaryview)
 
 static void summary_date_clicked(GtkWidget *button, SummaryView *summaryview)
 {
-       summary_sort_by_column_click(summaryview, SORT_BY_DATE);
+       if (summaryview->sort_key == SORT_BY_THREAD_DATE)
+               summary_sort_by_column_click(summaryview, SORT_BY_THREAD_DATE);
+       else
+               summary_sort_by_column_click(summaryview, SORT_BY_DATE);
 }
 
 static void summary_from_clicked(GtkWidget *button, SummaryView *summaryview)
@@ -7022,7 +7241,7 @@ static void summary_start_drag(GtkWidget *widget, gint button, GdkEvent *event,
                                 GDK_ACTION_MOVE|GDK_ACTION_COPY|GDK_ACTION_DEFAULT, button, event);
        gtk_drag_set_icon_default(context);
        if (prefs_common.layout_mode == SMALL_LAYOUT) {
-               GtkWidget *paned = GTK_WIDGET_PTR(summaryview)->parent;
+               GtkWidget *paned = gtk_widget_get_parent(GTK_WIDGET_PTR(summaryview));
                if (paned && GTK_IS_PANED(paned)) {
                        mainwindow_reset_paned(GTK_PANED(paned));
                }
@@ -7099,17 +7318,50 @@ static void summary_drag_data_get(GtkWidget        *widget,
 
                if (mail_list != NULL) {
                        gtk_selection_data_set(selection_data,
-                                              selection_data->target, 8,
+                                              gtk_selection_data_get_target(selection_data), 8,
                                               mail_list, strlen(mail_list));
                        g_free(mail_list);
                } 
        } else if (info == TARGET_DUMMY) {
                if (GTK_CMCLIST(summaryview->ctree)->selection)
                        gtk_selection_data_set(selection_data,
-                                              selection_data->target, 8,
+                                              gtk_selection_data_get_target(selection_data), 8,
                                               "Dummy-Summaryview", 
                                               strlen("Dummy-Summaryview")+1);
-       }
+       } else if (info == TARGET_MAIL_CM_PATH_LIST) {
+               /* content: folder_item_identifier\nmsgid1\nmsgid2\nmsgid3 */
+
+               GtkCMCTree *ctree = GTK_CMCTREE(summaryview->ctree);
+               GList *cur;
+               MsgInfo *msginfo;
+               gchar *path_list = NULL;
+
+               /* identifier */
+               if(GTK_CMCLIST(ctree)->selection != NULL) {
+                       msginfo = gtk_cmctree_node_get_row_data(ctree, GTK_CMCTREE_NODE(GTK_CMCLIST(ctree)->selection->data));
+            if(msginfo && msginfo->folder)
+              path_list = folder_item_get_identifier(msginfo->folder);
+               }
+
+               for (cur = GTK_CMCLIST(ctree)->selection;
+                    cur != NULL && cur->data != NULL; cur = cur->next) {
+                       gchar *tmp;
+
+                       msginfo = gtk_cmctree_node_get_row_data(ctree, GTK_CMCTREE_NODE(cur->data));
+            if(!msginfo)
+              continue;
+                       tmp = path_list;
+                       path_list = g_strconcat(path_list, "\n", (msginfo->msgid ? msginfo->msgid : "unknown"), NULL);
+                       g_free(tmp);
+               }
+
+               if (path_list != NULL) {
+                       gtk_selection_data_set(selection_data,
+                                              gtk_selection_data_get_target(selection_data), 8,
+                                              path_list, strlen(path_list));
+                       g_free(path_list);
+               }
+    }
 }
 
 static gboolean summary_drag_motion_cb(GtkWidget      *widget,
@@ -7155,7 +7407,8 @@ static void summary_drag_data_received(GtkWidget        *widget,
                        gtk_drag_finish(drag_context, FALSE, FALSE, time);                      
                        return;
                } else {
-                       folderview_finish_dnd(data->data, drag_context, time, item);
+                       folderview_finish_dnd(gtk_selection_data_get_data(data),
+                               drag_context, time, item);
                }
        }
 }
@@ -7612,25 +7865,30 @@ void summary_toggle_show_del_messages(SummaryView *summaryview)
        summary_show(summaryview, summaryview->folder_item);
 }
  
-static void summary_set_hide_read_msgs_menu (SummaryView *summaryview,
-                                            guint action)
+void summary_toggle_show_read_threads(SummaryView *summaryview)
 {
-       GtkWidget *widget;
+       FolderItemUpdateData source;
+       if (summaryview->folder_item->hide_read_threads)
+               summaryview->folder_item->hide_read_threads = 0;
+       else
+               summaryview->folder_item->hide_read_threads = 1;
 
-       widget = gtk_ui_manager_get_widget(summaryview->mainwin->ui_manager, "/Menu/View/HideReadMessages");
-       g_object_set_data(G_OBJECT(widget), "dont_toggle",
-                         GINT_TO_POINTER(1));
-       gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM(widget), action);
-       g_object_set_data(G_OBJECT(widget), "dont_toggle",
-                         GINT_TO_POINTER(0));
+       source.item = summaryview->folder_item;
+       source.update_flags = F_ITEM_UPDATE_NAME;
+       source.msg = NULL;
+       hooks_invoke(FOLDER_ITEM_UPDATE_HOOKLIST, &source);
+       summary_show(summaryview, summaryview->folder_item);
 }
-
-static void summary_set_hide_del_msgs_menu (SummaryView *summaryview,
-                                            guint action)
+static void summary_set_hide_menu (SummaryView *summaryview,
+                                  const gchar *menu_item,
+                                  guint action)
 {
        GtkWidget *widget;
 
-       widget = gtk_ui_manager_get_widget(summaryview->mainwin->ui_manager, "/Menu/View/HideDelMessages");
+       widget = gtk_ui_manager_get_widget(summaryview->mainwin->ui_manager, menu_item);
+       cm_return_if_fail(widget != NULL);
+
        g_object_set_data(G_OBJECT(widget), "dont_toggle",
                          GINT_TO_POINTER(1));
        gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM(widget), action);
@@ -7649,6 +7907,7 @@ void summary_reflect_prefs_pixmap_theme(SummaryView *summaryview)
        stock_pixbuf_gdk(ctree, STOCK_PIXMAP_UNREAD, &unreadxpm);
        stock_pixbuf_gdk(ctree, STOCK_PIXMAP_REPLIED, &repliedxpm);
        stock_pixbuf_gdk(ctree, STOCK_PIXMAP_FORWARDED, &forwardedxpm);
+       stock_pixbuf_gdk(ctree, STOCK_PIXMAP_REPLIED_AND_FORWARDED, &repliedandforwardedxpm);
        stock_pixbuf_gdk(ctree, STOCK_PIXMAP_CLIP, &clipxpm);
        stock_pixbuf_gdk(ctree, STOCK_PIXMAP_LOCKED, &lockedxpm);
        stock_pixbuf_gdk(ctree, STOCK_PIXMAP_IGNORETHREAD, &ignorethreadxpm);
@@ -7688,20 +7947,22 @@ void summary_reflect_prefs_pixmap_theme(SummaryView *summaryview)
 void summary_reflect_prefs_custom_colors(SummaryView *summaryview)
 {
        GtkMenuShell *menu;
-       GList *cur;
+       GList *children, *cur;
 
        /* re-create colorlabel submenu */
        menu = GTK_MENU_SHELL(summaryview->colorlabel_menu);
        cm_return_if_fail(menu != NULL);
 
        /* clear items. get item pointers. */
-       for (cur = menu->children; cur != NULL && cur->data != NULL; cur = cur->next) {
+       children = gtk_container_get_children(GTK_CONTAINER(menu));
+       for (cur = children; cur != NULL && cur->data != NULL; cur = cur->next) {
                g_signal_handlers_disconnect_matched
                         (gtk_ui_manager_get_accel_group(summaryview->mainwin->ui_manager), 
                         G_SIGNAL_MATCH_DATA|G_SIGNAL_MATCH_FUNC,
                         0, 0, NULL, mainwin_accel_changed_cb, cur->data);
                gtk_menu_item_set_submenu(GTK_MENU_ITEM(cur->data), NULL);
        }
+       g_list_free(children);
        summary_colorlabel_menu_create(summaryview, TRUE);
 }
 
@@ -7722,11 +7983,12 @@ void summary_harvest_address(SummaryView *summaryview)
                        continue;
                msgList = g_list_append( msgList, GUINT_TO_POINTER( msginfo->msgnum ) );
        }
+
        addressbook_harvest( summaryview->folder_item, TRUE, msgList );
+
        g_list_free( msgList );
 }
 
-#ifndef G_OS_WIN32
 static regex_t *summary_compile_simplify_regexp(gchar *simplify_subject_regexp)
 {
        int err;
@@ -7746,7 +8008,6 @@ static regex_t *summary_compile_simplify_regexp(gchar *simplify_subject_regexp)
        
        return preg;
 }
-#endif
 void summary_set_prefs_from_folderitem(SummaryView *summaryview, FolderItem *item)
 {
        FolderSortKey sort_key;
@@ -7755,7 +8016,6 @@ void summary_set_prefs_from_folderitem(SummaryView *summaryview, FolderItem *ite
        cm_return_if_fail(item != NULL);
 
        /* Subject simplification */
-#ifndef G_OS_WIN32
        if(summaryview->simplify_subject_preg) {
                regfree(summaryview->simplify_subject_preg);
                g_free(summaryview->simplify_subject_preg);
@@ -7764,7 +8024,7 @@ void summary_set_prefs_from_folderitem(SummaryView *summaryview, FolderItem *ite
        if(item->prefs && item->prefs->simplify_subject_regexp && 
           item->prefs->simplify_subject_regexp[0] && item->prefs->enable_simplify_subject)
                summaryview->simplify_subject_preg = summary_compile_simplify_regexp(item->prefs->simplify_subject_regexp);
-#endif
+
        /* Sorting */
        sort_key = item->sort_key;
        sort_type = item->sort_type;
@@ -7821,9 +8081,6 @@ void summary_update_unread(SummaryView *summaryview, FolderItem *removed_item)
        guint new, unread, unreadmarked, marked, total;
        guint replied, forwarded, locked, ignored, watched;
        static gboolean tips_initialized = FALSE;
-#if !(GTK_CHECK_VERSION(2,12,0))
-       GtkTooltips *tips = summaryview->tooltips;
-#endif
 
        if (prefs_common.layout_mode != SMALL_LAYOUT) {
                if (tips_initialized) {
@@ -7880,9 +8137,9 @@ static gboolean summary_update_folder_hook(gpointer source, gpointer data)
        FolderUpdateData *hookdata;
        SummaryView *summaryview = (SummaryView *)data;
        hookdata = source;
-       if (hookdata->update_flags & FOLDER_REMOVE_FOLDERITEM)
+       if (hookdata->update_flags & FOLDER_REMOVE_FOLDERITEM) {
                summary_update_unread(summaryview, hookdata->item);
-       else
+       else
                summary_update_unread(summaryview, NULL);
 
        return FALSE;
@@ -7918,7 +8175,7 @@ static void summary_find_answers (SummaryView *summaryview, MsgInfo *msg)
        
        gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(summaryview->toggle_search), TRUE);
 
-       quicksearch_set(summaryview->quicksearch, QUICK_SEARCH_EXTENDED, buf);
+       quicksearch_set(summaryview->quicksearch, ADVANCED_SEARCH_EXTENDED, buf);
        g_free(buf);
 
        node = gtk_cmctree_node_nth(GTK_CMCTREE(summaryview->ctree), 0);