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>
48 #include <tny-camel-folder.h>
49 #include <tny-camel-imap-folder.h>
50 #include <tny-camel-pop-folder.h>
52 #ifdef MODEST_PLATFORM_MAEMO
53 #include "maemo/modest-osso-state-saving.h"
54 #include "maemo/modest-maemo-utils.h"
55 #include "maemo/modest-hildon-includes.h"
56 #endif /* MODEST_PLATFORM_MAEMO */
58 #include "widgets/modest-ui-constants.h"
59 #include <widgets/modest-main-window.h>
60 #include <widgets/modest-msg-view-window.h>
61 #include <widgets/modest-account-view-window.h>
62 #include <widgets/modest-details-dialog.h>
63 #include <widgets/modest-attachments-view.h>
64 #include "widgets/modest-folder-view.h"
65 #include "widgets/modest-global-settings-dialog.h"
66 #include "modest-connection-specific-smtp-window.h"
67 #include "modest-account-mgr-helpers.h"
68 #include "modest-mail-operation.h"
69 #include "modest-text-utils.h"
71 #ifdef MODEST_HAVE_EASYSETUP
72 #include "easysetup/modest-easysetup-wizard.h"
73 #endif /* MODEST_HAVE_EASYSETUP */
75 #include <modest-widget-memory.h>
76 #include <tny-error.h>
77 #include <tny-simple-list.h>
78 #include <tny-msg-view.h>
79 #include <tny-device.h>
80 #include <tny-merge-folder.h>
82 #include <gtkhtml/gtkhtml.h>
84 typedef struct _GetMsgAsyncHelper {
86 ModestMailOperation *mail_op;
93 typedef enum _ReplyForwardAction {
99 typedef struct _ReplyForwardHelper {
100 guint reply_forward_type;
101 ReplyForwardAction action;
103 GtkWidget *parent_window;
104 } ReplyForwardHelper;
106 typedef struct _MoveToHelper {
107 ModestMailOperation *mail_op;
111 typedef struct _PasteAsAttachmentHelper {
112 ModestMsgEditWindow *window;
114 } PasteAsAttachmentHelper;
118 * The do_headers_action uses this kind of functions to perform some
119 * action to each member of a list of headers
121 typedef void (*HeadersFunc) (TnyHeader *header, ModestWindow *win, gpointer user_data);
123 static void do_headers_action (ModestWindow *win,
127 static void open_msg_cb (ModestMailOperation *mail_op,
132 static void reply_forward_cb (ModestMailOperation *mail_op,
137 static void reply_forward (ReplyForwardAction action, ModestWindow *win);
139 static void folder_refreshed_cb (ModestMailOperation *mail_op,
143 static void _on_send_receive_progress_changed (ModestMailOperation *mail_op,
144 ModestMailOperationState *state,
147 static gint header_list_count_uncached_msgs (TnyList *header_list);
148 static gboolean connect_to_get_msg (
150 gint num_of_uncached_msgs);
152 static gboolean remote_folder_is_pop (const TnyFolderStore *folder);
154 static gboolean msgs_already_deleted_from_server ( TnyList *headers,
155 const TnyFolderStore *src_folder);
159 * This function checks whether a TnyFolderStore is a pop account
162 remote_folder_is_pop (const TnyFolderStore *folder)
164 const gchar *proto = NULL;
165 TnyAccount *account = NULL;
167 g_return_val_if_fail (TNY_IS_FOLDER_STORE(folder), FALSE);
169 if (TNY_IS_ACCOUNT (folder)) {
170 account = TNY_ACCOUNT(folder);
171 g_object_ref(account);
172 } else if (TNY_IS_FOLDER (folder)) {
173 account = tny_folder_get_account(TNY_FOLDER(folder));
176 proto = tny_account_get_proto(account);
177 g_object_unref (account);
180 (modest_protocol_info_get_transport_store_protocol (proto) == MODEST_PROTOCOL_STORE_POP);
184 * This functions checks whether if a list of messages are already
185 * deleted from the server: that is, if the server is a POP account
186 * and all messages are already cached.
189 msgs_already_deleted_from_server (TnyList *headers, const TnyFolderStore *src_folder)
191 g_return_val_if_fail (TNY_IS_FOLDER_STORE(src_folder), FALSE);
192 g_return_val_if_fail (TNY_IS_LIST(headers), FALSE);
194 gboolean src_is_pop = remote_folder_is_pop (src_folder);
195 gint uncached_msgs = header_list_count_uncached_msgs (headers);
197 return (src_is_pop && !uncached_msgs);
200 /* Show the account creation wizard dialog.
201 * returns: TRUE if an account was created. FALSE if the user cancelled.
204 modest_run_account_setup_wizard (ModestWindow *win)
206 gboolean result = FALSE;
209 wizard = modest_window_mgr_get_easysetup_dialog
210 (modest_runtime_get_window_mgr());
212 /* old wizard is active already; present it and
213 * act as if the user cancelled the non-existing
216 printf ("wizard already active\n");
219 /* there is no such wizard yet */
220 wizard = GTK_DIALOG(modest_easysetup_wizard_dialog_new ());
221 modest_window_mgr_set_easysetup_dialog
222 (modest_runtime_get_window_mgr(), GTK_DIALOG(wizard));
226 /* always present a main window in the background
227 * we do it here, so we cannot end up with to wizards (as this
228 * function might be called in modest_window_mgr_get_main_window as well */
230 win = modest_window_mgr_get_main_window (modest_runtime_get_window_mgr());
232 /* make sure the mainwindow is visible */
233 gtk_widget_show_all (GTK_WIDGET(win));
234 gtk_window_present (GTK_WINDOW(win));
237 gtk_window_set_transient_for (GTK_WINDOW (wizard), GTK_WINDOW (win));
239 /* Don't make this a modal window, because secondary windows will then
240 * be unusable, freezing the UI: */
241 /* gtk_window_set_modal (GTK_WINDOW (wizard), TRUE); */
243 gint dialog_response = gtk_dialog_run (GTK_DIALOG (wizard));
244 if (dialog_response == GTK_RESPONSE_CANCEL)
247 /* Check whether an account was created: */
248 result = modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE);
251 gtk_widget_destroy (GTK_WIDGET (wizard));
253 /* clear it from the window mgr */
254 modest_window_mgr_set_easysetup_dialog
255 (modest_runtime_get_window_mgr(), NULL);
262 modest_ui_actions_on_about (GtkAction *action, ModestWindow *win)
265 const gchar *authors[] = {
266 "Dirk-Jan C. Binnema <dirk-jan.binnema@nokia.com>",
269 about = gtk_about_dialog_new ();
270 gtk_about_dialog_set_name (GTK_ABOUT_DIALOG(about), PACKAGE_NAME);
271 gtk_about_dialog_set_version (GTK_ABOUT_DIALOG(about),PACKAGE_VERSION);
272 gtk_about_dialog_set_copyright (GTK_ABOUT_DIALOG(about),
273 _("Copyright (c) 2006, Nokia Corporation\n"
274 "All rights reserved."));
275 gtk_about_dialog_set_comments (GTK_ABOUT_DIALOG(about),
276 _("a modest e-mail client\n\n"
277 "design and implementation: Dirk-Jan C. Binnema\n"
278 "contributions from the fine people at KC and Ig\n"
279 "uses the tinymail email framework written by Philip van Hoof"));
280 gtk_about_dialog_set_authors (GTK_ABOUT_DIALOG(about), authors);
281 gtk_about_dialog_set_website (GTK_ABOUT_DIALOG(about), "http://modest.garage.maemo.org");
282 gtk_window_set_transient_for (GTK_WINDOW (about), GTK_WINDOW (win));
283 gtk_window_set_modal (GTK_WINDOW (about), TRUE);
285 gtk_dialog_run (GTK_DIALOG (about));
286 gtk_widget_destroy(about);
290 * Gets the list of currently selected messages. If the win is the
291 * main window, then it returns a newly allocated list of the headers
292 * selected in the header view. If win is the msg view window, then
293 * the value returned is a list with just a single header.
295 * The caller of this funcion must free the list.
298 get_selected_headers (ModestWindow *win)
300 if (MODEST_IS_MAIN_WINDOW(win)) {
301 GtkWidget *header_view;
303 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
304 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
305 return modest_header_view_get_selected_headers (MODEST_HEADER_VIEW(header_view));
307 } else if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
308 /* for MsgViewWindows, we simply return a list with one element */
310 TnyList *list = NULL;
312 header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW (win));
313 if (header != NULL) {
314 list = tny_simple_list_new ();
315 tny_list_prepend (list, G_OBJECT(header));
316 g_object_unref (G_OBJECT(header));
326 headers_action_mark_as_read (TnyHeader *header,
330 TnyHeaderFlags flags;
332 g_return_if_fail (TNY_IS_HEADER(header));
334 flags = tny_header_get_flags (header);
335 if (flags & TNY_HEADER_FLAG_SEEN) return;
336 tny_header_set_flags (header, TNY_HEADER_FLAG_SEEN);
340 headers_action_mark_as_unread (TnyHeader *header,
344 TnyHeaderFlags flags;
346 g_return_if_fail (TNY_IS_HEADER(header));
348 flags = tny_header_get_flags (header);
349 if (flags & TNY_HEADER_FLAG_SEEN) {
350 tny_header_unset_flags (header, TNY_HEADER_FLAG_SEEN);
354 /** A convenience method, because deleting a message is
355 * otherwise complicated, and it's best to change it in one place
358 void modest_do_message_delete (TnyHeader *header, ModestWindow *win)
360 ModestMailOperation *mail_op = NULL;
361 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_DELETE,
362 win ? G_OBJECT(win) : NULL);
363 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
366 /* Always delete. TODO: Move to trash still not supported */
367 modest_mail_operation_remove_msg (mail_op, header, FALSE);
368 g_object_unref (G_OBJECT (mail_op));
371 /** A convenience method, because deleting a message is
372 * otherwise complicated, and it's best to change it in one place
375 void modest_do_messages_delete (TnyList *headers, ModestWindow *win)
377 ModestMailOperation *mail_op = NULL;
378 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_DELETE,
379 win ? G_OBJECT(win) : NULL);
380 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
383 /* Always delete. TODO: Move to trash still not supported */
384 modest_mail_operation_remove_msgs (mail_op, headers, FALSE);
385 g_object_unref (G_OBJECT (mail_op));
389 /* headers_action_delete (TnyHeader *header, */
390 /* ModestWindow *win, */
391 /* gpointer user_data) */
393 /* modest_do_message_delete (header, win); */
397 /** After deleing a message that is currently visible in a window,
398 * show the next message from the list, or close the window if there are no more messages.
400 void modest_ui_actions_refresh_message_window_after_delete (ModestMsgViewWindow* win)
402 /* Close msg view window or select next */
403 if (modest_msg_view_window_last_message_selected (win) &&
404 modest_msg_view_window_first_message_selected (win)) {
405 modest_ui_actions_on_close_window (NULL, MODEST_WINDOW (win));
407 if (!modest_msg_view_window_select_next_message (win)) {
409 g_signal_emit_by_name (G_OBJECT (win), "delete-event", NULL, &ret_value);
415 modest_ui_actions_on_delete_message (GtkAction *action, ModestWindow *win)
417 TnyList *header_list = NULL;
418 TnyIterator *iter = NULL;
419 TnyHeader *header = NULL;
420 gchar *message = NULL;
423 ModestWindowMgr *mgr;
424 GtkWidget *header_view = NULL;
426 g_return_if_fail (MODEST_IS_WINDOW(win));
428 /* Check first if the header view has the focus */
429 if (MODEST_IS_MAIN_WINDOW (win)) {
431 modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
432 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
433 if (!gtk_widget_is_focus (header_view))
437 /* Get the headers, either from the header view (if win is the main window),
438 * or from the message view window: */
439 header_list = get_selected_headers (win);
440 if (!header_list) return;
442 /* Check if any of the headers are already opened, or in the process of being opened */
443 if (MODEST_IS_MAIN_WINDOW (win)) {
445 iter = tny_list_create_iterator (header_list);
447 mgr = modest_runtime_get_window_mgr ();
448 while (!tny_iterator_is_done (iter) && !found) {
449 header = TNY_HEADER (tny_iterator_get_current (iter));
451 found = modest_window_mgr_find_registered_header (mgr, header, NULL);
452 g_object_unref (header);
455 tny_iterator_next (iter);
457 g_object_unref (iter);
462 num = g_strdup_printf ("%d", tny_list_get_length (header_list));
463 msg = g_strdup_printf (_("mcen_nc_unable_to_delete_n_messages"), num);
465 modest_platform_run_information_dialog (GTK_WINDOW (win), (const gchar *) msg);
469 g_object_unref (header_list);
475 if (tny_list_get_length(header_list) == 1) {
476 iter = tny_list_create_iterator (header_list);
477 header = TNY_HEADER (tny_iterator_get_current (iter));
479 desc = g_strdup_printf ("%s", tny_header_get_subject (header));
480 g_object_unref (header);
483 g_object_unref (iter);
485 message = g_strdup_printf(ngettext("emev_nc_delete_message", "emev_nc_delete_messages",
486 tny_list_get_length(header_list)), desc);
488 /* Confirmation dialog */
489 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (win),
493 if (response == GTK_RESPONSE_OK) {
494 ModestWindow *main_window = NULL;
495 ModestWindowMgr *mgr = NULL;
496 GtkTreeModel *model = NULL;
497 GtkTreeSelection *sel = NULL;
498 GList *sel_list = NULL, *tmp = NULL;
499 GtkTreeRowReference *next_row_reference = NULL;
500 GtkTreeRowReference *prev_row_reference = NULL;
501 GtkTreePath *next_path = NULL;
502 GtkTreePath *prev_path = NULL;
505 /* Find last selected row */
506 if (MODEST_IS_MAIN_WINDOW (win)) {
507 model = gtk_tree_view_get_model (GTK_TREE_VIEW (header_view));
508 sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (header_view));
509 sel_list = gtk_tree_selection_get_selected_rows (sel, &model);
510 for (tmp=sel_list; tmp; tmp=tmp->next) {
511 if (tmp->next == NULL) {
512 prev_path = gtk_tree_path_copy((GtkTreePath *) tmp->data);
513 next_path = gtk_tree_path_copy((GtkTreePath *) tmp->data);
515 gtk_tree_path_prev (prev_path);
516 gtk_tree_path_next (next_path);
518 prev_row_reference = gtk_tree_row_reference_new (model, prev_path);
519 next_row_reference = gtk_tree_row_reference_new (model, next_path);
524 /* Disable window dimming management */
525 modest_window_disable_dimming (MODEST_WINDOW(win));
527 /* Remove each header. If it's a view window header_view == NULL */
528 modest_do_messages_delete (header_list, win);
530 /* Enable window dimming management */
531 gtk_tree_selection_unselect_all (sel);
532 modest_window_enable_dimming (MODEST_WINDOW(win));
534 if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
535 modest_ui_actions_refresh_message_window_after_delete (MODEST_MSG_VIEW_WINDOW (win));
537 /* Get main window */
538 mgr = modest_runtime_get_window_mgr ();
539 main_window = modest_window_mgr_get_main_window (mgr);
542 /* Move cursor to next row */
545 /* Select next or previous row */
546 if (gtk_tree_row_reference_valid (next_row_reference)) {
547 /* next_path = gtk_tree_row_reference_get_path (row_reference); */
548 gtk_tree_selection_select_path (sel, next_path);
550 else if (gtk_tree_row_reference_valid (prev_row_reference)) {
551 gtk_tree_selection_select_path (sel, prev_path);
555 if (next_row_reference != NULL)
556 gtk_tree_row_reference_free (next_row_reference);
557 if (next_path != NULL)
558 gtk_tree_path_free (next_path);
559 if (prev_row_reference != NULL)
560 gtk_tree_row_reference_free (prev_row_reference);
561 if (prev_path != NULL)
562 gtk_tree_path_free (prev_path);
566 printf ("DEBUG: %s: Error: code=%d, text=%s\n", __FUNCTION__, err->code, err->message);
570 /* Update toolbar dimming state */
571 modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (main_window));
574 g_list_foreach (sel_list, (GFunc) gtk_tree_path_free, NULL);
575 g_list_free (sel_list);
581 g_object_unref (header_list);
587 /* delete either message or folder, based on where we are */
589 modest_ui_actions_on_delete_message_or_folder (GtkAction *action, ModestWindow *win)
591 g_return_if_fail (MODEST_IS_WINDOW(win));
593 /* Check first if the header view has the focus */
594 if (MODEST_IS_MAIN_WINDOW (win)) {
596 w = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
597 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
598 if (gtk_widget_is_focus (w)) {
599 modest_ui_actions_on_delete_folder (action, MODEST_MAIN_WINDOW(win));
603 modest_ui_actions_on_delete_message (action, win);
609 modest_ui_actions_on_quit (GtkAction *action, ModestWindow *win)
611 ModestWindowMgr *mgr = NULL;
613 #ifdef MODEST_PLATFORM_MAEMO
614 modest_osso_save_state();
615 #endif /* MODEST_PLATFORM_MAEMO */
617 g_debug ("closing down, clearing %d item(s) from operation queue",
618 modest_mail_operation_queue_num_elements
619 (modest_runtime_get_mail_operation_queue()));
621 /* cancel all outstanding operations */
622 modest_mail_operation_queue_cancel_all
623 (modest_runtime_get_mail_operation_queue());
625 g_debug ("queue has been cleared");
628 /* Check if there are opened editing windows */
629 mgr = modest_runtime_get_window_mgr ();
630 modest_window_mgr_close_all_windows (mgr);
632 /* note: when modest-tny-account-store is finalized,
633 it will automatically set all network connections
636 /* gtk_main_quit (); */
640 modest_ui_actions_on_close_window (GtkAction *action, ModestWindow *win)
644 g_signal_emit_by_name (G_OBJECT (win), "delete-event", NULL, &ret_value);
646 /* if (MODEST_IS_MSG_VIEW_WINDOW (win)) { */
647 /* gtk_widget_destroy (GTK_WIDGET (win)); */
648 /* } else if (MODEST_IS_MSG_EDIT_WINDOW (win)) { */
649 /* gboolean ret_value; */
650 /* g_signal_emit_by_name (G_OBJECT (win), "delete-event", NULL, &ret_value); */
651 /* } else if (MODEST_IS_WINDOW (win)) { */
652 /* gtk_widget_destroy (GTK_WIDGET (win)); */
654 /* g_return_if_reached (); */
659 modest_ui_actions_on_add_to_contacts (GtkAction *action, ModestWindow *win)
661 GtkClipboard *clipboard = NULL;
662 gchar *selection = NULL;
664 clipboard = gtk_clipboard_get (GDK_SELECTION_PRIMARY);
665 selection = gtk_clipboard_wait_for_text (clipboard);
667 /* Question: why is the clipboard being used here?
668 * It doesn't really make a lot of sense. */
672 modest_address_book_add_address (selection);
678 modest_ui_actions_on_accounts (GtkAction *action, ModestWindow *win)
680 /* This is currently only implemented for Maemo */
681 #ifdef MODEST_PLATFORM_MAEMO /* Defined in config.h */
682 if (!modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE)) {
683 modest_run_account_setup_wizard (win);
686 /* Show the list of accounts: */
687 GtkDialog *account_win = GTK_DIALOG(modest_account_view_window_new ());
688 gtk_window_set_transient_for (GTK_WINDOW (account_win), GTK_WINDOW (win));
690 /* The accounts dialog must be modal */
691 gtk_window_set_modal (GTK_WINDOW (account_win), TRUE);
692 modest_maemo_show_dialog_and_forget (GTK_WINDOW (win), account_win);
695 GtkWidget *dialog, *label;
697 /* Create the widgets */
699 dialog = gtk_dialog_new_with_buttons ("Message",
701 GTK_DIALOG_DESTROY_WITH_PARENT,
705 label = gtk_label_new ("Hello World!");
707 /* Ensure that the dialog box is destroyed when the user responds. */
709 g_signal_connect_swapped (dialog, "response",
710 G_CALLBACK (gtk_widget_destroy),
713 /* Add the label, and show everything we've added to the dialog. */
715 gtk_container_add (GTK_CONTAINER (GTK_DIALOG(dialog)->vbox),
717 gtk_widget_show_all (dialog);
718 #endif /* MODEST_PLATFORM_MAEMO */
722 on_smtp_servers_window_hide (GtkWindow* window, gpointer user_data)
724 /* Save any changes. */
725 modest_connection_specific_smtp_window_save_server_accounts (
726 MODEST_CONNECTION_SPECIFIC_SMTP_WINDOW (window));
727 gtk_widget_destroy (GTK_WIDGET (window));
733 modest_ui_actions_on_smtp_servers (GtkAction *action, ModestWindow *win)
735 /* This is currently only implemented for Maemo,
736 * because it requires an API (libconic) to detect different connection
739 #ifdef MODEST_PLATFORM_MAEMO /* Defined in config.h */
741 /* Create the window if necessary: */
742 GtkWidget *specific_window = GTK_WIDGET (modest_connection_specific_smtp_window_new ());
743 modest_connection_specific_smtp_window_fill_with_connections (
744 MODEST_CONNECTION_SPECIFIC_SMTP_WINDOW (specific_window),
745 modest_runtime_get_account_mgr());
747 /* Show the window: */
748 gtk_window_set_transient_for (GTK_WINDOW (specific_window), GTK_WINDOW (win));
749 gtk_window_set_modal (GTK_WINDOW (specific_window), TRUE);
750 gtk_widget_show (specific_window);
752 /* Save changes when the window is hidden: */
753 g_signal_connect (specific_window, "hide",
754 G_CALLBACK (on_smtp_servers_window_hide), win);
755 #endif /* MODEST_PLATFORM_MAEMO */
759 modest_ui_actions_on_new_msg (GtkAction *action, ModestWindow *win)
761 ModestWindow *msg_win = NULL;
763 TnyFolder *folder = NULL;
764 gchar *account_name = NULL;
765 gchar *from_str = NULL;
766 /* GError *err = NULL; */
767 TnyAccount *account = NULL;
768 ModestWindowMgr *mgr;
769 gchar *signature = NULL, *blank_and_signature = NULL;
771 /* if there are no accounts yet, just show the wizard */
772 if (!modest_account_mgr_has_accounts (modest_runtime_get_account_mgr(), TRUE)) {
773 const gboolean created = modest_run_account_setup_wizard (win);
778 account_name = g_strdup (modest_window_get_active_account (win));
780 account_name = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr ());
782 g_printerr ("modest: no account found\n");
786 account = modest_tny_account_store_get_server_account (modest_runtime_get_account_store(),
788 TNY_ACCOUNT_TYPE_STORE);
790 g_printerr ("modest: failed to get tnyaccount for '%s'\n", account_name);
794 from_str = modest_account_mgr_get_from_string (modest_runtime_get_account_mgr(), account_name);
796 g_printerr ("modest: failed get from string for '%s'\n", account_name);
800 gboolean use_signature = FALSE;
801 signature = modest_account_mgr_get_signature (modest_runtime_get_account_mgr (), account_name, &use_signature);
804 blank_and_signature = g_strconcat ("\n", signature, NULL);
806 blank_and_signature = g_strdup ("");
811 msg = modest_tny_msg_new ("", from_str, "", "", "", blank_and_signature, NULL);
813 g_printerr ("modest: failed to create new msg\n");
817 folder = modest_tny_account_get_special_folder (account, TNY_FOLDER_TYPE_DRAFTS);
819 g_printerr ("modest: failed to find Drafts folder\n");
824 /* Create and register edit window */
825 /* This is destroyed by TODO. */
826 msg_win = modest_msg_edit_window_new (msg, account_name, FALSE);
827 mgr = modest_runtime_get_window_mgr ();
828 modest_window_mgr_register_window (mgr, msg_win);
831 gtk_window_set_transient_for (GTK_WINDOW (msg_win),
833 gtk_widget_show_all (GTK_WIDGET (msg_win));
836 g_free (account_name);
838 g_free (blank_and_signature);
840 g_object_unref (msg_win);
842 g_object_unref (G_OBJECT(account));
844 g_object_unref (G_OBJECT(msg));
846 g_object_unref (G_OBJECT(folder));
850 modest_ui_actions_msg_retrieval_check (ModestMailOperation *mail_op,
854 ModestMailOperationStatus status;
856 /* If there is no message or the operation was not successful */
857 status = modest_mail_operation_get_status (mail_op);
858 if (!msg || status != MODEST_MAIL_OPERATION_STATUS_SUCCESS) {
860 /* Remove the header from the preregistered uids */
861 modest_window_mgr_unregister_header (modest_runtime_get_window_mgr (),
871 open_msg_cb (ModestMailOperation *mail_op, TnyHeader *header, TnyMsg *msg, gpointer user_data)
873 ModestWindowMgr *mgr = NULL;
874 ModestWindow *parent_win = NULL;
875 ModestWindow *win = NULL;
876 TnyFolderType folder_type = TNY_FOLDER_TYPE_UNKNOWN;
877 gchar *account = NULL;
880 /* Do nothing if there was any problem with the mail
881 operation. The error will be shown by the error_handler of
882 the mail operation */
883 if (!modest_ui_actions_msg_retrieval_check (mail_op, header, msg))
886 parent_win = (ModestWindow *) modest_mail_operation_get_source (mail_op);
887 folder = tny_header_get_folder (header);
889 /* Mark header as read */
890 headers_action_mark_as_read (header, MODEST_WINDOW(parent_win), NULL);
893 account = g_strdup (modest_window_get_active_account (MODEST_WINDOW (parent_win)));
895 account = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
897 /* Gets folder type (OUTBOX headers will be opened in edit window */
898 if (modest_tny_folder_is_local_folder (folder))
899 folder_type = modest_tny_folder_get_local_or_mmc_folder_type (folder);
901 /* If the header is in the drafts folder then open the editor,
902 else the message view window */
903 if ((folder_type == TNY_FOLDER_TYPE_DRAFTS) ||
904 (folder_type == TNY_FOLDER_TYPE_OUTBOX)) {
905 /* we cannot edit without a valid account... */
906 if (!modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE)) {
907 const gboolean created = modest_run_account_setup_wizard(parent_win);
911 win = modest_msg_edit_window_new (msg, account, TRUE);
915 modest_platform_information_banner (NULL, NULL, _("mail_ib_opening_draft_message"));
918 gchar *uid = modest_tny_folder_get_header_unique_id (header);
920 if (MODEST_IS_MAIN_WINDOW (parent_win)) {
921 GtkWidget *header_view;
922 GtkTreeSelection *sel;
923 GList *sel_list = NULL;
926 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(parent_win),
927 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
929 sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (header_view));
930 sel_list = gtk_tree_selection_get_selected_rows (sel, &model);
932 if (sel_list != NULL) {
933 GtkTreeRowReference *row_reference;
935 row_reference = gtk_tree_row_reference_new (model, (GtkTreePath *) sel_list->data);
936 g_list_foreach (sel_list, (GFunc) gtk_tree_path_free, NULL);
937 g_list_free (sel_list);
939 win = modest_msg_view_window_new_with_header_model (
940 msg, account, (const gchar*) uid,
941 model, row_reference);
942 gtk_tree_row_reference_free (row_reference);
944 win = modest_msg_view_window_new_for_attachment (msg, account, (const gchar*) uid);
947 win = modest_msg_view_window_new_for_attachment (msg, account, (const gchar*) uid);
952 /* Register and show new window */
954 mgr = modest_runtime_get_window_mgr ();
955 modest_window_mgr_register_window (mgr, win);
956 g_object_unref (win);
957 gtk_window_set_transient_for (GTK_WINDOW (win), GTK_WINDOW (parent_win));
958 gtk_widget_show_all (GTK_WIDGET(win));
961 /* Update toolbar dimming state */
962 if (MODEST_IS_MAIN_WINDOW (parent_win)) {
963 modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (parent_win));
969 g_object_unref (parent_win);
970 g_object_unref (folder);
974 modest_ui_actions_get_msgs_full_error_handler (ModestMailOperation *mail_op,
978 GObject *win = modest_mail_operation_get_source (mail_op);
980 error = modest_mail_operation_get_error (mail_op);
981 /* printf ("DEBUG: %s: Error: code=%d, text=%s\n", __FUNCTION__, error->code, error->message); */
983 if (error->code == MODEST_MAIL_OPERATION_ERROR_MESSAGE_SIZE_LIMIT) {
985 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL,
988 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL,
989 _("mail_ni_ui_folder_get_msg_folder_error"));
993 g_object_unref (win);
997 * This function is used by both modest_ui_actions_on_open and
998 * modest_ui_actions_on_header_activated. This way we always do the
999 * same when trying to open messages.
1002 _modest_ui_actions_open (TnyList *headers, ModestWindow *win)
1004 ModestWindowMgr *mgr = NULL;
1005 TnyIterator *iter = NULL;
1006 ModestMailOperation *mail_op = NULL;
1007 TnyList *not_opened_headers = NULL;
1008 TnyHeaderFlags flags = 0;
1010 g_return_if_fail (headers != NULL);
1012 /* Check that only one message is selected for opening */
1013 if (tny_list_get_length (headers) != 1) {
1014 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL,
1015 _("mcen_ib_select_one_message"));
1020 /* Look if we already have a message view for each header. If
1021 true, then remove the header from the list of headers to
1023 mgr = modest_runtime_get_window_mgr ();
1024 iter = tny_list_create_iterator (headers);
1025 not_opened_headers = tny_simple_list_new ();
1027 while (!tny_iterator_is_done (iter)) {
1029 ModestWindow *window = NULL;
1030 TnyHeader *header = NULL;
1031 gboolean found = FALSE;
1033 header = TNY_HEADER (tny_iterator_get_current (iter));
1035 flags = tny_header_get_flags (header);
1038 found = modest_window_mgr_find_registered_header (mgr, header, &window);
1040 /* Do not open again the message and present the
1041 window to the user */
1044 gtk_window_present (GTK_WINDOW (window));
1046 /* the header has been registered already, we don't do
1047 * anything but wait for the window to come up*/
1048 g_debug ("header %p already registered, waiting for window", header);
1050 tny_list_append (not_opened_headers, G_OBJECT (header));
1054 g_object_unref (header);
1056 tny_iterator_next (iter);
1058 g_object_unref (iter);
1061 /* If some messages would have to be downloaded, ask the user to
1062 * make a connection. It's generally easier to do this here (in the mainloop)
1063 * than later in a thread:
1065 if (tny_list_get_length (not_opened_headers) > 0) {
1067 gboolean found = FALSE;
1069 iter = tny_list_create_iterator (not_opened_headers);
1070 while (!tny_iterator_is_done (iter) && !found) {
1071 TnyHeader *header = TNY_HEADER (tny_iterator_get_current (iter));
1072 if (!(tny_header_get_flags (header) & TNY_HEADER_FLAG_CACHED))
1075 tny_iterator_next (iter);
1077 g_object_unref (header);
1079 g_object_unref (iter);
1081 if (found && !modest_platform_connect_and_wait (GTK_WINDOW (win), NULL)) {
1082 g_object_unref (not_opened_headers);
1087 /* Register the headers before actually creating the windows: */
1088 TnyIterator *iter_not_opened = tny_list_create_iterator (not_opened_headers);
1089 while (!tny_iterator_is_done (iter_not_opened)) {
1090 TnyHeader *header = TNY_HEADER (tny_iterator_get_current (iter_not_opened));
1092 modest_window_mgr_register_header (mgr, header);
1093 g_object_unref (header);
1096 tny_iterator_next (iter_not_opened);
1098 g_object_unref (iter_not_opened);
1099 iter_not_opened = NULL;
1101 /* Open each message */
1102 if (tny_list_get_length (not_opened_headers) > 0) {
1103 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
1105 modest_ui_actions_get_msgs_full_error_handler,
1107 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
1108 if (tny_list_get_length (not_opened_headers) > 1) {
1109 modest_mail_operation_get_msgs_full (mail_op,
1115 TnyIterator *iter = tny_list_create_iterator (not_opened_headers);
1116 TnyHeader *header = TNY_HEADER (tny_iterator_get_current (iter));
1117 modest_mail_operation_get_msg (mail_op, header, open_msg_cb, NULL);
1118 g_object_unref (header);
1119 g_object_unref (iter);
1121 g_object_unref (mail_op);
1125 if (not_opened_headers != NULL)
1126 g_object_unref (not_opened_headers);
1130 modest_ui_actions_on_open (GtkAction *action, ModestWindow *win)
1135 headers = get_selected_headers (win);
1140 _modest_ui_actions_open (headers, win);
1142 g_object_unref(headers);
1147 free_reply_forward_helper (gpointer data)
1149 ReplyForwardHelper *helper;
1151 helper = (ReplyForwardHelper *) data;
1152 g_free (helper->account_name);
1153 g_slice_free (ReplyForwardHelper, helper);
1157 reply_forward_cb (ModestMailOperation *mail_op, TnyHeader *header, TnyMsg *msg,
1161 ReplyForwardHelper *rf_helper;
1162 ModestWindow *msg_win = NULL;
1163 ModestEditType edit_type;
1165 TnyAccount *account = NULL;
1166 ModestWindowMgr *mgr = NULL;
1167 gchar *signature = NULL;
1169 /* If there was any error. The mail operation could be NULL,
1170 this means that we already have the message downloaded and
1171 that we didn't do a mail operation to retrieve it */
1172 if (mail_op && !modest_ui_actions_msg_retrieval_check (mail_op, header, msg))
1175 g_return_if_fail (user_data != NULL);
1176 rf_helper = (ReplyForwardHelper *) user_data;
1178 from = modest_account_mgr_get_from_string (modest_runtime_get_account_mgr(),
1179 rf_helper->account_name);
1180 if (modest_account_mgr_get_bool (modest_runtime_get_account_mgr(),
1181 rf_helper->account_name,
1182 MODEST_ACCOUNT_USE_SIGNATURE, FALSE)) {
1183 signature = modest_account_mgr_get_string (modest_runtime_get_account_mgr (),
1184 rf_helper->account_name,
1185 MODEST_ACCOUNT_SIGNATURE, FALSE);
1188 /* Create reply mail */
1189 switch (rf_helper->action) {
1192 modest_tny_msg_create_reply_msg (msg, header, from, signature,
1193 rf_helper->reply_forward_type,
1194 MODEST_TNY_MSG_REPLY_MODE_SENDER);
1196 case ACTION_REPLY_TO_ALL:
1198 modest_tny_msg_create_reply_msg (msg, header, from, signature, rf_helper->reply_forward_type,
1199 MODEST_TNY_MSG_REPLY_MODE_ALL);
1200 edit_type = MODEST_EDIT_TYPE_REPLY;
1202 case ACTION_FORWARD:
1204 modest_tny_msg_create_forward_msg (msg, from, signature, rf_helper->reply_forward_type);
1205 edit_type = MODEST_EDIT_TYPE_FORWARD;
1208 g_return_if_reached ();
1215 g_printerr ("modest: failed to create message\n");
1219 account = modest_tny_account_store_get_server_account (modest_runtime_get_account_store(),
1220 rf_helper->account_name,
1221 TNY_ACCOUNT_TYPE_STORE);
1223 g_printerr ("modest: failed to get tnyaccount for '%s'\n", rf_helper->account_name);
1227 /* Create and register the windows */
1228 msg_win = modest_msg_edit_window_new (new_msg, rf_helper->account_name, FALSE);
1229 mgr = modest_runtime_get_window_mgr ();
1230 modest_window_mgr_register_window (mgr, msg_win);
1232 if (rf_helper->parent_window != NULL) {
1233 gdouble parent_zoom;
1235 parent_zoom = modest_window_get_zoom (MODEST_WINDOW (rf_helper->parent_window));
1236 modest_window_set_zoom (msg_win, parent_zoom);
1239 /* Show edit window */
1240 gtk_widget_show_all (GTK_WIDGET (msg_win));
1244 g_object_unref (msg_win);
1246 g_object_unref (G_OBJECT (new_msg));
1248 g_object_unref (G_OBJECT (account));
1249 /* g_object_unref (msg); */
1250 free_reply_forward_helper (rf_helper);
1253 /* Checks a list of headers. If any of them are not currently
1254 * downloaded (CACHED) then returns TRUE else returns FALSE.
1257 header_list_count_uncached_msgs (TnyList *header_list)
1260 gint uncached_messages = 0;
1262 iter = tny_list_create_iterator (header_list);
1263 while (!tny_iterator_is_done (iter)) {
1266 header = TNY_HEADER (tny_iterator_get_current (iter));
1268 if (!(tny_header_get_flags (header) & TNY_HEADER_FLAG_CACHED))
1269 uncached_messages ++;
1270 g_object_unref (header);
1273 tny_iterator_next (iter);
1275 g_object_unref (iter);
1277 return uncached_messages;
1280 /* Returns FALSE if the user does not want to download the
1281 * messages. Returns TRUE if the user allowed the download.
1284 connect_to_get_msg (GtkWindow *win,
1285 gint num_of_uncached_msgs)
1287 /* Allways download if we are online. */
1288 if (tny_device_is_online (modest_runtime_get_device ()))
1291 /* If offline, then ask for user permission to download the messages */
1292 GtkResponseType response;
1293 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (win),
1294 ngettext("mcen_nc_get_msg",
1296 num_of_uncached_msgs));
1297 if (response == GTK_RESPONSE_CANCEL)
1300 return modest_platform_connect_and_wait(win, NULL);
1304 * Common code for the reply and forward actions
1307 reply_forward (ReplyForwardAction action, ModestWindow *win)
1309 ModestMailOperation *mail_op = NULL;
1310 TnyList *header_list = NULL;
1311 ReplyForwardHelper *rf_helper = NULL;
1312 guint reply_forward_type;
1313 gboolean continue_download = TRUE;
1314 gboolean do_retrieve = TRUE;
1316 g_return_if_fail (MODEST_IS_WINDOW(win));
1318 /* we need an account when editing */
1319 if (!modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE)) {
1320 const gboolean created = modest_run_account_setup_wizard (win);
1325 header_list = get_selected_headers (win);
1329 reply_forward_type =
1330 modest_conf_get_int (modest_runtime_get_conf (),
1331 (action == ACTION_FORWARD) ? MODEST_CONF_FORWARD_TYPE : MODEST_CONF_REPLY_TYPE,
1334 /* check if we need to download msg before asking about it */
1335 do_retrieve = (action == ACTION_FORWARD) ||
1336 (reply_forward_type != MODEST_TNY_MSG_REPLY_TYPE_CITE);
1339 gint num_of_unc_msgs;
1340 /* check that the messages have been previously downloaded */
1341 num_of_unc_msgs = header_list_count_uncached_msgs(header_list);
1342 /* If there are any uncached message ask the user
1343 * whether he/she wants to download them. */
1344 if (num_of_unc_msgs)
1345 continue_download = connect_to_get_msg (
1350 if (!continue_download) {
1351 g_object_unref (header_list);
1355 /* We assume that we can only select messages of the
1356 same folder and that we reply all of them from the
1357 same account. In fact the interface currently only
1358 allows single selection */
1361 rf_helper = g_slice_new0 (ReplyForwardHelper);
1362 rf_helper->reply_forward_type = reply_forward_type;
1363 rf_helper->action = action;
1364 rf_helper->account_name = g_strdup (modest_window_get_active_account (win));
1366 if ((win != NULL) && (MODEST_IS_WINDOW (win)))
1367 rf_helper->parent_window = GTK_WIDGET (win);
1368 if (!rf_helper->account_name)
1369 rf_helper->account_name =
1370 modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
1372 if (MODEST_IS_MSG_VIEW_WINDOW(win)) {
1375 /* Get header and message. Do not free them here, the
1376 reply_forward_cb must do it */
1377 msg = modest_msg_view_window_get_message (MODEST_MSG_VIEW_WINDOW(win));
1378 header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW(win));
1379 if (!msg || !header) {
1381 g_object_unref (msg);
1382 g_printerr ("modest: no message found\n");
1385 reply_forward_cb (NULL, header, msg, rf_helper);
1388 g_object_unref (header);
1393 /* Only reply/forward to one message */
1394 iter = tny_list_create_iterator (header_list);
1395 header = TNY_HEADER (tny_iterator_get_current (iter));
1396 g_object_unref (iter);
1399 /* Retrieve messages */
1401 mail_op = modest_mail_operation_new_with_error_handling (
1402 MODEST_MAIL_OPERATION_TYPE_RECEIVE,
1404 modest_ui_actions_get_msgs_full_error_handler,
1406 modest_mail_operation_queue_add (
1407 modest_runtime_get_mail_operation_queue (), mail_op);
1409 modest_mail_operation_get_msg (mail_op,
1414 g_object_unref(mail_op);
1416 /* we put a ref here to prevent double unref as the reply
1417 * forward callback unrefs the header at its end */
1418 reply_forward_cb (NULL, header, NULL, rf_helper);
1422 g_object_unref (header);
1428 g_object_unref (header_list);
1432 modest_ui_actions_on_reply (GtkAction *action, ModestWindow *win)
1434 g_return_if_fail (MODEST_IS_WINDOW(win));
1436 reply_forward (ACTION_REPLY, win);
1440 modest_ui_actions_on_forward (GtkAction *action, ModestWindow *win)
1442 g_return_if_fail (MODEST_IS_WINDOW(win));
1444 reply_forward (ACTION_FORWARD, win);
1448 modest_ui_actions_on_reply_all (GtkAction *action, ModestWindow *win)
1450 g_return_if_fail (MODEST_IS_WINDOW(win));
1452 reply_forward (ACTION_REPLY_TO_ALL, win);
1456 modest_ui_actions_on_next (GtkAction *action,
1457 ModestWindow *window)
1459 if (MODEST_IS_MAIN_WINDOW (window)) {
1460 GtkWidget *header_view;
1462 header_view = modest_main_window_get_child_widget (
1463 MODEST_MAIN_WINDOW(window),
1464 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
1468 modest_header_view_select_next (
1469 MODEST_HEADER_VIEW(header_view));
1470 } else if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
1471 modest_msg_view_window_select_next_message (
1472 MODEST_MSG_VIEW_WINDOW (window));
1474 g_return_if_reached ();
1479 modest_ui_actions_on_prev (GtkAction *action,
1480 ModestWindow *window)
1482 g_return_if_fail (MODEST_IS_WINDOW(window));
1484 if (MODEST_IS_MAIN_WINDOW (window)) {
1485 GtkWidget *header_view;
1486 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(window),
1487 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
1491 modest_header_view_select_prev (MODEST_HEADER_VIEW(header_view));
1492 } else if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
1493 modest_msg_view_window_select_previous_message (MODEST_MSG_VIEW_WINDOW (window));
1495 g_return_if_reached ();
1500 modest_ui_actions_on_sort (GtkAction *action,
1501 ModestWindow *window)
1503 g_return_if_fail (MODEST_IS_WINDOW(window));
1505 if (MODEST_IS_MAIN_WINDOW (window)) {
1506 GtkWidget *header_view;
1507 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(window),
1508 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
1510 modest_platform_information_banner (NULL, NULL, _CS("ckdg_ib_nothing_to_sort"));
1515 /* Show sorting dialog */
1516 modest_platform_run_sort_dialog (GTK_WINDOW (window), MODEST_SORT_HEADERS);
1521 new_messages_arrived (ModestMailOperation *self,
1522 TnyList *new_headers,
1525 ModestMainWindow *win = NULL;
1526 GtkWidget *folder_view = NULL;
1527 TnyFolderStore *folder = NULL;
1528 gboolean folder_empty = FALSE;
1530 g_return_if_fail (MODEST_IS_MAIN_WINDOW (user_data));
1531 win = MODEST_MAIN_WINDOW (user_data);
1533 /* Don't do anything if there are not new headers, this could
1534 happen if there was any problem with the mail operation */
1538 /* Set contents style of headers view */
1539 if (modest_main_window_get_contents_style (win) == MODEST_MAIN_WINDOW_CONTENTS_STYLE_EMPTY) {
1540 folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
1541 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
1542 folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1545 folder_empty = (tny_folder_get_all_count (TNY_FOLDER (folder)) == 0);
1548 modest_main_window_set_contents_style (win,
1549 MODEST_MAIN_WINDOW_CONTENTS_STYLE_HEADERS);
1552 /* Notify new messages have been downloaded */
1553 if (tny_list_get_length (new_headers) > 0) {
1554 TnyIterator *iter = tny_list_create_iterator (new_headers);
1556 TnyHeader *header = NULL;
1558 header = TNY_HEADER (tny_iterator_get_current (iter));
1559 modest_platform_on_new_header_received (header);
1560 g_object_unref (header);
1562 tny_iterator_next (iter);
1563 } while (!tny_iterator_is_done (iter));
1564 g_object_unref (iter);
1569 * This function performs the send & receive required actions. The
1570 * window is used to create the mail operation. Typically it should
1571 * always be the main window, but we pass it as argument in order to
1575 modest_ui_actions_do_send_receive (const gchar *account_name, ModestWindow *win)
1577 gchar *acc_name = NULL;
1578 ModestMailOperation *mail_op;
1579 TnyAccount *store_account = NULL;
1581 /* If no account name was provided then get the current account, and if
1582 there is no current account then pick the default one: */
1583 if (!account_name) {
1584 acc_name = g_strdup (modest_window_get_active_account(win));
1586 acc_name = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
1588 g_printerr ("modest: cannot get default account\n");
1592 acc_name = g_strdup (account_name);
1596 /* Ensure that we have a connection available */
1598 modest_tny_account_store_get_server_account (modest_runtime_get_account_store (),
1600 TNY_ACCOUNT_TYPE_STORE);
1601 if (!modest_platform_connect_and_wait (NULL, TNY_ACCOUNT (store_account))) {
1602 g_object_unref (store_account);
1605 g_object_unref (store_account);
1607 /* Set send/receive operation in progress */
1608 modest_main_window_notify_send_receive_initied (MODEST_MAIN_WINDOW(win));
1610 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
1612 modest_ui_actions_send_receive_error_handler,
1615 g_signal_connect (G_OBJECT(mail_op), "progress-changed",
1616 G_CALLBACK (_on_send_receive_progress_changed),
1619 /* Send & receive. */
1620 /* TODO: The spec wants us to first do any pending deletions, before receiving. */
1621 /* Receive and then send. The operation is tagged initially as
1622 a receive operation because the account update performs a
1623 receive and then a send. The operation changes its type
1624 internally, so the progress objects will receive the proper
1625 progress information */
1626 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
1627 modest_mail_operation_update_account (mail_op, acc_name, new_messages_arrived, win);
1628 g_object_unref (G_OBJECT (mail_op));
1636 modest_ui_actions_do_cancel_send (const gchar *account_name,
1639 TnyTransportAccount *transport_account;
1640 TnySendQueue *send_queue = NULL;
1641 GError *error = NULL;
1643 /* Get transport account */
1645 TNY_TRANSPORT_ACCOUNT(modest_tny_account_store_get_server_account
1646 (modest_runtime_get_account_store(),
1648 TNY_ACCOUNT_TYPE_TRANSPORT));
1649 if (!transport_account) {
1650 g_printerr ("modest: no transport account found for '%s'\n", account_name);
1655 send_queue = TNY_SEND_QUEUE (modest_runtime_get_send_queue (transport_account));
1656 if (!TNY_IS_SEND_QUEUE(send_queue)) {
1657 g_set_error (&error, MODEST_MAIL_OPERATION_ERROR,
1658 MODEST_MAIL_OPERATION_ERROR_ITEM_NOT_FOUND,
1659 "modest: could not find send queue for account\n");
1661 /* Keeep messages in outbox folder */
1662 tny_send_queue_cancel (send_queue, FALSE, &error);
1666 if (transport_account != NULL)
1667 g_object_unref (G_OBJECT (transport_account));
1671 modest_ui_actions_cancel_send_all (ModestWindow *win)
1673 GSList *account_names, *iter;
1675 account_names = modest_account_mgr_account_names (modest_runtime_get_account_mgr(),
1678 iter = account_names;
1680 modest_ui_actions_do_cancel_send ((const char*) iter->data, win);
1681 iter = g_slist_next (iter);
1684 modest_account_mgr_free_account_names (account_names);
1685 account_names = NULL;
1689 modest_ui_actions_cancel_send (GtkAction *action, ModestWindow *win)
1692 /* Check if accounts exist */
1693 gboolean accounts_exist =
1694 modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE);
1696 /* If not, allow the user to create an account before trying to send/receive. */
1697 if (!accounts_exist)
1698 modest_ui_actions_on_accounts (NULL, win);
1700 /* Cancel all sending operaitons */
1701 modest_ui_actions_cancel_send_all (win);
1705 * Refreshes all accounts. This function will be used by automatic
1709 modest_ui_actions_do_send_receive_all (ModestWindow *win)
1711 GSList *account_names, *iter;
1713 account_names = modest_account_mgr_account_names (modest_runtime_get_account_mgr(),
1716 iter = account_names;
1718 modest_ui_actions_do_send_receive ((const char*) iter->data, win);
1719 iter = g_slist_next (iter);
1722 modest_account_mgr_free_account_names (account_names);
1723 account_names = NULL;
1727 modest_do_refresh_current_folder(ModestWindow *win)
1729 /* Refresh currently selected folder. Note that if we only
1730 want to retreive the headers, then the refresh only will
1731 invoke a poke_status over all folders, i.e., only the
1732 total/unread count will be updated */
1733 if (MODEST_IS_MAIN_WINDOW (win)) {
1734 GtkWidget *header_view, *folder_view;
1735 TnyFolderStore *folder_store;
1737 /* Get folder and header view */
1739 modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
1740 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
1744 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
1746 if (folder_store && TNY_IS_FOLDER (folder_store)) {
1748 modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
1749 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
1751 /* We do not need to set the contents style
1752 because it hasn't changed. We also do not
1753 need to save the widget status. Just force
1755 modest_header_view_set_folder (MODEST_HEADER_VIEW(header_view),
1756 TNY_FOLDER (folder_store),
1757 folder_refreshed_cb,
1758 MODEST_MAIN_WINDOW (win));
1762 g_object_unref (folder_store);
1768 * Handler of the click on Send&Receive button in the main toolbar
1771 modest_ui_actions_on_send_receive (GtkAction *action, ModestWindow *win)
1773 /* Check if accounts exist */
1774 gboolean accounts_exist =
1775 modest_account_mgr_has_accounts(modest_runtime_get_account_mgr(), TRUE);
1777 /* If not, allow the user to create an account before trying to send/receive. */
1778 if (!accounts_exist)
1779 modest_ui_actions_on_accounts (NULL, win);
1781 modest_do_refresh_current_folder (win);
1783 /* Refresh the active account */
1784 modest_ui_actions_do_send_receive (NULL, win);
1789 modest_ui_actions_toggle_header_list_view (GtkAction *action, ModestMainWindow *main_window)
1792 GtkWidget *header_view;
1794 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1796 header_view = modest_main_window_get_child_widget (main_window,
1797 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
1801 conf = modest_runtime_get_conf ();
1803 /* what is saved/restored is depending on the style; thus; we save with
1804 * old style, then update the style, and restore for this new style
1806 modest_widget_memory_save (conf, G_OBJECT(header_view), MODEST_CONF_HEADER_VIEW_KEY);
1808 if (modest_header_view_get_style
1809 (MODEST_HEADER_VIEW(header_view)) == MODEST_HEADER_VIEW_STYLE_DETAILS)
1810 modest_header_view_set_style (MODEST_HEADER_VIEW(header_view),
1811 MODEST_HEADER_VIEW_STYLE_TWOLINES);
1813 modest_header_view_set_style (MODEST_HEADER_VIEW(header_view),
1814 MODEST_HEADER_VIEW_STYLE_DETAILS);
1816 modest_widget_memory_restore (conf, G_OBJECT(header_view),
1817 MODEST_CONF_HEADER_VIEW_KEY);
1822 modest_ui_actions_on_header_selected (ModestHeaderView *header_view,
1824 ModestMainWindow *main_window)
1826 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1827 g_return_if_fail (MODEST_IS_HEADER_VIEW (header_view));
1829 /* in the case the folder is empty, show the empty folder message and focus
1831 if (!header && gtk_widget_is_focus (GTK_WIDGET (header_view))) {
1832 if (modest_header_view_is_empty (header_view)) {
1833 TnyFolder *folder = modest_header_view_get_folder (header_view);
1834 GtkWidget *folder_view =
1835 modest_main_window_get_child_widget (main_window,
1836 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
1838 modest_folder_view_select_folder (MODEST_FOLDER_VIEW (folder_view), folder, FALSE);
1839 gtk_widget_grab_focus (GTK_WIDGET (folder_view));
1843 /* If no header has been selected then exit */
1848 if (!gtk_widget_is_focus (GTK_WIDGET(header_view)))
1849 gtk_widget_grab_focus (GTK_WIDGET(header_view));
1851 /* Update toolbar dimming state */
1852 modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (main_window));
1856 modest_ui_actions_on_header_activated (ModestHeaderView *header_view,
1858 ModestMainWindow *main_window)
1862 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1868 /* headers = tny_simple_list_new (); */
1869 /* tny_list_prepend (headers, G_OBJECT (header)); */
1870 headers = modest_header_view_get_selected_headers (header_view);
1872 _modest_ui_actions_open (headers, MODEST_WINDOW (main_window));
1874 g_object_unref (headers);
1878 set_active_account_from_tny_account (TnyAccount *account,
1879 ModestWindow *window)
1881 const gchar *server_acc_name = tny_account_get_id (account);
1883 /* We need the TnyAccount provided by the
1884 account store because that is the one that
1885 knows the name of the Modest account */
1886 TnyAccount *modest_server_account = modest_server_account =
1887 modest_tny_account_store_get_tny_account_by (modest_runtime_get_account_store (),
1888 MODEST_TNY_ACCOUNT_STORE_QUERY_ID,
1890 if (!modest_server_account) {
1891 g_warning ("%s: could not get tny account\n", __FUNCTION__);
1895 /* Update active account, but only if it's not a pseudo-account */
1896 if ((!modest_tny_account_is_virtual_local_folders(modest_server_account)) &&
1897 (!modest_tny_account_is_memory_card_account(modest_server_account))) {
1898 const gchar *modest_acc_name =
1899 modest_tny_account_get_parent_modest_account_name_for_server_account (modest_server_account);
1900 if (modest_acc_name)
1901 modest_window_set_active_account (window, modest_acc_name);
1904 g_object_unref (modest_server_account);
1909 folder_refreshed_cb (ModestMailOperation *mail_op,
1913 ModestMainWindow *win = NULL;
1914 GtkWidget *header_view;
1915 gboolean folder_empty = FALSE;
1916 gboolean all_marked_as_deleted = FALSE;
1918 g_return_if_fail (TNY_IS_FOLDER (folder));
1920 win = MODEST_MAIN_WINDOW (user_data);
1922 modest_main_window_get_child_widget(win, MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
1925 TnyFolder *current_folder;
1927 current_folder = modest_header_view_get_folder (MODEST_HEADER_VIEW (header_view));
1928 if (current_folder != NULL && folder != current_folder) {
1929 g_object_unref (current_folder);
1932 g_object_unref (current_folder);
1935 /* Check if folder is empty and set headers view contents style */
1936 folder_empty = (tny_folder_get_all_count (folder) == 0);
1937 all_marked_as_deleted = modest_header_view_is_empty (MODEST_HEADER_VIEW(header_view));
1938 if (folder_empty || all_marked_as_deleted)
1939 modest_main_window_set_contents_style (win,
1940 MODEST_MAIN_WINDOW_CONTENTS_STYLE_EMPTY);
1944 modest_ui_actions_on_folder_selection_changed (ModestFolderView *folder_view,
1945 TnyFolderStore *folder_store,
1947 ModestMainWindow *main_window)
1950 GtkWidget *header_view;
1952 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1954 header_view = modest_main_window_get_child_widget(main_window,
1955 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
1959 conf = modest_runtime_get_conf ();
1961 if (TNY_IS_ACCOUNT (folder_store)) {
1963 set_active_account_from_tny_account (TNY_ACCOUNT (folder_store), MODEST_WINDOW (main_window));
1965 /* Show account details */
1966 modest_main_window_set_contents_style (main_window, MODEST_MAIN_WINDOW_CONTENTS_STYLE_DETAILS);
1969 if (TNY_IS_FOLDER (folder_store) && selected) {
1971 /* Update the active account */
1972 TnyAccount *account = modest_tny_folder_get_account (TNY_FOLDER (folder_store));
1974 set_active_account_from_tny_account (account, MODEST_WINDOW (main_window));
1975 g_object_unref (account);
1979 /* Set the header style by default, it could
1980 be changed later by the refresh callback to
1982 modest_main_window_set_contents_style (main_window,
1983 MODEST_MAIN_WINDOW_CONTENTS_STYLE_HEADERS);
1985 /* Set folder on header view. This function
1986 will call tny_folder_refresh_async so we
1987 pass a callback that will be called when
1988 finished. We use that callback to set the
1989 empty view if there are no messages */
1990 modest_header_view_set_folder (MODEST_HEADER_VIEW(header_view),
1991 TNY_FOLDER (folder_store),
1992 folder_refreshed_cb,
1995 /* Restore configuration. We need to do this
1996 *after* the set_folder because the widget
1997 memory asks the header view about its
1999 modest_widget_memory_restore (modest_runtime_get_conf (),
2000 G_OBJECT(header_view),
2001 MODEST_CONF_HEADER_VIEW_KEY);
2003 /* Update the active account */
2004 //modest_window_set_active_account (MODEST_WINDOW (main_window), NULL);
2005 /* Save only if we're seeing headers */
2006 if (modest_main_window_get_contents_style (main_window) ==
2007 MODEST_MAIN_WINDOW_CONTENTS_STYLE_HEADERS)
2008 modest_widget_memory_save (conf, G_OBJECT (header_view),
2009 MODEST_CONF_HEADER_VIEW_KEY);
2010 modest_header_view_clear (MODEST_HEADER_VIEW(header_view));
2014 /* Update toolbar dimming state */
2015 modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (main_window));
2019 modest_ui_actions_on_item_not_found (ModestHeaderView *header_view,ModestItemType type,
2026 item = (type == MODEST_ITEM_TYPE_FOLDER) ? "folder" : "message";
2028 online = tny_device_is_online (modest_runtime_get_device());
2031 /* already online -- the item is simply not there... */
2032 dialog = gtk_message_dialog_new (GTK_WINDOW (win),
2034 GTK_MESSAGE_WARNING,
2036 _("The %s you selected cannot be found"),
2038 gtk_dialog_add_button (GTK_DIALOG (dialog),_("mcen_bd_dialog_ok"), GTK_RESPONSE_ACCEPT);
2039 gtk_dialog_run (GTK_DIALOG(dialog));
2041 dialog = gtk_dialog_new_with_buttons (_("Connection requested"),
2044 _("mcen_bd_dialog_cancel"),
2045 GTK_RESPONSE_REJECT,
2046 _("mcen_bd_dialog_ok"),
2047 GTK_RESPONSE_ACCEPT,
2049 txt = g_strdup_printf (_("This %s is not available in offline mode.\n"
2050 "Do you want to get online?"), item);
2051 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox),
2052 gtk_label_new (txt), FALSE, FALSE, 0);
2053 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
2056 gtk_window_set_default_size (GTK_WINDOW(dialog), 300, 300);
2057 if (gtk_dialog_run (GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT) {
2058 /* TODO: Comment about why is this commented out: */
2059 /* modest_platform_connect_and_wait (); */
2062 gtk_widget_destroy (dialog);
2066 modest_ui_actions_on_msg_link_hover (ModestMsgView *msgview, const gchar* link,
2069 /* g_message ("%s %s", __FUNCTION__, link); */
2074 modest_ui_actions_on_msg_link_clicked (ModestMsgView *msgview, const gchar* link,
2077 modest_platform_activate_uri (link);
2081 modest_ui_actions_on_msg_link_contextual (ModestMsgView *msgview, const gchar* link,
2084 modest_platform_show_uri_popup (link);
2088 modest_ui_actions_on_msg_attachment_clicked (ModestMsgView *msgview, TnyMimePart *mime_part,
2091 modest_msg_view_window_view_attachment (MODEST_MSG_VIEW_WINDOW (win), mime_part);
2095 modest_ui_actions_on_msg_recpt_activated (ModestMsgView *msgview,
2096 const gchar *address,
2099 /* g_message ("%s %s", __FUNCTION__, address); */
2103 modest_ui_actions_on_save_to_drafts (GtkWidget *widget, ModestMsgEditWindow *edit_window)
2105 TnyTransportAccount *transport_account;
2106 ModestMailOperation *mail_operation;
2108 gchar *account_name, *from;
2109 ModestAccountMgr *account_mgr;
2110 gchar *info_text = NULL;
2112 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW(edit_window));
2114 data = modest_msg_edit_window_get_msg_data (edit_window);
2116 account_mgr = modest_runtime_get_account_mgr();
2117 account_name = g_strdup(modest_window_get_active_account (MODEST_WINDOW(edit_window)));
2119 account_name = modest_account_mgr_get_default_account (account_mgr);
2120 if (!account_name) {
2121 g_printerr ("modest: no account found\n");
2122 modest_msg_edit_window_free_msg_data (edit_window, data);
2126 if (!strcmp (account_name, MODEST_LOCAL_FOLDERS_ACCOUNT_ID)) {
2127 account_name = g_strdup (data->account_name);
2131 TNY_TRANSPORT_ACCOUNT(modest_tny_account_store_get_server_account
2132 (modest_runtime_get_account_store(),
2134 TNY_ACCOUNT_TYPE_TRANSPORT));
2135 if (!transport_account) {
2136 g_printerr ("modest: no transport account found for '%s'\n", account_name);
2137 g_free (account_name);
2138 modest_msg_edit_window_free_msg_data (edit_window, data);
2141 from = modest_account_mgr_get_from_string (account_mgr, account_name);
2143 /* Create the mail operation */
2144 mail_operation = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_INFO, G_OBJECT(edit_window));
2145 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_operation);
2147 modest_mail_operation_save_to_drafts (mail_operation,
2159 data->priority_flags);
2162 g_free (account_name);
2163 g_object_unref (G_OBJECT (transport_account));
2164 g_object_unref (G_OBJECT (mail_operation));
2166 modest_msg_edit_window_free_msg_data (edit_window, data);
2168 info_text = g_strdup_printf (_("mail_va_saved_to_drafts"), _("mcen_me_folder_drafts"));
2169 modest_platform_information_banner (NULL, NULL, info_text);
2173 /* For instance, when clicking the Send toolbar button when editing a message: */
2175 modest_ui_actions_on_send (GtkWidget *widget, ModestMsgEditWindow *edit_window)
2177 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW(edit_window));
2179 if (!modest_msg_edit_window_check_names (edit_window, TRUE))
2182 /* Offer the connection dialog, if necessary: */
2183 if (!modest_platform_connect_and_wait (GTK_WINDOW (edit_window), NULL))
2186 /* FIXME: Code added just for testing. The final version will
2187 use the send queue provided by tinymail and some
2189 ModestAccountMgr *account_mgr = modest_runtime_get_account_mgr();
2190 gchar *account_name = g_strdup(modest_window_get_active_account (MODEST_WINDOW(edit_window)));
2192 account_name = modest_account_mgr_get_default_account (account_mgr);
2194 if (!account_name) {
2195 /* Run account setup wizard */
2196 const gboolean created = modest_run_account_setup_wizard(MODEST_WINDOW(edit_window));
2201 MsgData *data = modest_msg_edit_window_get_msg_data (edit_window);
2203 if (!strcmp (account_name, MODEST_LOCAL_FOLDERS_ACCOUNT_ID)) {
2204 account_name = g_strdup (data->account_name);
2207 /* Get the currently-active transport account for this modest account: */
2208 TnyTransportAccount *transport_account =
2209 TNY_TRANSPORT_ACCOUNT(modest_tny_account_store_get_transport_account_for_open_connection
2210 (modest_runtime_get_account_store(),
2212 if (!transport_account) {
2213 /* Run account setup wizard */
2214 const gboolean created = modest_run_account_setup_wizard(MODEST_WINDOW(edit_window));
2219 gchar *from = modest_account_mgr_get_from_string (account_mgr, account_name);
2221 /* Create the mail operation */
2222 ModestMailOperation *mail_operation = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_SEND, G_OBJECT(edit_window));
2223 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_operation);
2225 modest_mail_operation_send_new_mail (mail_operation,
2236 data->priority_flags);
2240 g_free (account_name);
2241 g_object_unref (G_OBJECT (transport_account));
2242 g_object_unref (G_OBJECT (mail_operation));
2244 modest_msg_edit_window_free_msg_data (edit_window, data);
2245 modest_msg_edit_window_set_sent (edit_window, TRUE);
2247 /* Save settings and close the window: */
2248 modest_ui_actions_on_close_window (NULL, MODEST_WINDOW (edit_window));
2252 modest_ui_actions_on_toggle_bold (GtkToggleAction *action,
2253 ModestMsgEditWindow *window)
2255 ModestMsgEditFormatState *format_state = NULL;
2257 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2258 g_return_if_fail (GTK_IS_TOGGLE_ACTION (action));
2260 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW (window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2263 format_state = modest_msg_edit_window_get_format_state (window);
2264 g_return_if_fail (format_state != NULL);
2266 format_state->bold = gtk_toggle_action_get_active (action);
2267 modest_msg_edit_window_set_format_state (window, format_state);
2268 g_free (format_state);
2273 modest_ui_actions_on_toggle_italics (GtkToggleAction *action,
2274 ModestMsgEditWindow *window)
2276 ModestMsgEditFormatState *format_state = NULL;
2278 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2279 g_return_if_fail (GTK_IS_TOGGLE_ACTION (action));
2281 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2284 format_state = modest_msg_edit_window_get_format_state (window);
2285 g_return_if_fail (format_state != NULL);
2287 format_state->italics = gtk_toggle_action_get_active (action);
2288 modest_msg_edit_window_set_format_state (window, format_state);
2289 g_free (format_state);
2294 modest_ui_actions_on_toggle_bullets (GtkToggleAction *action,
2295 ModestMsgEditWindow *window)
2297 ModestMsgEditFormatState *format_state = NULL;
2299 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2300 g_return_if_fail (GTK_IS_TOGGLE_ACTION (action));
2302 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW (window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2305 format_state = modest_msg_edit_window_get_format_state (window);
2306 g_return_if_fail (format_state != NULL);
2308 format_state->bullet = gtk_toggle_action_get_active (action);
2309 modest_msg_edit_window_set_format_state (window, format_state);
2310 g_free (format_state);
2315 modest_ui_actions_on_change_justify (GtkRadioAction *action,
2316 GtkRadioAction *selected,
2317 ModestMsgEditWindow *window)
2319 ModestMsgEditFormatState *format_state = NULL;
2320 GtkJustification value;
2322 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2324 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2327 value = gtk_radio_action_get_current_value (selected);
2329 format_state = modest_msg_edit_window_get_format_state (window);
2330 g_return_if_fail (format_state != NULL);
2332 format_state->justification = value;
2333 modest_msg_edit_window_set_format_state (window, format_state);
2334 g_free (format_state);
2338 modest_ui_actions_on_select_editor_color (GtkAction *action,
2339 ModestMsgEditWindow *window)
2341 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2342 g_return_if_fail (GTK_IS_ACTION (action));
2344 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2347 modest_msg_edit_window_select_color (window);
2351 modest_ui_actions_on_select_editor_background_color (GtkAction *action,
2352 ModestMsgEditWindow *window)
2354 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2355 g_return_if_fail (GTK_IS_ACTION (action));
2357 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2360 modest_msg_edit_window_select_background_color (window);
2364 modest_ui_actions_on_insert_image (GtkAction *action,
2365 ModestMsgEditWindow *window)
2367 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2368 g_return_if_fail (GTK_IS_ACTION (action));
2370 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
2373 modest_msg_edit_window_insert_image (window);
2377 modest_ui_actions_on_attach_file (GtkAction *action,
2378 ModestMsgEditWindow *window)
2380 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2381 g_return_if_fail (GTK_IS_ACTION (action));
2383 modest_msg_edit_window_offer_attach_file (window);
2387 modest_ui_actions_on_remove_attachments (GtkAction *action,
2388 ModestMsgEditWindow *window)
2390 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2391 g_return_if_fail (GTK_IS_ACTION (action));
2393 modest_msg_edit_window_remove_attachments (window, NULL);
2397 modest_ui_actions_new_folder_error_handler (ModestMailOperation *mail_op,
2400 ModestMainWindow *window = MODEST_MAIN_WINDOW (user_data);
2401 const GError *error = modest_mail_operation_get_error (mail_op);
2405 modest_platform_information_banner (GTK_WIDGET (window), NULL,
2406 modest_mail_operation_get_error (mail_op)->message);
2411 modest_ui_actions_create_folder(GtkWidget *parent_window,
2412 GtkWidget *folder_view)
2414 TnyFolderStore *parent_folder;
2416 parent_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
2418 if (parent_folder) {
2419 gboolean finished = FALSE;
2421 gchar *folder_name = NULL, *suggested_name = NULL;
2422 const gchar *proto_str = NULL;
2423 TnyAccount *account;
2425 if (TNY_IS_ACCOUNT (parent_folder))
2426 account = g_object_ref (parent_folder);
2428 account = tny_folder_get_account (TNY_FOLDER (parent_folder));
2429 proto_str = tny_account_get_proto (TNY_ACCOUNT (account));
2431 if (proto_str && modest_protocol_info_get_transport_store_protocol (proto_str) ==
2432 MODEST_PROTOCOL_STORE_POP) {
2434 hildon_banner_show_information (NULL, NULL, _("mail_in_ui_folder_create_error"));
2436 g_object_unref (account);
2438 /* Run the new folder dialog */
2440 result = modest_platform_run_new_folder_dialog (GTK_WINDOW (parent_window),
2445 g_free (suggested_name);
2446 suggested_name = NULL;
2448 if (result == GTK_RESPONSE_REJECT) {
2451 ModestMailOperation *mail_op;
2452 TnyFolder *new_folder = NULL;
2454 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_INFO,
2455 G_OBJECT(parent_window),
2456 modest_ui_actions_new_folder_error_handler,
2459 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2461 new_folder = modest_mail_operation_create_folder (mail_op,
2463 (const gchar *) folder_name);
2465 modest_folder_view_select_folder (MODEST_FOLDER_VIEW(folder_view),
2468 g_object_unref (new_folder);
2471 g_object_unref (mail_op);
2474 suggested_name = folder_name;
2478 g_object_unref (parent_folder);
2483 modest_ui_actions_on_new_folder (GtkAction *action, ModestMainWindow *main_window)
2485 GtkWidget *folder_view;
2487 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2489 folder_view = modest_main_window_get_child_widget (main_window,
2490 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
2494 modest_ui_actions_create_folder (GTK_WIDGET (main_window), folder_view);
2498 modest_ui_actions_rename_folder_error_handler (ModestMailOperation *mail_op,
2501 ModestMainWindow *window = MODEST_MAIN_WINDOW (user_data);
2502 const GError *error = NULL;
2503 const gchar *message = NULL;
2505 /* Get error message */
2506 error = modest_mail_operation_get_error (mail_op);
2508 g_return_if_reached ();
2510 switch (error->code) {
2511 case MODEST_MAIL_OPERATION_ERROR_FOLDER_EXISTS:
2512 message = _CS("ckdg_ib_folder_already_exists");
2515 g_return_if_reached ();
2518 modest_platform_information_banner (GTK_WIDGET (window), NULL, message);
2522 modest_ui_actions_on_rename_folder (GtkAction *action,
2523 ModestMainWindow *main_window)
2525 TnyFolderStore *folder;
2526 GtkWidget *folder_view;
2527 GtkWidget *header_view;
2529 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2531 folder_view = modest_main_window_get_child_widget (main_window,
2532 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
2536 header_view = modest_main_window_get_child_widget (main_window,
2537 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
2542 folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
2547 if (TNY_IS_FOLDER (folder)) {
2550 const gchar *current_name;
2551 TnyFolderStore *parent;
2552 gboolean do_rename = TRUE;
2554 current_name = tny_folder_get_name (TNY_FOLDER (folder));
2555 parent = tny_folder_get_folder_store (TNY_FOLDER (folder));
2556 response = modest_platform_run_rename_folder_dialog (GTK_WINDOW (main_window),
2557 parent, current_name,
2559 g_object_unref (parent);
2561 if (response != GTK_RESPONSE_ACCEPT || strlen (folder_name) == 0) {
2563 } else if (modest_platform_is_network_folderstore(folder) &&
2564 !tny_device_is_online (modest_runtime_get_device())) {
2565 TnyAccount *account = tny_folder_get_account(TNY_FOLDER(folder));
2566 do_rename = modest_platform_connect_and_wait(GTK_WINDOW(main_window), account);
2567 g_object_unref(account);
2571 ModestMailOperation *mail_op;
2572 GtkTreeSelection *sel = NULL;
2575 modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_INFO,
2576 G_OBJECT(main_window),
2577 modest_ui_actions_rename_folder_error_handler,
2580 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2583 /* Clear the headers view */
2584 sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (folder_view));
2585 gtk_tree_selection_unselect_all (sel);
2587 /* Select *after* the changes */
2588 modest_folder_view_select_folder (MODEST_FOLDER_VIEW(folder_view),
2589 TNY_FOLDER(folder), TRUE);
2591 /* Actually rename the folder */
2592 modest_mail_operation_rename_folder (mail_op,
2593 TNY_FOLDER (folder),
2594 (const gchar *) folder_name);
2596 g_object_unref (mail_op);
2597 g_free (folder_name);
2600 g_object_unref (folder);
2604 modest_ui_actions_delete_folder_error_handler (ModestMailOperation *mail_op,
2607 GObject *win = modest_mail_operation_get_source (mail_op);
2609 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL,
2610 _("mail_in_ui_folder_delete_error"));
2611 g_object_unref (win);
2615 delete_folder (ModestMainWindow *main_window, gboolean move_to_trash)
2617 TnyFolderStore *folder;
2618 GtkWidget *folder_view;
2621 gboolean do_delete = TRUE;
2623 g_return_if_fail (MODEST_IS_MAIN_WINDOW (main_window));
2625 folder_view = modest_main_window_get_child_widget (main_window,
2626 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
2630 folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
2632 /* Show an error if it's an account */
2633 if (!TNY_IS_FOLDER (folder)) {
2634 modest_platform_run_information_dialog (GTK_WINDOW (main_window),
2635 _("mail_in_ui_folder_delete_error"));
2636 g_object_unref (G_OBJECT (folder));
2641 message = g_strdup_printf (_("mcen_nc_delete_folder_text"),
2642 tny_folder_get_name (TNY_FOLDER (folder)));
2643 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (main_window),
2644 (const gchar *) message);
2647 if (response != GTK_RESPONSE_OK) {
2649 } else if (modest_platform_is_network_folderstore(folder) &&
2650 !tny_device_is_online (modest_runtime_get_device())) {
2651 TnyAccount *account = tny_folder_get_account(TNY_FOLDER(folder));
2652 do_delete = modest_platform_connect_and_wait(GTK_WINDOW(main_window), account);
2653 g_object_unref(account);
2657 ModestMailOperation *mail_op;
2658 GtkTreeSelection *sel;
2660 /* Unselect the folder before deleting it to free the headers */
2661 sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (folder_view));
2662 gtk_tree_selection_unselect_all (sel);
2664 /* Create the mail operation */
2666 modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_DELETE,
2667 G_OBJECT(main_window),
2668 modest_ui_actions_delete_folder_error_handler,
2671 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2673 modest_mail_operation_remove_folder (mail_op, TNY_FOLDER (folder), move_to_trash);
2674 g_object_unref (G_OBJECT (mail_op));
2677 g_object_unref (G_OBJECT (folder));
2681 modest_ui_actions_on_delete_folder (GtkAction *action,
2682 ModestMainWindow *main_window)
2684 GtkWidget *folder_view;
2685 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2687 delete_folder (main_window, FALSE);
2688 folder_view = modest_main_window_get_child_widget (main_window,
2689 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
2692 modest_folder_view_select_first_inbox_or_local (MODEST_FOLDER_VIEW (folder_view));
2696 modest_ui_actions_on_move_folder_to_trash_folder (GtkAction *action, ModestMainWindow *main_window)
2698 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2700 delete_folder (main_window, TRUE);
2705 show_error (GtkWidget *parent_widget, const gchar* text)
2707 hildon_banner_show_information(parent_widget, NULL, text);
2710 GtkDialog *dialog = GTK_DIALOG (hildon_note_new_information (parent_window, text)); */
2712 GtkDialog *dialog = GTK_DIALOG (gtk_message_dialog_new (parent_window,
2719 gtk_dialog_run (dialog);
2720 gtk_widget_destroy (GTK_WIDGET (dialog));
2725 modest_ui_actions_on_password_requested (TnyAccountStore *account_store,
2726 const gchar* server_account_name,
2731 ModestMainWindow *main_window)
2733 g_return_if_fail(server_account_name);
2734 /* printf("DEBUG: %s: server_account_name=%s\n", __FUNCTION__, server_account_name); */
2736 /* Initalize output parameters: */
2743 #ifdef MODEST_PLATFORM_MAEMO
2744 /* Maemo uses a different (awkward) button order,
2745 * It should probably just use gtk_alternative_dialog_button_order ().
2747 GtkWidget *dialog = gtk_dialog_new_with_buttons (_("mail_ti_password_protected"),
2750 _("mcen_bd_dialog_ok"),
2751 GTK_RESPONSE_ACCEPT,
2752 _("mcen_bd_dialog_cancel"),
2753 GTK_RESPONSE_REJECT,
2756 GtkWidget *dialog = gtk_dialog_new_with_buttons (_("mail_ti_password_protected"),
2760 GTK_RESPONSE_REJECT,
2762 GTK_RESPONSE_ACCEPT,
2764 #endif /* MODEST_PLATFORM_MAEMO */
2766 gtk_window_set_transient_for (GTK_WINDOW(dialog), GTK_WINDOW(main_window));
2768 gchar *server_name = modest_server_account_get_hostname (
2769 modest_runtime_get_account_mgr(), server_account_name);
2770 if (!server_name) {/* This happened once, though I don't know why. murrayc. */
2771 g_warning("%s: Could not get server name for server account '%s'", __FUNCTION__, server_account_name);
2776 /* This causes a warning because the logical ID has no %s in it,
2777 * though the translation does, but there is not much we can do about that: */
2778 gchar *txt = g_strdup_printf (_("mail_ia_password_info"), server_name);
2779 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), gtk_label_new(txt),
2782 g_free (server_name);
2786 gchar *initial_username = modest_server_account_get_username (
2787 modest_runtime_get_account_mgr(), server_account_name);
2789 GtkWidget *entry_username = gtk_entry_new ();
2790 if (initial_username)
2791 gtk_entry_set_text (GTK_ENTRY (entry_username), initial_username);
2792 /* Dim this if a connection has ever succeeded with this username,
2793 * as per the UI spec: */
2794 const gboolean username_known =
2795 modest_server_account_get_username_has_succeeded(
2796 modest_runtime_get_account_mgr(), server_account_name);
2797 gtk_widget_set_sensitive (entry_username, !username_known);
2799 #ifdef MODEST_PLATFORM_MAEMO
2800 /* Auto-capitalization is the default, so let's turn it off: */
2801 hildon_gtk_entry_set_input_mode (GTK_ENTRY (entry_username), HILDON_GTK_INPUT_MODE_FULL);
2803 /* Create a size group to be used by all captions.
2804 * Note that HildonCaption does not create a default size group if we do not specify one.
2805 * We use GTK_SIZE_GROUP_HORIZONTAL, so that the widths are the same. */
2806 GtkSizeGroup *sizegroup = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
2808 GtkWidget *caption = hildon_caption_new (sizegroup,
2809 _("mail_fi_username"), entry_username, NULL, HILDON_CAPTION_MANDATORY);
2810 gtk_widget_show (entry_username);
2811 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), caption,
2812 FALSE, FALSE, MODEST_MARGIN_HALF);
2813 gtk_widget_show (caption);
2815 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), entry_username,
2817 #endif /* MODEST_PLATFORM_MAEMO */
2820 GtkWidget *entry_password = gtk_entry_new ();
2821 gtk_entry_set_visibility (GTK_ENTRY(entry_password), FALSE);
2822 /* gtk_entry_set_invisible_char (GTK_ENTRY(entry_password), "*"); */
2824 #ifdef MODEST_PLATFORM_MAEMO
2825 /* Auto-capitalization is the default, so let's turn it off: */
2826 hildon_gtk_entry_set_input_mode (GTK_ENTRY (entry_password),
2827 HILDON_GTK_INPUT_MODE_FULL | HILDON_GTK_INPUT_MODE_INVISIBLE);
2829 caption = hildon_caption_new (sizegroup,
2830 _("mail_fi_password"), entry_password, NULL, HILDON_CAPTION_MANDATORY);
2831 gtk_widget_show (entry_password);
2832 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), caption,
2833 FALSE, FALSE, MODEST_MARGIN_HALF);
2834 gtk_widget_show (caption);
2835 g_object_unref (sizegroup);
2837 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), entry_password,
2839 #endif /* MODEST_PLATFORM_MAEMO */
2841 /* This is not in the Maemo UI spec:
2842 remember_pass_check = gtk_check_button_new_with_label (_("Remember password"));
2843 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), remember_pass_check,
2847 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
2849 if (gtk_dialog_run (GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT) {
2851 *username = g_strdup (gtk_entry_get_text (GTK_ENTRY(entry_username)));
2853 modest_server_account_set_username (
2854 modest_runtime_get_account_mgr(), server_account_name,
2857 const gboolean username_was_changed =
2858 (strcmp (*username, initial_username) != 0);
2859 if (username_was_changed) {
2860 g_warning ("%s: tinymail does not yet support changing the "
2861 "username in the get_password() callback.\n", __FUNCTION__);
2866 *password = g_strdup (gtk_entry_get_text (GTK_ENTRY(entry_password)));
2868 /* We do not save the password in the configuration,
2869 * because this function is only called for passwords that should
2870 * not be remembered:
2871 modest_server_account_set_password (
2872 modest_runtime_get_account_mgr(), server_account_name,
2881 show_error(GTK_WIDGET (main_window), _("mail_ib_login_cancelled"));
2893 /* This is not in the Maemo UI spec:
2894 if (gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (remember_pass_check)))
2900 gtk_widget_destroy (dialog);
2902 /* printf ("DEBUG: %s: cancel=%d\n", __FUNCTION__, *cancel); */
2906 modest_ui_actions_on_cut (GtkAction *action,
2907 ModestWindow *window)
2909 GtkWidget *focused_widget;
2910 GtkClipboard *clipboard;
2912 clipboard = gtk_clipboard_get (GDK_SELECTION_CLIPBOARD);
2913 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
2914 if (GTK_IS_EDITABLE (focused_widget)) {
2915 gtk_editable_cut_clipboard (GTK_EDITABLE(focused_widget));
2916 gtk_clipboard_set_can_store (clipboard, NULL, 0);
2917 gtk_clipboard_store (clipboard);
2918 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
2919 GtkTextBuffer *buffer;
2921 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
2922 gtk_text_buffer_cut_clipboard (buffer, clipboard, TRUE);
2923 gtk_clipboard_set_can_store (clipboard, NULL, 0);
2924 gtk_clipboard_store (clipboard);
2925 } else if (MODEST_IS_HEADER_VIEW (focused_widget)) {
2926 TnyList *header_list = modest_header_view_get_selected_headers (
2927 MODEST_HEADER_VIEW (focused_widget));
2928 gboolean continue_download = FALSE;
2929 gint num_of_unc_msgs;
2931 num_of_unc_msgs = header_list_count_uncached_msgs(header_list);
2933 if (num_of_unc_msgs)
2934 continue_download = connect_to_get_msg(
2935 GTK_WINDOW (window),
2938 if (num_of_unc_msgs == 0 || continue_download) {
2939 /* modest_platform_information_banner (
2940 NULL, NULL, _CS("mcen_ib_getting_items"));*/
2941 modest_header_view_cut_selection (
2942 MODEST_HEADER_VIEW (focused_widget));
2945 g_object_unref (header_list);
2946 } else if (MODEST_IS_FOLDER_VIEW (focused_widget)) {
2947 modest_folder_view_cut_selection (MODEST_FOLDER_VIEW (focused_widget));
2952 modest_ui_actions_on_copy (GtkAction *action,
2953 ModestWindow *window)
2955 GtkClipboard *clipboard;
2956 GtkWidget *focused_widget;
2957 gboolean copied = TRUE;
2959 clipboard = gtk_clipboard_get (GDK_SELECTION_CLIPBOARD);
2960 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
2962 if (GTK_IS_LABEL (focused_widget)) {
2963 gtk_clipboard_set_text (clipboard, gtk_label_get_text (GTK_LABEL (focused_widget)), -1);
2964 gtk_clipboard_set_can_store (clipboard, NULL, 0);
2965 gtk_clipboard_store (clipboard);
2966 } else if (GTK_IS_EDITABLE (focused_widget)) {
2967 gtk_editable_copy_clipboard (GTK_EDITABLE(focused_widget));
2968 gtk_clipboard_set_can_store (clipboard, NULL, 0);
2969 gtk_clipboard_store (clipboard);
2970 } else if (GTK_IS_HTML (focused_widget)) {
2971 gtk_html_copy (GTK_HTML (focused_widget));
2972 gtk_clipboard_set_can_store (clipboard, NULL, 0);
2973 gtk_clipboard_store (clipboard);
2974 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
2975 GtkTextBuffer *buffer;
2976 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
2977 gtk_text_buffer_copy_clipboard (buffer, clipboard);
2978 gtk_clipboard_set_can_store (clipboard, NULL, 0);
2979 gtk_clipboard_store (clipboard);
2980 } else if (MODEST_IS_HEADER_VIEW (focused_widget)) {
2981 TnyList *header_list = modest_header_view_get_selected_headers (
2982 MODEST_HEADER_VIEW (focused_widget));
2983 gboolean continue_download = FALSE;
2984 gint num_of_unc_msgs;
2986 num_of_unc_msgs = header_list_count_uncached_msgs(header_list);
2988 if (num_of_unc_msgs)
2989 continue_download = connect_to_get_msg(
2990 GTK_WINDOW (window),
2993 if (num_of_unc_msgs == 0 || continue_download) {
2994 modest_platform_information_banner (
2995 NULL, NULL, _CS("mcen_ib_getting_items"));
2996 modest_header_view_copy_selection (
2997 MODEST_HEADER_VIEW (focused_widget));
3001 g_object_unref (header_list);
3003 } else if (MODEST_IS_FOLDER_VIEW (focused_widget)) {
3004 modest_folder_view_copy_selection (MODEST_FOLDER_VIEW (focused_widget));
3007 /* Show information banner if there was a copy to clipboard */
3009 modest_platform_information_banner (
3010 NULL, NULL, _CS("ecoc_ib_edwin_copied"));
3014 modest_ui_actions_on_undo (GtkAction *action,
3015 ModestWindow *window)
3017 ModestEmailClipboard *clipboard = NULL;
3019 if (MODEST_IS_MSG_EDIT_WINDOW (window)) {
3020 modest_msg_edit_window_undo (MODEST_MSG_EDIT_WINDOW (window));
3021 } else if (MODEST_IS_MAIN_WINDOW (window)) {
3022 /* Clear clipboard source */
3023 clipboard = modest_runtime_get_email_clipboard ();
3024 modest_email_clipboard_clear (clipboard);
3027 g_return_if_reached ();
3032 modest_ui_actions_on_redo (GtkAction *action,
3033 ModestWindow *window)
3035 if (MODEST_IS_MSG_EDIT_WINDOW (window)) {
3036 modest_msg_edit_window_redo (MODEST_MSG_EDIT_WINDOW (window));
3039 g_return_if_reached ();
3045 paste_msgs_cb (const GObject *object, gpointer user_data)
3047 g_return_if_fail (MODEST_IS_MAIN_WINDOW (object));
3048 g_return_if_fail (GTK_IS_WIDGET (user_data));
3050 /* destroy information note */
3051 gtk_widget_destroy (GTK_WIDGET(user_data));
3056 paste_as_attachment_free (gpointer data)
3058 PasteAsAttachmentHelper *helper = (PasteAsAttachmentHelper *) data;
3060 gtk_widget_destroy (helper->banner);
3061 g_object_unref (helper->banner);
3066 paste_msg_as_attachment_cb (ModestMailOperation *mail_op,
3071 PasteAsAttachmentHelper *helper = (PasteAsAttachmentHelper *) userdata;
3072 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (helper->window));
3077 modest_msg_edit_window_add_part (MODEST_MSG_EDIT_WINDOW (helper->window), TNY_MIME_PART (msg));
3082 modest_ui_actions_on_paste (GtkAction *action,
3083 ModestWindow *window)
3085 GtkWidget *focused_widget = NULL;
3086 GtkWidget *inf_note = NULL;
3087 ModestMailOperation *mail_op = NULL;
3089 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
3090 if (GTK_IS_EDITABLE (focused_widget)) {
3091 gtk_editable_paste_clipboard (GTK_EDITABLE(focused_widget));
3092 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
3093 ModestEmailClipboard *e_clipboard = NULL;
3094 e_clipboard = modest_runtime_get_email_clipboard ();
3095 if (modest_email_clipboard_cleared (e_clipboard)) {
3096 GtkTextBuffer *buffer;
3097 GtkClipboard *clipboard;
3099 clipboard = gtk_clipboard_get (GDK_SELECTION_CLIPBOARD);
3100 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
3101 gtk_text_buffer_paste_clipboard (buffer, clipboard, NULL, TRUE);
3102 } else if (MODEST_IS_MSG_EDIT_WINDOW (window)) {
3103 ModestMailOperation *mail_op;
3104 TnyFolder *src_folder;
3107 PasteAsAttachmentHelper *helper = g_new0 (PasteAsAttachmentHelper, 1);
3108 helper->window = MODEST_MSG_EDIT_WINDOW (window);
3109 helper->banner = modest_platform_animation_banner (GTK_WIDGET (window), NULL,
3110 _CS("ckct_nw_pasting"));
3111 modest_email_clipboard_get_data (e_clipboard, &src_folder, &data, &delete);
3112 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
3114 if (helper->banner != NULL) {
3115 g_object_ref (G_OBJECT (helper->banner));
3116 gtk_window_set_modal (GTK_WINDOW (helper->banner), FALSE);
3117 gtk_widget_show (GTK_WIDGET (helper->banner));
3121 modest_mail_operation_get_msgs_full (mail_op,
3123 (GetMsgAsyncUserCallback) paste_msg_as_attachment_cb,
3125 paste_as_attachment_free);
3128 } else if (MODEST_IS_FOLDER_VIEW (focused_widget)) {
3129 ModestEmailClipboard *clipboard = NULL;
3130 TnyFolder *src_folder = NULL;
3131 TnyFolderStore *folder_store = NULL;
3132 TnyList *data = NULL;
3133 gboolean delete = FALSE;
3135 /* Check clipboard source */
3136 clipboard = modest_runtime_get_email_clipboard ();
3137 if (modest_email_clipboard_cleared (clipboard))
3140 /* Get elements to paste */
3141 modest_email_clipboard_get_data (clipboard, &src_folder, &data, &delete);
3143 /* Create a new mail operation */
3144 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_TYPE_RECEIVE, G_OBJECT(window));
3146 /* Get destination folder */
3147 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (focused_widget));
3149 /* transfer messages */
3153 /* Ask for user confirmation */
3154 response = msgs_move_to_confirmation (GTK_WINDOW (window),
3155 TNY_FOLDER (folder_store),
3159 if (response == GTK_RESPONSE_OK) {
3160 /* Launch notification */
3161 inf_note = modest_platform_animation_banner (GTK_WIDGET (window), NULL,
3162 _CS("ckct_nw_pasting"));
3163 if (inf_note != NULL) {
3164 gtk_window_set_modal (GTK_WINDOW(inf_note), FALSE);
3165 gtk_widget_show (GTK_WIDGET(inf_note));
3168 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
3169 modest_mail_operation_xfer_msgs (mail_op,
3171 TNY_FOLDER (folder_store),
3176 g_object_unref (mail_op);
3179 } else if (src_folder != NULL) {
3180 /* Launch notification */
3181 inf_note = modest_platform_animation_banner (GTK_WIDGET (window), NULL,
3182 _CS("ckct_nw_pasting"));
3183 if (inf_note != NULL) {
3184 gtk_window_set_modal (GTK_WINDOW(inf_note), FALSE);
3185 gtk_widget_show (GTK_WIDGET(inf_note));
3188 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
3189 modest_mail_operation_xfer_folder (mail_op,
3199 g_object_unref (data);
3200 if (src_folder != NULL)
3201 g_object_unref (src_folder);
3202 if (folder_store != NULL)
3203 g_object_unref (folder_store);
3209 modest_ui_actions_on_select_all (GtkAction *action,
3210 ModestWindow *window)
3212 GtkWidget *focused_widget;
3214 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
3215 if (MODEST_IS_ATTACHMENTS_VIEW (focused_widget)) {
3216 modest_attachments_view_select_all (MODEST_ATTACHMENTS_VIEW (focused_widget));
3217 } else if (GTK_IS_LABEL (focused_widget)) {
3218 gtk_label_select_region (GTK_LABEL (focused_widget), 0, -1);
3219 } else if (GTK_IS_EDITABLE (focused_widget)) {
3220 gtk_editable_select_region (GTK_EDITABLE(focused_widget), 0, -1);
3221 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
3222 GtkTextBuffer *buffer;
3223 GtkTextIter start, end;
3225 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
3226 gtk_text_buffer_get_start_iter (buffer, &start);
3227 gtk_text_buffer_get_end_iter (buffer, &end);
3228 gtk_text_buffer_select_range (buffer, &start, &end);
3229 } else if (GTK_IS_HTML (focused_widget)) {
3230 gtk_html_select_all (GTK_HTML (focused_widget));
3231 } else if (MODEST_IS_MAIN_WINDOW (window)) {
3232 GtkWidget *header_view = focused_widget;
3233 GtkTreeSelection *selection = NULL;
3235 if (!(MODEST_IS_HEADER_VIEW (focused_widget))) {
3236 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (window),
3237 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
3240 /* Disable window dimming management */
3241 modest_window_disable_dimming (MODEST_WINDOW(window));
3243 /* Select all messages */
3244 selection = gtk_tree_view_get_selection (GTK_TREE_VIEW(header_view));
3245 gtk_tree_selection_select_all (selection);
3247 /* Set focuse on header view */
3248 gtk_widget_grab_focus (header_view);
3251 /* Enable window dimming management */
3252 modest_window_enable_dimming (MODEST_WINDOW(window));
3253 modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (window));
3259 modest_ui_actions_on_mark_as_read (GtkAction *action,
3260 ModestWindow *window)
3262 g_return_if_fail (MODEST_IS_WINDOW(window));
3264 /* Mark each header as read */
3265 do_headers_action (window, headers_action_mark_as_read, NULL);
3269 modest_ui_actions_on_mark_as_unread (GtkAction *action,
3270 ModestWindow *window)
3272 g_return_if_fail (MODEST_IS_WINDOW(window));
3274 /* Mark each header as read */
3275 do_headers_action (window, headers_action_mark_as_unread, NULL);
3279 modest_ui_actions_on_change_zoom (GtkRadioAction *action,
3280 GtkRadioAction *selected,
3281 ModestWindow *window)
3285 value = gtk_radio_action_get_current_value (selected);
3286 if (MODEST_IS_WINDOW (window)) {
3287 modest_window_set_zoom (MODEST_WINDOW (window), ((gdouble)value)/100);
3292 modest_ui_actions_msg_edit_on_change_priority (GtkRadioAction *action,
3293 GtkRadioAction *selected,
3294 ModestWindow *window)
3296 TnyHeaderFlags flags;
3297 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3299 flags = gtk_radio_action_get_current_value (selected);
3300 modest_msg_edit_window_set_priority_flags (MODEST_MSG_EDIT_WINDOW (window), flags);
3304 modest_ui_actions_msg_edit_on_change_file_format (GtkRadioAction *action,
3305 GtkRadioAction *selected,
3306 ModestWindow *window)
3310 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3312 file_format = gtk_radio_action_get_current_value (selected);
3313 modest_msg_edit_window_set_file_format (MODEST_MSG_EDIT_WINDOW (window), file_format);
3318 modest_ui_actions_on_zoom_plus (GtkAction *action,
3319 ModestWindow *window)
3321 g_return_if_fail (MODEST_IS_WINDOW (window));
3323 modest_window_zoom_plus (MODEST_WINDOW (window));
3327 modest_ui_actions_on_zoom_minus (GtkAction *action,
3328 ModestWindow *window)
3330 g_return_if_fail (MODEST_IS_WINDOW (window));
3332 modest_window_zoom_minus (MODEST_WINDOW (window));
3336 modest_ui_actions_on_toggle_fullscreen (GtkToggleAction *toggle,
3337 ModestWindow *window)
3339 ModestWindowMgr *mgr;
3340 gboolean fullscreen, active;
3341 g_return_if_fail (MODEST_IS_WINDOW (window));
3343 mgr = modest_runtime_get_window_mgr ();
3345 active = (gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (toggle)))?1:0;
3346 fullscreen = modest_window_mgr_get_fullscreen_mode (mgr);
3348 if (active != fullscreen) {
3349 modest_window_mgr_set_fullscreen_mode (mgr, active);
3350 gtk_window_present (GTK_WINDOW (window));
3355 modest_ui_actions_on_change_fullscreen (GtkAction *action,
3356 ModestWindow *window)
3358 ModestWindowMgr *mgr;
3359 gboolean fullscreen;
3361 g_return_if_fail (MODEST_IS_WINDOW (window));
3363 mgr = modest_runtime_get_window_mgr ();
3364 fullscreen = modest_window_mgr_get_fullscreen_mode (mgr);
3365 modest_window_mgr_set_fullscreen_mode (mgr, !fullscreen);
3367 gtk_window_present (GTK_WINDOW (window));
3371 * Used by modest_ui_actions_on_details to call do_headers_action
3374 headers_action_show_details (TnyHeader *header,
3375 ModestWindow *window,
3382 dialog = modest_details_dialog_new_with_header (GTK_WINDOW (window), header);
3385 gtk_window_set_modal (GTK_WINDOW (dialog), TRUE);
3386 gtk_widget_show_all (dialog);
3387 gtk_dialog_run (GTK_DIALOG (dialog));
3389 gtk_widget_destroy (dialog);
3393 * Show the folder details in a ModestDetailsDialog widget
3396 show_folder_details (TnyFolder *folder,
3402 dialog = modest_details_dialog_new_with_folder (window, folder);
3405 gtk_window_set_modal (GTK_WINDOW (dialog), TRUE);
3406 gtk_widget_show_all (dialog);
3407 gtk_dialog_run (GTK_DIALOG (dialog));
3409 gtk_widget_destroy (dialog);
3413 * Show the header details in a ModestDetailsDialog widget
3416 modest_ui_actions_on_details (GtkAction *action,
3419 TnyList * headers_list;
3423 if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
3426 msg = modest_msg_view_window_get_message (MODEST_MSG_VIEW_WINDOW (win));
3429 g_object_unref (msg);
3431 headers_list = get_selected_headers (win);
3435 iter = tny_list_create_iterator (headers_list);
3437 header = TNY_HEADER (tny_iterator_get_current (iter));
3439 headers_action_show_details (header, win, NULL);
3440 g_object_unref (header);
3443 g_object_unref (iter);
3444 g_object_unref (headers_list);
3446 } else if (MODEST_IS_MAIN_WINDOW (win)) {
3447 GtkWidget *folder_view, *header_view;
3449 /* Check which widget has the focus */
3450 folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
3451 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
3452 if (gtk_widget_is_focus (folder_view)) {
3453 TnyFolderStore *folder_store
3454 = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
3455 if (!folder_store) {
3456 g_warning ("%s: No item was selected.\n", __FUNCTION__);
3459 /* Show only when it's a folder */
3460 /* This function should not be called for account items,
3461 * because we dim the menu item for them. */
3462 if (TNY_IS_FOLDER (folder_store)) {
3463 show_folder_details (TNY_FOLDER (folder_store), GTK_WINDOW (win));
3466 g_object_unref (folder_store);
3469 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
3470 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
3471 /* Show details of each header */
3472 do_headers_action (win, headers_action_show_details, header_view);
3478 modest_ui_actions_on_toggle_show_cc (GtkToggleAction *toggle,
3479 ModestMsgEditWindow *window)
3481 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3483 modest_msg_edit_window_show_cc (window, gtk_toggle_action_get_active (toggle));
3487 modest_ui_actions_on_toggle_show_bcc (GtkToggleAction *toggle,
3488 ModestMsgEditWindow *window)
3490 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3492 modest_msg_edit_window_show_bcc (window, gtk_toggle_action_get_active (toggle));
3496 modest_ui_actions_toggle_folders_view (GtkAction *action,
3497 ModestMainWindow *main_window)
3499 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
3501 if (gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (action)))
3502 modest_main_window_set_style (main_window, MODEST_MAIN_WINDOW_STYLE_SPLIT);
3504 modest_main_window_set_style (main_window, MODEST_MAIN_WINDOW_STYLE_SIMPLE);
3508 modest_ui_actions_on_toggle_toolbar (GtkToggleAction *toggle,
3509 ModestWindow *window)
3511 gboolean active, fullscreen = FALSE;
3512 ModestWindowMgr *mgr;
3514 active = gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (toggle));
3516 /* Check if we want to toggle the toolbar vuew in fullscreen
3518 if (!strcmp (gtk_action_get_name (GTK_ACTION (toggle)),
3519 "ViewShowToolbarFullScreen")) {
3523 /* Toggle toolbar */
3524 mgr = modest_runtime_get_window_mgr ();
3525 modest_window_mgr_show_toolbars (mgr, G_TYPE_FROM_INSTANCE (window), active, fullscreen);
3529 modest_ui_actions_msg_edit_on_select_font (GtkAction *action,
3530 ModestMsgEditWindow *window)
3532 modest_msg_edit_window_select_font (window);
3536 modest_ui_actions_on_folder_display_name_changed (ModestFolderView *folder_view,
3537 const gchar *display_name,
3540 /* Do not change the application name if the widget has not
3541 the focus. This callback could be called even if the folder
3542 view has not the focus, because the handled signal could be
3543 emitted when the folder view is redrawn */
3544 if (gtk_widget_is_focus (GTK_WIDGET (folder_view))) {
3546 gtk_window_set_title (window, display_name);
3548 gtk_window_set_title (window, " ");
3553 modest_ui_actions_on_select_contacts (GtkAction *action, ModestMsgEditWindow *window)
3555 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3556 modest_msg_edit_window_select_contacts (window);
3560 modest_ui_actions_on_check_names (GtkAction *action, ModestMsgEditWindow *window)
3562 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
3563 modest_msg_edit_window_check_names (window, FALSE);
3567 create_move_to_dialog_on_new_folder(GtkWidget *button, gpointer user_data)
3569 modest_ui_actions_create_folder (gtk_widget_get_toplevel (button),
3570 GTK_WIDGET (user_data));
3574 * This function is used to track changes in the selection of the
3575 * folder view that is inside the "move to" dialog to enable/disable
3576 * the OK button because we do not want the user to select a disallowed
3577 * destination for a folder.
3578 * The user also not desired to be able to use NEW button on items where
3579 * folder creation is not possibel.
3582 on_move_to_dialog_folder_selection_changed (ModestFolderView* self,
3583 TnyFolderStore *folder_store,
3587 GtkWidget *dialog = NULL;
3588 GtkWidget *ok_button = NULL, *new_button = NULL;
3589 GList *children = NULL;
3590 gboolean ok_sensitive = TRUE, new_sensitive = TRUE;
3591 gboolean moving_folder = FALSE;
3592 gboolean is_local_account = TRUE;
3593 GtkWidget *folder_view = NULL;
3594 ModestTnyFolderRules rules;
3599 /* Get the OK button */
3600 dialog = gtk_widget_get_ancestor (GTK_WIDGET (self), GTK_TYPE_DIALOG);
3604 children = gtk_container_get_children (GTK_CONTAINER (GTK_DIALOG (dialog)->action_area));
3605 ok_button = GTK_WIDGET (children->next->next->data);
3606 new_button = GTK_WIDGET (children->next->data);
3607 g_list_free (children);
3609 /* check if folder_store is an remote account */
3610 if (TNY_IS_ACCOUNT (folder_store)) {
3611 TnyAccount *local_account = NULL;
3612 ModestTnyAccountStore *account_store = NULL;
3614 account_store = modest_runtime_get_account_store ();
3615 local_account = modest_tny_account_store_get_local_folders_account (account_store);
3617 if ((gpointer) local_account != (gpointer) folder_store) {
3618 is_local_account = FALSE;
3619 /* New button should be dimmed on remote
3621 new_sensitive = FALSE;
3623 g_object_unref (local_account);
3626 /* Check the target folder rules */
3627 if (TNY_IS_FOLDER (folder_store)) {
3628 rules = modest_tny_folder_get_rules (TNY_FOLDER (folder_store));
3629 if (rules & MODEST_FOLDER_RULES_FOLDER_NON_WRITEABLE) {
3630 ok_sensitive = FALSE;
3631 new_sensitive = FALSE;
3636 /* Check if we're moving a folder */
3637 if (MODEST_IS_MAIN_WINDOW (user_data)) {
3638 /* Get the widgets */
3639 folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (user_data),
3640 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
3641 if (gtk_widget_is_focus (folder_view))
3642 moving_folder = TRUE;
3645 if (moving_folder) {
3646 TnyFolderStore *moved_folder = NULL, *parent = NULL;
3648 /* Get the folder to move */
3649 moved_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
3651 /* Check that we're not moving to the same folder */
3652 if (TNY_IS_FOLDER (moved_folder)) {
3653 parent = tny_folder_get_folder_store (TNY_FOLDER (moved_folder));
3654 if (parent == folder_store)
3655 ok_sensitive = FALSE;
3656 g_object_unref (parent);
3659 if (ok_sensitive && TNY_IS_ACCOUNT (folder_store)) {
3660 /* Do not allow to move to an account unless it's the
3661 local folders account */
3662 if (!is_local_account)
3663 ok_sensitive = FALSE;
3666 if (ok_sensitive && (moved_folder == folder_store)) {
3667 /* Do not allow to move to itself */
3668 ok_sensitive = FALSE;
3670 g_object_unref (moved_folder);
3672 TnyHeader *header = NULL;
3673 TnyFolder *src_folder = NULL;
3675 /* Moving a message */
3676 if (MODEST_IS_MSG_VIEW_WINDOW (user_data)) {
3677 header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW (user_data));
3678 src_folder = tny_header_get_folder (header);
3679 g_object_unref (header);
3682 TNY_FOLDER (modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view)));
3685 /* Do not allow to move the msg to the same folder */
3686 /* Do not allow to move the msg to an account */
3687 if ((gpointer) src_folder == (gpointer) folder_store ||
3688 TNY_IS_ACCOUNT (folder_store))
3689 ok_sensitive = FALSE;
3690 g_object_unref (src_folder);
3694 /* Set sensitivity of the OK button */
3695 gtk_widget_set_sensitive (ok_button, ok_sensitive);
3696 /* Set sensitivity of the NEW button */
3697 gtk_widget_set_sensitive (new_button, new_sensitive);
3701 create_move_to_dialog (GtkWindow *win,
3702 GtkWidget *folder_view,
3703 GtkWidget **tree_view)
3705 GtkWidget *dialog, *scroll;
3706 GtkWidget *new_button;
3708 dialog = gtk_dialog_new_with_buttons (_("mcen_ti_moveto_folders_title"),
3710 GTK_DIALOG_MODAL | GTK_DIALOG_NO_SEPARATOR | GTK_DIALOG_DESTROY_WITH_PARENT,
3713 gtk_dialog_add_button (GTK_DIALOG (dialog), _("mcen_bd_dialog_ok"), GTK_RESPONSE_ACCEPT);
3714 /* We do this manually so GTK+ does not associate a response ID for
3716 new_button = gtk_button_new_from_stock (_("mcen_bd_new"));
3717 gtk_box_pack_end (GTK_BOX (GTK_DIALOG (dialog)->action_area), new_button, FALSE, FALSE, 0);
3718 gtk_dialog_add_button (GTK_DIALOG (dialog), _("mcen_bd_dialog_cancel"), GTK_RESPONSE_REJECT);
3720 /* Create scrolled window */
3721 scroll = gtk_scrolled_window_new (NULL, NULL);
3722 gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scroll),
3723 GTK_POLICY_AUTOMATIC,
3724 GTK_POLICY_AUTOMATIC);
3726 /* Create folder view */
3727 *tree_view = modest_platform_create_folder_view (NULL);
3729 /* Track changes in the selection to
3730 * disable the OK button whenever "Move to" is not possible
3731 * disbale NEW button whenever New is not possible */
3732 g_signal_connect (*tree_view,
3733 "folder_selection_changed",
3734 G_CALLBACK (on_move_to_dialog_folder_selection_changed),
3737 /* Listen to clicks on New button */
3738 g_signal_connect (G_OBJECT (new_button),
3740 G_CALLBACK(create_move_to_dialog_on_new_folder),
3743 /* It could happen that we're trying to move a message from a
3744 window (msg window for example) after the main window was
3745 closed, so we can not just get the model of the folder
3747 if (MODEST_IS_FOLDER_VIEW (folder_view)) {
3748 const gchar *visible_id = NULL;
3750 modest_folder_view_copy_model (MODEST_FOLDER_VIEW(folder_view),
3751 MODEST_FOLDER_VIEW(*tree_view));
3754 modest_folder_view_get_account_id_of_visible_server_account (MODEST_FOLDER_VIEW(folder_view));
3756 /* Show the same account than the one that is shown in the main window */
3757 modest_folder_view_set_account_id_of_visible_server_account (MODEST_FOLDER_VIEW(*tree_view),
3760 const gchar *active_account_name = NULL;
3761 ModestAccountMgr *mgr = NULL;
3762 ModestAccountData *acc_data = NULL;
3764 modest_folder_view_update_model (MODEST_FOLDER_VIEW (*tree_view),
3765 TNY_ACCOUNT_STORE (modest_runtime_get_account_store ()));
3767 active_account_name = modest_window_get_active_account (MODEST_WINDOW (win));
3768 mgr = modest_runtime_get_account_mgr ();
3769 acc_data = modest_account_mgr_get_account_data (mgr, active_account_name);
3771 /* Set the new visible & active account */
3772 if (acc_data && acc_data->store_account) {
3773 modest_folder_view_set_account_id_of_visible_server_account (MODEST_FOLDER_VIEW (*tree_view),
3774 acc_data->store_account->account_name);
3775 modest_account_mgr_free_account_data (mgr, acc_data);
3779 /* Hide special folders */
3780 modest_folder_view_show_non_move_folders (MODEST_FOLDER_VIEW (*tree_view), FALSE);
3782 gtk_container_add (GTK_CONTAINER (scroll), *tree_view);
3784 /* Add scroll to dialog */
3785 gtk_box_pack_start (GTK_BOX (GTK_DIALOG (dialog)->vbox),
3786 scroll, TRUE, TRUE, 0);
3788 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
3789 gtk_window_set_default_size (GTK_WINDOW (dialog), 300, 300);
3795 * Returns TRUE if at least one of the headers of the list belongs to
3796 * a message that has been fully retrieved.
3798 #if 0 /* no longer in use. delete in 2007.10 */
3800 has_retrieved_msgs (TnyList *list)
3803 gboolean found = FALSE;
3805 iter = tny_list_create_iterator (list);
3806 while (!tny_iterator_is_done (iter) && !found) {
3808 TnyHeaderFlags flags = 0;
3810 header = TNY_HEADER (tny_iterator_get_current (iter));
3812 flags = tny_header_get_flags (header);
3813 if (flags & TNY_HEADER_FLAG_CACHED)
3814 /* if (!(flags & TNY_HEADER_FLAG_PARTIAL)) */
3817 g_object_unref (header);
3821 tny_iterator_next (iter);
3823 g_object_unref (iter);
3831 * Shows a confirmation dialog to the user when we're moving messages
3832 * from a remote server to the local storage. Returns the dialog
3833 * response. If it's other kind of movement then it always returns
3836 * This one is used by the next functions:
3837 * modest_ui_actions_on_paste - commented out
3838 * drag_and_drop_from_header_view (for d&d in modest_folder_view.c)
3841 msgs_move_to_confirmation (GtkWindow *win,
3842 TnyFolder *dest_folder,
3846 gint response = GTK_RESPONSE_OK;
3848 /* return with OK if the destination is a remote folder */
3849 if (modest_tny_folder_is_remote_folder (dest_folder))
3850 return GTK_RESPONSE_OK;
3852 TnyFolder *src_folder = NULL;
3853 TnyIterator *iter = NULL;
3854 TnyHeader *header = NULL;
3856 /* Get source folder */
3857 iter = tny_list_create_iterator (headers);
3858 header = TNY_HEADER (tny_iterator_get_current (iter));
3860 src_folder = tny_header_get_folder (header);
3861 g_object_unref (header);
3863 g_object_unref (iter);
3865 /* if no src_folder, message may be an attahcment */
3866 if (src_folder == NULL)
3867 return GTK_RESPONSE_CANCEL;
3869 /* If the source is a local or MMC folder */
3870 if (!modest_tny_folder_is_remote_folder (src_folder)) {
3871 g_object_unref (src_folder);
3872 return GTK_RESPONSE_OK;
3874 g_object_unref (src_folder);
3876 /* now if offline we ask the user */
3877 if(connect_to_get_msg( GTK_WINDOW (win),
3878 tny_list_get_length (headers)))
3879 response = GTK_RESPONSE_OK;
3881 response = GTK_RESPONSE_CANCEL;
3889 move_to_cb (const GObject *object, gpointer user_data)
3891 ModestMsgViewWindow *self = NULL;
3892 g_return_if_fail (GTK_IS_WIDGET (user_data));
3893 g_return_if_fail (MODEST_IS_WINDOW (object));
3895 if (MODEST_IS_MSG_VIEW_WINDOW (object)) {
3896 self = MODEST_MSG_VIEW_WINDOW (object);
3898 if (!modest_msg_view_window_select_next_message (self))
3899 if (!modest_msg_view_window_select_previous_message (self))
3900 /* No more messages to view, so close this window */
3901 modest_ui_actions_on_close_window (NULL, MODEST_WINDOW(self));
3903 gtk_widget_destroy (GTK_WIDGET(user_data));
3907 modest_ui_actions_move_folder_error_handler (ModestMailOperation *mail_op,
3910 ModestMainWindow *main_window = NULL;
3911 GtkWidget *folder_view = NULL;
3912 GObject *win = modest_mail_operation_get_source (mail_op);
3913 const GError *error = NULL;
3914 const gchar *message = NULL;
3916 /* Get error message */
3917 error = modest_mail_operation_get_error (mail_op);
3918 if (error != NULL && error->message != NULL) {
3919 message = error->message;
3921 message = _("mail_in_ui_folder_move_target_error");
3924 /* Disable next automatic folder selection */
3925 if (MODEST_IS_MAIN_WINDOW (user_data)) {
3926 main_window = MODEST_MAIN_WINDOW(user_data);
3927 folder_view = modest_main_window_get_child_widget (main_window,
3928 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
3929 modest_folder_view_disable_next_folder_selection (MODEST_FOLDER_VIEW(folder_view));
3932 /* Show notification dialog */
3933 modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL, message);
3934 g_object_unref (win);
3938 modest_ui_actions_send_receive_error_handler (ModestMailOperation *mail_op,
3941 GObject *win = modest_mail_operation_get_source (mail_op);
3942 const GError *error = modest_mail_operation_get_error (mail_op);
3944 g_return_if_fail (error != NULL);
3945 if (error->message != NULL)
3946 g_printerr ("modest: %s\n", error->message);
3948 g_printerr ("modest: unkonw error on send&receive operation");
3950 /* Show error message */
3951 /* if (modest_mail_operation_get_id (mail_op) == MODEST_MAIL_OPERATION_TYPE_RECEIVE) */
3952 /* modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL, */
3953 /* _CS("sfil_ib_unable_to_receive")); */
3955 /* modest_platform_run_information_dialog ((win) ? GTK_WINDOW (win) : NULL, */
3956 /* _CS("sfil_ib_unable_to_send")); */
3957 g_object_unref (win);
3961 open_msg_for_purge_cb (ModestMailOperation *mail_op,
3968 gint pending_purges = 0;
3969 gboolean some_purged = FALSE;
3970 ModestWindow *win = MODEST_WINDOW (user_data);
3971 ModestWindowMgr *mgr = modest_runtime_get_window_mgr ();
3973 /* If there was any error */
3974 if (!modest_ui_actions_msg_retrieval_check (mail_op, header, msg)) {
3975 modest_window_mgr_unregister_header (mgr, header);
3979 /* Once the message has been retrieved for purging, we check if
3980 * it's all ok for purging */
3982 parts = tny_simple_list_new ();
3983 tny_mime_part_get_parts (TNY_MIME_PART (msg), parts);
3984 iter = tny_list_create_iterator (parts);
3986 while (!tny_iterator_is_done (iter)) {
3988 part = TNY_MIME_PART (tny_iterator_get_current (iter));
3989 if (part && (tny_mime_part_is_attachment (part) || TNY_IS_MSG (part))) {
3990 if (tny_mime_part_is_purged (part))
3997 g_object_unref (part);
3999 tny_iterator_next (iter);
4002 if (pending_purges>0) {
4004 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (win),_("mcen_nc_purge_file_text_inbox"));
4006 if (response == GTK_RESPONSE_OK) {
4007 modest_platform_information_banner (NULL, NULL, _("mcen_ib_removing_attachment"));
4008 tny_iterator_first (iter);
4009 while (!tny_iterator_is_done (iter)) {
4012 part = TNY_MIME_PART (tny_iterator_get_current (iter));
4013 if (part && (tny_mime_part_is_attachment (part) || TNY_IS_MSG (part)))
4014 tny_mime_part_set_purged (part);
4017 g_object_unref (part);
4019 tny_iterator_next (iter);
4022 tny_msg_rewrite_cache (msg);
4025 modest_platform_information_banner (NULL, NULL, _("mail_ib_attachment_already_purged"));
4028 /* remove attachments */
4029 tny_iterator_first (iter);
4030 while (!tny_iterator_is_done (iter)) {
4033 part = TNY_MIME_PART (tny_iterator_get_current (iter));
4035 /* One for the reference given by tny_iterator_get_current(): */
4036 g_object_unref (part);
4038 /* TODO: Is this meant to remove the attachment by doing another unref()?
4039 * Otherwise, this seems useless. */
4042 tny_iterator_next (iter);
4044 modest_window_mgr_unregister_header (mgr, header);
4046 g_object_unref (iter);
4047 g_object_unref (parts);
4051 modest_ui_actions_on_main_window_remove_attachments (GtkAction *action,
4052 ModestMainWindow *win)
4054 GtkWidget *header_view;
4055 TnyList *header_list;
4058 TnyHeaderFlags flags;
4059 ModestWindow *msg_view_window = NULL;
4062 g_return_if_fail (MODEST_IS_MAIN_WINDOW (win));
4064 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
4065 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
4067 header_list = modest_header_view_get_selected_headers (MODEST_HEADER_VIEW (header_view));
4069 if (tny_list_get_length (header_list) == 1) {
4070 iter = tny_list_create_iterator (header_list);
4071 header = TNY_HEADER (tny_iterator_get_current (iter));
4072 g_object_unref (iter);
4077 found = modest_window_mgr_find_registered_header (modest_runtime_get_window_mgr (),
4078 header, &msg_view_window);
4079 flags = tny_header_get_flags (header);
4080 if (!(flags & TNY_HEADER_FLAG_CACHED))
4083 if (msg_view_window != NULL)
4084 modest_msg_view_window_remove_attachments (MODEST_MSG_VIEW_WINDOW (msg_view_window), TRUE);
4086 /* do nothing; uid was registered before, so window is probably on it's way */
4087 g_warning ("debug: header %p has already been registered", header);
4090 ModestMailOperation *mail_op = NULL;
4091 modest_window_mgr_register_header (modest_runtime_get_window_mgr (), header);
4092 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
4094 modest_ui_actions_get_msgs_full_error_handler,
4096 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
4097 modest_mail_operation_get_msg (mail_op, header, open_msg_for_purge_cb, win);
4099 g_object_unref (mail_op);
4102 g_object_unref (header);
4104 g_object_unref (header_list);
4108 * Utility function that transfer messages from both the main window
4109 * and the msg view window when using the "Move to" dialog
4112 modest_ui_actions_xfer_messages_from_move_to (TnyFolderStore *dst_folder,
4115 TnyList *headers = NULL;
4116 TnyAccount *dst_account = NULL;
4117 const gchar *proto_str = NULL;
4118 gboolean dst_is_pop = FALSE;
4120 if (!TNY_IS_FOLDER (dst_folder)) {
4121 modest_platform_information_banner (GTK_WIDGET (win),
4123 _CS("ckdg_ib_unable_to_move_to_current_location"));
4127 dst_account = tny_folder_get_account (TNY_FOLDER (dst_folder));
4128 proto_str = tny_account_get_proto (dst_account);
4130 /* tinymail will return NULL for local folders it seems */
4131 dst_is_pop = proto_str &&
4132 (modest_protocol_info_get_transport_store_protocol (proto_str) ==
4133 MODEST_PROTOCOL_STORE_POP);
4135 g_object_unref (dst_account);
4137 /* Get selected headers */
4138 headers = get_selected_headers (MODEST_WINDOW (win));
4141 modest_platform_information_banner (GTK_WIDGET (win),
4143 ngettext("mail_in_ui_folder_move_target_error",
4144 "mail_in_ui_folder_move_targets_error",
4145 tny_list_get_length (headers)));
4146 g_object_unref (headers);
4150 GtkWidget *inf_note;
4151 inf_note = modest_platform_animation_banner (GTK_WIDGET (win), NULL,
4152 _CS("ckct_nw_pasting"));
4153 if (inf_note != NULL) {
4154 gtk_window_set_modal (GTK_WINDOW(inf_note), FALSE);
4155 gtk_widget_show (GTK_WIDGET(inf_note));
4158 ModestMailOperation *mail_op =
4159 modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
4161 modest_ui_actions_move_folder_error_handler,
4163 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
4166 modest_mail_operation_xfer_msgs (mail_op,
4168 TNY_FOLDER (dst_folder),
4173 g_object_unref (G_OBJECT (mail_op));
4174 g_object_unref (headers);
4178 * UI handler for the "Move to" action when invoked from the
4182 modest_ui_actions_on_main_window_move_to (GtkAction *action,
4183 GtkWidget *folder_view,
4184 TnyFolderStore *dst_folder,
4185 ModestMainWindow *win)
4187 ModestHeaderView *header_view = NULL;
4188 ModestMailOperation *mail_op = NULL;
4189 TnyFolderStore *src_folder;
4190 gboolean online = (tny_device_is_online (modest_runtime_get_device()));
4192 g_return_if_fail (MODEST_IS_MAIN_WINDOW (win));
4194 /* Get the source folder */
4195 src_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
4197 /* Get header view */
4198 header_view = MODEST_HEADER_VIEW(modest_main_window_get_child_widget (win, MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW));
4200 /* Get folder or messages to transfer */
4201 if (gtk_widget_is_focus (folder_view)) {
4202 GtkTreeSelection *sel;
4203 gboolean do_xfer = TRUE;
4205 /* Allow only to transfer folders to the local root folder */
4206 if (TNY_IS_ACCOUNT (dst_folder) &&
4207 !MODEST_IS_TNY_LOCAL_FOLDERS_ACCOUNT (dst_folder)) {
4209 } else if (!TNY_IS_FOLDER (src_folder)) {
4210 g_warning ("%s: src_folder is not a TnyFolder.\n", __FUNCTION__);
4212 } else if (!online && modest_platform_is_network_folderstore(src_folder)) {
4213 guint num_headers = tny_folder_get_all_count(TNY_FOLDER(src_folder));
4214 if (!connect_to_get_msg(GTK_WINDOW(win), num_headers)) {
4220 GtkWidget *inf_note;
4221 inf_note = modest_platform_animation_banner (GTK_WIDGET (win), NULL,
4222 _CS("ckct_nw_pasting"));
4223 if (inf_note != NULL) {
4224 gtk_window_set_modal (GTK_WINDOW(inf_note), FALSE);
4225 gtk_widget_show (GTK_WIDGET(inf_note));
4227 /* Clean folder on header view before moving it */
4228 sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (folder_view));
4229 gtk_tree_selection_unselect_all (sel);
4232 modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
4234 modest_ui_actions_move_folder_error_handler,
4236 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
4239 /* Select *after* the changes */
4240 /* TODO: this function hangs UI after transfer */
4241 /* modest_folder_view_select_folder (MODEST_FOLDER_VIEW(folder_view), */
4242 /* TNY_FOLDER (src_folder), TRUE); */
4244 modest_mail_operation_xfer_folder (mail_op,
4245 TNY_FOLDER (src_folder),
4247 TRUE, move_to_cb, inf_note);
4248 /* Unref mail operation */
4249 g_object_unref (G_OBJECT (mail_op));
4251 } else if (gtk_widget_is_focus (GTK_WIDGET(header_view))) {
4252 gboolean do_xfer = TRUE;
4253 /* Ask for confirmation if the source folder is remote and we're not connected */
4254 if (!online && modest_platform_is_network_folderstore(src_folder)) {
4255 TnyList *headers = modest_header_view_get_selected_headers(header_view);
4256 if (!msgs_already_deleted_from_server(headers, src_folder)) {
4257 guint num_headers = tny_list_get_length(headers);
4258 if (!connect_to_get_msg(GTK_WINDOW(win), num_headers)) {
4262 g_object_unref(headers);
4264 if (do_xfer) /* Transfer messages */
4265 modest_ui_actions_xfer_messages_from_move_to (dst_folder, MODEST_WINDOW (win));
4269 g_object_unref (src_folder);
4274 * UI handler for the "Move to" action when invoked from the
4275 * ModestMsgViewWindow
4278 modest_ui_actions_on_msg_view_window_move_to (GtkAction *action,
4279 TnyFolderStore *dst_folder,
4280 ModestMsgViewWindow *win)
4282 TnyHeader *header = NULL;
4283 TnyFolderStore *src_folder;
4285 /* Create header list */
4286 header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW (win));
4287 src_folder = TNY_FOLDER_STORE(tny_header_get_folder(header));
4288 g_object_unref (header);
4290 /* Transfer the message if online or confirmed by the user */
4291 if (tny_device_is_online (modest_runtime_get_device()) || remote_folder_is_pop(src_folder) ||
4292 (modest_platform_is_network_folderstore(src_folder) && connect_to_get_msg(GTK_WINDOW(win), 1))) {
4293 modest_ui_actions_xfer_messages_from_move_to (dst_folder, MODEST_WINDOW (win));
4296 g_object_unref (src_folder);
4300 modest_ui_actions_on_move_to (GtkAction *action,
4303 GtkWidget *dialog = NULL, *folder_view = NULL, *tree_view = NULL;
4305 TnyFolderStore *dst_folder = NULL;
4306 ModestMainWindow *main_window;
4308 g_return_if_fail (MODEST_IS_MAIN_WINDOW (win) ||
4309 MODEST_IS_MSG_VIEW_WINDOW (win));
4311 /* Get the main window if exists */
4312 if (MODEST_IS_MAIN_WINDOW (win))
4313 main_window = MODEST_MAIN_WINDOW (win);
4316 MODEST_MAIN_WINDOW (modest_window_mgr_get_main_window (modest_runtime_get_window_mgr ()));
4318 /* Get the folder view widget if exists */
4320 folder_view = modest_main_window_get_child_widget (main_window,
4321 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
4325 /* Create and run the dialog */
4326 dialog = create_move_to_dialog (GTK_WINDOW (win), folder_view, &tree_view);
4327 modest_folder_view_select_first_inbox_or_local (MODEST_FOLDER_VIEW (tree_view));
4328 gtk_window_set_modal (GTK_WINDOW (dialog), TRUE);
4329 result = gtk_dialog_run (GTK_DIALOG(dialog));
4330 g_object_ref (tree_view);
4331 gtk_widget_destroy (dialog);
4333 if (result != GTK_RESPONSE_ACCEPT)
4336 dst_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (tree_view));
4337 /* Do window specific stuff */
4338 if (MODEST_IS_MAIN_WINDOW (win)) {
4339 modest_ui_actions_on_main_window_move_to (action,
4342 MODEST_MAIN_WINDOW (win));
4344 modest_ui_actions_on_msg_view_window_move_to (action,
4346 MODEST_MSG_VIEW_WINDOW (win));
4350 g_object_unref (dst_folder);
4354 * Calls #HeadersFunc for each header already selected in the main
4355 * window or the message currently being shown in the msg view window
4358 do_headers_action (ModestWindow *win,
4362 TnyList *headers_list = NULL;
4363 TnyIterator *iter = NULL;
4364 TnyHeader *header = NULL;
4365 TnyFolder *folder = NULL;
4368 headers_list = get_selected_headers (win);
4372 /* Get the folder */
4373 iter = tny_list_create_iterator (headers_list);
4374 header = TNY_HEADER (tny_iterator_get_current (iter));
4376 folder = tny_header_get_folder (header);
4377 g_object_unref (header);
4380 /* Call the function for each header */
4381 while (!tny_iterator_is_done (iter)) {
4382 header = TNY_HEADER (tny_iterator_get_current (iter));
4383 func (header, win, user_data);
4384 g_object_unref (header);
4385 tny_iterator_next (iter);
4388 /* Trick: do a poke status in order to speed up the signaling
4390 tny_folder_poke_status (folder);
4393 g_object_unref (folder);
4394 g_object_unref (iter);
4395 g_object_unref (headers_list);
4399 modest_ui_actions_view_attachment (GtkAction *action,
4400 ModestWindow *window)
4402 if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
4403 modest_msg_view_window_view_attachment (MODEST_MSG_VIEW_WINDOW (window), NULL);
4405 /* not supported window for this action */
4406 g_return_if_reached ();
4411 modest_ui_actions_save_attachments (GtkAction *action,
4412 ModestWindow *window)
4414 if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
4415 modest_msg_view_window_save_attachments (MODEST_MSG_VIEW_WINDOW (window), NULL);
4417 /* not supported window for this action */
4418 g_return_if_reached ();
4423 modest_ui_actions_remove_attachments (GtkAction *action,
4424 ModestWindow *window)
4426 if (MODEST_IS_MAIN_WINDOW (window)) {
4427 modest_ui_actions_on_main_window_remove_attachments (action, MODEST_MAIN_WINDOW (window));
4428 } else if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
4429 modest_msg_view_window_remove_attachments (MODEST_MSG_VIEW_WINDOW (window), FALSE);
4431 /* not supported window for this action */
4432 g_return_if_reached ();
4437 modest_ui_actions_on_settings (GtkAction *action,
4442 dialog = modest_platform_get_global_settings_dialog ();
4443 gtk_window_set_transient_for (GTK_WINDOW (dialog), GTK_WINDOW (win));
4444 gtk_window_set_modal (GTK_WINDOW (dialog), TRUE);
4445 gtk_widget_show_all (dialog);
4447 gtk_dialog_run (GTK_DIALOG (dialog));
4449 gtk_widget_destroy (dialog);
4453 modest_ui_actions_on_help (GtkAction *action,
4456 const gchar *help_id = NULL;
4458 if (MODEST_IS_MAIN_WINDOW (win)) {
4459 GtkWidget *folder_view;
4460 TnyFolderStore *folder_store;
4462 /* Get selected folder */
4463 folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
4464 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
4465 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
4467 /* Switch help_id */
4468 if (TNY_IS_FOLDER (folder_store)) {
4469 switch (modest_tny_folder_guess_folder_type (TNY_FOLDER (folder_store))) {
4470 case TNY_FOLDER_TYPE_NORMAL:
4471 help_id = "applications_email_managefolders";
4473 case TNY_FOLDER_TYPE_INBOX:
4474 help_id = "applications_email_inbox";
4476 case TNY_FOLDER_TYPE_OUTBOX:
4477 help_id = "applications_email_outbox";
4479 case TNY_FOLDER_TYPE_SENT:
4480 help_id = "applications_email_sent";
4482 case TNY_FOLDER_TYPE_DRAFTS:
4483 help_id = "applications_email_drafts";
4485 case TNY_FOLDER_TYPE_ARCHIVE:
4486 help_id = "applications_email_managefolders";
4489 help_id = "applications_email_managefolders";
4492 help_id = "applications_email_mainview";
4494 g_object_unref (folder_store);
4495 } else if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
4496 help_id = "applications_email_viewer";
4497 } else if (MODEST_IS_MSG_EDIT_WINDOW (win))
4498 help_id = "applications_email_editor";
4500 modest_platform_show_help (GTK_WINDOW (win), help_id);
4504 modest_ui_actions_on_retrieve_msg_contents (GtkAction *action,
4505 ModestWindow *window)
4507 ModestMailOperation *mail_op;
4511 headers = get_selected_headers (window);
4515 /* Create mail operation */
4516 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_TYPE_RECEIVE,
4518 modest_ui_actions_get_msgs_full_error_handler,
4520 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
4521 modest_mail_operation_get_msgs_full (mail_op, headers, NULL, NULL, NULL);
4524 g_object_unref (headers);
4525 g_object_unref (mail_op);
4529 modest_ui_actions_on_email_menu_activated (GtkAction *action,
4530 ModestWindow *window)
4532 g_return_if_fail (MODEST_IS_WINDOW (window));
4535 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
4539 modest_ui_actions_on_edit_menu_activated (GtkAction *action,
4540 ModestWindow *window)
4542 g_return_if_fail (MODEST_IS_WINDOW (window));
4545 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
4549 modest_ui_actions_on_view_menu_activated (GtkAction *action,
4550 ModestWindow *window)
4552 g_return_if_fail (MODEST_IS_WINDOW (window));
4555 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
4559 modest_ui_actions_on_format_menu_activated (GtkAction *action,
4560 ModestWindow *window)
4562 g_return_if_fail (MODEST_IS_WINDOW (window));
4565 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
4569 modest_ui_actions_on_tools_menu_activated (GtkAction *action,
4570 ModestWindow *window)
4572 g_return_if_fail (MODEST_IS_WINDOW (window));
4575 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
4579 modest_ui_actions_on_attachment_menu_activated (GtkAction *action,
4580 ModestWindow *window)
4582 g_return_if_fail (MODEST_IS_WINDOW (window));
4585 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
4589 modest_ui_actions_on_toolbar_csm_menu_activated (GtkAction *action,
4590 ModestWindow *window)
4592 g_return_if_fail (MODEST_IS_WINDOW (window));
4595 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
4599 modest_ui_actions_on_folder_view_csm_menu_activated (GtkAction *action,
4600 ModestWindow *window)
4602 g_return_if_fail (MODEST_IS_WINDOW (window));
4605 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
4609 modest_ui_actions_on_header_view_csm_menu_activated (GtkAction *action,
4610 ModestWindow *window)
4612 g_return_if_fail (MODEST_IS_WINDOW (window));
4615 modest_window_check_dimming_rules_group (window, "ModestMenuDimmingRules");
4619 modest_ui_actions_check_toolbar_dimming_rules (ModestWindow *window)
4621 g_return_if_fail (MODEST_IS_WINDOW (window));
4624 modest_window_check_dimming_rules_group (window, "ModestToolbarDimmingRules");
4628 modest_ui_actions_on_search_messages (GtkAction *action, ModestWindow *window)
4630 g_return_if_fail (MODEST_IS_WINDOW (window));
4632 modest_platform_show_search_messages (GTK_WINDOW (window));
4636 modest_ui_actions_on_open_addressbook (GtkAction *action, ModestWindow *win)
4638 g_return_if_fail (MODEST_IS_WINDOW (win));
4639 modest_platform_show_addressbook (GTK_WINDOW (win));
4644 modest_ui_actions_on_toggle_find_in_page (GtkToggleAction *action,
4645 ModestWindow *window)
4647 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
4649 modest_msg_edit_window_toggle_find_toolbar (MODEST_MSG_EDIT_WINDOW (window), gtk_toggle_action_get_active (action));
4653 _on_send_receive_progress_changed (ModestMailOperation *mail_op,
4654 ModestMailOperationState *state,
4657 g_return_if_fail (MODEST_IS_MAIN_WINDOW(user_data));
4659 /* Set send/receive operation finished */
4660 if (state->status != MODEST_MAIL_OPERATION_STATUS_IN_PROGRESS)
4661 modest_main_window_notify_send_receive_completed (MODEST_MAIN_WINDOW(user_data));
4667 modest_ui_actions_on_send_queue_error_happened (TnySendQueue *self,
4673 const gchar* server_name = NULL;
4674 TnyTransportAccount *server_account;
4675 gchar *message = NULL;
4677 /* Don't show anything if the user cancelled something */
4678 if (err->code == TNY_TRANSPORT_ACCOUNT_ERROR_SEND_USER_CANCEL)
4681 /* Get the server name: */
4683 TNY_TRANSPORT_ACCOUNT (tny_camel_send_queue_get_transport_account (TNY_CAMEL_SEND_QUEUE (self)));
4684 if (server_account) {
4685 server_name = tny_account_get_hostname (TNY_ACCOUNT (server_account));
4687 g_object_unref (server_account);
4688 server_account = NULL;
4691 g_return_if_fail (server_name);
4693 /* Show the appropriate message text for the GError: */
4694 switch (err->code) {
4695 case TNY_TRANSPORT_ACCOUNT_ERROR_SEND_HOST_LOOKUP_FAILED:
4696 message = g_strdup_printf (_("emev_ib_ui_smtp_server_invalid"), server_name);
4698 case TNY_TRANSPORT_ACCOUNT_ERROR_SEND_SERVICE_UNAVAILABLE:
4699 message = g_strdup_printf (_("emev_ib_ui_smtp_server_invalid"), server_name);
4701 case TNY_TRANSPORT_ACCOUNT_ERROR_SEND_AUTHENTICATION_NOT_SUPPORTED:
4702 message = g_strdup_printf (_("emev_ni_ui_smtp_authentication_fail_error"), server_name);
4704 case TNY_TRANSPORT_ACCOUNT_ERROR_SEND:
4705 message = g_strdup (_("emev_ib_ui_smtp_send_error"));
4708 g_return_if_reached ();
4711 /* TODO if the username or the password where not defined we
4712 should show the Accounts Settings dialog or the Connection
4713 specific SMTP server window */
4715 modest_platform_run_information_dialog (NULL, message);
4720 modest_ui_actions_on_send_queue_status_changed (ModestTnySendQueue *send_queue,
4725 ModestMainWindow *main_window = NULL;
4726 ModestWindowMgr *mgr = NULL;
4727 GtkWidget *folder_view = NULL, *header_view = NULL;
4728 TnyFolderStore *selected_folder = NULL;
4729 TnyFolderType folder_type;
4731 mgr = modest_runtime_get_window_mgr ();
4732 main_window = MODEST_MAIN_WINDOW (modest_window_mgr_get_main_window (mgr));
4737 /* Check if selected folder is OUTBOX */
4738 folder_view = modest_main_window_get_child_widget (main_window,
4739 MODEST_MAIN_WINDOW_WIDGET_TYPE_FOLDER_VIEW);
4740 header_view = modest_main_window_get_child_widget (main_window,
4741 MODEST_MAIN_WINDOW_WIDGET_TYPE_HEADER_VIEW);
4743 selected_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
4744 if (!TNY_IS_FOLDER (selected_folder))
4747 /* gtk_tree_view_column_queue_resize is only available in GTK+ 2.8 */
4748 #if GTK_CHECK_VERSION(2, 8, 0)
4749 folder_type = modest_tny_folder_guess_folder_type (TNY_FOLDER (selected_folder));
4750 if (folder_type == TNY_FOLDER_TYPE_OUTBOX) {
4751 GtkTreeViewColumn *tree_column;
4753 tree_column = gtk_tree_view_get_column (GTK_TREE_VIEW (header_view),
4754 TNY_GTK_HEADER_LIST_MODEL_FROM_COLUMN);
4755 gtk_tree_view_column_queue_resize (tree_column);
4758 gtk_widget_queue_draw (header_view);
4763 if (selected_folder != NULL)
4764 g_object_unref (selected_folder);