1 /* Copyright (c) 2006, Nokia Corporation
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are
8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the
12 * documentation and/or other materials provided with the distribution.
13 * * Neither the name of the Nokia Corporation nor the names of its
14 * contributors may be used to endorse or promote products derived from
15 * this software without specific prior written permission.
17 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
18 * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
19 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
20 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
21 * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
22 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
23 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
24 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
25 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
26 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
27 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 #endif /*HAVE_CONFIG_H*/
34 #include <glib/gi18n.h>
35 #include <glib/gprintf.h>
37 #include <modest-runtime.h>
38 #include <modest-tny-folder.h>
39 #include <modest-tny-msg.h>
40 #include <modest-tny-account.h>
41 #include <modest-address-book.h>
42 #include "modest-error.h"
43 #include "modest-ui-actions.h"
45 #include "modest-tny-platform-factory.h"
46 #include "modest-platform.h"
47 #include <tny-mime-part.h>
49 #ifdef MODEST_PLATFORM_MAEMO
50 #include "maemo/modest-osso-state-saving.h"
51 #include "maemo/modest-maemo-utils.h"
52 #endif /* MODEST_PLATFORM_MAEMO */
54 #include "widgets/modest-ui-constants.h"
55 #include <widgets/modest-main-window.h>
56 #include <widgets/modest-msg-view-window.h>
57 #include <widgets/modest-account-view-window.h>
58 #include <widgets/modest-details-dialog.h>
59 #include <widgets/modest-attachments-view.h>
60 #include "widgets/modest-folder-view.h"
61 #include "widgets/modest-global-settings-dialog.h"
62 #include "modest-connection-specific-smtp-window.h"
63 #include "modest-account-mgr-helpers.h"
64 #include "modest-mail-operation.h"
65 #include "modest-text-utils.h"
67 #ifdef MODEST_HAVE_EASYSETUP
68 #include "easysetup/modest-easysetup-wizard.h"
69 #endif /* MODEST_HAVE_EASYSETUP */
71 #include <modest-widget-memory.h>
72 #include <tny-error.h>
73 #include <tny-simple-list.h>
74 #include <tny-msg-view.h>
75 #include <tny-device.h>
76 #include <tny-merge-folder.h>
78 #include <gtkhtml/gtkhtml.h>
80 typedef struct _GetMsgAsyncHelper {
82 ModestMailOperation *mail_op;
89 typedef enum _ReplyForwardAction {
95 typedef struct _ReplyForwardHelper {
96 guint reply_forward_type;
97 ReplyForwardAction action;
99 GtkWidget *parent_window;
100 } ReplyForwardHelper;
104 * The do_headers_action uses this kind of functions to perform some
105 * action to each member of a list of headers
107 typedef void (*HeadersFunc) (TnyHeader *header, ModestWindow *win, gpointer user_data);
109 static void do_headers_action (ModestWindow *win,
113 static void open_msg_cb (ModestMailOperation *mail_op,
118 static void reply_forward_cb (ModestMailOperation *mail_op,
123 static void reply_forward (ReplyForwardAction action, ModestWindow *win);
125 static void folder_refreshed_cb (ModestMailOperation *mail_op,
129 static void _on_send_receive_progress_changed (ModestMailOperation *mail_op,
130 ModestMailOperationState *state,
136 run_account_setup_wizard (ModestWindow *win)
138 ModestEasysetupWizardDialog *wizard;
140 g_return_if_fail (MODEST_IS_WINDOW(win));
142 wizard = modest_easysetup_wizard_dialog_new ();
143 gtk_window_set_transient_for (GTK_WINDOW (wizard), GTK_WINDOW (win));
144 gtk_dialog_run (GTK_DIALOG (wizard));
145 gtk_widget_destroy (GTK_WIDGET (wizard));
150 modest_ui_actions_on_about (GtkAction *action, ModestWindow *win)
153 const gchar *authors[] = {
154 "Dirk-Jan C. Binnema <dirk-jan.binnema@nokia.com>",
157 about = gtk_about_dialog_new ();
158 gtk_about_dialog_set_name (GTK_ABOUT_DIALOG(about), PACKAGE_NAME);
159 gtk_about_dialog_set_version (GTK_ABOUT_DIALOG(about),PACKAGE_VERSION);
160 gtk_about_dialog_set_copyright (GTK_ABOUT_DIALOG(about),
161 _("Copyright (c) 2006, Nokia Corporation\n"
162 "All rights reserved."));
163 gtk_about_dialog_set_comments (GTK_ABOUT_DIALOG(about),
164 _("a modest e-mail client\n\n"
165 "design and implementation: Dirk-Jan C. Binnema\n"
166 "contributions from the fine people at KC and Ig\n"
167 "uses the tinymail email framework written by Philip van Hoof"));
168 gtk_about_dialog_set_authors (GTK_ABOUT_DIALOG(about), authors);
169 gtk_about_dialog_set_website (GTK_ABOUT_DIALOG(about), "http://modest.garage.maemo.org");
171 gtk_dialog_run (GTK_DIALOG (about));
172 gtk_widget_destroy(about);
176 * Gets the list of currently selected messages. If the win is the
177 * main window, then it returns a newly allocated list of the headers
178 * selected in the header view. If win is the msg view window, then
179 * the value returned is a list with just a single header.
181 * The caller of this funcion must free the list.
184 get_selected_headers (ModestWindow *win)
186 if (MODEST_IS_MAIN_WINDOW(win)) {
187 GtkWidget *header_view;
189 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
190 MODEST_WIDGET_TYPE_HEADER_VIEW);
191 return modest_header_view_get_selected_headers (MODEST_HEADER_VIEW(header_view));
193 } else if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
194 /* for MsgViewWindows, we simply return a list with one element */
196 TnyList *list = NULL;
198 header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW (win));
199 if (header != NULL) {
200 list = tny_simple_list_new ();
201 tny_list_prepend (list, G_OBJECT(header));
202 g_object_unref (G_OBJECT(header));
212 headers_action_mark_as_read (TnyHeader *header,
216 TnyHeaderFlags flags;
218 g_return_if_fail (TNY_IS_HEADER(header));
220 flags = tny_header_get_flags (header);
221 if (flags & TNY_HEADER_FLAG_SEEN) return;
222 tny_header_set_flags (header, TNY_HEADER_FLAG_SEEN);
226 headers_action_mark_as_unread (TnyHeader *header,
230 TnyHeaderFlags flags;
232 g_return_if_fail (TNY_IS_HEADER(header));
234 flags = tny_header_get_flags (header);
235 if (flags & TNY_HEADER_FLAG_SEEN) {
236 tny_header_unset_flags (header, TNY_HEADER_FLAG_SEEN);
242 headers_action_delete (TnyHeader *header,
246 ModestMailOperation *mail_op = NULL;
248 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_DELETE, G_OBJECT(win));
249 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
252 /* Always delete. TODO: Move to trash still not supported */
253 modest_mail_operation_remove_msg (mail_op, header, FALSE);
254 g_object_unref (G_OBJECT (mail_op));
256 /* refilter treemodel to hide marked-as-deleted rows */
257 /* if (MODEST_IS_HEADER_VIEW (user_data)) */
258 /* modest_header_view_refilter (MODEST_HEADER_VIEW (user_data)); */
262 modest_ui_actions_on_delete_message (GtkAction *action, ModestWindow *win)
264 TnyList *header_list = NULL;
265 TnyIterator *iter = NULL;
266 TnyHeader *header = NULL;
267 gchar *message = NULL;
270 ModestWindowMgr *mgr;
271 GtkWidget *header_view = NULL;
273 g_return_if_fail (MODEST_IS_WINDOW(win));
275 /* Check first if the header view has the focus */
276 if (MODEST_IS_MAIN_WINDOW (win)) {
278 modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
279 MODEST_WIDGET_TYPE_HEADER_VIEW);
280 if (!gtk_widget_is_focus (header_view))
284 header_list = get_selected_headers (win);
285 if (!header_list) return;
287 /* Check if any of the headers is already opened, or in the process of being opened */
288 if (MODEST_IS_MAIN_WINDOW (win)) {
290 iter = tny_list_create_iterator (header_list);
292 mgr = modest_runtime_get_window_mgr ();
293 while (!tny_iterator_is_done (iter) && !found) {
294 header = TNY_HEADER (tny_iterator_get_current (iter));
295 found = modest_window_mgr_find_registered_header (mgr, header, NULL);
296 g_object_unref (header);
297 tny_iterator_next (iter);
299 g_object_unref (iter);
304 num = g_strdup_printf ("%d", tny_list_get_length (header_list));
305 msg = g_strdup_printf (_("mcen_nc_unable_to_delete_n_messages"), num);
307 modest_platform_run_information_dialog (GTK_WINDOW (win), (const gchar *) msg);
311 g_object_unref (header_list);
317 if (tny_list_get_length(header_list) == 1) {
318 iter = tny_list_create_iterator (header_list);
319 header = TNY_HEADER (tny_iterator_get_current (iter));
320 desc = g_strdup_printf ("%s", tny_header_get_subject (header));
321 g_object_unref (header);
322 g_object_unref (iter);
324 message = g_strdup_printf(ngettext("emev_nc_delete_message", "emev_nc_delete_messages",
325 tny_list_get_length(header_list)), desc);
327 /* Confirmation dialog */
328 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (win),
332 if (response == GTK_RESPONSE_OK) {
333 ModestWindow *main_window = NULL;
334 ModestWindowMgr *mgr = NULL;
335 GtkTreeModel *model = NULL;
336 GtkTreeSelection *sel = NULL;
337 GList *sel_list = NULL, *tmp = NULL;
338 GtkTreeRowReference *row_reference = NULL;
339 GtkTreePath *next_path = NULL;
341 /* Find last selected row */
342 if (MODEST_IS_MAIN_WINDOW (win)) {
343 model = gtk_tree_view_get_model (GTK_TREE_VIEW (header_view));
344 sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (header_view));
345 sel_list = gtk_tree_selection_get_selected_rows (sel, &model);
346 for (tmp=sel_list; tmp; tmp=tmp->next) {
347 if (tmp->next == NULL) {
348 next_path = gtk_tree_path_copy((GtkTreePath *) tmp->data);
349 gtk_tree_path_next (next_path);
350 row_reference = gtk_tree_row_reference_new (model, next_path);
351 gtk_tree_path_free (next_path);
356 /* Remove each header. If it's a view window header_view == NULL */
357 do_headers_action (win, headers_action_delete, header_view);
359 if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
360 /* Close msg view window or select next */
361 if (modest_msg_view_window_last_message_selected (MODEST_MSG_VIEW_WINDOW (win)) &&
362 modest_msg_view_window_first_message_selected (MODEST_MSG_VIEW_WINDOW (win))) {
363 modest_ui_actions_on_close_window (NULL, MODEST_WINDOW (win));
365 modest_msg_view_window_select_next_message (MODEST_MSG_VIEW_WINDOW (win));
368 /* Get main window */
369 mgr = modest_runtime_get_window_mgr ();
370 main_window = modest_window_mgr_get_main_window (mgr);
373 /* Move cursor to next row */
376 /* Select next row */
377 if (gtk_tree_row_reference_valid (row_reference)) {
378 next_path = gtk_tree_row_reference_get_path (row_reference);
379 gtk_tree_selection_select_path (sel, next_path);
380 gtk_tree_path_free (next_path);
382 if (row_reference != NULL)
383 gtk_tree_row_reference_free (row_reference);
386 /* Update toolbar dimming state */
387 modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (main_window));
390 g_list_foreach (sel_list, (GFunc) gtk_tree_path_free, NULL);
391 g_list_free (sel_list);
397 g_object_unref (header_list);
403 /* delete either message or folder, based on where we are */
405 modest_ui_actions_on_delete_message_or_folder (GtkAction *action, ModestWindow *win)
407 g_return_if_fail (MODEST_IS_WINDOW(win));
409 /* Check first if the header view has the focus */
410 if (MODEST_IS_MAIN_WINDOW (win)) {
412 w = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
413 MODEST_WIDGET_TYPE_FOLDER_VIEW);
414 if (gtk_widget_is_focus (w)) {
415 modest_ui_actions_on_delete_folder (action, MODEST_MAIN_WINDOW(win));
419 modest_ui_actions_on_delete_message (action, win);
425 modest_ui_actions_on_quit (GtkAction *action, ModestWindow *win)
427 #ifdef MODEST_PLATFORM_MAEMO
428 modest_osso_save_state();
429 #endif /* MODEST_PLATFORM_MAEMO */
431 g_debug ("closing down, clearing %d item(s) from operation queue",
432 modest_mail_operation_queue_num_elements
433 (modest_runtime_get_mail_operation_queue()));
435 /* cancel all outstanding operations */
436 modest_mail_operation_queue_cancel_all
437 (modest_runtime_get_mail_operation_queue());
439 g_debug ("queue has been cleared");
441 /* note: when modest-tny-account-store is finalized,
442 it will automatically set all network connections
449 modest_ui_actions_on_close_window (GtkAction *action, ModestWindow *win)
452 g_signal_emit_by_name (G_OBJECT (win), "delete-event", NULL, &ret_value);
454 /* if (MODEST_IS_MSG_VIEW_WINDOW (win)) { */
455 /* gtk_widget_destroy (GTK_WIDGET (win)); */
456 /* } else if (MODEST_IS_MSG_EDIT_WINDOW (win)) { */
457 /* gboolean ret_value; */
458 /* g_signal_emit_by_name (G_OBJECT (win), "delete-event", NULL, &ret_value); */
459 /* } else if (MODEST_IS_WINDOW (win)) { */
460 /* gtk_widget_destroy (GTK_WIDGET (win)); */
462 /* g_return_if_reached (); */
467 modest_ui_actions_on_add_to_contacts (GtkAction *action, ModestWindow *win)
469 GtkClipboard *clipboard = NULL;
470 gchar *selection = NULL;
472 clipboard = gtk_clipboard_get (GDK_SELECTION_PRIMARY);
473 selection = gtk_clipboard_wait_for_text (clipboard);
475 /* Question: why is the clipboard being used here?
476 * It doesn't really make a lot of sense. */
480 modest_address_book_add_address (selection);
486 modest_ui_actions_on_accounts (GtkAction *action, ModestWindow *win)
488 /* This is currently only implemented for Maemo */
489 #ifdef MODEST_PLATFORM_MAEMO /* Defined in config.h */
490 if (!modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE)) {
491 run_account_setup_wizard (win);
494 /* Show the list of accounts: */
495 GtkDialog *account_win = GTK_DIALOG(modest_account_view_window_new ());
496 modest_maemo_show_dialog_and_forget (GTK_WINDOW (win), account_win);
499 GtkWidget *dialog, *label;
501 /* Create the widgets */
503 dialog = gtk_dialog_new_with_buttons ("Message",
505 GTK_DIALOG_DESTROY_WITH_PARENT,
509 label = gtk_label_new ("Hello World!");
511 /* Ensure that the dialog box is destroyed when the user responds. */
513 g_signal_connect_swapped (dialog, "response",
514 G_CALLBACK (gtk_widget_destroy),
517 /* Add the label, and show everything we've added to the dialog. */
519 gtk_container_add (GTK_CONTAINER (GTK_DIALOG(dialog)->vbox),
521 gtk_widget_show_all (dialog);
522 #endif /* MODEST_PLATFORM_MAEMO */
526 on_smtp_servers_window_hide (GtkWindow* window, gpointer user_data)
528 ModestWindow *main_window = MODEST_WINDOW (user_data);
530 /* Save any changes. */
531 modest_connection_specific_smtp_window_save_server_accounts (
532 MODEST_CONNECTION_SPECIFIC_SMTP_WINDOW (window),
533 modest_window_get_active_account (main_window));
534 gtk_widget_destroy (GTK_WIDGET (window));
540 modest_ui_actions_on_smtp_servers (GtkAction *action, ModestWindow *win)
542 /* This is currently only implemented for Maemo,
543 * because it requires an API (libconic) to detect different connection
546 #ifdef MODEST_PLATFORM_MAEMO /* Defined in config.h */
548 /* Create the window if necessary: */
549 const gchar *active_account_name = modest_window_get_active_account (win);
551 /* TODO: Dim the menu item (not in the UI spec)? or show a warning,
552 * or show the default account?
553 * If we show the default account then the account name should be shown in
554 * the window when we show it. */
555 if (!active_account_name) {
556 g_warning ("%s: No account is active.", __FUNCTION__);
560 GtkWidget *specific_window = GTK_WIDGET (modest_connection_specific_smtp_window_new ());
561 modest_connection_specific_smtp_window_fill_with_connections (
562 MODEST_CONNECTION_SPECIFIC_SMTP_WINDOW (specific_window),
563 modest_runtime_get_account_mgr(),
564 active_account_name);
566 /* Show the window: */
567 gtk_window_set_transient_for (GTK_WINDOW (specific_window), GTK_WINDOW (win));
568 gtk_window_set_modal (GTK_WINDOW (specific_window), TRUE);
569 gtk_widget_show (specific_window);
571 /* Save changes when the window is hidden: */
572 g_signal_connect (specific_window, "hide",
573 G_CALLBACK (on_smtp_servers_window_hide), win);
574 #endif /* MODEST_PLATFORM_MAEMO */
578 modest_ui_actions_on_new_msg (GtkAction *action, ModestWindow *win)
580 ModestWindow *msg_win = NULL;
582 TnyFolder *folder = NULL;
583 gchar *account_name = NULL;
584 gchar *from_str = NULL;
585 /* GError *err = NULL; */
586 TnyAccount *account = NULL;
587 ModestWindowMgr *mgr;
588 gchar *signature = NULL, *blank_and_signature = NULL;
590 /* if there are no accounts yet, just show the wizard */
591 if (!modest_account_mgr_has_accounts (modest_runtime_get_account_mgr(), TRUE)) {
592 run_account_setup_wizard (win);
596 account_name = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr ());
598 account_name = g_strdup (modest_window_get_active_account (win));
600 g_printerr ("modest: no account found\n");
604 account = modest_tny_account_store_get_server_account (modest_runtime_get_account_store(),
606 TNY_ACCOUNT_TYPE_STORE);
608 g_printerr ("modest: failed to get tnyaccount for '%s'\n", account_name);
612 from_str = modest_account_mgr_get_from_string (modest_runtime_get_account_mgr(), account_name);
614 g_printerr ("modest: failed get from string for '%s'\n", account_name);
618 if (modest_account_mgr_get_bool (modest_runtime_get_account_mgr (), account_name,
619 MODEST_ACCOUNT_USE_SIGNATURE, FALSE)) {
620 signature = modest_account_mgr_get_string (modest_runtime_get_account_mgr (), account_name,
621 MODEST_ACCOUNT_SIGNATURE, FALSE);
622 blank_and_signature = g_strconcat ("\n", signature, NULL);
625 blank_and_signature = g_strdup ("");
628 msg = modest_tny_msg_new ("", from_str, "", "", "", blank_and_signature, NULL);
630 g_printerr ("modest: failed to create new msg\n");
634 folder = modest_tny_account_get_special_folder (account, TNY_FOLDER_TYPE_DRAFTS);
636 g_printerr ("modest: failed to find Drafts folder\n");
641 /* Create and register edit window */
642 /* This is destroyed by TOOD. */
643 msg_win = modest_msg_edit_window_new (msg, account_name);
644 mgr = modest_runtime_get_window_mgr ();
645 modest_window_mgr_register_window (mgr, msg_win);
648 gtk_window_set_transient_for (GTK_WINDOW (msg_win),
650 gtk_widget_show_all (GTK_WIDGET (msg_win));
653 g_free (account_name);
655 g_free (blank_and_signature);
657 g_object_unref (msg_win);
659 g_object_unref (G_OBJECT(account));
661 g_object_unref (G_OBJECT(msg));
663 g_object_unref (G_OBJECT(folder));
667 modest_ui_actions_msg_retrieval_check (ModestMailOperation *mail_op,
671 ModestMailOperationStatus status;
673 /* If there is no message or the operation was not successful */
674 status = modest_mail_operation_get_status (mail_op);
675 if (!msg || status != MODEST_MAIL_OPERATION_STATUS_SUCCESS) {
677 /* Remove the header from the preregistered uids */
678 modest_window_mgr_unregister_header (modest_runtime_get_window_mgr (),
688 open_msg_cb (ModestMailOperation *mail_op,
693 ModestWindowMgr *mgr = NULL;
694 ModestWindow *parent_win = NULL;
695 ModestWindow *win = NULL;
696 TnyFolderType folder_type = TNY_FOLDER_TYPE_UNKNOWN;
697 gchar *account = NULL;
700 /* Do nothing if there was any problem with the mail
701 operation. The error will be shown by the error_handler of
702 the mail operation */
703 if (!modest_ui_actions_msg_retrieval_check (mail_op, header, msg)) {
704 printf ("DEBUG: %s: modest_ui_actions_msg_retrieval_check() failed.\n",
709 parent_win = (ModestWindow *) modest_mail_operation_get_source (mail_op);
710 folder = tny_header_get_folder (header);
712 /* Mark header as read */
713 headers_action_mark_as_read (header, MODEST_WINDOW(parent_win), NULL);
716 account = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
718 account = g_strdup (modest_window_get_active_account (MODEST_WINDOW (parent_win)));
720 /* Gets folder type (OUTBOX headers will be opened in edit window */
721 if (modest_tny_folder_is_local_folder (folder))
722 folder_type = modest_tny_folder_get_local_folder_type (folder);
724 /* If the header is in the drafts folder then open the editor,
725 else the message view window */
726 if (folder_type == TNY_FOLDER_TYPE_DRAFTS) {
727 /* we cannot edit without a valid account... */
728 if (!modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE)) {
729 run_account_setup_wizard(parent_win);
732 win = modest_msg_edit_window_new (msg, account);
734 gchar *uid = modest_tny_folder_get_header_unique_id (header);
736 if (MODEST_IS_MAIN_WINDOW (parent_win)) {
737 GtkWidget *header_view;
738 GtkTreeSelection *sel;
739 GList *sel_list = NULL;
742 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(parent_win),
743 MODEST_WIDGET_TYPE_HEADER_VIEW);
745 sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (header_view));
746 sel_list = gtk_tree_selection_get_selected_rows (sel, &model);
748 if (sel_list != NULL) {
749 GtkTreeRowReference *row_reference;
751 row_reference = gtk_tree_row_reference_new (model, (GtkTreePath *) sel_list->data);
752 g_list_foreach (sel_list, (GFunc) gtk_tree_path_free, NULL);
753 g_list_free (sel_list);
755 win = modest_msg_view_window_new_with_header_model (msg,
760 gtk_tree_row_reference_free (row_reference);
762 win = modest_msg_view_window_new (msg, account, (const gchar*) uid);
765 win = modest_msg_view_window_new (msg, account, (const gchar*) uid);
770 /* Register and show new window */
772 mgr = modest_runtime_get_window_mgr ();
773 modest_window_mgr_register_window (mgr, win);
774 g_object_unref (win);
775 gtk_window_set_transient_for (GTK_WINDOW (win), GTK_WINDOW (parent_win));
776 gtk_widget_show_all (GTK_WIDGET(win));
779 /* Update toolbar dimming state */
780 if (MODEST_IS_MAIN_WINDOW (parent_win)) {
781 modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (parent_win));
787 g_object_unref (parent_win);
788 /* g_object_unref (msg); */
789 g_object_unref (folder);
793 modest_ui_actions_get_msgs_full_error_handler (ModestMailOperation *mail_op,
797 GObject *win = modest_mail_operation_get_source (mail_op);
799 error = modest_mail_operation_get_error (mail_op);
800 printf ("DEBUG: %s: Error: code=%d, text=%s\n", __FUNCTION__, error->code, error->message);
802 if (error->code == MODEST_MAIL_OPERATION_ERROR_MESSAGE_SIZE_LIMIT) {
804 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL,
807 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL,
808 _("mail_ni_ui_folder_get_msg_folder_error"));
812 g_object_unref (win);
816 * This function is used by both modest_ui_actions_on_open and
817 * modest_ui_actions_on_header_activated. This way we always do the
818 * same when trying to open messages.
821 _modest_ui_actions_open (TnyList *headers, ModestWindow *win)
823 ModestWindowMgr *mgr = NULL;
824 TnyIterator *iter = NULL;
825 ModestMailOperation *mail_op1 = NULL;
826 ModestMailOperation *mail_op2 = NULL;
827 TnyList *not_opened_headers = NULL;
828 TnyList *not_opened_cached_headers = NULL;
829 TnyHeaderFlags flags;
831 /* Look if we already have a message view for each header. If
832 true, then remove the header from the list of headers to
834 mgr = modest_runtime_get_window_mgr ();
835 iter = tny_list_create_iterator (headers);
836 not_opened_headers = tny_simple_list_new ();
837 not_opened_cached_headers = tny_simple_list_new ();
838 while (!tny_iterator_is_done (iter)) {
840 ModestWindow *window;
844 header = TNY_HEADER (tny_iterator_get_current (iter));
845 flags = tny_header_get_flags (header);
848 found = modest_window_mgr_find_registered_header (mgr, header, &window);
850 /* Do not open again the message and present the
851 window to the user */
854 gtk_window_present (GTK_WINDOW (window));
856 /* the header has been registered already, we don't do
857 * anything but wait for the window to come up*/
858 g_warning ("debug: header %p already registered, waiting for window",
861 if (!(flags & TNY_HEADER_FLAG_CACHED))
862 tny_list_append (not_opened_headers, G_OBJECT (header));
863 /* Check if msg has already been retreived */
865 tny_list_append (not_opened_cached_headers, G_OBJECT (header));
867 g_object_unref (header);
868 tny_iterator_next (iter);
870 g_object_unref (iter);
873 /* If some messages would have to be downloaded, ask the user to
874 * make a connection. It's generally easier to do this here (in the mainloop)
875 * than later in a thread:
877 if (tny_list_get_length (not_opened_cached_headers) > 0) {
878 gboolean connected = modest_platform_connect_and_wait (GTK_WINDOW (win));
880 /* Don't go further if a connection would be necessary but none is available: */
882 g_object_unref (not_opened_headers);
883 g_object_unref (not_opened_cached_headers);
888 /* Register the headers before actually creating the windows: */
889 TnyIterator *iter_not_opened = tny_list_create_iterator (not_opened_headers);
890 while (!tny_iterator_is_done (iter_not_opened)) {
891 TnyHeader *header = TNY_HEADER (tny_iterator_get_current (iter_not_opened));
892 modest_window_mgr_register_header (mgr, header);
893 g_object_unref (header);
895 tny_iterator_next (iter_not_opened);
897 g_object_unref (iter_not_opened);
898 iter_not_opened = NULL;
900 TnyIterator *iter_cached = tny_list_create_iterator (not_opened_cached_headers);
901 while (!tny_iterator_is_done (iter_cached)) {
902 TnyHeader *header = TNY_HEADER (tny_iterator_get_current (iter_cached));
903 modest_window_mgr_register_header (mgr, header);
904 g_object_unref (header);
906 tny_iterator_next (iter_cached);
908 g_object_unref (iter_cached);
912 /* Open each uncached message */
913 if (tny_list_get_length (not_opened_headers) > 0) {
914 mail_op1 = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
916 modest_ui_actions_get_msgs_full_error_handler,
918 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op1);
919 if (tny_list_get_length (not_opened_headers) > 1) {
920 modest_mail_operation_get_msgs_full (mail_op1,
926 TnyIterator *iter = tny_list_create_iterator (not_opened_headers);
927 TnyHeader *header = TNY_HEADER (tny_iterator_get_current (iter));
928 modest_mail_operation_get_msg (mail_op1, header, open_msg_cb, NULL);
929 g_object_unref (header);
930 g_object_unref (iter);
934 /* Open each cached message */
935 if (tny_list_get_length (not_opened_cached_headers) > 0) {
936 mail_op2 = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
938 modest_ui_actions_get_msgs_full_error_handler,
940 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op2);
941 if (tny_list_get_length (not_opened_cached_headers) > 1) {
942 modest_mail_operation_get_msgs_full (mail_op2,
948 TnyIterator *iter = tny_list_create_iterator (not_opened_cached_headers);
949 TnyHeader *header = TNY_HEADER (tny_iterator_get_current (iter));
950 modest_mail_operation_get_msg (mail_op2, header, open_msg_cb, NULL);
951 g_object_unref (header);
952 g_object_unref (iter);
957 if (not_opened_headers != NULL)
958 g_object_unref (not_opened_headers);
959 if (not_opened_cached_headers != NULL)
960 g_object_unref (not_opened_cached_headers);
962 g_object_unref (iter);
963 if (mail_op1 != NULL)
964 g_object_unref (mail_op1);
965 if (mail_op2 != NULL)
966 g_object_unref (mail_op2);
970 modest_ui_actions_on_open (GtkAction *action, ModestWindow *win)
975 headers = get_selected_headers (win);
980 _modest_ui_actions_open (headers, win);
982 g_object_unref(headers);
987 free_reply_forward_helper (gpointer data)
989 ReplyForwardHelper *helper;
991 helper = (ReplyForwardHelper *) data;
992 g_free (helper->account_name);
993 g_slice_free (ReplyForwardHelper, helper);
997 reply_forward_cb (ModestMailOperation *mail_op,
1003 ReplyForwardHelper *rf_helper;
1004 ModestWindow *msg_win = NULL;
1005 ModestEditType edit_type;
1007 TnyAccount *account = NULL;
1008 ModestWindowMgr *mgr = NULL;
1009 gchar *signature = NULL;
1011 /* If there was any error. The mail operation could be NULL,
1012 this means that we already have the message downloaded and
1013 that we didn't do a mail operation to retrieve it */
1014 if (mail_op && !modest_ui_actions_msg_retrieval_check (mail_op, header, msg))
1017 g_return_if_fail (user_data != NULL);
1018 rf_helper = (ReplyForwardHelper *) user_data;
1020 from = modest_account_mgr_get_from_string (modest_runtime_get_account_mgr(),
1021 rf_helper->account_name);
1022 if (modest_account_mgr_get_bool (modest_runtime_get_account_mgr(),
1023 rf_helper->account_name,
1024 MODEST_ACCOUNT_USE_SIGNATURE, FALSE)) {
1025 signature = modest_account_mgr_get_string (modest_runtime_get_account_mgr (),
1026 rf_helper->account_name,
1027 MODEST_ACCOUNT_SIGNATURE, FALSE);
1030 /* Create reply mail */
1031 switch (rf_helper->action) {
1034 modest_tny_msg_create_reply_msg (msg, from, signature,
1035 rf_helper->reply_forward_type,
1036 MODEST_TNY_MSG_REPLY_MODE_SENDER);
1038 case ACTION_REPLY_TO_ALL:
1040 modest_tny_msg_create_reply_msg (msg, from, signature, rf_helper->reply_forward_type,
1041 MODEST_TNY_MSG_REPLY_MODE_ALL);
1042 edit_type = MODEST_EDIT_TYPE_REPLY;
1044 case ACTION_FORWARD:
1046 modest_tny_msg_create_forward_msg (msg, from, signature, rf_helper->reply_forward_type);
1047 edit_type = MODEST_EDIT_TYPE_FORWARD;
1050 g_return_if_reached ();
1057 g_printerr ("modest: failed to create message\n");
1061 account = modest_tny_account_store_get_server_account (modest_runtime_get_account_store(),
1062 rf_helper->account_name,
1063 TNY_ACCOUNT_TYPE_STORE);
1065 g_printerr ("modest: failed to get tnyaccount for '%s'\n", rf_helper->account_name);
1069 /* Create and register the windows */
1070 msg_win = modest_msg_edit_window_new (new_msg, rf_helper->account_name);
1071 mgr = modest_runtime_get_window_mgr ();
1072 modest_window_mgr_register_window (mgr, msg_win);
1074 if (rf_helper->parent_window != NULL) {
1075 gdouble parent_zoom;
1077 parent_zoom = modest_window_get_zoom (MODEST_WINDOW (rf_helper->parent_window));
1078 modest_window_set_zoom (msg_win, parent_zoom);
1081 /* Show edit window */
1082 gtk_widget_show_all (GTK_WIDGET (msg_win));
1086 g_object_unref (msg_win);
1088 g_object_unref (G_OBJECT (new_msg));
1090 g_object_unref (G_OBJECT (account));
1091 /* g_object_unref (msg); */
1092 g_object_unref (header);
1093 free_reply_forward_helper (rf_helper);
1097 * Checks a list of headers. If any of them are not currently
1098 * downloaded (CACHED) then it asks the user for permission to
1101 * Returns FALSE if the user does not want to download the
1102 * messages. Returns TRUE if the user allowed the download or if all
1103 * of them are currently downloaded
1106 download_uncached_messages (TnyList *header_list, GtkWindow *win,
1111 gint uncached_messages = 0;
1113 iter = tny_list_create_iterator (header_list);
1114 while (!tny_iterator_is_done (iter)) {
1116 TnyHeaderFlags flags;
1118 header = TNY_HEADER (tny_iterator_get_current (iter));
1119 flags = tny_header_get_flags (header);
1120 /* TODO: is this the right flag?, it seems that some
1121 headers that have been previously downloaded do not
1123 if (! (flags & TNY_HEADER_FLAG_CACHED))
1124 uncached_messages ++;
1125 g_object_unref (header);
1126 tny_iterator_next (iter);
1128 g_object_unref (iter);
1130 /* Ask for user permission to download the messages */
1132 if (uncached_messages > 0) {
1133 GtkResponseType response;
1135 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (win),
1136 _("emev_nc_include_original"));
1139 modest_platform_run_confirmation_dialog (GTK_WINDOW (win),
1140 ngettext("mcen_nc_get_msg",
1142 uncached_messages));
1143 if (response == GTK_RESPONSE_CANCEL)
1146 /* If a download will be necessary, make sure that we have a connection: */
1147 retval = modest_platform_connect_and_wait(win);
1155 * Common code for the reply and forward actions
1158 reply_forward (ReplyForwardAction action, ModestWindow *win)
1160 ModestMailOperation *mail_op = NULL;
1161 TnyList *header_list = NULL;
1162 ReplyForwardHelper *rf_helper = NULL;
1163 guint reply_forward_type;
1164 gboolean continue_download;
1166 g_return_if_fail (MODEST_IS_WINDOW(win));
1168 /* we need an account when editing */
1169 if (!modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE)) {
1170 run_account_setup_wizard (win);
1174 header_list = get_selected_headers (win);
1178 /* Check that the messages have been previously downloaded */
1179 continue_download = download_uncached_messages (header_list, GTK_WINDOW (win), TRUE);
1180 if (!continue_download) {
1181 g_object_unref (header_list);
1185 reply_forward_type =
1186 modest_conf_get_int (modest_runtime_get_conf (),
1187 (action == ACTION_FORWARD) ? MODEST_CONF_FORWARD_TYPE : MODEST_CONF_REPLY_TYPE,
1189 /* We assume that we can only select messages of the
1190 same folder and that we reply all of them from the
1191 same account. In fact the interface currently only
1192 allows single selection */
1195 rf_helper = g_slice_new0 (ReplyForwardHelper);
1196 rf_helper->reply_forward_type = reply_forward_type;
1197 rf_helper->action = action;
1198 rf_helper->account_name = g_strdup (modest_window_get_active_account (win));
1199 if ((win != NULL) && (MODEST_IS_WINDOW (win)))
1200 rf_helper->parent_window = GTK_WIDGET (win);
1201 if (!rf_helper->account_name)
1202 rf_helper->account_name =
1203 modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
1205 if (MODEST_IS_MSG_VIEW_WINDOW(win)) {
1208 /* Get header and message. Do not free them here, the
1209 reply_forward_cb must do it */
1210 msg = modest_msg_view_window_get_message (MODEST_MSG_VIEW_WINDOW(win));
1211 header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW(win));
1212 if (!msg || !header) {
1214 g_object_unref (msg);
1216 g_object_unref (header);
1217 g_printerr ("modest: no message found\n");
1220 reply_forward_cb (NULL, header, msg, rf_helper);
1226 /* Retrieve messages */
1227 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
1229 modest_ui_actions_get_msgs_full_error_handler,
1231 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
1233 /* Only reply/forward to one message */
1234 iter = tny_list_create_iterator (header_list);
1235 header = TNY_HEADER (tny_iterator_get_current (iter));
1236 g_object_unref (iter);
1238 modest_mail_operation_get_msg (mail_op,
1243 /* modest_mail_operation_get_msgs_full (mail_op, */
1245 /* reply_forward_cb, */
1247 /* free_reply_forward_helper); */
1250 g_object_unref(mail_op);
1254 g_object_unref (header_list);
1258 modest_ui_actions_on_reply (GtkAction *action, ModestWindow *win)
1260 g_return_if_fail (MODEST_IS_WINDOW(win));
1262 reply_forward (ACTION_REPLY, win);
1266 modest_ui_actions_on_forward (GtkAction *action, ModestWindow *win)
1268 g_return_if_fail (MODEST_IS_WINDOW(win));
1270 reply_forward (ACTION_FORWARD, win);
1274 modest_ui_actions_on_reply_all (GtkAction *action, ModestWindow *win)
1276 g_return_if_fail (MODEST_IS_WINDOW(win));
1278 reply_forward (ACTION_REPLY_TO_ALL, win);
1282 modest_ui_actions_on_next (GtkAction *action,
1283 ModestWindow *window)
1285 if (MODEST_IS_MAIN_WINDOW (window)) {
1286 GtkWidget *header_view;
1288 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(window),
1289 MODEST_WIDGET_TYPE_HEADER_VIEW);
1293 modest_header_view_select_next (MODEST_HEADER_VIEW(header_view));
1294 } else if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
1295 modest_msg_view_window_select_next_message (MODEST_MSG_VIEW_WINDOW (window));
1297 g_return_if_reached ();
1302 modest_ui_actions_on_prev (GtkAction *action,
1303 ModestWindow *window)
1305 g_return_if_fail (MODEST_IS_WINDOW(window));
1307 if (MODEST_IS_MAIN_WINDOW (window)) {
1308 GtkWidget *header_view;
1309 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(window),
1310 MODEST_WIDGET_TYPE_HEADER_VIEW);
1314 modest_header_view_select_prev (MODEST_HEADER_VIEW(header_view));
1315 } else if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
1316 modest_msg_view_window_select_previous_message (MODEST_MSG_VIEW_WINDOW (window));
1318 g_return_if_reached ();
1323 modest_ui_actions_on_sort (GtkAction *action,
1324 ModestWindow *window)
1326 g_return_if_fail (MODEST_IS_WINDOW(window));
1328 if (MODEST_IS_MAIN_WINDOW (window)) {
1329 GtkWidget *header_view;
1330 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(window),
1331 MODEST_WIDGET_TYPE_HEADER_VIEW);
1335 /* Show sorting dialog */
1336 modest_platform_run_sort_dialog (GTK_WINDOW (window), MODEST_SORT_HEADERS);
1341 new_messages_arrived (ModestMailOperation *self,
1345 if (new_messages == 0)
1348 modest_platform_on_new_msg ();
1352 * This function performs the send & receive required actions. The
1353 * window is used to create the mail operation. Typically it should
1354 * always be the main window, but we pass it as argument in order to
1358 modest_ui_actions_do_send_receive (const gchar *account_name, ModestWindow *win)
1360 gchar *acc_name = NULL;
1361 ModestMailOperation *mail_op;
1363 /* If no account name was provided then get the current account, and if
1364 there is no current account then pick the default one: */
1365 if (!account_name) {
1366 acc_name = g_strdup (modest_window_get_active_account(win));
1368 acc_name = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
1370 g_printerr ("modest: cannot get default account\n");
1374 acc_name = g_strdup (account_name);
1377 /* Set send/receive operation in progress */
1378 modest_main_window_notify_send_receive_initied (MODEST_MAIN_WINDOW(win));
1380 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
1382 modest_ui_actions_send_receive_error_handler,
1385 g_signal_connect (G_OBJECT(mail_op), "progress-changed",
1386 G_CALLBACK (_on_send_receive_progress_changed),
1389 /* Send & receive. */
1390 /* TODO: The spec wants us to first do any pending deletions, before receiving. */
1391 /* Receive and then send. The operation is tagged initially as
1392 a receive operation because the account update performs a
1393 receive and then a send. The operation changes its type
1394 internally, so the progress objects will receive the proper
1395 progress information */
1396 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
1397 modest_mail_operation_update_account (mail_op, acc_name, new_messages_arrived, NULL);
1398 g_object_unref (G_OBJECT (mail_op));
1406 modest_ui_actions_do_cancel_send (const gchar *account_name,
1409 TnyTransportAccount *transport_account;
1410 TnySendQueue *send_queue = NULL;
1411 GError *error = NULL;
1413 /* Get transport account */
1415 TNY_TRANSPORT_ACCOUNT(modest_tny_account_store_get_server_account
1416 (modest_runtime_get_account_store(),
1418 TNY_ACCOUNT_TYPE_TRANSPORT));
1419 if (!transport_account) {
1420 g_printerr ("modest: no transport account found for '%s'\n", account_name);
1425 send_queue = TNY_SEND_QUEUE (modest_runtime_get_send_queue (transport_account));
1426 if (!TNY_IS_SEND_QUEUE(send_queue)) {
1427 g_set_error (&error, MODEST_MAIL_OPERATION_ERROR,
1428 MODEST_MAIL_OPERATION_ERROR_ITEM_NOT_FOUND,
1429 "modest: could not find send queue for account\n");
1431 /* Keeep messages in outbox folder */
1432 tny_send_queue_cancel (send_queue, FALSE, &error);
1436 if (transport_account != NULL)
1437 g_object_unref (G_OBJECT (transport_account));
1441 modest_ui_actions_cancel_send_all (ModestWindow *win)
1443 GSList *account_names, *iter;
1445 account_names = modest_account_mgr_account_names (modest_runtime_get_account_mgr(),
1448 iter = account_names;
1450 modest_ui_actions_do_cancel_send ((const char*) iter->data, win);
1451 iter = g_slist_next (iter);
1454 modest_account_mgr_free_account_names (account_names);
1455 account_names = NULL;
1459 modest_ui_actions_cancel_send (GtkAction *action, ModestWindow *win)
1462 /* Check if accounts exist */
1463 gboolean accounts_exist =
1464 modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE);
1466 /* If not, allow the user to create an account before trying to send/receive. */
1467 if (!accounts_exist)
1468 modest_ui_actions_on_accounts (NULL, win);
1470 /* Cancel all sending operaitons */
1471 modest_ui_actions_cancel_send_all (win);
1475 * Refreshes all accounts. This function will be used by automatic
1479 modest_ui_actions_do_send_receive_all (ModestWindow *win)
1481 GSList *account_names, *iter;
1483 account_names = modest_account_mgr_account_names (modest_runtime_get_account_mgr(),
1486 iter = account_names;
1488 modest_ui_actions_do_send_receive ((const char*) iter->data, win);
1489 iter = g_slist_next (iter);
1492 modest_account_mgr_free_account_names (account_names);
1493 account_names = NULL;
1497 * Handler of the click on Send&Receive button in the main toolbar
1500 modest_ui_actions_on_send_receive (GtkAction *action, ModestWindow *win)
1502 /* Check if accounts exist */
1503 gboolean accounts_exist =
1504 modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE);
1506 /* If not, allow the user to create an account before trying to send/receive. */
1507 if (!accounts_exist)
1508 modest_ui_actions_on_accounts (NULL, win);
1510 /* Refresh currently selected folder. Note that if we only
1511 want to retrive the headers, then the refresh only will
1512 invoke a poke_status over all folders, i.e., only the
1513 total/unread count will be updated */
1514 if (MODEST_IS_MAIN_WINDOW (win)) {
1515 GtkWidget *header_view, *folder_view;
1516 TnyFolderStore *folder_store;
1518 /* Get folder and header view */
1520 modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
1521 MODEST_WIDGET_TYPE_FOLDER_VIEW);
1523 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
1525 if (folder_store && TNY_IS_FOLDER (folder_store)) {
1527 modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
1528 MODEST_WIDGET_TYPE_HEADER_VIEW);
1530 /* We do not need to set the contents style
1531 because it hasn't changed. We also do not
1532 need to save the widget status. Just force
1534 modest_header_view_set_folder (MODEST_HEADER_VIEW(header_view),
1535 TNY_FOLDER (folder_store),
1536 folder_refreshed_cb,
1537 MODEST_MAIN_WINDOW (win));
1541 g_object_unref (folder_store);
1544 /* Refresh the active account */
1545 modest_ui_actions_do_send_receive (NULL, win);
1550 modest_ui_actions_toggle_header_list_view (GtkAction *action, ModestMainWindow *main_window)
1553 GtkWidget *header_view;
1555 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1557 header_view = modest_main_window_get_child_widget (main_window,
1558 MODEST_WIDGET_TYPE_HEADER_VIEW);
1562 conf = modest_runtime_get_conf ();
1564 /* what is saved/restored is depending on the style; thus; we save with
1565 * old style, then update the style, and restore for this new style
1567 modest_widget_memory_save (conf, G_OBJECT(header_view), MODEST_CONF_HEADER_VIEW_KEY);
1569 if (modest_header_view_get_style
1570 (MODEST_HEADER_VIEW(header_view)) == MODEST_HEADER_VIEW_STYLE_DETAILS)
1571 modest_header_view_set_style (MODEST_HEADER_VIEW(header_view),
1572 MODEST_HEADER_VIEW_STYLE_TWOLINES);
1574 modest_header_view_set_style (MODEST_HEADER_VIEW(header_view),
1575 MODEST_HEADER_VIEW_STYLE_DETAILS);
1577 modest_widget_memory_restore (conf, G_OBJECT(header_view),
1578 MODEST_CONF_HEADER_VIEW_KEY);
1583 modest_ui_actions_on_header_selected (ModestHeaderView *header_view,
1585 ModestMainWindow *main_window)
1587 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1588 g_return_if_fail (MODEST_IS_HEADER_VIEW (header_view));
1590 /* If no header has been selected then exit */
1595 if (!gtk_widget_is_focus (GTK_WIDGET(header_view)))
1596 gtk_widget_grab_focus (GTK_WIDGET(header_view));
1598 /* Update Main window title */
1599 if (gtk_widget_is_focus (GTK_WIDGET(header_view))) {
1600 const gchar *subject = tny_header_get_subject (header);
1601 if (subject && strlen(subject) > 0)
1602 gtk_window_set_title (GTK_WINDOW (main_window), subject);
1604 gtk_window_set_title (GTK_WINDOW (main_window), _("mail_va_no_subject"));
1607 /* Update toolbar dimming state */
1608 modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (main_window));
1612 modest_ui_actions_on_header_activated (ModestHeaderView *header_view,
1614 ModestMainWindow *main_window)
1618 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1623 headers = tny_simple_list_new ();
1624 tny_list_prepend (headers, G_OBJECT (header));
1626 _modest_ui_actions_open (headers, MODEST_WINDOW (main_window));
1628 g_object_unref (headers);
1632 set_active_account_from_tny_account (TnyAccount *account,
1633 ModestWindow *window)
1635 const gchar *server_acc_name = tny_account_get_id (account);
1637 /* We need the TnyAccount provided by the
1638 account store because that is the one that
1639 knows the name of the Modest account */
1640 TnyAccount *modest_server_account = modest_server_account =
1641 modest_tny_account_store_get_tny_account_by (modest_runtime_get_account_store (),
1642 MODEST_TNY_ACCOUNT_STORE_QUERY_ID,
1645 const gchar *modest_acc_name =
1646 modest_tny_account_get_parent_modest_account_name_for_server_account (modest_server_account);
1647 modest_window_set_active_account (window, modest_acc_name);
1648 g_object_unref (modest_server_account);
1653 folder_refreshed_cb (ModestMailOperation *mail_op,
1657 ModestMainWindow *win = NULL;
1658 GtkWidget *header_view;
1660 g_return_if_fail (TNY_IS_FOLDER (folder));
1662 win = MODEST_MAIN_WINDOW (user_data);
1664 modest_main_window_get_child_widget(win, MODEST_WIDGET_TYPE_HEADER_VIEW);
1666 /* Check if folder is empty and set headers view contents style */
1667 if (tny_folder_get_all_count (folder) == 0) {
1668 printf ("DEBUG: %s: tny_folder_get_all_count() returned 0.\n", __FUNCTION__);
1669 modest_main_window_set_contents_style (win,
1670 MODEST_MAIN_WINDOW_CONTENTS_STYLE_EMPTY);
1672 printf ("DEBUG: %s: tny_folder_get_all_count() returned >0.\n", __FUNCTION__);
1677 modest_ui_actions_on_folder_selection_changed (ModestFolderView *folder_view,
1678 TnyFolderStore *folder_store,
1680 ModestMainWindow *main_window)
1683 GtkWidget *header_view;
1685 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1687 header_view = modest_main_window_get_child_widget(main_window,
1688 MODEST_WIDGET_TYPE_HEADER_VIEW);
1692 conf = modest_runtime_get_conf ();
1694 if (TNY_IS_ACCOUNT (folder_store)) {
1696 /* Update active account */
1697 set_active_account_from_tny_account (TNY_ACCOUNT (folder_store), MODEST_WINDOW (main_window));
1698 /* Show account details */
1699 modest_main_window_set_contents_style (main_window, MODEST_MAIN_WINDOW_CONTENTS_STYLE_DETAILS);
1702 if (TNY_IS_FOLDER (folder_store) && selected) {
1704 /* Update the active account */
1705 TnyAccount *account = modest_tny_folder_get_account (TNY_FOLDER (folder_store));
1707 set_active_account_from_tny_account (account, MODEST_WINDOW (main_window));
1708 g_object_unref (account);
1712 /* Set the header style by default, it could
1713 be changed later by the refresh callback to
1715 modest_main_window_set_contents_style (main_window,
1716 MODEST_MAIN_WINDOW_CONTENTS_STYLE_HEADERS);
1718 /* Set folder on header view. This function
1719 will call tny_folder_refresh_async so we
1720 pass a callback that will be called when
1721 finished. We use that callback to set the
1722 empty view if there are no messages */
1723 modest_header_view_set_folder (MODEST_HEADER_VIEW(header_view),
1724 TNY_FOLDER (folder_store),
1725 folder_refreshed_cb,
1728 /* Restore configuration. We need to do this
1729 *after* the set_folder because the widget
1730 memory asks the header view about its
1732 modest_widget_memory_restore (modest_runtime_get_conf (),
1733 G_OBJECT(header_view),
1734 MODEST_CONF_HEADER_VIEW_KEY);
1736 /* Update the active account */
1737 modest_window_set_active_account (MODEST_WINDOW (main_window), NULL);
1738 /* Save only if we're seeing headers */
1739 if (modest_main_window_get_contents_style (main_window) ==
1740 MODEST_MAIN_WINDOW_CONTENTS_STYLE_HEADERS)
1741 modest_widget_memory_save (conf, G_OBJECT (header_view),
1742 MODEST_CONF_HEADER_VIEW_KEY);
1743 modest_header_view_clear (MODEST_HEADER_VIEW(header_view));
1747 /* Update toolbar dimming state */
1748 modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (main_window));
1752 modest_ui_actions_on_item_not_found (ModestHeaderView *header_view,ModestItemType type,
1759 item = (type == MODEST_ITEM_TYPE_FOLDER) ? "folder" : "message";
1761 online = tny_device_is_online (modest_runtime_get_device());
1764 /* already online -- the item is simply not there... */
1765 dialog = gtk_message_dialog_new (GTK_WINDOW (win),
1767 GTK_MESSAGE_WARNING,
1769 _("The %s you selected cannot be found"),
1771 gtk_dialog_run (GTK_DIALOG(dialog));
1773 dialog = gtk_dialog_new_with_buttons (_("Connection requested"),
1777 GTK_RESPONSE_REJECT,
1779 GTK_RESPONSE_ACCEPT,
1781 txt = g_strdup_printf (_("This %s is not available in offline mode.\n"
1782 "Do you want to get online?"), item);
1783 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox),
1784 gtk_label_new (txt), FALSE, FALSE, 0);
1785 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
1788 gtk_window_set_default_size (GTK_WINDOW(dialog), 300, 300);
1789 if (gtk_dialog_run (GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT) {
1790 // modest_platform_connect_and_wait ();
1793 gtk_widget_destroy (dialog);
1797 modest_ui_actions_on_msg_link_hover (ModestMsgView *msgview, const gchar* link,
1800 /* g_message ("%s %s", __FUNCTION__, link); */
1805 modest_ui_actions_on_msg_link_clicked (ModestMsgView *msgview, const gchar* link,
1808 modest_platform_activate_uri (link);
1812 modest_ui_actions_on_msg_link_contextual (ModestMsgView *msgview, const gchar* link,
1815 modest_platform_show_uri_popup (link);
1819 modest_ui_actions_on_msg_attachment_clicked (ModestMsgView *msgview, TnyMimePart *mime_part,
1822 modest_msg_view_window_view_attachment (MODEST_MSG_VIEW_WINDOW (win), mime_part);
1826 modest_ui_actions_on_msg_recpt_activated (ModestMsgView *msgview,
1827 const gchar *address,
1830 /* g_message ("%s %s", __FUNCTION__, address); */
1834 modest_ui_actions_on_save_to_drafts (GtkWidget *widget, ModestMsgEditWindow *edit_window)
1836 TnyTransportAccount *transport_account;
1837 ModestMailOperation *mail_operation;
1839 gchar *account_name, *from;
1840 ModestAccountMgr *account_mgr;
1841 gchar *info_text = NULL;
1843 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW(edit_window));
1845 data = modest_msg_edit_window_get_msg_data (edit_window);
1847 account_mgr = modest_runtime_get_account_mgr();
1848 account_name = g_strdup(modest_window_get_active_account (MODEST_WINDOW(edit_window)));
1850 account_name = modest_account_mgr_get_default_account (account_mgr);
1851 if (!account_name) {
1852 g_printerr ("modest: no account found\n");
1853 modest_msg_edit_window_free_msg_data (edit_window, data);
1857 if (!strcmp (account_name, MODEST_LOCAL_FOLDERS_ACCOUNT_ID)) {
1858 account_name = g_strdup (data->account_name);
1862 TNY_TRANSPORT_ACCOUNT(modest_tny_account_store_get_server_account
1863 (modest_runtime_get_account_store(),
1865 TNY_ACCOUNT_TYPE_TRANSPORT));
1866 if (!transport_account) {
1867 g_printerr ("modest: no transport account found for '%s'\n", account_name);
1868 g_free (account_name);
1869 modest_msg_edit_window_free_msg_data (edit_window, data);
1872 from = modest_account_mgr_get_from_string (account_mgr, account_name);
1874 /* Create the mail operation */
1875 mail_operation = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_INFO, G_OBJECT(edit_window));
1876 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_operation);
1878 modest_mail_operation_save_to_drafts (mail_operation,
1890 data->priority_flags);
1893 g_free (account_name);
1894 g_object_unref (G_OBJECT (transport_account));
1895 g_object_unref (G_OBJECT (mail_operation));
1897 modest_msg_edit_window_free_msg_data (edit_window, data);
1899 info_text = g_strdup_printf (_("mail_va_saved_to_drafts"), _("mcen_me_folder_drafts"));
1900 modest_platform_information_banner (NULL, NULL, info_text);
1904 /* For instance, when clicking the Send toolbar button when editing a message: */
1906 modest_ui_actions_on_send (GtkWidget *widget, ModestMsgEditWindow *edit_window)
1908 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW(edit_window));
1910 if (!modest_msg_edit_window_check_names (edit_window))
1913 /* Offer the connection dialog, if necessary: */
1914 if (!modest_platform_connect_and_wait (GTK_WINDOW (edit_window)))
1917 /* FIXME: Code added just for testing. The final version will
1918 use the send queue provided by tinymail and some
1920 ModestAccountMgr *account_mgr = modest_runtime_get_account_mgr();
1921 gchar *account_name = g_strdup(modest_window_get_active_account (MODEST_WINDOW(edit_window)));
1923 account_name = modest_account_mgr_get_default_account (account_mgr);
1925 if (!account_name) {
1926 g_printerr ("modest: no account found\n");
1930 MsgData *data = modest_msg_edit_window_get_msg_data (edit_window);
1932 if (!strcmp (account_name, MODEST_LOCAL_FOLDERS_ACCOUNT_ID)) {
1933 account_name = g_strdup (data->account_name);
1936 /* Get the currently-active transport account for this modest account: */
1937 TnyTransportAccount *transport_account =
1938 TNY_TRANSPORT_ACCOUNT(modest_tny_account_store_get_transport_account_for_open_connection
1939 (modest_runtime_get_account_store(),
1941 if (!transport_account) {
1942 g_printerr ("modest: no transport account found for '%s'\n", account_name);
1943 g_free (account_name);
1944 modest_msg_edit_window_free_msg_data (edit_window, data);
1948 gchar *from = modest_account_mgr_get_from_string (account_mgr, account_name);
1950 /* mail content checks and dialogs */
1951 if (data->subject == NULL || data->subject[0] == '\0') {
1952 GtkResponseType response;
1953 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (edit_window),
1954 _("mcen_nc_subject_is_empty_send"));
1955 if (response == GTK_RESPONSE_CANCEL) {
1956 g_free (account_name);
1961 if (data->plain_body == NULL || data->plain_body[0] == '\0') {
1962 GtkResponseType response;
1963 gchar *note_message;
1964 gchar *note_subject = data->subject;
1965 if (note_subject == NULL || note_subject[0] == '\0')
1966 note_subject = _("mail_va_no_subject");
1967 note_message = g_strdup_printf (_("emev_ni_ui_smtp_message_null"), note_subject);
1968 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (edit_window),
1970 g_free (note_message);
1971 if (response == GTK_RESPONSE_CANCEL) {
1972 g_free (account_name);
1977 modest_platform_information_banner (NULL, NULL, _("mcen_ib_outbox_waiting_to_be_sent"));
1979 /* Create the mail operation */
1980 ModestMailOperation *mail_operation = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_SEND, G_OBJECT(edit_window));
1981 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_operation);
1983 modest_mail_operation_send_new_mail (mail_operation,
1994 data->priority_flags);
1998 g_free (account_name);
1999 g_object_unref (G_OBJECT (transport_account));
2000 g_object_unref (G_OBJECT (mail_operation));
2002 modest_msg_edit_window_free_msg_data (edit_window, data);
2003 modest_msg_edit_window_set_sent (edit_window, TRUE);
2005 /* Save settings and close the window: */
2006 modest_ui_actions_on_close_window (NULL, MODEST_WINDOW (edit_window));
2010 modest_ui_actions_on_toggle_bold (GtkToggleAction *action,
2011 ModestMsgEditWindow *window)
2013 ModestMsgEditFormatState *format_state = NULL;
2015 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2016 g_return_if_fail (GTK_IS_TOGGLE_ACTION (action));
2018 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW (window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2021 format_state = modest_msg_edit_window_get_format_state (window);
2022 g_return_if_fail (format_state != NULL);
2024 format_state->bold = gtk_toggle_action_get_active (action);
2025 modest_msg_edit_window_set_format_state (window, format_state);
2026 g_free (format_state);
2031 modest_ui_actions_on_toggle_italics (GtkToggleAction *action,
2032 ModestMsgEditWindow *window)
2034 ModestMsgEditFormatState *format_state = NULL;
2036 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2037 g_return_if_fail (GTK_IS_TOGGLE_ACTION (action));
2039 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2042 format_state = modest_msg_edit_window_get_format_state (window);
2043 g_return_if_fail (format_state != NULL);
2045 format_state->italics = gtk_toggle_action_get_active (action);
2046 modest_msg_edit_window_set_format_state (window, format_state);
2047 g_free (format_state);
2052 modest_ui_actions_on_toggle_bullets (GtkToggleAction *action,
2053 ModestMsgEditWindow *window)
2055 ModestMsgEditFormatState *format_state = NULL;
2057 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2058 g_return_if_fail (GTK_IS_TOGGLE_ACTION (action));
2060 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW (window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2063 format_state = modest_msg_edit_window_get_format_state (window);
2064 g_return_if_fail (format_state != NULL);
2066 format_state->bullet = gtk_toggle_action_get_active (action);
2067 modest_msg_edit_window_set_format_state (window, format_state);
2068 g_free (format_state);
2073 modest_ui_actions_on_change_justify (GtkRadioAction *action,
2074 GtkRadioAction *selected,
2075 ModestMsgEditWindow *window)
2077 ModestMsgEditFormatState *format_state = NULL;
2078 GtkJustification value;
2080 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2082 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2085 value = gtk_radio_action_get_current_value (selected);
2087 format_state = modest_msg_edit_window_get_format_state (window);
2088 g_return_if_fail (format_state != NULL);
2090 format_state->justification = value;
2091 modest_msg_edit_window_set_format_state (window, format_state);
2092 g_free (format_state);
2096 modest_ui_actions_on_select_editor_color (GtkAction *action,
2097 ModestMsgEditWindow *window)
2099 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2100 g_return_if_fail (GTK_IS_ACTION (action));
2102 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2105 modest_msg_edit_window_select_color (window);
2109 modest_ui_actions_on_select_editor_background_color (GtkAction *action,
2110 ModestMsgEditWindow *window)
2112 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2113 g_return_if_fail (GTK_IS_ACTION (action));
2115 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2118 modest_msg_edit_window_select_background_color (window);
2122 modest_ui_actions_on_insert_image (GtkAction *action,
2123 ModestMsgEditWindow *window)
2125 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2126 g_return_if_fail (GTK_IS_ACTION (action));
2128 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2131 modest_msg_edit_window_insert_image (window);
2135 modest_ui_actions_on_attach_file (GtkAction *action,
2136 ModestMsgEditWindow *window)
2138 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2139 g_return_if_fail (GTK_IS_ACTION (action));
2141 modest_msg_edit_window_attach_file (window);
2145 modest_ui_actions_on_remove_attachments (GtkAction *action,
2146 ModestMsgEditWindow *window)
2148 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2149 g_return_if_fail (GTK_IS_ACTION (action));
2151 modest_msg_edit_window_remove_attachments (window, NULL);
2155 modest_ui_actions_new_folder_error_handler (ModestMailOperation *mail_op,
2158 ModestMainWindow *window = MODEST_MAIN_WINDOW (user_data);
2160 /* TODO: Note that folder creation might go wrong due to other
2161 * failures such as when the parent folder is non-writable. We can
2162 * query a GError* with modest_mail_operation_get_error(), but the
2163 * the error code (from tinymail) does not give us a clue about what
2164 * has gone wrong. We might use the error->message but it might come
2165 * from camel and not be suitable to show to the user directly. */
2166 modest_platform_information_banner (GTK_WIDGET (window), NULL,
2167 _CS("ckdg_ib_folder_already_exists"));
2169 /* modest_platform_information_banner (GTK_WIDGET (window), NULL,
2170 modest_mail_operation_get_error (mail_op)->message);*/
2175 modest_ui_actions_on_new_folder (GtkAction *action, ModestMainWindow *main_window)
2177 TnyFolderStore *parent_folder;
2178 GtkWidget *folder_view;
2180 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2182 folder_view = modest_main_window_get_child_widget (main_window,
2183 MODEST_WIDGET_TYPE_FOLDER_VIEW);
2187 parent_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
2189 if (parent_folder) {
2190 gboolean finished = FALSE;
2192 gchar *folder_name = NULL, *suggested_name = NULL;
2194 /* Run the new folder dialog */
2196 result = modest_platform_run_new_folder_dialog (GTK_WINDOW (main_window),
2201 g_free (suggested_name);
2202 suggested_name = NULL;
2204 if (result == GTK_RESPONSE_REJECT) {
2207 ModestMailOperation *mail_op;
2208 TnyFolder *new_folder = NULL;
2210 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_INFO,
2211 G_OBJECT(main_window),
2212 modest_ui_actions_new_folder_error_handler,
2215 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2217 new_folder = modest_mail_operation_create_folder (mail_op,
2219 (const gchar *) folder_name);
2222 folder_view = modest_main_window_get_child_widget (main_window,
2223 MODEST_WIDGET_TYPE_FOLDER_VIEW);
2225 modest_folder_view_select_folder (MODEST_FOLDER_VIEW(folder_view),
2229 g_object_unref (new_folder);
2232 g_object_unref (mail_op);
2235 suggested_name = folder_name;
2239 g_object_unref (parent_folder);
2244 modest_ui_actions_rename_folder_error_handler (ModestMailOperation *mail_op,
2247 GObject *win = modest_mail_operation_get_source (mail_op);
2248 const GError *error = NULL;
2249 const gchar *message = NULL;
2251 /* Get error message */
2252 error = modest_mail_operation_get_error (mail_op);
2253 if (error != NULL && error->message != NULL) {
2254 message = error->message;
2256 message = _("!!! FIXME: Unable to rename");
2259 /* Show notification dialog */
2260 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL, message);
2261 g_object_unref (win);
2265 modest_ui_actions_on_rename_folder (GtkAction *action,
2266 ModestMainWindow *main_window)
2268 TnyFolderStore *folder;
2269 GtkWidget *folder_view;
2270 GtkWidget *header_view;
2272 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2274 folder_view = modest_main_window_get_child_widget (main_window,
2275 MODEST_WIDGET_TYPE_FOLDER_VIEW);
2279 header_view = modest_main_window_get_child_widget (main_window,
2280 MODEST_WIDGET_TYPE_HEADER_VIEW);
2285 folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
2287 /* Offer the connection dialog if necessary: */
2288 if (!modest_platform_connect_and_wait_if_network_folderstore (NULL, folder)) {
2289 g_object_unref (G_OBJECT (folder));
2294 if (folder && TNY_IS_FOLDER (folder)) {
2297 const gchar *current_name;
2299 current_name = tny_folder_get_name (TNY_FOLDER (folder));
2300 response = modest_platform_run_rename_folder_dialog (GTK_WINDOW (main_window), NULL,
2301 current_name, &folder_name);
2303 if (response == GTK_RESPONSE_ACCEPT && strlen (folder_name) > 0) {
2304 ModestMailOperation *mail_op;
2307 modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_INFO,
2308 G_OBJECT(main_window),
2309 modest_ui_actions_rename_folder_error_handler,
2313 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2316 modest_header_view_clear (MODEST_HEADER_VIEW (header_view));
2318 modest_folder_view_select_folder (MODEST_FOLDER_VIEW(folder_view),
2319 TNY_FOLDER(folder), TRUE);
2321 modest_mail_operation_rename_folder (mail_op,
2322 TNY_FOLDER (folder),
2323 (const gchar *) folder_name);
2325 g_object_unref (mail_op);
2326 g_free (folder_name);
2328 g_object_unref (folder);
2333 modest_ui_actions_delete_folder_error_handler (ModestMailOperation *mail_op,
2336 GObject *win = modest_mail_operation_get_source (mail_op);
2338 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL,
2339 _("mail_in_ui_folder_delete_error"));
2340 g_object_unref (win);
2344 delete_folder (ModestMainWindow *main_window, gboolean move_to_trash)
2346 TnyFolderStore *folder;
2347 GtkWidget *folder_view;
2351 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2353 folder_view = modest_main_window_get_child_widget (main_window,
2354 MODEST_WIDGET_TYPE_FOLDER_VIEW);
2358 folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
2360 /* Show an error if it's an account */
2361 if (!TNY_IS_FOLDER (folder)) {
2362 modest_platform_run_information_dialog (GTK_WINDOW (main_window),
2363 _("mail_in_ui_folder_delete_error"));
2364 g_object_unref (G_OBJECT (folder));
2368 /* Offer the connection dialog if necessary: */
2369 if (!modest_platform_connect_and_wait_if_network_folderstore (NULL, folder)) {
2370 g_object_unref (G_OBJECT (folder));
2375 message = g_strdup_printf (_("mcen_nc_delete_folder_text"),
2376 tny_folder_get_name (TNY_FOLDER (folder)));
2377 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (main_window),
2378 (const gchar *) message);
2381 if (response == GTK_RESPONSE_OK) {
2382 ModestMailOperation *mail_op =
2383 modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_DELETE,
2384 G_OBJECT(main_window),
2385 modest_ui_actions_delete_folder_error_handler,
2388 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2390 modest_mail_operation_remove_folder (mail_op, TNY_FOLDER (folder), move_to_trash);
2391 g_object_unref (G_OBJECT (mail_op));
2394 g_object_unref (G_OBJECT (folder));
2398 modest_ui_actions_on_delete_folder (GtkAction *action,
2399 ModestMainWindow *main_window)
2401 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2403 delete_folder (main_window, FALSE);
2407 modest_ui_actions_on_move_folder_to_trash_folder (GtkAction *action, ModestMainWindow *main_window)
2409 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2411 delete_folder (main_window, TRUE);
2415 modest_ui_actions_on_password_requested (TnyAccountStore *account_store,
2416 const gchar* server_account_name,
2421 ModestMainWindow *main_window)
2423 g_return_if_fail(server_account_name);
2424 /* printf("DEBUG: %s: server_account_name=%s\n", __FUNCTION__, server_account_name); */
2426 /* Initalize output parameters: */
2433 #ifdef MODEST_PLATFORM_MAEMO
2434 /* Maemo uses a different (awkward) button order,
2435 * It should probably just use gtk_alternative_dialog_button_order ().
2437 GtkWidget *dialog = gtk_dialog_new_with_buttons (_("mail_ti_password_protected"),
2441 GTK_RESPONSE_ACCEPT,
2443 GTK_RESPONSE_REJECT,
2446 GtkWidget *dialog = gtk_dialog_new_with_buttons (_("mail_ti_password_protected"),
2450 GTK_RESPONSE_REJECT,
2452 GTK_RESPONSE_ACCEPT,
2454 #endif /* MODEST_PLATFORM_MAEMO */
2456 gtk_window_set_transient_for (GTK_WINDOW(dialog), GTK_WINDOW(main_window));
2458 gchar *server_name = modest_server_account_get_hostname (
2459 modest_runtime_get_account_mgr(), server_account_name);
2460 if (!server_name) {/* This happened once, though I don't know why. murrayc. */
2461 g_warning("%s: Could not get server name for server account '%s'", __FUNCTION__, server_account_name);
2466 /* This causes a warning because the logical ID has no %s in it,
2467 * though the translation does, but there is not much we can do about that: */
2468 gchar *txt = g_strdup_printf (_("mail_ia_password_info"), server_name);
2469 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), gtk_label_new(txt),
2472 g_free (server_name);
2476 gchar *initial_username = modest_server_account_get_username (
2477 modest_runtime_get_account_mgr(), server_account_name);
2479 GtkWidget *entry_username = gtk_entry_new ();
2480 if (initial_username)
2481 gtk_entry_set_text (GTK_ENTRY (entry_username), initial_username);
2482 /* Dim this if a connection has ever succeeded with this username,
2483 * as per the UI spec: */
2484 const gboolean username_known =
2485 modest_server_account_get_username_has_succeeded(
2486 modest_runtime_get_account_mgr(), server_account_name);
2487 gtk_widget_set_sensitive (entry_username, !username_known);
2489 #ifdef MODEST_PLATFORM_MAEMO
2490 /* Auto-capitalization is the default, so let's turn it off: */
2491 hildon_gtk_entry_set_input_mode (GTK_ENTRY (entry_username), HILDON_GTK_INPUT_MODE_FULL);
2493 /* Create a size group to be used by all captions.
2494 * Note that HildonCaption does not create a default size group if we do not specify one.
2495 * We use GTK_SIZE_GROUP_HORIZONTAL, so that the widths are the same. */
2496 GtkSizeGroup *sizegroup = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
2498 GtkWidget *caption = hildon_caption_new (sizegroup,
2499 _("mail_fi_username"), entry_username, NULL, HILDON_CAPTION_MANDATORY);
2500 gtk_widget_show (entry_username);
2501 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), caption,
2502 FALSE, FALSE, MODEST_MARGIN_HALF);
2503 gtk_widget_show (caption);
2505 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), entry_username,
2507 #endif /* MODEST_PLATFORM_MAEMO */
2510 GtkWidget *entry_password = gtk_entry_new ();
2511 gtk_entry_set_visibility (GTK_ENTRY(entry_password), FALSE);
2512 /* gtk_entry_set_invisible_char (GTK_ENTRY(entry_password), "*"); */
2514 #ifdef MODEST_PLATFORM_MAEMO
2515 /* Auto-capitalization is the default, so let's turn it off: */
2516 hildon_gtk_entry_set_input_mode (GTK_ENTRY (entry_password),
2517 HILDON_GTK_INPUT_MODE_FULL | HILDON_GTK_INPUT_MODE_INVISIBLE);
2519 caption = hildon_caption_new (sizegroup,
2520 _("mail_fi_password"), entry_password, NULL, HILDON_CAPTION_MANDATORY);
2521 gtk_widget_show (entry_password);
2522 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), caption,
2523 FALSE, FALSE, MODEST_MARGIN_HALF);
2524 gtk_widget_show (caption);
2525 g_object_unref (sizegroup);
2527 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), entry_password,
2529 #endif /* MODEST_PLATFORM_MAEMO */
2531 /* This is not in the Maemo UI spec:
2532 remember_pass_check = gtk_check_button_new_with_label (_("Remember password"));
2533 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), remember_pass_check,
2537 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
2539 if (gtk_dialog_run (GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT) {
2541 *username = g_strdup (gtk_entry_get_text (GTK_ENTRY(entry_username)));
2543 modest_server_account_set_username (
2544 modest_runtime_get_account_mgr(), server_account_name,
2547 const gboolean username_was_changed =
2548 (strcmp (*username, initial_username) != 0);
2549 if (username_was_changed) {
2550 g_warning ("%s: tinymail does not yet support changing the "
2551 "username in the get_password() callback.\n", __FUNCTION__);
2556 *password = g_strdup (gtk_entry_get_text (GTK_ENTRY(entry_password)));
2558 /* We do not save the password in the configuration,
2559 * because this function is only called for passwords that should
2560 * not be remembered:
2561 modest_server_account_set_password (
2562 modest_runtime_get_account_mgr(), server_account_name,
2581 /* This is not in the Maemo UI spec:
2582 if (gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (remember_pass_check)))
2588 gtk_widget_destroy (dialog);
2590 /* printf ("DEBUG: %s: cancel=%d\n", __FUNCTION__, *cancel); */
2594 modest_ui_actions_on_cut (GtkAction *action,
2595 ModestWindow *window)
2597 GtkWidget *focused_widget;
2599 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
2600 if (GTK_IS_EDITABLE (focused_widget)) {
2601 gtk_editable_cut_clipboard (GTK_EDITABLE(focused_widget));
2602 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
2603 GtkTextBuffer *buffer;
2604 GtkClipboard *clipboard;
2606 clipboard = gtk_clipboard_get (GDK_SELECTION_CLIPBOARD);
2607 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
2608 gtk_text_buffer_cut_clipboard (buffer, clipboard, TRUE);
2609 gtk_clipboard_set_can_store (clipboard, NULL, 0);
2610 } else if (MODEST_IS_HEADER_VIEW (focused_widget)) {
2611 modest_header_view_cut_selection (MODEST_HEADER_VIEW (focused_widget));
2612 } else if (MODEST_IS_FOLDER_VIEW (focused_widget)) {
2613 modest_folder_view_cut_selection (MODEST_FOLDER_VIEW (focused_widget));
2618 modest_ui_actions_on_copy (GtkAction *action,
2619 ModestWindow *window)
2621 GtkClipboard *clipboard;
2622 GtkWidget *focused_widget;
2624 clipboard = gtk_clipboard_get (GDK_SELECTION_CLIPBOARD);
2625 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
2627 if (GTK_IS_LABEL (focused_widget)) {
2628 gtk_clipboard_set_text (clipboard, gtk_label_get_text (GTK_LABEL (focused_widget)), -1);
2629 } else if (GTK_IS_EDITABLE (focused_widget)) {
2630 gtk_editable_copy_clipboard (GTK_EDITABLE(focused_widget));
2631 } else if (GTK_IS_HTML (focused_widget)) {
2632 gtk_html_copy (GTK_HTML (focused_widget));
2633 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
2634 GtkTextBuffer *buffer;
2635 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
2636 gtk_text_buffer_copy_clipboard (buffer, clipboard);
2637 gtk_clipboard_set_can_store (clipboard, NULL, 0);
2638 } else if (MODEST_IS_HEADER_VIEW (focused_widget)) {
2639 TnyList *header_list = modest_header_view_get_selected_headers (MODEST_HEADER_VIEW (focused_widget));
2640 TnyIterator *iter = tny_list_create_iterator (header_list);
2641 TnyHeader *header = TNY_HEADER (tny_iterator_get_current (iter));
2642 TnyFolder *folder = tny_header_get_folder (header);
2643 TnyAccount *account = tny_folder_get_account (folder);
2644 const gchar *proto_str = tny_account_get_proto (TNY_ACCOUNT (account));
2645 /* If it's POP then ask */
2646 gboolean ask = (modest_protocol_info_get_transport_store_protocol (proto_str) ==
2647 MODEST_PROTOCOL_STORE_POP) ? TRUE : FALSE;
2648 g_object_unref (account);
2649 g_object_unref (folder);
2650 g_object_unref (header);
2651 g_object_unref (iter);
2653 /* Check that the messages have been previously downloaded */
2654 gboolean continue_download = TRUE;
2656 continue_download = download_uncached_messages (header_list, GTK_WINDOW (window), FALSE);
2657 if (continue_download)
2658 modest_header_view_copy_selection (MODEST_HEADER_VIEW (focused_widget));
2659 g_object_unref (header_list);
2660 } else if (MODEST_IS_FOLDER_VIEW (focused_widget)) {
2661 modest_folder_view_copy_selection (MODEST_FOLDER_VIEW (focused_widget));
2664 /* Show information banner */
2665 modest_platform_information_banner (NULL, NULL, _CS("ecoc_ib_edwin_copied"));
2670 modest_ui_actions_on_undo (GtkAction *action,
2671 ModestWindow *window)
2673 ModestEmailClipboard *clipboard = NULL;
2675 if (MODEST_IS_MSG_EDIT_WINDOW (window)) {
2676 modest_msg_edit_window_undo (MODEST_MSG_EDIT_WINDOW (window));
2677 } else if (MODEST_IS_MAIN_WINDOW (window)) {
2678 /* Clear clipboard source */
2679 clipboard = modest_runtime_get_email_clipboard ();
2680 modest_email_clipboard_clear (clipboard);
2683 g_return_if_reached ();
2688 modest_ui_actions_on_redo (GtkAction *action,
2689 ModestWindow *window)
2691 if (MODEST_IS_MSG_EDIT_WINDOW (window)) {
2692 modest_msg_edit_window_redo (MODEST_MSG_EDIT_WINDOW (window));
2695 g_return_if_reached ();
2701 paste_msgs_cb (const GObject *object, gpointer user_data)
2703 g_return_if_fail (MODEST_IS_MAIN_WINDOW (object));
2704 g_return_if_fail (GTK_IS_WIDGET (user_data));
2706 /* destroy information note */
2707 gtk_widget_destroy (GTK_WIDGET(user_data));
2711 modest_ui_actions_on_paste (GtkAction *action,
2712 ModestWindow *window)
2714 GtkWidget *focused_widget = NULL;
2715 GtkWidget *inf_note = NULL;
2716 ModestMailOperation *mail_op = NULL;
2718 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
2719 if (GTK_IS_EDITABLE (focused_widget)) {
2720 gtk_editable_paste_clipboard (GTK_EDITABLE(focused_widget));
2721 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
2722 GtkTextBuffer *buffer;
2723 GtkClipboard *clipboard;
2725 clipboard = gtk_clipboard_get (GDK_SELECTION_CLIPBOARD);
2726 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
2727 gtk_text_buffer_paste_clipboard (buffer, clipboard, NULL, TRUE);
2728 } else if (MODEST_IS_FOLDER_VIEW (focused_widget)) {
2729 ModestEmailClipboard *clipboard = NULL;
2730 TnyFolder *src_folder = NULL;
2731 TnyFolderStore *folder_store = NULL;
2732 TnyList *data = NULL;
2733 gboolean delete = FALSE;
2735 /* Check clipboard source */
2736 clipboard = modest_runtime_get_email_clipboard ();
2737 if (modest_email_clipboard_cleared (clipboard))
2740 /* Get elements to paste */
2741 modest_email_clipboard_get_data (clipboard, &src_folder, &data, &delete);
2743 /* Create a new mail operation */
2744 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_RECEIVE, G_OBJECT(window));
2745 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2748 /* Get destination folder */
2749 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (focused_widget));
2751 /* Launch notification */
2752 inf_note = modest_platform_animation_banner (GTK_WIDGET (window), NULL,
2753 _CS("ckct_nw_pasting"));
2754 if (inf_note != NULL) {
2755 gtk_window_set_modal (GTK_WINDOW(inf_note), FALSE);
2756 gtk_widget_show (GTK_WIDGET(inf_note));
2759 /* transfer messages */
2761 modest_mail_operation_xfer_msgs (mail_op,
2763 TNY_FOLDER (folder_store),
2768 } else if (src_folder != NULL) {
2769 modest_mail_operation_xfer_folder (mail_op,
2779 g_object_unref (data);
2780 if (src_folder != NULL)
2781 g_object_unref (src_folder);
2782 if (folder_store != NULL)
2783 g_object_unref (folder_store);
2789 modest_ui_actions_on_select_all (GtkAction *action,
2790 ModestWindow *window)
2792 GtkWidget *focused_widget;
2794 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
2795 if (MODEST_IS_ATTACHMENTS_VIEW (focused_widget)) {
2796 modest_attachments_view_select_all (MODEST_ATTACHMENTS_VIEW (focused_widget));
2797 } else if (GTK_IS_LABEL (focused_widget)) {
2798 gtk_label_select_region (GTK_LABEL (focused_widget), 0, -1);
2799 } else if (GTK_IS_EDITABLE (focused_widget)) {
2800 gtk_editable_select_region (GTK_EDITABLE(focused_widget), 0, -1);
2801 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
2802 GtkTextBuffer *buffer;
2803 GtkTextIter start, end;
2805 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
2806 gtk_text_buffer_get_start_iter (buffer, &start);
2807 gtk_text_buffer_get_end_iter (buffer, &end);
2808 gtk_text_buffer_select_range (buffer, &start, &end);
2809 } else if (GTK_IS_HTML (focused_widget)) {
2810 gtk_html_select_all (GTK_HTML (focused_widget));
2811 } else if (MODEST_IS_MAIN_WINDOW (window)) {
2812 GtkWidget *header_view = focused_widget;
2813 GtkTreeSelection *selection = NULL;
2815 if (!(MODEST_IS_HEADER_VIEW (focused_widget)))
2816 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (window),
2817 MODEST_WIDGET_TYPE_HEADER_VIEW);
2819 /* Select all messages */
2820 selection = gtk_tree_view_get_selection (GTK_TREE_VIEW(header_view));
2821 gtk_tree_selection_select_all (selection);
2823 /* Set focuse on header view */
2824 gtk_widget_grab_focus (header_view);
2830 modest_ui_actions_on_mark_as_read (GtkAction *action,
2831 ModestWindow *window)
2833 g_return_if_fail (MODEST_IS_WINDOW(window));
2835 /* Mark each header as read */
2836 do_headers_action (window, headers_action_mark_as_read, NULL);
2840 modest_ui_actions_on_mark_as_unread (GtkAction *action,
2841 ModestWindow *window)
2843 g_return_if_fail (MODEST_IS_WINDOW(window));
2845 /* Mark each header as read */
2846 do_headers_action (window, headers_action_mark_as_unread, NULL);
2850 modest_ui_actions_on_change_zoom (GtkRadioAction *action,
2851 GtkRadioAction *selected,
2852 ModestWindow *window)
2856 value = gtk_radio_action_get_current_value (selected);
2857 if (MODEST_IS_WINDOW (window)) {
2858 modest_window_set_zoom (MODEST_WINDOW (window), ((gdouble)value)/100);
2862 void modest_ui_actions_msg_edit_on_change_priority (GtkRadioAction *action,
2863 GtkRadioAction *selected,
2864 ModestWindow *window)
2866 TnyHeaderFlags flags;
2867 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2869 flags = gtk_radio_action_get_current_value (selected);
2870 modest_msg_edit_window_set_priority_flags (MODEST_MSG_EDIT_WINDOW (window), flags);
2873 void modest_ui_actions_msg_edit_on_change_file_format (GtkRadioAction *action,
2874 GtkRadioAction *selected,
2875 ModestWindow *window)
2879 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2881 file_format = gtk_radio_action_get_current_value (selected);
2882 modest_msg_edit_window_set_file_format (MODEST_MSG_EDIT_WINDOW (window), file_format);
2887 modest_ui_actions_on_zoom_plus (GtkAction *action,
2888 ModestWindow *window)
2890 g_return_if_fail (MODEST_IS_WINDOW (window));
2892 modest_window_zoom_plus (MODEST_WINDOW (window));
2896 modest_ui_actions_on_zoom_minus (GtkAction *action,
2897 ModestWindow *window)
2899 g_return_if_fail (MODEST_IS_WINDOW (window));
2901 modest_window_zoom_minus (MODEST_WINDOW (window));
2905 modest_ui_actions_on_toggle_fullscreen (GtkToggleAction *toggle,
2906 ModestWindow *window)
2908 ModestWindowMgr *mgr;
2909 gboolean fullscreen, active;
2910 g_return_if_fail (MODEST_IS_WINDOW (window));
2912 mgr = modest_runtime_get_window_mgr ();
2914 active = (gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (toggle)))?1:0;
2915 fullscreen = modest_window_mgr_get_fullscreen_mode (mgr);
2917 if (active != fullscreen) {
2918 modest_window_mgr_set_fullscreen_mode (mgr, active);
2919 gtk_window_present (GTK_WINDOW (window));
2924 modest_ui_actions_on_change_fullscreen (GtkAction *action,
2925 ModestWindow *window)
2927 ModestWindowMgr *mgr;
2928 gboolean fullscreen;
2930 g_return_if_fail (MODEST_IS_WINDOW (window));
2932 mgr = modest_runtime_get_window_mgr ();
2933 fullscreen = modest_window_mgr_get_fullscreen_mode (mgr);
2934 modest_window_mgr_set_fullscreen_mode (mgr, !fullscreen);
2936 gtk_window_present (GTK_WINDOW (window));
2940 * Used by modest_ui_actions_on_details to call do_headers_action
2943 headers_action_show_details (TnyHeader *header,
2944 ModestWindow *window,
2951 dialog = modest_details_dialog_new_with_header (GTK_WINDOW (window), header);
2954 gtk_widget_show_all (dialog);
2955 gtk_dialog_run (GTK_DIALOG (dialog));
2957 gtk_widget_destroy (dialog);
2961 * Show the folder details in a ModestDetailsDialog widget
2964 show_folder_details (TnyFolder *folder,
2970 dialog = modest_details_dialog_new_with_folder (window, folder);
2973 gtk_widget_show_all (dialog);
2974 gtk_dialog_run (GTK_DIALOG (dialog));
2976 gtk_widget_destroy (dialog);
2980 * Show the header details in a ModestDetailsDialog widget
2983 modest_ui_actions_on_details (GtkAction *action,
2986 TnyList * headers_list;
2990 if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
2993 msg = modest_msg_view_window_get_message (MODEST_MSG_VIEW_WINDOW (win));
2996 g_object_unref (msg);
2998 headers_list = get_selected_headers (win);
3002 iter = tny_list_create_iterator (headers_list);
3004 header = TNY_HEADER (tny_iterator_get_current (iter));
3005 headers_action_show_details (header, win, NULL);
3006 g_object_unref (header);
3008 g_object_unref (iter);
3009 g_object_unref (headers_list);
3011 } else if (MODEST_IS_MAIN_WINDOW (win)) {
3012 GtkWidget *folder_view, *header_view;
3014 /* Check which widget has the focus */
3015 folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
3016 MODEST_WIDGET_TYPE_FOLDER_VIEW);
3017 if (gtk_widget_is_focus (folder_view)) {
3018 TnyFolderStore *folder_store
3019 = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
3020 if (!folder_store) {
3021 g_warning ("%s: No item was selected.\n", __FUNCTION__);
3024 /* Show only when it's a folder */
3025 /* This function should not be called for account items,
3026 * because we dim the menu item for them. */
3027 if (TNY_IS_FOLDER (folder_store)) {
3028 show_folder_details (TNY_FOLDER (folder_store), GTK_WINDOW (win));
3031 g_object_unref (folder_store);
3034 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
3035 MODEST_WIDGET_TYPE_HEADER_VIEW);
3036 /* Show details of each header */
3037 do_headers_action (win, headers_action_show_details, header_view);
3043 modest_ui_actions_on_toggle_show_cc (GtkToggleAction *toggle,
3044 ModestMsgEditWindow *window)
3046 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3048 modest_msg_edit_window_show_cc (window, gtk_toggle_action_get_active (toggle));
3052 modest_ui_actions_on_toggle_show_bcc (GtkToggleAction *toggle,
3053 ModestMsgEditWindow *window)
3055 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3057 modest_msg_edit_window_show_bcc (window, gtk_toggle_action_get_active (toggle));
3061 modest_ui_actions_toggle_folders_view (GtkAction *action,
3062 ModestMainWindow *main_window)
3064 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
3066 if (gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (action)))
3067 modest_main_window_set_style (main_window, MODEST_MAIN_WINDOW_STYLE_SPLIT);
3069 modest_main_window_set_style (main_window, MODEST_MAIN_WINDOW_STYLE_SIMPLE);
3073 modest_ui_actions_on_toggle_toolbar (GtkToggleAction *toggle,
3074 ModestWindow *window)
3076 gboolean active, fullscreen = FALSE;
3077 ModestWindowMgr *mgr;
3079 active = gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (toggle));
3081 /* Check if we want to toggle the toolbar vuew in fullscreen
3083 if (!strcmp (gtk_action_get_name (GTK_ACTION (toggle)),
3084 "ViewShowToolbarFullScreen")) {
3088 /* Toggle toolbar */
3089 mgr = modest_runtime_get_window_mgr ();
3090 modest_window_mgr_show_toolbars (mgr, active, fullscreen);
3094 modest_ui_actions_msg_edit_on_select_font (GtkAction *action,
3095 ModestMsgEditWindow *window)
3097 modest_msg_edit_window_select_font (window);
3101 modest_ui_actions_on_folder_display_name_changed (ModestFolderView *folder_view,
3102 const gchar *display_name,
3105 /* Do not change the application name if the widget has not
3106 the focus. This callback could be called even if the folder
3107 view has not the focus, because the handled signal could be
3108 emitted when the folder view is redrawn */
3109 if (gtk_widget_is_focus (GTK_WIDGET (folder_view))) {
3111 gtk_window_set_title (window, display_name);
3113 gtk_window_set_title (window, " ");
3118 modest_ui_actions_on_select_contacts (GtkAction *action, ModestMsgEditWindow *window)
3120 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3121 modest_msg_edit_window_select_contacts (window);
3125 modest_ui_actions_on_check_names (GtkAction *action, ModestMsgEditWindow *window)
3127 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3128 modest_msg_edit_window_check_names (window);
3133 create_move_to_dialog (GtkWindow *win,
3134 GtkWidget *folder_view,
3135 GtkWidget **tree_view)
3137 GtkWidget *dialog, *scroll;
3139 dialog = gtk_dialog_new_with_buttons (_("mcen_ti_moveto_folders_title"),
3141 GTK_DIALOG_MODAL | GTK_DIALOG_NO_SEPARATOR | GTK_DIALOG_DESTROY_WITH_PARENT,
3143 GTK_RESPONSE_ACCEPT,
3145 GTK_RESPONSE_REJECT,
3148 /* Create scrolled window */
3149 scroll = gtk_scrolled_window_new (NULL, NULL);
3150 gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scroll),
3151 GTK_POLICY_AUTOMATIC,
3152 GTK_POLICY_AUTOMATIC);
3154 /* Create folder view */
3155 *tree_view = modest_platform_create_folder_view (NULL);
3157 /* It could happen that we're trying to move a message from a
3158 window (msg window for example) after the main window was
3159 closed, so we can not just get the model of the folder
3161 if (MODEST_IS_FOLDER_VIEW (folder_view))
3162 gtk_tree_view_set_model (GTK_TREE_VIEW (*tree_view),
3163 gtk_tree_view_get_model (GTK_TREE_VIEW (folder_view)));
3165 modest_folder_view_update_model (MODEST_FOLDER_VIEW (*tree_view),
3166 TNY_ACCOUNT_STORE (modest_runtime_get_account_store ()));
3168 modest_folder_view_show_non_move_folders(MODEST_FOLDER_VIEW (*tree_view), FALSE);
3170 gtk_container_add (GTK_CONTAINER (scroll), *tree_view);
3172 /* Add scroll to dialog */
3173 gtk_box_pack_start (GTK_BOX (GTK_DIALOG (dialog)->vbox),
3174 scroll, FALSE, FALSE, 0);
3176 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
3178 /* Select INBOX or local account */
3179 modest_folder_view_select_first_inbox_or_local (MODEST_FOLDER_VIEW (*tree_view));
3185 * Returns TRUE if at least one of the headers of the list belongs to
3186 * a message that has been fully retrieved.
3189 has_retrieved_msgs (TnyList *list)
3192 gboolean found = FALSE;
3194 iter = tny_list_create_iterator (list);
3195 while (tny_iterator_is_done (iter) && !found) {
3197 TnyHeaderFlags flags;
3199 header = TNY_HEADER (tny_iterator_get_current (iter));
3200 flags = tny_header_get_flags (header);
3201 if (!(flags & TNY_HEADER_FLAG_PARTIAL))
3205 tny_iterator_next (iter);
3207 g_object_unref (iter);
3213 * Shows a confirmation dialog to the user when we're moving messages
3214 * from a remote server to the local storage. Returns the dialog
3215 * response. If it's other kind of movement the it always returns
3219 msgs_move_to_confirmation (GtkWindow *win,
3220 TnyFolder *dest_folder,
3223 gint response = GTK_RESPONSE_OK;
3225 /* If the destination is a local folder */
3226 if (modest_tny_folder_is_local_folder (dest_folder)) {
3227 TnyFolder *src_folder;
3231 /* Get source folder */
3232 iter = tny_list_create_iterator (headers);
3233 header = TNY_HEADER (tny_iterator_get_current (iter));
3234 src_folder = tny_header_get_folder (header);
3235 g_object_unref (header);
3236 g_object_unref (iter);
3238 /* if no src_folder, message may be an attahcment */
3239 if (src_folder == NULL)
3240 return GTK_RESPONSE_CANCEL;
3242 /* If the source is a remote folder */
3243 if (!modest_tny_folder_is_local_folder (src_folder)) {
3244 const gchar *message;
3246 if (has_retrieved_msgs (headers))
3247 message = ngettext ("mcen_nc_move_retrieve", "mcen_nc_move_retrieves",
3248 tny_list_get_length (headers));
3250 message = ngettext ("mcen_nc_move_header", "mcen_nc_move_headers",
3251 tny_list_get_length (headers));
3253 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (win),
3254 (const gchar *) message);
3256 g_object_unref (src_folder);
3264 transfer_msgs_from_viewer_cb (const GObject *object, gpointer user_data)
3266 ModestMsgViewWindow *self = NULL;
3267 gboolean last, first;
3269 g_return_if_fail (MODEST_IS_MSG_VIEW_WINDOW (object));
3270 self = MODEST_MSG_VIEW_WINDOW (object);
3272 last = modest_msg_view_window_last_message_selected (self);
3273 first = modest_msg_view_window_first_message_selected (self);
3275 /* No more messages to view, so close this window */
3276 /* gboolean ret_value; */
3277 /* g_signal_emit_by_name (G_OBJECT (self), "delete-event", NULL, &ret_value); */
3278 modest_ui_actions_on_close_window (NULL, MODEST_WINDOW(self));
3280 modest_msg_view_window_select_previous_message (self);
3282 modest_msg_view_window_select_next_message (self);
3286 modest_ui_actions_move_folder_error_handler (ModestMailOperation *mail_op,
3289 GObject *win = modest_mail_operation_get_source (mail_op);
3290 const GError *error = NULL;
3291 const gchar *message = NULL;
3293 /* Get error message */
3294 error = modest_mail_operation_get_error (mail_op);
3295 if (error != NULL && error->message != NULL) {
3296 message = error->message;
3298 message = _("mail_in_ui_folder_move_target_error");
3301 /* Show notification dialog */
3302 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL, message);
3303 g_object_unref (win);
3307 modest_ui_actions_send_receive_error_handler (ModestMailOperation *mail_op,
3310 GObject *win = modest_mail_operation_get_source (mail_op);
3311 const GError *error = modest_mail_operation_get_error (mail_op);
3313 g_return_if_fail (error != NULL);
3314 if (error->message != NULL)
3315 g_printerr ("modest: %s\n", error->message);
3317 g_printerr ("modest: unkonw error on send&receive operation");
3319 /* Show error message */
3320 /* if (modest_mail_operation_get_id (mail_op) == MODEST_MAIL_OPERATION_TYPE_RECEIVE) */
3321 /* modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL, */
3322 /* _CS("sfil_ib_unable_to_receive")); */
3324 /* modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL, */
3325 /* _CS("sfil_ib_unable_to_send")); */
3326 g_object_unref (win);
3330 open_msg_for_purge_cb (ModestMailOperation *mail_op,
3337 gint pending_purges = 0;
3338 gboolean some_purged = FALSE;
3339 ModestWindow *win = MODEST_WINDOW (user_data);
3341 /* If there was any error */
3342 if (!modest_ui_actions_msg_retrieval_check (mail_op, header, msg))
3345 /* Once the message has been retrieved for purging, we check if
3346 * it's all ok for purging */
3348 parts = tny_simple_list_new ();
3349 tny_mime_part_get_parts (TNY_MIME_PART (msg), parts);
3350 iter = tny_list_create_iterator (parts);
3352 while (!tny_iterator_is_done (iter)) {
3354 part = TNY_MIME_PART (tny_iterator_get_current (iter));
3355 if (tny_mime_part_is_attachment (part) || TNY_IS_MSG (part)) {
3356 if (tny_mime_part_is_purged (part))
3361 tny_iterator_next (iter);
3364 if (pending_purges>0) {
3366 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (win),_("mcen_nc_purge_file_text_inbox"));
3368 if (response == GTK_RESPONSE_OK) {
3369 modest_platform_information_banner (NULL, NULL, _("mcen_ib_removing_attachment"));
3370 tny_iterator_first (iter);
3371 while (!tny_iterator_is_done (iter)) {
3374 part = TNY_MIME_PART (tny_iterator_get_current (iter));
3375 if (tny_mime_part_is_attachment (part) || TNY_IS_MSG (part))
3376 tny_mime_part_set_purged (part);
3377 tny_iterator_next (iter);
3380 tny_msg_rewrite_cache (msg);
3383 modest_platform_information_banner (NULL, NULL, _("mail_ib_attachment_already_purged"));
3386 /* remove attachments */
3387 tny_iterator_first (iter);
3388 while (!tny_iterator_is_done (iter)) {
3391 part = TNY_MIME_PART (tny_iterator_get_current (iter));
3392 g_object_unref (part);
3393 tny_iterator_next (iter);
3396 g_object_unref (iter);
3397 g_object_unref (parts);
3401 modest_ui_actions_on_main_window_remove_attachments (GtkAction *action,
3402 ModestMainWindow *win)
3404 GtkWidget *header_view;
3405 TnyList *header_list;
3408 TnyHeaderFlags flags;
3409 ModestWindow *msg_view_window = NULL;
3412 g_return_if_fail (MODEST_IS_MAIN_WINDOW (win));
3414 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
3415 MODEST_WIDGET_TYPE_HEADER_VIEW);
3417 header_list = modest_header_view_get_selected_headers (MODEST_HEADER_VIEW (header_view));
3419 if (tny_list_get_length (header_list) == 1) {
3420 iter = tny_list_create_iterator (header_list);
3421 header = TNY_HEADER (tny_iterator_get_current (iter));
3422 g_object_unref (iter);
3427 found = modest_window_mgr_find_registered_header (modest_runtime_get_window_mgr (),
3428 header, &msg_view_window);
3429 flags = tny_header_get_flags (header);
3430 if (!(flags & TNY_HEADER_FLAG_CACHED))
3433 if (msg_view_window != NULL)
3434 modest_msg_view_window_remove_attachments (MODEST_MSG_VIEW_WINDOW (msg_view_window), TRUE);
3436 /* do nothing; uid was registered before, so window is probably on it's way */
3437 g_warning ("debug: header %p has already been registered", header);
3440 ModestMailOperation *mail_op = NULL;
3441 modest_window_mgr_register_header (modest_runtime_get_window_mgr (), header);
3442 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
3444 modest_ui_actions_get_msgs_full_error_handler,
3446 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
3447 modest_mail_operation_get_msg (mail_op, header, open_msg_for_purge_cb, win);
3449 g_object_unref (mail_op);
3452 g_object_unref (header);
3454 g_object_unref (header_list);
3458 * UI handler for the "Move to" action when invoked from the
3462 modest_ui_actions_on_main_window_move_to (GtkAction *action,
3463 ModestMainWindow *win)
3465 GtkWidget *dialog = NULL, *folder_view = NULL, *tree_view = NULL;
3466 GtkWidget *header_view = NULL;
3468 TnyFolderStore *folder_store = NULL;
3469 ModestMailOperation *mail_op = NULL;
3471 g_return_if_fail (MODEST_IS_MAIN_WINDOW (win));
3473 /* Get the folder view */
3474 folder_view = modest_main_window_get_child_widget (win,
3475 MODEST_WIDGET_TYPE_FOLDER_VIEW);
3477 TnyFolderStore *src_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
3479 /* Offer the connection dialog if necessary, if the source folder is in a networked account: */
3480 if (!modest_platform_connect_and_wait_if_network_folderstore (GTK_WINDOW (win), src_folder)) {
3482 g_object_unref (src_folder);
3488 /* Get header view */
3489 header_view = modest_main_window_get_child_widget (win,
3490 MODEST_WIDGET_TYPE_HEADER_VIEW);
3492 /* Create and run the dialog */
3493 dialog = create_move_to_dialog (GTK_WINDOW(win), folder_view, &tree_view);
3494 modest_folder_view_select_first_inbox_or_local (MODEST_FOLDER_VIEW (tree_view));
3495 result = gtk_dialog_run (GTK_DIALOG(dialog));
3496 modest_folder_view_show_non_move_folders(MODEST_FOLDER_VIEW (tree_view), TRUE);
3497 g_object_ref (tree_view);
3499 /* We do this to save an indentation level ;-) */
3500 if (result != GTK_RESPONSE_ACCEPT)
3503 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (tree_view));
3505 if (TNY_IS_ACCOUNT (folder_store) &&
3506 !MODEST_IS_TNY_LOCAL_FOLDERS_ACCOUNT (folder_store))
3509 /* Offer the connection dialog if necessary: */
3510 if (!modest_platform_connect_and_wait_if_network_folderstore (GTK_WINDOW (win), folder_store)) {
3514 /* Get folder or messages to transfer */
3515 if (gtk_widget_is_focus (folder_view)) {
3517 /* Clean folder on header view before moving it */
3518 modest_header_view_clear (MODEST_HEADER_VIEW (header_view));
3520 if (TNY_IS_FOLDER (src_folder)) {
3522 modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
3524 modest_ui_actions_move_folder_error_handler,
3526 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
3528 modest_mail_operation_xfer_folder (mail_op,
3529 TNY_FOLDER (src_folder),
3532 /* Unref mail operation */
3533 g_object_unref (G_OBJECT (mail_op));
3535 g_warning ("%s: src_folder is not a TnyFolder.\n", __FUNCTION__);
3538 if (gtk_widget_is_focus (header_view)) {
3539 TnyList *headers = NULL;
3542 /* TODO: Check for connection if the headers are on a network account. */
3543 headers = modest_header_view_get_selected_headers (MODEST_HEADER_VIEW (header_view));
3545 /* Ask for user confirmation */
3546 response = msgs_move_to_confirmation (GTK_WINDOW (win),
3547 TNY_FOLDER (folder_store),
3550 /* Transfer messages */
3551 if (response == GTK_RESPONSE_OK) {
3553 modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
3555 modest_ui_actions_move_folder_error_handler,
3557 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
3560 modest_mail_operation_xfer_msgs (mail_op,
3562 TNY_FOLDER (folder_store),
3567 g_object_unref (G_OBJECT (mail_op));
3569 g_object_unref (headers);
3575 g_object_unref (src_folder);
3578 g_object_unref (folder_store);
3580 gtk_widget_destroy (dialog);
3585 * UI handler for the "Move to" action when invoked from the
3586 * ModestMsgViewWindow
3589 modest_ui_actions_on_msg_view_window_move_to (GtkAction *action,
3590 ModestMsgViewWindow *win)
3592 GtkWidget *dialog, *folder_view, *tree_view = NULL;
3594 ModestMainWindow *main_window = NULL;
3595 TnyHeader *header = NULL;
3596 TnyList *headers = NULL;
3598 /* Get the folder view */
3599 main_window = MODEST_MAIN_WINDOW (modest_window_mgr_get_main_window (modest_runtime_get_window_mgr ()));
3601 folder_view = modest_main_window_get_child_widget (main_window,
3602 MODEST_WIDGET_TYPE_FOLDER_VIEW);
3606 /* Create and run the dialog */
3607 dialog = create_move_to_dialog (GTK_WINDOW (win), folder_view, &tree_view);
3608 result = gtk_dialog_run (GTK_DIALOG(dialog));
3609 modest_folder_view_show_non_move_folders(MODEST_FOLDER_VIEW (tree_view), TRUE);
3611 if (result == GTK_RESPONSE_ACCEPT) {
3612 TnyFolderStore *folder_store;
3615 /* Create header list */
3616 header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW (win));
3617 g_return_if_fail (header != NULL);
3619 /* Offer the connection dialog if necessary: */
3620 /* TODO: What's the extra g_object_ref() for? Isn't this leaking a ref? */
3621 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (g_object_ref (tree_view)));
3622 TnyFolder *header_folder = tny_header_get_folder(header);
3623 if (modest_platform_connect_and_wait_if_network_folderstore (NULL, folder_store) &&
3624 modest_platform_connect_and_wait_if_network_folderstore (NULL, TNY_FOLDER_STORE (header_folder))) {
3626 headers = tny_simple_list_new ();
3627 tny_list_prepend (headers, G_OBJECT (header));
3628 g_object_unref (header);
3630 /* Ask user for confirmation. MSG-NOT404 */
3631 response = msgs_move_to_confirmation (GTK_WINDOW (win),
3632 TNY_FOLDER (folder_store),
3635 /* Transfer current msg */
3636 if (response == GTK_RESPONSE_OK) {
3637 ModestMailOperation *mail_op;
3639 /* Create mail op */
3640 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_RECEIVE, G_OBJECT(win));
3641 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
3644 /* Transfer messages */
3645 modest_mail_operation_xfer_msgs (mail_op,
3647 TNY_FOLDER (folder_store),
3649 transfer_msgs_from_viewer_cb,
3651 g_object_unref (G_OBJECT (mail_op));
3656 g_object_unref (header_folder);
3659 g_object_unref (headers);
3662 g_object_unref (folder_store);
3665 gtk_widget_destroy (dialog);
3669 modest_ui_actions_on_move_to (GtkAction *action,
3672 g_return_if_fail (MODEST_IS_MAIN_WINDOW (win) ||
3673 MODEST_IS_MSG_VIEW_WINDOW (win));
3675 if (MODEST_IS_MAIN_WINDOW (win))
3676 modest_ui_actions_on_main_window_move_to (action,
3677 MODEST_MAIN_WINDOW (win));
3679 modest_ui_actions_on_msg_view_window_move_to (action,
3680 MODEST_MSG_VIEW_WINDOW (win));
3684 * Calls #HeadersFunc for each header already selected in the main
3685 * window or the message currently being shown in the msg view window
3688 do_headers_action (ModestWindow *win,
3692 TnyList *headers_list;
3698 headers_list = get_selected_headers (win);
3702 /* Get the folder */
3703 iter = tny_list_create_iterator (headers_list);
3704 header = TNY_HEADER (tny_iterator_get_current (iter));
3705 folder = tny_header_get_folder (header);
3706 g_object_unref (header);
3708 /* Call the function for each header */
3709 while (!tny_iterator_is_done (iter)) {
3710 header = TNY_HEADER (tny_iterator_get_current (iter));
3711 func (header, win, user_data);
3712 g_object_unref (header);
3713 tny_iterator_next (iter);
3716 /* Trick: do a poke status in order to speed up the signaling
3718 tny_folder_poke_status (folder);
3721 g_object_unref (folder);
3722 g_object_unref (iter);
3723 g_object_unref (headers_list);
3727 modest_ui_actions_view_attachment (GtkAction *action,
3728 ModestWindow *window)
3730 if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
3731 modest_msg_view_window_view_attachment (MODEST_MSG_VIEW_WINDOW (window), NULL);
3733 /* not supported window for this action */
3734 g_return_if_reached ();
3739 modest_ui_actions_save_attachments (GtkAction *action,
3740 ModestWindow *window)
3742 if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
3743 modest_msg_view_window_save_attachments (MODEST_MSG_VIEW_WINDOW (window), NULL);
3745 /* not supported window for this action */
3746 g_return_if_reached ();
3751 modest_ui_actions_remove_attachments (GtkAction *action,
3752 ModestWindow *window)
3754 if (MODEST_IS_MAIN_WINDOW (window)) {
3755 modest_ui_actions_on_main_window_remove_attachments (action, MODEST_MAIN_WINDOW (window));
3756 } else if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
3757 modest_msg_view_window_remove_attachments (MODEST_MSG_VIEW_WINDOW (window), FALSE);
3759 /* not supported window for this action */
3760 g_return_if_reached ();
3765 modest_ui_actions_on_settings (GtkAction *action,
3770 dialog = modest_platform_get_global_settings_dialog ();
3771 gtk_window_set_transient_for (GTK_WINDOW (dialog), GTK_WINDOW (win));
3772 gtk_widget_show_all (dialog);
3774 gtk_dialog_run (GTK_DIALOG (dialog));
3776 gtk_widget_destroy (dialog);
3780 modest_ui_actions_on_help (GtkAction *action,
3783 const gchar *help_id = NULL;
3785 if (MODEST_IS_MAIN_WINDOW (win)) {
3786 const gchar *action_name;
3787 action_name = gtk_action_get_name (action);
3789 if (!strcmp (action_name, "FolderViewCSMHelp") ||
3790 !strcmp (action_name, "HeaderViewCSMHelp")) {
3791 GtkWidget *folder_view;
3792 TnyFolderStore *folder_store;
3793 /* Get selected folder */
3794 folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
3795 MODEST_WIDGET_TYPE_FOLDER_VIEW);
3796 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
3798 /* Switch help_id */
3799 if (TNY_IS_FOLDER (folder_store)) {
3800 switch (tny_folder_get_folder_type (TNY_FOLDER (folder_store))) {
3801 case TNY_FOLDER_TYPE_NORMAL:
3802 help_id = "applications_email_userfolder";
3804 case TNY_FOLDER_TYPE_INBOX:
3805 help_id = "applications_email_inbox";
3807 case TNY_FOLDER_TYPE_OUTBOX:
3808 help_id = "applications_email_outbox";
3810 case TNY_FOLDER_TYPE_SENT:
3811 help_id = "applications_email_sent";
3813 case TNY_FOLDER_TYPE_DRAFTS:
3814 help_id = "applications_email_drafts";
3816 case TNY_FOLDER_TYPE_ARCHIVE:
3817 help_id = "applications_email_archive";
3820 help_id = "applications_email_mainview";
3823 help_id = "applications_email_mainview";
3825 g_object_unref (folder_store);
3827 help_id = "applications_email_mainview";
3829 } else if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
3830 help_id = "applications_email_viewer";
3831 } else if (MODEST_IS_MSG_EDIT_WINDOW (win))
3832 help_id = "applications_email_editor";
3834 modest_platform_show_help (GTK_WINDOW (win), help_id);
3838 modest_ui_actions_on_retrieve_msg_contents (GtkAction *action,
3839 ModestWindow *window)
3841 ModestMailOperation *mail_op;
3845 headers = get_selected_headers (window);
3849 /* Create mail operation */
3850 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
3852 modest_ui_actions_get_msgs_full_error_handler,
3854 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
3855 modest_mail_operation_get_msgs_full (mail_op, headers, NULL, NULL, NULL);
3858 g_object_unref (headers);
3859 g_object_unref (mail_op);
3863 modest_ui_actions_on_email_menu_activated (GtkAction *action,
3864 ModestWindow *window)
3866 g_return_if_fail (MODEST_IS_WINDOW (window));
3869 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
3873 modest_ui_actions_on_edit_menu_activated (GtkAction *action,
3874 ModestWindow *window)
3876 g_return_if_fail (MODEST_IS_WINDOW (window));
3879 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
3883 modest_ui_actions_on_view_menu_activated (GtkAction *action,
3884 ModestWindow *window)
3886 g_return_if_fail (MODEST_IS_WINDOW (window));
3889 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
3893 modest_ui_actions_on_tools_menu_activated (GtkAction *action,
3894 ModestWindow *window)
3896 g_return_if_fail (MODEST_IS_WINDOW (window));
3899 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
3903 modest_ui_actions_on_attachment_menu_activated (GtkAction *action,
3904 ModestWindow *window)
3906 g_return_if_fail (MODEST_IS_WINDOW (window));
3909 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
3913 modest_ui_actions_on_toolbar_csm_menu_activated (GtkAction *action,
3914 ModestWindow *window)
3916 g_return_if_fail (MODEST_IS_WINDOW (window));
3919 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
3923 modest_ui_actions_on_folder_view_csm_menu_activated (GtkAction *action,
3924 ModestWindow *window)
3926 g_return_if_fail (MODEST_IS_WINDOW (window));
3929 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
3933 modest_ui_actions_on_header_view_csm_menu_activated (GtkAction *action,
3934 ModestWindow *window)
3936 g_return_if_fail (MODEST_IS_WINDOW (window));
3939 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
3943 modest_ui_actions_check_toolbar_dimming_rules (ModestWindow *window)
3945 g_return_if_fail (MODEST_IS_WINDOW (window));
3948 modest_window_check_dimming_rules_group (window, "ModestToolbarDimmingRules");
3952 modest_ui_actions_on_search_messages (GtkAction *action, ModestWindow *window)
3954 g_return_if_fail (MODEST_IS_WINDOW (window));
3956 modest_platform_show_search_messages (GTK_WINDOW (window));
3960 modest_ui_actions_on_open_addressbook (GtkAction *action, ModestWindow *win)
3962 g_return_if_fail (MODEST_IS_WINDOW (win));
3963 modest_platform_show_addressbook (GTK_WINDOW (win));
3968 modest_ui_actions_on_toggle_find_in_page (GtkToggleAction *action,
3969 ModestWindow *window)
3971 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3973 modest_msg_edit_window_toggle_find_toolbar (MODEST_MSG_EDIT_WINDOW (window), gtk_toggle_action_get_active (action));
3977 _on_send_receive_progress_changed (ModestMailOperation *mail_op,
3978 ModestMailOperationState *state,
3981 g_return_if_fail (MODEST_IS_MAIN_WINDOW(user_data));
3983 /* Set send/receive operation finished */
3984 if (state->status != MODEST_MAIL_OPERATION_STATUS_IN_PROGRESS)
3985 modest_main_window_notify_send_receive_completed (MODEST_MAIN_WINDOW(user_data));