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>
36 #include <modest-runtime.h>
37 #include <modest-tny-folder.h>
38 #include <modest-tny-msg.h>
39 #include <modest-tny-account.h>
40 #include <modest-address-book.h>
42 #include "modest-ui-actions.h"
44 #include "modest-tny-platform-factory.h"
45 #include "modest-platform.h"
47 #ifdef MODEST_PLATFORM_MAEMO
48 #include "maemo/modest-osso-state-saving.h"
49 #endif /* MODEST_PLATFORM_MAEMO */
51 #include "widgets/modest-ui-constants.h"
52 #include <widgets/modest-main-window.h>
53 #include <widgets/modest-msg-view-window.h>
54 #include <widgets/modest-account-view-window.h>
55 #include <widgets/modest-details-dialog.h>
56 #include <widgets/modest-attachments-view.h>
57 #include "widgets/modest-global-settings-dialog.h"
58 #include "modest-connection-specific-smtp-window.h"
59 #include "modest-account-mgr-helpers.h"
60 #include "modest-mail-operation.h"
61 #include "modest-text-utils.h"
63 #ifdef MODEST_HAVE_EASYSETUP
64 #include "easysetup/modest-easysetup-wizard.h"
65 #endif /* MODEST_HAVE_EASYSETUP */
67 #include <modest-widget-memory.h>
68 #include <tny-error.h>
69 #include <tny-simple-list.h>
70 #include <tny-msg-view.h>
71 #include <tny-device.h>
73 typedef struct _GetMsgAsyncHelper {
75 ModestMailOperation *mail_op;
82 typedef enum _ReplyForwardAction {
88 typedef struct _ReplyForwardHelper {
89 guint reply_forward_type;
90 ReplyForwardAction action;
94 typedef struct _HeaderActivatedHelper {
96 GtkTreeRowReference *row_reference;
99 } HeaderActivatedHelper;
102 * The do_headers_action uses this kind of functions to perform some
103 * action to each member of a list of headers
105 typedef void (*HeadersFunc) (TnyHeader *header, ModestWindow *win, gpointer user_data);
108 do_headers_action (ModestWindow *win,
113 static void open_msg_func (const GObject *obj, TnyMsg *msg, gpointer user_data);
115 static void reply_forward_func (const GObject *obj, TnyMsg *msg, gpointer user_data);
117 static void reply_forward (ReplyForwardAction action, ModestWindow *win);
119 static gchar* ask_for_folder_name (GtkWindow *parent_window, const gchar *title);
122 modest_ui_actions_on_about (GtkAction *action, ModestWindow *win)
125 const gchar *authors[] = {
126 "Dirk-Jan C. Binnema <dirk-jan.binnema@nokia.com>",
129 about = gtk_about_dialog_new ();
130 gtk_about_dialog_set_name (GTK_ABOUT_DIALOG(about), PACKAGE_NAME);
131 gtk_about_dialog_set_version (GTK_ABOUT_DIALOG(about),PACKAGE_VERSION);
132 gtk_about_dialog_set_copyright (GTK_ABOUT_DIALOG(about),
133 _("Copyright (c) 2006, Nokia Corporation\n"
134 "All rights reserved."));
135 gtk_about_dialog_set_comments (GTK_ABOUT_DIALOG(about),
136 _("a modest e-mail client\n\n"
137 "design and implementation: Dirk-Jan C. Binnema\n"
138 "contributions from the fine people at KC and Ig\n"
139 "uses the tinymail email framework written by Philip van Hoof"));
140 gtk_about_dialog_set_authors (GTK_ABOUT_DIALOG(about), authors);
141 gtk_about_dialog_set_website (GTK_ABOUT_DIALOG(about), "http://modest.garage.maemo.org");
143 gtk_dialog_run (GTK_DIALOG (about));
144 gtk_widget_destroy(about);
149 get_selected_headers (ModestWindow *win)
151 if (MODEST_IS_MAIN_WINDOW(win)) {
152 GtkWidget *header_view;
154 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(win),
155 MODEST_WIDGET_TYPE_HEADER_VIEW);
156 return modest_header_view_get_selected_headers (MODEST_HEADER_VIEW(header_view));
158 } else if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
159 /* for MsgViewWindows, we simply return a list with one element */
161 TnyList *list = NULL;
163 header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW (win));
164 if (header != NULL) {
165 list = tny_simple_list_new ();
166 tny_list_prepend (list, G_OBJECT(header));
167 g_object_unref (G_OBJECT(header));
177 headers_action_mark_as_read (TnyHeader *header,
181 TnyHeaderFlags flags;
183 g_return_if_fail (TNY_IS_HEADER(header));
185 flags = tny_header_get_flags (header);
186 if (flags & TNY_HEADER_FLAG_SEEN) return;
187 tny_header_set_flags (header, TNY_HEADER_FLAG_SEEN);
191 headers_action_mark_as_unread (TnyHeader *header,
195 TnyHeaderFlags flags;
197 g_return_if_fail (TNY_IS_HEADER(header));
199 flags = tny_header_get_flags (header);
200 if (flags & TNY_HEADER_FLAG_SEEN) {
201 tny_header_unset_flags (header, TNY_HEADER_FLAG_SEEN);
207 headers_action_delete (TnyHeader *header,
211 ModestMailOperation *mail_op = NULL;
213 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_DELETE, G_OBJECT(win));
214 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
217 /* Always delete. TODO: Move to trash still not supported */
218 modest_mail_operation_remove_msg (mail_op, header, FALSE);
219 g_object_unref (G_OBJECT (mail_op));
223 modest_ui_actions_on_delete (GtkAction *action, ModestWindow *win)
225 TnyList *header_list = NULL;
226 TnyIterator *iter = NULL;
227 TnyHeader *header = NULL;
228 gchar *message = NULL;
232 g_return_if_fail (MODEST_IS_WINDOW(win));
234 header_list = get_selected_headers (win);
235 if (!header_list) return;
238 if (tny_list_get_length(header_list) > 1)
239 message = g_strdup(_("emev_nc_delete_messages"));
241 iter = tny_list_create_iterator (header_list);
242 header = TNY_HEADER (tny_iterator_get_current (iter));
243 desc = g_strdup_printf ("%s", tny_header_get_subject (header));
244 message = g_strdup_printf(_("emev_nc_delete_message"), desc);
247 /* Confirmation dialog */
248 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (win),
252 if (response == GTK_RESPONSE_OK) {
253 if (MODEST_IS_MSG_EDIT_WINDOW (win)) {
255 g_signal_emit_by_name (G_OBJECT (win), "delete-event", NULL, &ret_value);
259 /* Remove each header */
260 do_headers_action (win, headers_action_delete, NULL);
262 if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
263 gtk_widget_destroy (GTK_WIDGET(win));
270 g_object_unref (header_list);
271 g_object_unref (iter);
276 modest_ui_actions_on_quit (GtkAction *action, ModestWindow *win)
278 #ifdef MODEST_PLATFORM_MAEMO
279 modest_osso_save_state();
280 #endif /* MODEST_PLATFORM_MAEMO */
286 modest_ui_actions_on_close_window (GtkAction *action, ModestWindow *win)
288 if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
289 gtk_widget_destroy (GTK_WIDGET (win));
290 } else if (MODEST_IS_MSG_EDIT_WINDOW (win)) {
292 g_signal_emit_by_name (G_OBJECT (win), "delete-event", NULL, &ret_value);
293 } else if (MODEST_IS_WINDOW (win)) {
294 gtk_widget_destroy (GTK_WIDGET (win));
296 g_return_if_reached ();
301 modest_ui_actions_on_add_to_contacts (GtkAction *action, ModestWindow *win)
303 GtkClipboard *clipboard = NULL;
304 gchar *selection = NULL;
306 clipboard = gtk_clipboard_get (GDK_SELECTION_PRIMARY);
307 selection = gtk_clipboard_wait_for_text (clipboard);
309 modest_address_book_add_address (selection);
314 modest_ui_actions_on_accounts (GtkAction *action, ModestWindow *win)
316 /* This is currently only implemented for Maemo,
317 * because it requires a providers preset file which is not publically available.
319 #ifdef MODEST_PLATFORM_MAEMO /* Defined in config.h */
320 GSList *account_names = modest_account_mgr_account_names (modest_runtime_get_account_mgr(),
321 TRUE /* enabled accounts only */);
322 gboolean accounts_exist = account_names != NULL;
323 g_slist_free (account_names);
325 if (!accounts_exist) {
326 /* If there are no accounts yet, just show the easy-setup wizard, as per the UI spec: */
327 ModestEasysetupWizardDialog *wizard = modest_easysetup_wizard_dialog_new ();
328 gtk_window_set_transient_for (GTK_WINDOW (wizard), GTK_WINDOW (win));
329 gtk_dialog_run (GTK_DIALOG (wizard));
330 gtk_widget_destroy (GTK_WIDGET (wizard));
332 /* Show the list of accounts: */
333 GtkDialog *account_win = GTK_DIALOG(modest_account_view_window_new ());
334 gtk_window_set_transient_for (GTK_WINDOW (account_win), GTK_WINDOW(win));
335 gtk_dialog_run (account_win);
336 gtk_widget_destroy (GTK_WIDGET(account_win));
339 GtkWidget *dialog, *label;
341 /* Create the widgets */
343 dialog = gtk_dialog_new_with_buttons ("Message",
345 GTK_DIALOG_DESTROY_WITH_PARENT,
349 label = gtk_label_new ("Hello World!");
351 /* Ensure that the dialog box is destroyed when the user responds. */
353 g_signal_connect_swapped (dialog, "response",
354 G_CALLBACK (gtk_widget_destroy),
357 /* Add the label, and show everything we've added to the dialog. */
359 gtk_container_add (GTK_CONTAINER (GTK_DIALOG(dialog)->vbox),
361 gtk_widget_show_all (dialog);
362 #endif /* MODEST_PLATFORM_MAEMO */
366 on_smtp_servers_window_hide (GtkWindow* window, gpointer user_data)
368 ModestWindow *main_window = MODEST_WINDOW (user_data);
370 /* Save any changes. */
371 modest_connection_specific_smtp_window_save_server_accounts (
372 MODEST_CONNECTION_SPECIFIC_SMTP_WINDOW (window),
373 modest_window_get_active_account (main_window));
374 gtk_widget_destroy (GTK_WIDGET (window));
378 modest_ui_actions_on_smtp_servers (GtkAction *action, ModestWindow *win)
380 /* This is currently only implemented for Maemo,
381 * because it requires an API (libconic) to detect different connection
384 #ifdef MODEST_PLATFORM_MAEMO /* Defined in config.h */
386 /* Create the window if necessary: */
387 GtkWidget *specific_window = GTK_WIDGET (modest_connection_specific_smtp_window_new ());
388 modest_connection_specific_smtp_window_fill_with_connections (
389 MODEST_CONNECTION_SPECIFIC_SMTP_WINDOW (specific_window),
390 modest_runtime_get_account_mgr(),
391 modest_window_get_active_account (win));
393 /* Show the window: */
394 gtk_window_set_transient_for (GTK_WINDOW (specific_window), GTK_WINDOW (win));
395 gtk_window_set_modal (GTK_WINDOW (specific_window), TRUE);
396 gtk_widget_show (specific_window);
398 /* Save changes when the window is hidden: */
399 g_signal_connect (specific_window, "hide",
400 G_CALLBACK (on_smtp_servers_window_hide), win);
401 #endif /* MODEST_PLATFORM_MAEMO */
405 modest_ui_actions_on_new_msg (GtkAction *action, ModestWindow *win)
407 ModestWindow *msg_win;
409 TnyFolder *folder = NULL;
410 gchar *account_name = NULL;
411 gchar *from_str = NULL;
412 /* GError *err = NULL; */
413 TnyAccount *account = NULL;
414 ModestWindowMgr *mgr;
415 gchar *signature = NULL;
417 account_name = g_strdup(modest_window_get_active_account (win));
419 account_name = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
421 g_printerr ("modest: no account found\n");
425 account = modest_tny_account_store_get_tny_account_by_account (modest_runtime_get_account_store(),
427 TNY_ACCOUNT_TYPE_STORE);
429 g_printerr ("modest: failed to get tnyaccount for '%s'\n", account_name);
433 from_str = modest_account_mgr_get_from_string (modest_runtime_get_account_mgr(), account_name);
435 g_printerr ("modest: failed get from string for '%s'\n", account_name);
439 if (modest_account_mgr_get_bool (modest_runtime_get_account_mgr (), account_name,
440 MODEST_ACCOUNT_USE_SIGNATURE, FALSE)) {
441 signature = modest_account_mgr_get_string (modest_runtime_get_account_mgr (), account_name,
442 MODEST_ACCOUNT_SIGNATURE, FALSE);
444 signature = g_strdup ("");
447 msg = modest_tny_msg_new ("", from_str, "", "", "", signature, NULL);
449 g_printerr ("modest: failed to create new msg\n");
453 folder = modest_tny_account_get_special_folder (account, TNY_FOLDER_TYPE_DRAFTS);
455 g_printerr ("modest: failed to find Drafts folder\n");
459 /* tny_folder_add_msg (folder, msg, &err); */
461 /* g_printerr ("modest: error adding msg to Drafts folder: %s", */
463 /* g_error_free (err); */
467 /* Create and register edit window */
468 msg_win = modest_msg_edit_window_new (msg, account_name);
469 mgr = modest_runtime_get_window_mgr ();
470 modest_window_mgr_register_window (mgr, msg_win);
473 gtk_window_set_transient_for (GTK_WINDOW (msg_win),
475 gtk_widget_show_all (GTK_WIDGET (msg_win));
478 g_free (account_name);
482 g_object_unref (G_OBJECT(account));
484 g_object_unref (G_OBJECT(msg));
486 g_object_unref (G_OBJECT(folder));
490 headers_action_open (TnyHeader *header,
494 modest_ui_actions_on_header_activated (MODEST_HEADER_VIEW (user_data),
496 MODEST_MAIN_WINDOW (win));
500 modest_ui_actions_on_open (GtkAction *action, ModestWindow *win)
502 GtkWidget *header_view;
504 /* Get header view */
505 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
506 MODEST_WIDGET_TYPE_HEADER_VIEW);
508 /* Open each message */
509 do_headers_action (win, headers_action_open, header_view);
514 open_msg_func (const GObject *obj, TnyMsg *msg, gpointer user_data)
516 ModestWindowMgr *mgr = NULL;
517 ModestWindow *parent_win = NULL;
518 ModestWindow *win = NULL;
519 HeaderActivatedHelper *helper = NULL;
520 TnyFolderType folder_type = TNY_FOLDER_TYPE_UNKNOWN;
521 gchar *account = NULL;
523 g_return_if_fail (MODEST_IS_WINDOW(obj));
524 g_return_if_fail (user_data != NULL);
526 /* TODO: Show an error? (review the specs) */
530 parent_win = MODEST_WINDOW(obj);
531 helper = (HeaderActivatedHelper *) user_data;
533 /* Mark header as read */
534 headers_action_mark_as_read (helper->header, MODEST_WINDOW(parent_win), NULL);
537 account = g_strdup(modest_window_get_active_account(MODEST_WINDOW(parent_win)));
539 account = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
541 /* Gets foldert type (OUTBOX headers will be opened in edit window */
542 if (modest_tny_folder_is_local_folder (helper->folder))
543 folder_type = modest_tny_folder_get_local_folder_type (helper->folder);
545 switch (folder_type) {
546 case TNY_FOLDER_TYPE_DRAFTS:
547 win = modest_msg_edit_window_new ((TnyMsg *) msg, account);
550 if (helper->model != NULL)
551 win = modest_msg_view_window_new_with_header_model ((TnyMsg *) msg, account, helper->model, helper->row_reference);
553 win = modest_msg_view_window_new ((TnyMsg *) msg, account);
556 /* Register and show new window */
558 mgr = modest_runtime_get_window_mgr ();
559 modest_window_mgr_register_window (mgr, win);
560 gtk_window_set_transient_for (GTK_WINDOW (win), GTK_WINDOW (parent_win));
561 gtk_widget_show_all (GTK_WIDGET(win));
566 /* g_object_unref (G_OBJECT(msg)); */
567 g_object_unref (G_OBJECT(helper->folder));
568 g_object_unref (G_OBJECT(helper->header));
569 gtk_tree_row_reference_free (helper->row_reference);
570 g_slice_free (HeaderActivatedHelper, helper);
574 free_reply_forward_helper (gpointer data)
576 ReplyForwardHelper *helper;
578 helper = (ReplyForwardHelper *) data;
579 g_free (helper->account_name);
580 g_slice_free (ReplyForwardHelper, helper);
584 reply_forward_func (const GObject *obj, TnyMsg *msg, gpointer user_data)
587 ReplyForwardHelper *rf_helper;
588 ModestWindow *msg_win;
589 ModestEditType edit_type;
592 TnyFolder *folder = NULL;
593 TnyAccount *account = NULL;
594 ModestWindowMgr *mgr;
595 gchar *signature = NULL;
597 g_return_if_fail (user_data != NULL);
598 rf_helper = (ReplyForwardHelper *) user_data;
600 from = modest_account_mgr_get_from_string (modest_runtime_get_account_mgr(),
601 rf_helper->account_name);
602 if (modest_account_mgr_get_bool (modest_runtime_get_account_mgr(),
603 rf_helper->account_name,
604 MODEST_ACCOUNT_USE_SIGNATURE, FALSE)) {
605 signature = modest_account_mgr_get_string (modest_runtime_get_account_mgr (),
606 rf_helper->account_name,
607 MODEST_ACCOUNT_SIGNATURE, FALSE);
610 /* Create reply mail */
611 switch (rf_helper->action) {
614 modest_tny_msg_create_reply_msg ((TnyMsg *) msg, from, signature,
615 rf_helper->reply_forward_type,
616 MODEST_TNY_MSG_REPLY_MODE_SENDER);
618 case ACTION_REPLY_TO_ALL:
620 modest_tny_msg_create_reply_msg ((TnyMsg *) msg, from, signature, rf_helper->reply_forward_type,
621 MODEST_TNY_MSG_REPLY_MODE_ALL);
622 edit_type = MODEST_EDIT_TYPE_REPLY;
626 modest_tny_msg_create_forward_msg ((TnyMsg *) msg, from, signature, rf_helper->reply_forward_type);
627 edit_type = MODEST_EDIT_TYPE_FORWARD;
630 g_return_if_reached ();
637 g_printerr ("modest: failed to create message\n");
641 account = modest_tny_account_store_get_tny_account_by_account (modest_runtime_get_account_store(),
642 rf_helper->account_name,
643 TNY_ACCOUNT_TYPE_STORE);
645 g_printerr ("modest: failed to get tnyaccount for '%s'\n", rf_helper->account_name);
649 folder = modest_tny_account_get_special_folder (account, TNY_FOLDER_TYPE_DRAFTS);
651 g_printerr ("modest: failed to find Drafts folder\n");
655 tny_folder_add_msg (folder, (TnyMsg *) msg, &err);
656 g_object_unref (msg);
658 g_printerr ("modest: error adding msg to Drafts folder: %s",
664 /* Create and register the windows */
665 msg_win = modest_msg_edit_window_new (new_msg, rf_helper->account_name);
666 mgr = modest_runtime_get_window_mgr ();
667 modest_window_mgr_register_window (mgr, msg_win);
669 /* Show edit window */
670 gtk_widget_show_all (GTK_WIDGET (msg_win));
674 g_object_unref (G_OBJECT (new_msg));
676 g_object_unref (G_OBJECT (folder));
678 g_object_unref (G_OBJECT (account));
682 * Common code for the reply and forward actions
685 reply_forward (ReplyForwardAction action, ModestWindow *win)
687 ModestMailOperation *mail_op = NULL;
688 TnyList *header_list = NULL;
689 ReplyForwardHelper *rf_helper = NULL;
690 guint reply_forward_type;
692 g_return_if_fail (MODEST_IS_WINDOW(win));
694 header_list = get_selected_headers (win);
698 reply_forward_type = modest_conf_get_int (modest_runtime_get_conf (),
699 (action == ACTION_FORWARD) ? MODEST_CONF_FORWARD_TYPE : MODEST_CONF_REPLY_TYPE,
701 /* We assume that we can only select messages of the
702 same folder and that we reply all of them from the
703 same account. In fact the interface currently only
704 allows single selection */
707 rf_helper = g_slice_new0 (ReplyForwardHelper);
708 rf_helper->reply_forward_type = reply_forward_type;
709 rf_helper->action = action;
710 rf_helper->account_name = g_strdup (modest_window_get_active_account (win));
711 if (!rf_helper->account_name)
712 rf_helper->account_name =
713 modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
715 if (MODEST_IS_MSG_VIEW_WINDOW(win)) {
717 msg = modest_msg_view_window_get_message(MODEST_MSG_VIEW_WINDOW(win));
719 g_printerr ("modest: no message found\n");
722 reply_forward_func (G_OBJECT(win), g_object_ref (msg), rf_helper);
724 /* Retrieve messages */
725 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_RECEIVE, G_OBJECT(win));
726 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
727 modest_mail_operation_get_msgs_full (mail_op,
731 free_reply_forward_helper);
734 g_object_unref(mail_op);
739 modest_ui_actions_on_reply (GtkAction *action, ModestWindow *win)
741 g_return_if_fail (MODEST_IS_WINDOW(win));
743 reply_forward (ACTION_REPLY, win);
747 modest_ui_actions_on_forward (GtkAction *action, ModestWindow *win)
749 g_return_if_fail (MODEST_IS_WINDOW(win));
751 reply_forward (ACTION_FORWARD, win);
755 modest_ui_actions_on_reply_all (GtkAction *action, ModestWindow *win)
757 g_return_if_fail (MODEST_IS_WINDOW(win));
759 reply_forward (ACTION_REPLY_TO_ALL, win);
763 modest_ui_actions_on_next (GtkAction *action,
764 ModestWindow *window)
766 if (MODEST_IS_MAIN_WINDOW (window)) {
767 GtkWidget *header_view;
769 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(window),
770 MODEST_WIDGET_TYPE_HEADER_VIEW);
774 modest_header_view_select_next (MODEST_HEADER_VIEW(header_view));
775 } else if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
776 modest_msg_view_window_select_next_message (MODEST_MSG_VIEW_WINDOW (window));
778 g_return_if_reached ();
783 modest_ui_actions_on_prev (GtkAction *action,
784 ModestWindow *window)
786 g_return_if_fail (MODEST_IS_WINDOW(window));
788 if (MODEST_IS_MAIN_WINDOW (window)) {
789 GtkWidget *header_view;
790 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(window),
791 MODEST_WIDGET_TYPE_HEADER_VIEW);
795 modest_header_view_select_prev (MODEST_HEADER_VIEW(header_view));
796 } else if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
797 modest_msg_view_window_select_previous_message (MODEST_MSG_VIEW_WINDOW (window));
799 g_return_if_reached ();
804 modest_ui_actions_on_sort (GtkAction *action,
805 ModestWindow *window)
807 g_return_if_fail (MODEST_IS_WINDOW(window));
809 if (MODEST_IS_MAIN_WINDOW (window)) {
810 GtkWidget *header_view;
811 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW(window),
812 MODEST_WIDGET_TYPE_HEADER_VIEW);
816 /* Show sorting dialog */
817 modest_platform_run_sort_dialog (GTK_WINDOW (window), MODEST_SORT_HEADERS);
821 /** Check that an appropriate connection is open.
823 gboolean check_for_connection (const gchar *account_name)
825 TnyDevice *device = modest_runtime_get_device ();
828 g_assert (TNY_IS_MAEMO_CONIC_DEVICE (device));
830 TnyMaemoConicDevice *maemo_device = TNY_MAEMO_CONIC_DEVICE (device);
833 if (tny_device_is_online (device))
836 modest_platform_connect_and_wait (NULL);
838 /* TODO: Wait until a result. */
844 * This function performs the send & receive required actions. The
845 * window it's used to create the mail operation. Tipically it should
846 * be allways the main window, but we pass it as argument in order to
850 modest_ui_actions_do_send_receive (const gchar *account_name, ModestWindow *win)
852 gchar *acc_name = NULL;
854 /* If no account name was provided get the current account, if
855 there is none either then pick the default one */
857 acc_name = g_strdup (modest_window_get_active_account(win));
859 acc_name = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr());
861 g_printerr ("modest: cannot get default account\n");
865 acc_name = g_strdup (account_name);
868 /* Send & receive. Do not continue if no suitable connection
870 if (check_for_connection (acc_name)) {
871 /* As per the UI spec,
872 * for POP accounts, we should receive,
873 * for IMAP we should synchronize everything, including receiving,
874 * for SMTP we should send,
875 * first receiving, then sending:
877 /* Create the mail operation */
878 /* TODO: The spec wants us to first do any pending deletions, before receiving. */
879 ModestMailOperation *mail_op;
880 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_RECEIVE, G_OBJECT(win));
881 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
882 modest_mail_operation_update_account (mail_op, acc_name);
883 g_object_unref (G_OBJECT (mail_op));
890 * Refreshes all accounts. This function will be used by automatic
894 modest_ui_actions_do_send_receive_all (ModestWindow *win)
896 GSList *account_names, *iter;
898 account_names = modest_account_mgr_account_names (modest_runtime_get_account_mgr(),
901 iter = account_names;
903 modest_ui_actions_do_send_receive ((const char*) iter->data, win);
904 iter = g_slist_next (iter);
907 g_slist_foreach (account_names, (GFunc) g_free, NULL);
908 g_slist_free (account_names);
912 * Handler of the click on Send&Receive button in the main toolbar
915 modest_ui_actions_on_send_receive (GtkAction *action, ModestWindow *win)
917 /* Check that at least one account exists: */
918 GSList *account_names = modest_account_mgr_account_names (modest_runtime_get_account_mgr(),
919 TRUE /* enabled accounts only */);
920 gboolean accounts_exist = account_names != NULL;
921 g_slist_free (account_names);
923 /* If not, allow the user to create an account before trying to send/receive. */
925 modest_ui_actions_on_accounts (NULL, win);
927 /* Refresh the active account */
928 modest_ui_actions_do_send_receive (NULL, win);
933 modest_ui_actions_toggle_header_list_view (GtkAction *action, ModestMainWindow *main_window)
936 GtkWidget *header_view;
938 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
940 header_view = modest_main_window_get_child_widget (main_window,
941 MODEST_WIDGET_TYPE_HEADER_VIEW);
945 conf = modest_runtime_get_conf ();
947 /* what is saved/restored is depending on the style; thus; we save with
948 * old style, then update the style, and restore for this new style
950 modest_widget_memory_save (conf, G_OBJECT(header_view), MODEST_CONF_HEADER_VIEW_KEY);
952 if (modest_header_view_get_style
953 (MODEST_HEADER_VIEW(header_view)) == MODEST_HEADER_VIEW_STYLE_DETAILS)
954 modest_header_view_set_style (MODEST_HEADER_VIEW(header_view),
955 MODEST_HEADER_VIEW_STYLE_TWOLINES);
957 modest_header_view_set_style (MODEST_HEADER_VIEW(header_view),
958 MODEST_HEADER_VIEW_STYLE_DETAILS);
960 modest_widget_memory_restore (conf, G_OBJECT(header_view),
961 MODEST_CONF_HEADER_VIEW_KEY);
966 modest_ui_actions_on_header_selected (ModestHeaderView *header_view,
968 ModestMainWindow *main_window)
970 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
972 /* If no header has been selected then exit */
976 /* Update Main window title */
977 if (GTK_WIDGET_HAS_FOCUS (header_view)) {
978 const gchar *subject = tny_header_get_subject (header);
979 if (subject && strcmp (subject, ""))
980 gtk_window_set_title (GTK_WINDOW (main_window), subject);
982 gtk_window_set_title (GTK_WINDOW (main_window), _("mail_va_no_subject"));
987 modest_ui_actions_on_header_activated (ModestHeaderView *header_view,
989 ModestMainWindow *main_window)
991 ModestMailOperation *mail_op = NULL;
992 HeaderActivatedHelper *helper = NULL;
993 ModestWindowMgr *mgr = NULL;
994 ModestWindow *win = NULL;
995 GtkTreeModel *model = NULL;
996 GtkTreeSelection *sel = NULL;
997 GList *sel_list = NULL;
999 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1004 /* Look if we already have a message view for that header */
1005 mgr = modest_runtime_get_window_mgr ();
1006 win = modest_window_mgr_find_window_by_msguid (mgr, tny_header_get_uid (header));
1010 helper = g_slice_new0 (HeaderActivatedHelper);
1011 helper->folder = tny_header_get_folder (header);
1012 helper->header = g_object_ref(header);
1013 helper->model = NULL;
1015 /* Get headers tree model and selected row reference to build message view */
1016 sel = gtk_tree_view_get_selection (GTK_TREE_VIEW (header_view));
1017 sel_list = gtk_tree_selection_get_selected_rows (sel, &model);
1018 if (sel_list != NULL) {
1021 helper->model = model;
1022 helper->row_reference = gtk_tree_row_reference_new (model, (GtkTreePath *) sel_list->data);
1024 g_list_foreach (sel_list, (GFunc) gtk_tree_path_free, NULL);
1025 g_list_free (sel_list);
1028 /* New mail operation */
1029 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_RECEIVE, G_OBJECT(main_window));
1030 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op);
1031 modest_mail_operation_get_msg (mail_op, header, open_msg_func, helper);
1034 g_object_unref (mail_op);
1038 set_active_account_from_tny_account (TnyAccount *account,
1039 ModestWindow *window)
1041 TnyAccount *modest_server_account;
1042 const gchar *server_acc_name;
1043 gchar *modest_acc_name;
1045 server_acc_name = tny_account_get_id (account);
1046 /* We need the TnyAccount provided by the
1047 account store because that is the one that
1048 knows the name of the Modest account */
1049 modest_server_account =
1050 modest_tny_account_store_get_tny_account_by_id (modest_runtime_get_account_store (),
1052 modest_acc_name = (gchar *) g_object_get_data (G_OBJECT (modest_server_account), "modest_account");
1053 modest_window_set_active_account (window, modest_acc_name);
1054 g_object_unref (modest_server_account);
1058 modest_ui_actions_on_folder_selection_changed (ModestFolderView *folder_view,
1059 TnyFolderStore *folder_store,
1061 ModestMainWindow *main_window)
1064 GtkWidget *header_view;
1065 TnyAccount *account;
1067 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1069 header_view = modest_main_window_get_child_widget(main_window,
1070 MODEST_WIDGET_TYPE_HEADER_VIEW);
1074 conf = modest_runtime_get_conf ();
1076 if (TNY_IS_ACCOUNT (folder_store)) {
1077 /* Update active account */
1078 set_active_account_from_tny_account (TNY_ACCOUNT (folder_store), MODEST_WINDOW (main_window));
1079 /* Show account details */
1080 modest_main_window_set_contents_style (main_window, MODEST_MAIN_WINDOW_CONTENTS_STYLE_DETAILS);
1082 if (TNY_IS_FOLDER (folder_store) && selected) {
1083 /* Update the active account */
1084 account = tny_folder_get_account (TNY_FOLDER (folder_store));
1085 set_active_account_from_tny_account (account, MODEST_WINDOW (main_window));
1086 g_object_unref (account);
1088 /* Set folder on header view */
1089 modest_main_window_set_contents_style (main_window,
1090 MODEST_MAIN_WINDOW_CONTENTS_STYLE_HEADERS);
1091 modest_header_view_set_folder (MODEST_HEADER_VIEW(header_view),
1092 TNY_FOLDER (folder_store));
1093 modest_widget_memory_restore (conf, G_OBJECT(header_view),
1094 MODEST_CONF_HEADER_VIEW_KEY);
1096 /* Update the active account */
1097 modest_window_set_active_account (MODEST_WINDOW (main_window), NULL);
1098 /* Do not show folder */
1099 modest_widget_memory_save (conf, G_OBJECT (header_view), MODEST_CONF_HEADER_VIEW_KEY);
1100 modest_header_view_set_folder (MODEST_HEADER_VIEW(header_view), NULL);
1106 modest_ui_actions_on_item_not_found (ModestHeaderView *header_view,ModestItemType type,
1113 item = (type == MODEST_ITEM_TYPE_FOLDER) ? "folder" : "message";
1115 if (g_main_depth > 0)
1116 gdk_threads_enter ();
1117 online = tny_device_is_online (modest_runtime_get_device());
1120 /* already online -- the item is simply not there... */
1121 dialog = gtk_message_dialog_new (GTK_WINDOW (win),
1123 GTK_MESSAGE_WARNING,
1125 _("The %s you selected cannot be found"),
1127 gtk_dialog_run (GTK_DIALOG(dialog));
1129 dialog = gtk_dialog_new_with_buttons (_("Connection requested"),
1133 GTK_RESPONSE_REJECT,
1135 GTK_RESPONSE_ACCEPT,
1137 txt = g_strdup_printf (_("This %s is not available in offline mode.\n"
1138 "Do you want to get online?"), item);
1139 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox),
1140 gtk_label_new (txt), FALSE, FALSE, 0);
1141 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
1144 gtk_window_set_default_size (GTK_WINDOW(dialog), 300, 300);
1145 if (gtk_dialog_run (GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT) {
1146 // modest_platform_connect_and_wait ();;
1149 gtk_widget_destroy (dialog);
1150 if (g_main_depth > 0)
1151 gdk_threads_leave ();
1155 modest_ui_actions_on_msg_link_hover (ModestMsgView *msgview, const gchar* link,
1158 /* g_message ("%s %s", __FUNCTION__, link); */
1163 modest_ui_actions_on_msg_link_clicked (ModestMsgView *msgview, const gchar* link,
1166 modest_platform_activate_uri (link);
1170 modest_ui_actions_on_msg_link_contextual (ModestMsgView *msgview, const gchar* link,
1173 modest_platform_show_uri_popup (link);
1177 modest_ui_actions_on_msg_attachment_clicked (ModestMsgView *msgview, TnyMimePart *mime_part,
1180 modest_msg_view_window_view_attachment (MODEST_MSG_VIEW_WINDOW (win), mime_part);
1184 modest_ui_actions_on_msg_recpt_activated (ModestMsgView *msgview,
1185 const gchar *address,
1188 /* g_message ("%s %s", __FUNCTION__, address); */
1192 modest_ui_actions_on_save_to_drafts (GtkWidget *widget, ModestMsgEditWindow *edit_window)
1194 TnyTransportAccount *transport_account;
1195 ModestMailOperation *mail_operation;
1197 gchar *account_name, *from;
1198 ModestAccountMgr *account_mgr;
1200 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW(edit_window));
1202 data = modest_msg_edit_window_get_msg_data (edit_window);
1204 account_mgr = modest_runtime_get_account_mgr();
1205 account_name = g_strdup(modest_window_get_active_account (MODEST_WINDOW(edit_window)));
1207 account_name = modest_account_mgr_get_default_account (account_mgr);
1208 if (!account_name) {
1209 g_printerr ("modest: no account found\n");
1210 modest_msg_edit_window_free_msg_data (edit_window, data);
1214 TNY_TRANSPORT_ACCOUNT(modest_tny_account_store_get_tny_account_by_account
1215 (modest_runtime_get_account_store(),
1217 TNY_ACCOUNT_TYPE_TRANSPORT));
1218 if (!transport_account) {
1219 g_printerr ("modest: no transport account found for '%s'\n", account_name);
1220 g_free (account_name);
1221 modest_msg_edit_window_free_msg_data (edit_window, data);
1224 from = modest_account_mgr_get_from_string (account_mgr, account_name);
1226 /* Create the mail operation */
1227 mail_operation = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_INFO, G_OBJECT(edit_window));
1228 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_operation);
1230 modest_mail_operation_save_to_drafts (mail_operation,
1240 data->priority_flags);
1243 g_free (account_name);
1244 g_object_unref (G_OBJECT (transport_account));
1245 g_object_unref (G_OBJECT (mail_operation));
1247 modest_msg_edit_window_free_msg_data (edit_window, data);
1249 /* Save settings and close the window */
1250 gtk_widget_destroy (GTK_WIDGET (edit_window));
1253 modest_ui_actions_on_send (GtkWidget *widget, ModestMsgEditWindow *edit_window)
1255 TnyTransportAccount *transport_account;
1256 ModestMailOperation *mail_operation;
1258 gchar *account_name, *from;
1259 ModestAccountMgr *account_mgr;
1261 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW(edit_window));
1263 if (!modest_msg_edit_window_check_names (edit_window))
1266 data = modest_msg_edit_window_get_msg_data (edit_window);
1268 /* FIXME: Code added just for testing. The final version will
1269 use the send queue provided by tinymail and some
1271 account_mgr = modest_runtime_get_account_mgr();
1272 account_name = g_strdup(modest_window_get_active_account (MODEST_WINDOW(edit_window)));
1274 account_name = modest_account_mgr_get_default_account (account_mgr);
1275 if (!account_name) {
1276 g_printerr ("modest: no account found\n");
1277 modest_msg_edit_window_free_msg_data (edit_window, data);
1281 TNY_TRANSPORT_ACCOUNT(modest_tny_account_store_get_transport_account_for_open_connection
1282 (modest_runtime_get_account_store(),
1284 if (!transport_account) {
1285 g_printerr ("modest: no transport account found for '%s'\n", account_name);
1286 g_free (account_name);
1287 modest_msg_edit_window_free_msg_data (edit_window, data);
1290 from = modest_account_mgr_get_from_string (account_mgr, account_name);
1292 /* Create the mail operation */
1293 mail_operation = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_SEND, G_OBJECT(edit_window));
1294 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_operation);
1296 modest_mail_operation_send_new_mail (mail_operation,
1306 data->priority_flags);
1309 g_free (account_name);
1310 g_object_unref (G_OBJECT (transport_account));
1311 g_object_unref (G_OBJECT (mail_operation));
1313 modest_msg_edit_window_free_msg_data (edit_window, data);
1315 /* Save settings and close the window */
1316 gtk_widget_destroy (GTK_WIDGET (edit_window));
1320 modest_ui_actions_on_toggle_bold (GtkToggleAction *action,
1321 ModestMsgEditWindow *window)
1323 ModestMsgEditFormatState *format_state = NULL;
1325 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1326 g_return_if_fail (GTK_IS_TOGGLE_ACTION (action));
1328 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW (window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
1331 format_state = modest_msg_edit_window_get_format_state (window);
1332 g_return_if_fail (format_state != NULL);
1334 format_state->bold = gtk_toggle_action_get_active (action);
1335 modest_msg_edit_window_set_format_state (window, format_state);
1336 g_free (format_state);
1341 modest_ui_actions_on_toggle_italics (GtkToggleAction *action,
1342 ModestMsgEditWindow *window)
1344 ModestMsgEditFormatState *format_state = NULL;
1346 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1347 g_return_if_fail (GTK_IS_TOGGLE_ACTION (action));
1349 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
1352 format_state = modest_msg_edit_window_get_format_state (window);
1353 g_return_if_fail (format_state != NULL);
1355 format_state->italics = gtk_toggle_action_get_active (action);
1356 modest_msg_edit_window_set_format_state (window, format_state);
1357 g_free (format_state);
1362 modest_ui_actions_on_toggle_bullets (GtkToggleAction *action,
1363 ModestMsgEditWindow *window)
1365 ModestMsgEditFormatState *format_state = NULL;
1367 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1368 g_return_if_fail (GTK_IS_TOGGLE_ACTION (action));
1370 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW (window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
1373 format_state = modest_msg_edit_window_get_format_state (window);
1374 g_return_if_fail (format_state != NULL);
1376 format_state->bullet = gtk_toggle_action_get_active (action);
1377 modest_msg_edit_window_set_format_state (window, format_state);
1378 g_free (format_state);
1383 modest_ui_actions_on_change_justify (GtkRadioAction *action,
1384 GtkRadioAction *selected,
1385 ModestMsgEditWindow *window)
1387 ModestMsgEditFormatState *format_state = NULL;
1388 GtkJustification value;
1390 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1392 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
1395 value = gtk_radio_action_get_current_value (selected);
1397 format_state = modest_msg_edit_window_get_format_state (window);
1398 g_return_if_fail (format_state != NULL);
1400 format_state->justification = value;
1401 modest_msg_edit_window_set_format_state (window, format_state);
1402 g_free (format_state);
1406 modest_ui_actions_on_select_editor_color (GtkAction *action,
1407 ModestMsgEditWindow *window)
1409 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1410 g_return_if_fail (GTK_IS_ACTION (action));
1412 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
1415 modest_msg_edit_window_select_color (window);
1419 modest_ui_actions_on_select_editor_background_color (GtkAction *action,
1420 ModestMsgEditWindow *window)
1422 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1423 g_return_if_fail (GTK_IS_ACTION (action));
1425 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
1428 modest_msg_edit_window_select_background_color (window);
1432 modest_ui_actions_on_insert_image (GtkAction *action,
1433 ModestMsgEditWindow *window)
1435 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1436 g_return_if_fail (GTK_IS_ACTION (action));
1438 if (modest_msg_edit_window_get_format (MODEST_MSG_EDIT_WINDOW(window)) == MODEST_MSG_EDIT_FORMAT_TEXT)
1441 modest_msg_edit_window_insert_image (window);
1445 modest_ui_actions_on_attach_file (GtkAction *action,
1446 ModestMsgEditWindow *window)
1448 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1449 g_return_if_fail (GTK_IS_ACTION (action));
1451 modest_msg_edit_window_attach_file (window);
1455 modest_ui_actions_on_remove_attachments (GtkAction *action,
1456 ModestMsgEditWindow *window)
1458 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1459 g_return_if_fail (GTK_IS_ACTION (action));
1461 modest_msg_edit_window_remove_attachments (window, NULL);
1465 * Shows a dialog with an entry that asks for some text. The returned
1466 * value must be freed by the caller. The dialog window title will be
1470 ask_for_folder_name (GtkWindow *parent_window,
1473 GtkWidget *dialog, *entry;
1474 gchar *folder_name = NULL;
1476 /* Ask for folder name */
1477 dialog = gtk_dialog_new_with_buttons (_("New Folder Name"),
1481 GTK_RESPONSE_REJECT,
1483 GTK_RESPONSE_ACCEPT,
1485 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox),
1486 gtk_label_new(title),
1489 entry = gtk_entry_new_with_max_length (40);
1490 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox),
1494 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
1496 if (gtk_dialog_run (GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT)
1497 folder_name = g_strdup (gtk_entry_get_text (GTK_ENTRY (entry)));
1499 gtk_widget_destroy (dialog);
1505 modest_ui_actions_on_new_folder (GtkAction *action, ModestMainWindow *main_window)
1507 TnyFolderStore *parent_folder;
1508 GtkWidget *folder_view;
1510 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1512 folder_view = modest_main_window_get_child_widget (main_window,
1513 MODEST_WIDGET_TYPE_FOLDER_VIEW);
1517 parent_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1519 if (parent_folder) {
1520 gboolean finished = FALSE;
1522 gchar *folder_name = NULL, *suggested_name = NULL;
1524 /* Run the new folder dialog */
1526 result = modest_platform_run_new_folder_dialog (GTK_WINDOW (main_window),
1531 if (result == GTK_RESPONSE_REJECT) {
1534 ModestMailOperation *mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_INFO, G_OBJECT(main_window));
1535 TnyFolder *new_folder = NULL;
1537 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
1540 new_folder = modest_mail_operation_create_folder (mail_op,
1542 (const gchar *) folder_name);
1544 g_object_unref (new_folder);
1548 /* /\* TODO: check error and follow proper actions *\/ */
1549 /* /\* suggested_name = X; *\/ */
1550 /* /\* Show error to the user *\/ */
1551 /* modest_platform_run_information_dialog (GTK_WINDOW (main_window), */
1552 /* _("mail_in_ui_folder_create_error")); */
1554 g_object_unref (mail_op);
1556 g_free (folder_name);
1560 g_object_unref (parent_folder);
1565 modest_ui_actions_on_rename_folder (GtkAction *action,
1566 ModestMainWindow *main_window)
1568 TnyFolderStore *folder;
1569 GtkWidget *folder_view;
1570 GtkWidget *header_view;
1572 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1574 folder_view = modest_main_window_get_child_widget (main_window,
1575 MODEST_WIDGET_TYPE_FOLDER_VIEW);
1579 header_view = modest_main_window_get_child_widget (main_window,
1580 MODEST_WIDGET_TYPE_HEADER_VIEW);
1585 folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW(folder_view));
1587 if (folder && TNY_IS_FOLDER (folder)) {
1589 folder_name = ask_for_folder_name (GTK_WINDOW (main_window),
1590 _("Please enter a new name for the folder"));
1592 if (folder_name != NULL && strlen (folder_name) > 0) {
1593 ModestMailOperation *mail_op;
1595 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_INFO, G_OBJECT(main_window));
1596 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
1599 modest_header_view_set_folder (MODEST_HEADER_VIEW (header_view), NULL);
1601 modest_mail_operation_rename_folder (mail_op,
1602 TNY_FOLDER (folder),
1603 (const gchar *) folder_name);
1605 g_object_unref (mail_op);
1606 g_free (folder_name);
1608 g_object_unref (folder);
1613 delete_folder (ModestMainWindow *main_window, gboolean move_to_trash)
1615 TnyFolderStore *folder;
1616 GtkWidget *folder_view;
1620 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1622 folder_view = modest_main_window_get_child_widget (main_window,
1623 MODEST_WIDGET_TYPE_FOLDER_VIEW);
1627 folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
1629 /* Show an error if it's an account */
1630 if (!TNY_IS_FOLDER (folder)) {
1631 modest_platform_run_information_dialog (GTK_WINDOW (main_window),
1632 _("mail_in_ui_folder_delete_error"));
1637 message = g_strdup_printf (_("mcen_nc_delete_folder_text"),
1638 tny_folder_get_name (TNY_FOLDER (folder)));
1639 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (main_window),
1640 (const gchar *) message);
1643 if (response == GTK_RESPONSE_OK) {
1644 ModestMailOperation *mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_DELETE, G_OBJECT(main_window));
1646 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
1648 modest_mail_operation_remove_folder (mail_op, TNY_FOLDER (folder), move_to_trash);
1650 /* Show error if happened */
1651 if (modest_mail_operation_get_error (mail_op))
1652 modest_platform_run_information_dialog (GTK_WINDOW (main_window),
1653 _("mail_in_ui_folder_delete_error"));
1655 g_object_unref (G_OBJECT (mail_op));
1658 g_object_unref (G_OBJECT (folder));
1662 modest_ui_actions_on_delete_folder (GtkAction *action,
1663 ModestMainWindow *main_window)
1665 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1667 delete_folder (main_window, FALSE);
1671 modest_ui_actions_on_move_folder_to_trash_folder (GtkAction *action, ModestMainWindow *main_window)
1673 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
1675 delete_folder (main_window, TRUE);
1679 modest_ui_actions_on_password_requested (TnyAccountStore *account_store,
1680 const gchar* server_account_name,
1685 ModestMainWindow *main_window)
1687 g_return_if_fail(server_account_name);
1688 /* printf("DEBUG: %s: server_account_name=%s\n", __FUNCTION__, server_account_name); */
1690 /* Initalize output parameters: */
1697 #ifdef MODEST_PLATFORM_MAEMO
1698 /* Maemo uses a different (awkward) button order,
1699 * It should probably just use gtk_alternative_dialog_button_order ().
1701 GtkWidget *dialog = gtk_dialog_new_with_buttons (_("mail_ti_password_protected"),
1705 GTK_RESPONSE_ACCEPT,
1707 GTK_RESPONSE_REJECT,
1710 GtkWidget *dialog = gtk_dialog_new_with_buttons (_("mail_ti_password_protected"),
1714 GTK_RESPONSE_REJECT,
1716 GTK_RESPONSE_ACCEPT,
1718 #endif /* MODEST_PLATFORM_MAEMO */
1720 gtk_window_set_transient_for (GTK_WINDOW(dialog), GTK_WINDOW(main_window));
1722 gchar *server_name = modest_server_account_get_hostname (
1723 modest_runtime_get_account_mgr(), server_account_name);
1725 /* This causes a warning because the logical ID has no %s in it,
1726 * though the translation does, but there is not much we can do about that: */
1727 gchar *txt = g_strdup_printf (_("mail_ia_password_info"), server_name);
1728 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), gtk_label_new(txt),
1731 g_free (server_name);
1735 gchar *initial_username = modest_server_account_get_username (
1736 modest_runtime_get_account_mgr(), server_account_name);
1738 GtkWidget *entry_username = gtk_entry_new ();
1739 if (initial_username)
1740 gtk_entry_set_text (GTK_ENTRY (entry_username), initial_username);
1741 /* Dim this if a connection has ever succeeded with this username,
1742 * as per the UI spec: */
1743 const gboolean username_known =
1744 modest_server_account_get_username_has_succeeded(
1745 modest_runtime_get_account_mgr(), server_account_name);
1746 gtk_widget_set_sensitive (entry_username, !username_known);
1748 #ifdef MODEST_PLATFORM_MAEMO
1749 /* Auto-capitalization is the default, so let's turn it off: */
1750 hildon_gtk_entry_set_input_mode (GTK_ENTRY (entry_username), HILDON_GTK_INPUT_MODE_FULL);
1752 /* Create a size group to be used by all captions.
1753 * Note that HildonCaption does not create a default size group if we do not specify one.
1754 * We use GTK_SIZE_GROUP_HORIZONTAL, so that the widths are the same. */
1755 GtkSizeGroup *sizegroup = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
1757 GtkWidget *caption = hildon_caption_new (sizegroup,
1758 _("mail_fi_username"), entry_username, NULL, HILDON_CAPTION_MANDATORY);
1759 gtk_widget_show (entry_username);
1760 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), caption,
1761 FALSE, FALSE, MODEST_MARGIN_HALF);
1762 gtk_widget_show (caption);
1764 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), entry_username,
1766 #endif /* MODEST_PLATFORM_MAEMO */
1769 GtkWidget *entry_password = gtk_entry_new ();
1770 gtk_entry_set_visibility (GTK_ENTRY(entry_password), FALSE);
1771 /* gtk_entry_set_invisible_char (GTK_ENTRY(entry_password), "*"); */
1773 #ifdef MODEST_PLATFORM_MAEMO
1774 /* Auto-capitalization is the default, so let's turn it off: */
1775 hildon_gtk_entry_set_input_mode (GTK_ENTRY (entry_password),
1776 HILDON_GTK_INPUT_MODE_FULL | HILDON_GTK_INPUT_MODE_INVISIBLE);
1778 caption = hildon_caption_new (sizegroup,
1779 _("mail_fi_password"), entry_password, NULL, HILDON_CAPTION_MANDATORY);
1780 gtk_widget_show (entry_password);
1781 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), caption,
1782 FALSE, FALSE, MODEST_MARGIN_HALF);
1783 gtk_widget_show (caption);
1784 g_object_unref (sizegroup);
1786 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), entry_password,
1788 #endif /* MODEST_PLATFORM_MAEMO */
1790 /* This is not in the Maemo UI spec:
1791 remember_pass_check = gtk_check_button_new_with_label (_("Remember password"));
1792 gtk_box_pack_start (GTK_BOX(GTK_DIALOG(dialog)->vbox), remember_pass_check,
1796 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
1798 if (gtk_dialog_run (GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT) {
1800 *username = g_strdup (gtk_entry_get_text (GTK_ENTRY(entry_username)));
1802 modest_server_account_set_username (
1803 modest_runtime_get_account_mgr(), server_account_name,
1806 const gboolean username_was_changed =
1807 (strcmp (*username, initial_username) != 0);
1808 if (username_was_changed) {
1809 /* To actually use a changed username,
1810 * we must reset the connection, according to pvanhoof.
1811 * This _might_ be a sensible way to do that: */
1812 TnyDevice *device = modest_runtime_get_device();
1813 tny_device_force_offline (device);
1814 tny_device_force_online (device);
1819 *password = g_strdup (gtk_entry_get_text (GTK_ENTRY(entry_password)));
1821 /* We do not save the password in the configuration,
1822 * because this function is only called for passwords that should
1823 * not be remembered:
1824 modest_server_account_set_password (
1825 modest_runtime_get_account_mgr(), server_account_name,
1844 /* This is not in the Maemo UI spec:
1845 if (gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON (remember_pass_check)))
1851 gtk_widget_destroy (dialog);
1853 printf ("DEBUG: %s: cancel=%d\n", __FUNCTION__, *cancel);
1857 modest_ui_actions_on_cut (GtkAction *action,
1858 ModestWindow *window)
1860 GtkWidget *focused_widget;
1862 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
1863 if (GTK_IS_EDITABLE (focused_widget)) {
1864 gtk_editable_cut_clipboard (GTK_EDITABLE(focused_widget));
1865 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
1866 GtkTextBuffer *buffer;
1867 GtkClipboard *clipboard;
1869 clipboard = gtk_clipboard_get (GDK_SELECTION_PRIMARY);
1870 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
1871 gtk_text_buffer_cut_clipboard (buffer, clipboard, TRUE);
1876 modest_ui_actions_on_copy (GtkAction *action,
1877 ModestWindow *window)
1879 GtkClipboard *clipboard;
1880 GtkWidget *focused_widget;
1882 clipboard = gtk_clipboard_get (GDK_SELECTION_PRIMARY);
1883 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
1884 if (GTK_IS_LABEL (focused_widget)) {
1885 gtk_clipboard_set_text (clipboard, gtk_label_get_text (GTK_LABEL (focused_widget)), -1);
1886 } else if (GTK_IS_EDITABLE (focused_widget)) {
1887 gtk_editable_copy_clipboard (GTK_EDITABLE(focused_widget));
1888 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
1889 GtkTextBuffer *buffer;
1891 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
1892 gtk_text_buffer_copy_clipboard (buffer, clipboard);
1897 modest_ui_actions_on_undo (GtkAction *action,
1898 ModestWindow *window)
1900 if (MODEST_IS_MSG_EDIT_WINDOW (window)) {
1901 modest_msg_edit_window_undo (MODEST_MSG_EDIT_WINDOW (window));
1903 g_return_if_reached ();
1908 modest_ui_actions_on_paste (GtkAction *action,
1909 ModestWindow *window)
1911 GtkWidget *focused_widget;
1913 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
1914 if (GTK_IS_EDITABLE (focused_widget)) {
1915 gtk_editable_paste_clipboard (GTK_EDITABLE(focused_widget));
1916 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
1917 GtkTextBuffer *buffer;
1918 GtkClipboard *clipboard;
1920 clipboard = gtk_clipboard_get (GDK_SELECTION_PRIMARY);
1921 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
1922 gtk_text_buffer_paste_clipboard (buffer, clipboard, NULL, TRUE);
1927 modest_ui_actions_on_select_all (GtkAction *action,
1928 ModestWindow *window)
1930 GtkWidget *focused_widget;
1932 focused_widget = gtk_window_get_focus (GTK_WINDOW (window));
1933 if (MODEST_IS_ATTACHMENTS_VIEW (focused_widget)) {
1934 modest_attachments_view_select_all (MODEST_ATTACHMENTS_VIEW (focused_widget));
1935 } else if (GTK_IS_LABEL (focused_widget)) {
1936 gtk_label_select_region (GTK_LABEL (focused_widget), 0, -1);
1937 } else if (GTK_IS_EDITABLE (focused_widget)) {
1938 gtk_editable_select_region (GTK_EDITABLE(focused_widget), 0, -1);
1939 } else if (GTK_IS_TEXT_VIEW (focused_widget)) {
1940 GtkTextBuffer *buffer;
1941 GtkTextIter start, end;
1943 buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused_widget));
1944 gtk_text_buffer_get_start_iter (buffer, &start);
1945 gtk_text_buffer_get_end_iter (buffer, &end);
1946 gtk_text_buffer_select_range (buffer, &start, &end);
1951 modest_ui_actions_on_mark_as_read (GtkAction *action,
1952 ModestWindow *window)
1954 g_return_if_fail (MODEST_IS_WINDOW(window));
1956 /* Mark each header as read */
1957 do_headers_action (window, headers_action_mark_as_read, NULL);
1961 modest_ui_actions_on_mark_as_unread (GtkAction *action,
1962 ModestWindow *window)
1964 g_return_if_fail (MODEST_IS_WINDOW(window));
1966 /* Mark each header as read */
1967 do_headers_action (window, headers_action_mark_as_unread, NULL);
1971 modest_ui_actions_on_change_zoom (GtkRadioAction *action,
1972 GtkRadioAction *selected,
1973 ModestWindow *window)
1977 value = gtk_radio_action_get_current_value (selected);
1978 if (MODEST_IS_WINDOW (window)) {
1979 modest_window_set_zoom (MODEST_WINDOW (window), ((gdouble)value)/100);
1983 void modest_ui_actions_msg_edit_on_change_priority (GtkRadioAction *action,
1984 GtkRadioAction *selected,
1985 ModestWindow *window)
1987 TnyHeaderFlags flags;
1988 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1990 flags = gtk_radio_action_get_current_value (selected);
1991 modest_msg_edit_window_set_priority_flags (MODEST_MSG_EDIT_WINDOW (window), flags);
1994 void modest_ui_actions_msg_edit_on_change_file_format (GtkRadioAction *action,
1995 GtkRadioAction *selected,
1996 ModestWindow *window)
2000 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2002 file_format = gtk_radio_action_get_current_value (selected);
2003 modest_msg_edit_window_set_file_format (MODEST_MSG_EDIT_WINDOW (window), file_format);
2008 modest_ui_actions_on_zoom_plus (GtkAction *action,
2009 ModestWindow *window)
2011 g_return_if_fail (MODEST_IS_WINDOW (window));
2013 modest_window_zoom_plus (MODEST_WINDOW (window));
2017 modest_ui_actions_on_zoom_minus (GtkAction *action,
2018 ModestWindow *window)
2020 g_return_if_fail (MODEST_IS_WINDOW (window));
2022 modest_window_zoom_minus (MODEST_WINDOW (window));
2026 modest_ui_actions_on_toggle_fullscreen (GtkToggleAction *toggle,
2027 ModestWindow *window)
2029 ModestWindowMgr *mgr;
2030 gboolean fullscreen, active;
2031 g_return_if_fail (MODEST_IS_WINDOW (window));
2033 mgr = modest_runtime_get_window_mgr ();
2035 active = (gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (toggle)))?1:0;
2036 fullscreen = modest_window_mgr_get_fullscreen_mode (mgr);
2038 if (active != fullscreen) {
2039 modest_window_mgr_set_fullscreen_mode (mgr, active);
2040 gtk_window_present (GTK_WINDOW (window));
2045 modest_ui_actions_on_change_fullscreen (GtkAction *action,
2046 ModestWindow *window)
2048 ModestWindowMgr *mgr;
2049 gboolean fullscreen;
2051 g_return_if_fail (MODEST_IS_WINDOW (window));
2053 mgr = modest_runtime_get_window_mgr ();
2054 fullscreen = modest_window_mgr_get_fullscreen_mode (mgr);
2055 modest_window_mgr_set_fullscreen_mode (mgr, !fullscreen);
2057 gtk_window_present (GTK_WINDOW (window));
2061 * Used by modest_ui_actions_on_details to call do_headers_action
2064 headers_action_show_details (TnyHeader *header,
2065 ModestWindow *window,
2072 dialog = modest_details_dialog_new_with_header (GTK_WINDOW (window), header);
2075 gtk_widget_show_all (dialog);
2076 gtk_dialog_run (GTK_DIALOG (dialog));
2078 gtk_widget_destroy (dialog);
2082 * Show the folder details in a ModestDetailsDialog widget
2085 show_folder_details (TnyFolder *folder,
2091 dialog = modest_details_dialog_new_with_folder (window, folder);
2094 gtk_widget_show_all (dialog);
2095 gtk_dialog_run (GTK_DIALOG (dialog));
2097 gtk_widget_destroy (dialog);
2101 * Show the header details in a ModestDetailsDialog widget
2104 modest_ui_actions_on_details (GtkAction *action,
2107 TnyList * headers_list;
2111 if (MODEST_IS_MSG_VIEW_WINDOW (win)) {
2114 msg = modest_msg_view_window_get_message (MODEST_MSG_VIEW_WINDOW (win));
2118 headers_list = get_selected_headers (win);
2122 iter = tny_list_create_iterator (headers_list);
2124 header = TNY_HEADER (tny_iterator_get_current (iter));
2125 headers_action_show_details (header, win, NULL);
2126 g_object_unref (header);
2128 g_object_unref (iter);
2130 } else if (MODEST_IS_MAIN_WINDOW (win)) {
2131 GtkWidget *folder_view, *header_view;
2133 /* Check which widget has the focus */
2134 folder_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
2135 MODEST_WIDGET_TYPE_FOLDER_VIEW);
2136 if (gtk_widget_is_focus (folder_view)) {
2139 folder = (TnyFolder *) modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
2141 /* Show only when it's a folder */
2142 if (!folder || !TNY_IS_FOLDER (folder))
2145 show_folder_details (folder, GTK_WINDOW (win));
2148 header_view = modest_main_window_get_child_widget (MODEST_MAIN_WINDOW (win),
2149 MODEST_WIDGET_TYPE_HEADER_VIEW);
2150 /* Show details of each header */
2151 do_headers_action (win, headers_action_show_details, header_view);
2157 modest_ui_actions_on_toggle_show_cc (GtkToggleAction *toggle,
2158 ModestMsgEditWindow *window)
2160 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2162 modest_msg_edit_window_show_cc (window, gtk_toggle_action_get_active (toggle));
2166 modest_ui_actions_on_toggle_show_bcc (GtkToggleAction *toggle,
2167 ModestMsgEditWindow *window)
2169 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2171 modest_msg_edit_window_show_bcc (window, gtk_toggle_action_get_active (toggle));
2175 modest_ui_actions_toggle_folders_view (GtkAction *action,
2176 ModestMainWindow *main_window)
2180 g_return_if_fail (MODEST_IS_MAIN_WINDOW(main_window));
2182 conf = modest_runtime_get_conf ();
2184 if (modest_main_window_get_style (main_window) == MODEST_MAIN_WINDOW_STYLE_SPLIT)
2185 modest_main_window_set_style (main_window, MODEST_MAIN_WINDOW_STYLE_SIMPLE);
2187 modest_main_window_set_style (main_window, MODEST_MAIN_WINDOW_STYLE_SPLIT);
2191 modest_ui_actions_on_toggle_toolbar (GtkToggleAction *toggle,
2192 ModestWindow *window)
2194 gboolean active, fullscreen = FALSE;
2195 ModestWindowMgr *mgr;
2197 active = gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (toggle));
2199 /* Check if we want to toggle the toolbar vuew in fullscreen
2201 if (!strcmp (gtk_action_get_name (GTK_ACTION (toggle)),
2202 "ViewShowToolbarFullScreen")) {
2206 /* Toggle toolbar */
2207 mgr = modest_runtime_get_window_mgr ();
2208 modest_window_mgr_show_toolbars (mgr, active, fullscreen);
2212 modest_ui_actions_msg_edit_on_select_font (GtkAction *action,
2213 ModestMsgEditWindow *window)
2215 modest_msg_edit_window_select_font (window);
2219 modest_ui_actions_on_folder_display_name_changed (ModestFolderView *folder_view,
2220 const gchar *display_name,
2223 /* Do not change the application name if the widget has not
2224 the focus. This callback could be called even if the folder
2225 view has not the focus, because the handled signal could be
2226 emitted when the folder view is redrawn */
2227 if (gtk_widget_is_focus (GTK_WIDGET (folder_view))) {
2229 gtk_window_set_title (window, display_name);
2231 gtk_window_set_title (window, " ");
2236 modest_ui_actions_on_select_contacts (GtkAction *action, ModestMsgEditWindow *window)
2238 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2239 modest_msg_edit_window_select_contacts (window);
2243 modest_ui_actions_on_check_names (GtkAction *action, ModestMsgEditWindow *window)
2245 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2246 modest_msg_edit_window_check_names (window);
2251 create_move_to_dialog (ModestWindow *win,
2252 GtkWidget *folder_view,
2253 GtkWidget **tree_view)
2255 GtkWidget *dialog, *scroll;
2257 dialog = gtk_dialog_new_with_buttons (_("mcen_ti_moveto_folders_title"),
2259 GTK_DIALOG_MODAL | GTK_DIALOG_NO_SEPARATOR | GTK_DIALOG_DESTROY_WITH_PARENT,
2261 GTK_RESPONSE_ACCEPT,
2263 GTK_RESPONSE_REJECT,
2266 /* Create scrolled window */
2267 scroll = gtk_scrolled_window_new (NULL, NULL);
2268 gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scroll),
2269 GTK_POLICY_AUTOMATIC,
2270 GTK_POLICY_AUTOMATIC);
2272 /* Create folder view */
2273 *tree_view = modest_folder_view_new (NULL);
2274 gtk_tree_view_set_model (GTK_TREE_VIEW (*tree_view),
2275 gtk_tree_view_get_model (GTK_TREE_VIEW (folder_view)));
2276 gtk_container_add (GTK_CONTAINER (scroll), *tree_view);
2278 /* Add scroll to dialog */
2279 gtk_box_pack_start (GTK_BOX (GTK_DIALOG (dialog)->vbox),
2280 scroll, FALSE, FALSE, 0);
2282 gtk_widget_show_all (GTK_WIDGET(GTK_DIALOG(dialog)->vbox));
2288 * Returns TRUE if at least one of the headers of the list belongs to
2289 * a message that has been fully retrieved.
2292 has_retrieved_msgs (TnyList *list)
2295 gboolean found = FALSE;
2297 iter = tny_list_create_iterator (list);
2298 while (tny_iterator_is_done (iter) && !found) {
2300 TnyHeaderFlags flags;
2302 header = TNY_HEADER (tny_iterator_get_current (iter));
2303 flags = tny_header_get_flags (header);
2304 if (!(flags & TNY_HEADER_FLAG_PARTIAL))
2308 tny_iterator_next (iter);
2310 g_object_unref (iter);
2316 * Shows a confirmation dialog to the user when we're moving messages
2317 * from a remote server to the local storage. Returns the dialog
2318 * response. If it's other kind of movement the it always returns
2322 msgs_move_to_confirmation (GtkWindow *win,
2323 TnyFolder *dest_folder,
2326 gint response = GTK_RESPONSE_OK;
2328 /* If the destination is a local folder */
2329 if (modest_tny_folder_is_local_folder (dest_folder)) {
2330 TnyFolder *src_folder;
2334 /* Get source folder */
2335 iter = tny_list_create_iterator (headers);
2336 header = TNY_HEADER (tny_iterator_get_current (iter));
2337 src_folder = tny_header_get_folder (header);
2338 g_object_unref (header);
2339 g_object_unref (iter);
2341 /* If the source is a remote folder */
2342 if (!modest_tny_folder_is_local_folder (src_folder)) {
2343 const gchar *message;
2345 if (tny_list_get_length (headers) == 1)
2346 if (has_retrieved_msgs (headers))
2347 message = _("mcen_nc_move_retrieve");
2349 message = _("mcen_nc_move_header");
2351 if (has_retrieved_msgs (headers))
2352 message = _("mcen_nc_move_retrieves");
2354 message = _("mcen_nc_move_headers");
2356 response = modest_platform_run_confirmation_dialog (GTK_WINDOW (win),
2357 (const gchar *) message);
2365 tranasfer_msgs_from_viewer_cb (const GObject *object, gpointer user_data)
2367 ModestMsgViewWindow *self = NULL;
2368 gboolean found = FALSE;
2370 g_return_if_fail (MODEST_IS_MSG_VIEW_WINDOW (object));
2371 self = MODEST_MSG_VIEW_WINDOW (object);
2373 found = modest_msg_view_window_select_first_message (self);
2374 g_return_if_fail (found);
2378 move_to_error_checking (const GObject *obj, gpointer user_data)
2380 ModestWindow *win = NULL;
2382 g_return_if_fail (MODEST_IS_WINDOW (obj));
2383 win = MODEST_WINDOW (obj);
2385 /* TODO: show error message */
2386 /* modest_platform_run_information_dialog (GTK_WINDOW (win), */
2387 /* _("mail_in_ui_folder_move_target_error")); */
2391 * UI handler for the "Move to" action when invoked from the
2395 modest_ui_actions_on_main_window_move_to (GtkAction *action,
2396 ModestMainWindow *win)
2398 GtkWidget *dialog = NULL, *folder_view = NULL, *tree_view = NULL;
2399 GtkWidget *header_view = NULL;
2401 TnyFolderStore *folder_store = NULL;
2402 ModestMailOperation *mail_op = NULL;
2404 g_return_if_fail (MODEST_IS_MAIN_WINDOW (win));
2406 /* Get the folder view */
2407 folder_view = modest_main_window_get_child_widget (win,
2408 MODEST_WIDGET_TYPE_FOLDER_VIEW);
2410 /* Get header view */
2411 header_view = modest_main_window_get_child_widget (win,
2412 MODEST_WIDGET_TYPE_HEADER_VIEW);
2414 /* Create and run the dialog */
2415 dialog = create_move_to_dialog (MODEST_WINDOW (win), folder_view, &tree_view);
2416 result = gtk_dialog_run (GTK_DIALOG(dialog));
2417 g_object_ref (tree_view);
2419 /* We do this to save an indentation level ;-) */
2420 if (result != GTK_RESPONSE_ACCEPT)
2423 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (tree_view));
2425 if (TNY_IS_ACCOUNT (folder_store))
2428 /* Get folder or messages to transfer */
2429 if (gtk_widget_is_focus (folder_view)) {
2430 TnyFolderStore *src_folder;
2431 src_folder = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (folder_view));
2433 /* Clean folder on header view before moving it */
2434 modest_header_view_set_folder (MODEST_HEADER_VIEW (header_view), NULL);
2436 if (TNY_IS_FOLDER (src_folder)) {
2437 mail_op = modest_mail_operation_new_with_error_handling (MODEST_MAIL_OPERATION_ID_RECEIVE,
2439 move_to_error_checking);
2440 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2443 modest_mail_operation_xfer_folder (mail_op,
2444 TNY_FOLDER (src_folder),
2447 g_object_unref (G_OBJECT (mail_op));
2452 g_object_unref (G_OBJECT (src_folder));
2454 if (gtk_widget_is_focus (header_view)) {
2458 headers = modest_header_view_get_selected_headers (MODEST_HEADER_VIEW (header_view));
2460 /* Ask for user confirmation */
2461 response = msgs_move_to_confirmation (GTK_WINDOW (win),
2462 TNY_FOLDER (folder_store),
2465 /* Transfer messages */
2466 if (response == GTK_RESPONSE_OK) {
2467 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_RECEIVE, G_OBJECT(win));
2468 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2471 modest_mail_operation_xfer_msgs (mail_op,
2473 TNY_FOLDER (folder_store),
2477 g_object_unref (G_OBJECT (mail_op));
2479 g_object_unref (headers);
2482 g_object_unref (folder_store);
2485 gtk_widget_destroy (dialog);
2490 * UI handler for the "Move to" action when invoked from the
2491 * ModestMsgViewWindow
2494 modest_ui_actions_on_msg_view_window_move_to (GtkAction *action,
2495 ModestMsgViewWindow *win)
2497 GtkWidget *dialog, *folder_view, *tree_view = NULL;
2499 ModestMainWindow *main_window;
2503 /* Get the folder view */
2504 main_window = MODEST_MAIN_WINDOW (modest_window_mgr_get_main_window (modest_runtime_get_window_mgr ()));
2505 folder_view = modest_main_window_get_child_widget (main_window,
2506 MODEST_WIDGET_TYPE_FOLDER_VIEW);
2508 /* Create and run the dialog */
2509 dialog = create_move_to_dialog (MODEST_WINDOW (win), folder_view, &tree_view);
2510 result = gtk_dialog_run (GTK_DIALOG(dialog));
2511 g_object_ref (tree_view);
2513 if (result == GTK_RESPONSE_ACCEPT) {
2514 TnyFolderStore *folder_store;
2517 folder_store = modest_folder_view_get_selected (MODEST_FOLDER_VIEW (tree_view));
2519 /* Create header list */
2520 header = modest_msg_view_window_get_header (MODEST_MSG_VIEW_WINDOW (win));
2521 headers = tny_simple_list_new ();
2522 tny_list_prepend (headers, G_OBJECT (header));
2523 g_object_unref (header);
2525 /* Ask user for confirmation. MSG-NOT404 */
2526 response = msgs_move_to_confirmation (GTK_WINDOW (win),
2527 TNY_FOLDER (folder_store),
2530 /* Transfer current msg */
2531 if (response == GTK_RESPONSE_OK) {
2532 ModestMailOperation *mail_op;
2534 /* Create mail op */
2535 mail_op = modest_mail_operation_new (MODEST_MAIL_OPERATION_ID_RECEIVE, G_OBJECT(win));
2536 modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (),
2539 /* Transfer messages */
2540 modest_mail_operation_xfer_msgs (mail_op,
2542 TNY_FOLDER (folder_store),
2544 tranasfer_msgs_from_viewer_cb,
2546 g_object_unref (G_OBJECT (mail_op));
2548 g_object_unref (headers);
2549 g_object_unref (folder_store);
2551 gtk_widget_destroy (dialog);
2555 modest_ui_actions_on_move_to (GtkAction *action,
2558 g_return_if_fail (MODEST_IS_MAIN_WINDOW (win) ||
2559 MODEST_IS_MSG_VIEW_WINDOW (win));
2561 if (MODEST_IS_MAIN_WINDOW (win))
2562 modest_ui_actions_on_main_window_move_to (action,
2563 MODEST_MAIN_WINDOW (win));
2565 modest_ui_actions_on_msg_view_window_move_to (action,
2566 MODEST_MSG_VIEW_WINDOW (win));
2570 * Calls #HeadersFunc for each header already selected in the main
2571 * window or the message currently being shown in the msg view window
2574 do_headers_action (ModestWindow *win,
2578 TnyList *headers_list;
2582 headers_list = get_selected_headers (win);
2586 /* Call the function for each header */
2587 iter = tny_list_create_iterator (headers_list);
2588 while (!tny_iterator_is_done (iter)) {
2591 header = TNY_HEADER (tny_iterator_get_current (iter));
2592 func (header, win, user_data);
2593 g_object_unref (header);
2594 tny_iterator_next (iter);
2596 g_object_unref (iter);
2600 modest_ui_actions_view_attachment (GtkAction *action,
2601 ModestWindow *window)
2603 if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
2604 modest_msg_view_window_view_attachment (MODEST_MSG_VIEW_WINDOW (window), NULL);
2606 /* not supported window for this action */
2607 g_return_if_reached ();
2612 modest_ui_actions_save_attachments (GtkAction *action,
2613 ModestWindow *window)
2615 if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
2616 modest_msg_view_window_save_attachments (MODEST_MSG_VIEW_WINDOW (window), NULL);
2618 /* not supported window for this action */
2619 g_return_if_reached ();
2624 modest_ui_actions_remove_attachments (GtkAction *action,
2625 ModestWindow *window)
2627 if (MODEST_IS_MSG_VIEW_WINDOW (window)) {
2628 modest_msg_view_window_remove_attachments (MODEST_MSG_VIEW_WINDOW (window), NULL);
2630 /* not supported window for this action */
2631 g_return_if_reached ();
2636 modest_ui_actions_on_settings (GtkAction *action,
2641 dialog = modest_platform_get_global_settings_dialog ();
2642 gtk_window_set_transient_for (GTK_WINDOW (dialog), GTK_WINDOW (win));
2643 gtk_widget_show (dialog);
2645 gtk_dialog_run (GTK_DIALOG (dialog));
2647 gtk_widget_destroy (dialog);