X-Git-Url: http://git.maemo.org/git/?p=modest;a=blobdiff_plain;f=src%2Fhildon2%2Fmodest-msg-view-window.c;h=41c6270d86f9239c49200aab4bbec41ad8c29393;hp=c2281662081328c27c03f5d5ff6ab14517ae0ba3;hb=be0ca7f2e3995569e4553ab4d979325680e73050;hpb=d30e246c2184dbc62e120bb30b71ea7631fd9830 diff --git a/src/hildon2/modest-msg-view-window.c b/src/hildon2/modest-msg-view-window.c index c228166..41c6270 100644 --- a/src/hildon2/modest-msg-view-window.c +++ b/src/hildon2/modest-msg-view-window.c @@ -33,6 +33,7 @@ #include #include #include +#include #include "modest-marshal.h" #include "modest-platform.h" #include @@ -93,7 +94,7 @@ struct _ModestMsgViewWindowPrivate { /* Whether the message is in outbox */ gboolean is_outbox; - + /* A reference to the @model of the header view * to allow selecting previous/next messages, * if the message is currently selected in the header view. @@ -115,7 +116,7 @@ struct _ModestMsgViewWindowPrivate { GtkWidget *remove_attachment_banner; gchar *msg_uid; - + GSList *sighandlers; }; @@ -221,6 +222,10 @@ static gboolean message_reader (ModestMsgViewWindow *window, GtkTreeRowReference *row_reference); static void setup_menu (ModestMsgViewWindow *self); +static gboolean _modest_msg_view_window_map_event (GtkWidget *widget, + GdkEvent *event, + gpointer userdata); + /* list my signals */ enum { @@ -529,7 +534,10 @@ init_window (ModestMsgViewWindow *obj) priv->find_toolbar = hildon_find_toolbar_new (NULL); hildon_window_add_toolbar (HILDON_WINDOW (obj), GTK_TOOLBAR (priv->find_toolbar)); gtk_widget_set_no_show_all (priv->find_toolbar, TRUE); - + + /* NULL-ize fields if the window is destroyed */ + g_signal_connect (priv->msg_view, "destroy", G_CALLBACK (gtk_widget_destroyed), &(priv->msg_view)); + gtk_widget_show_all (GTK_WIDGET(main_vbox)); } @@ -718,6 +726,7 @@ select_next_valid_row (GtkTreeModel *model, static void modest_msg_view_window_construct (ModestMsgViewWindow *self, const gchar *modest_account_name, + const gchar *mailbox, const gchar *msg_uid) { GObject *obj = NULL; @@ -784,6 +793,10 @@ modest_msg_view_window_construct (ModestMsgViewWindow *self, g_signal_connect (G_OBJECT (obj), "move-focus", G_CALLBACK (on_move_focus), obj); + g_signal_connect (G_OBJECT (obj), "map-event", + G_CALLBACK (_modest_msg_view_window_map_event), + G_OBJECT (obj)); + /* Mail Operation Queue */ priv->queue_change_handler = g_signal_connect (G_OBJECT (modest_runtime_get_mail_operation_queue ()), "queue-changed", @@ -797,6 +810,7 @@ modest_msg_view_window_construct (ModestMsgViewWindow *self, obj); modest_window_set_active_account (MODEST_WINDOW(obj), modest_account_name); + modest_window_set_active_mailbox (MODEST_WINDOW(obj), mailbox); g_signal_connect (G_OBJECT (priv->find_toolbar), "close", G_CALLBACK (modest_msg_view_window_find_toolbar_close), obj); g_signal_connect (G_OBJECT (priv->find_toolbar), "search", G_CALLBACK (modest_msg_view_window_find_toolbar_search), obj); @@ -816,6 +830,7 @@ modest_msg_view_window_construct (ModestMsgViewWindow *self, ModestWindow * modest_msg_view_window_new_with_header_model (TnyMsg *msg, const gchar *modest_account_name, + const gchar *mailbox, const gchar *msg_uid, GtkTreeModel *model, GtkTreeRowReference *row_reference) @@ -835,7 +850,7 @@ modest_msg_view_window_new_with_header_model (TnyMsg *msg, window = MODEST_MSG_VIEW_WINDOW (modest_window_mgr_get_msg_view_window (mgr)); g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW (window), NULL); - modest_msg_view_window_construct (window, modest_account_name, msg_uid); + modest_msg_view_window_construct (window, modest_account_name, mailbox, msg_uid); priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (window); @@ -914,6 +929,7 @@ modest_msg_view_window_new_with_header_model (TnyMsg *msg, ModestWindow * modest_msg_view_window_new_from_header_view (ModestHeaderView *header_view, const gchar *modest_account_name, + const gchar *mailbox, const gchar *msg_uid, GtkTreeRowReference *row_reference) { @@ -928,7 +944,7 @@ modest_msg_view_window_new_from_header_view (ModestHeaderView *header_view, window = MODEST_MSG_VIEW_WINDOW (modest_window_mgr_get_msg_view_window (mgr)); g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW (window), NULL); - modest_msg_view_window_construct (window, modest_account_name, msg_uid); + modest_msg_view_window_construct (window, modest_account_name, mailbox, msg_uid); priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (window); @@ -1008,6 +1024,7 @@ modest_msg_view_window_new_from_header_view (ModestHeaderView *header_view, ModestWindow * modest_msg_view_window_new_for_search_result (TnyMsg *msg, const gchar *modest_account_name, + const gchar *mailbox, const gchar *msg_uid) { ModestMsgViewWindow *window = NULL; @@ -1017,7 +1034,7 @@ modest_msg_view_window_new_for_search_result (TnyMsg *msg, mgr = modest_runtime_get_window_mgr (); window = MODEST_MSG_VIEW_WINDOW (modest_window_mgr_get_msg_view_window (mgr)); g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW (window), NULL); - modest_msg_view_window_construct (window, modest_account_name, msg_uid); + modest_msg_view_window_construct (window, modest_account_name, mailbox, msg_uid); priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (window); @@ -1041,8 +1058,9 @@ modest_msg_view_window_new_for_search_result (TnyMsg *msg, ModestWindow * modest_msg_view_window_new_for_attachment (TnyMsg *msg, - const gchar *modest_account_name, - const gchar *msg_uid) + const gchar *modest_account_name, + const gchar *mailbox, + const gchar *msg_uid) { GObject *obj = NULL; ModestMsgViewWindowPrivate *priv; @@ -1053,7 +1071,7 @@ modest_msg_view_window_new_for_attachment (TnyMsg *msg, obj = G_OBJECT (modest_window_mgr_get_msg_view_window (mgr)); priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (obj); modest_msg_view_window_construct (MODEST_MSG_VIEW_WINDOW (obj), - modest_account_name, msg_uid); + modest_account_name, mailbox, msg_uid); tny_msg_view_set_msg (TNY_MSG_VIEW (priv->msg_view), msg); update_window_title (MODEST_MSG_VIEW_WINDOW (obj)); @@ -1443,7 +1461,7 @@ modest_msg_view_window_find_toolbar_search (GtkWidget *widget, if ((current_search == NULL) || (strcmp (current_search, "") == 0)) { g_free (current_search); - hildon_banner_show_information (NULL, NULL, dgettext("hildon-common-strings", "ecdg_ib_find_rep_enter_text")); + hildon_banner_show_information (NULL, NULL, _CS("ecdg_ib_find_rep_enter_text")); return; } @@ -1454,20 +1472,20 @@ modest_msg_view_window_find_toolbar_search (GtkWidget *widget, result = modest_isearch_view_search (MODEST_ISEARCH_VIEW (priv->msg_view), priv->last_search); if (!result) { - hildon_banner_show_information (NULL, NULL, dgettext("hildon-libs", "ckct_ib_find_no_matches")); + hildon_banner_show_information (NULL, NULL, + _HL("ckct_ib_find_no_matches")); g_free (priv->last_search); priv->last_search = NULL; } else { - modest_msg_view_grab_focus (MODEST_MSG_VIEW (priv->msg_view)); hildon_find_toolbar_highlight_entry (HILDON_FIND_TOOLBAR (priv->find_toolbar), TRUE); } } else { if (!modest_isearch_view_search_next (MODEST_ISEARCH_VIEW (priv->msg_view))) { - hildon_banner_show_information (NULL, NULL, dgettext("hildon-libs", "ckct_ib_find_search_complete")); + hildon_banner_show_information (NULL, NULL, + _HL("ckct_ib_find_search_complete")); g_free (priv->last_search); priv->last_search = NULL; } else { - modest_msg_view_grab_focus (MODEST_MSG_VIEW (priv->msg_view)); hildon_find_toolbar_highlight_entry (HILDON_FIND_TOOLBAR (priv->find_toolbar), TRUE); } } @@ -1507,6 +1525,8 @@ modest_msg_view_window_zoom_plus (ModestWindow *window) { gdouble zoom_level; ModestMsgViewWindowPrivate *priv; + gint int_zoom; + gchar *banner_text; g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW (window), 1.0); priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (window); @@ -1514,7 +1534,8 @@ modest_msg_view_window_zoom_plus (ModestWindow *window) zoom_level = modest_zoomable_get_zoom (MODEST_ZOOMABLE (priv->msg_view)); if (zoom_level >= 2.0) { - hildon_banner_show_information (NULL, NULL, dgettext("hildon-common-strings", "ckct_ib_max_zoom_level_reached")); + hildon_banner_show_information (NULL, NULL, + _CS("ckct_ib_max_zoom_level_reached")); return FALSE; } else if (zoom_level >= 1.5) { zoom_level = 2.0; @@ -1531,10 +1552,13 @@ modest_msg_view_window_zoom_plus (ModestWindow *window) } /* set zoom level */ + int_zoom = (gint) rint (zoom_level*100.0+0.1); + banner_text = g_strdup_printf (_HL("wdgt_ib_zoom"), int_zoom); + modest_platform_information_banner (GTK_WIDGET (window), NULL, banner_text); + g_free (banner_text); modest_zoomable_set_zoom (MODEST_ZOOMABLE (priv->msg_view), zoom_level); return TRUE; - } static gboolean @@ -1542,6 +1566,8 @@ modest_msg_view_window_zoom_minus (ModestWindow *window) { gdouble zoom_level; ModestMsgViewWindowPrivate *priv; + gint int_zoom; + gchar *banner_text; g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW (window), 1.0); priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (window); @@ -1549,7 +1575,8 @@ modest_msg_view_window_zoom_minus (ModestWindow *window) zoom_level = modest_zoomable_get_zoom (MODEST_ZOOMABLE (priv->msg_view)); if (zoom_level <= 0.5) { - hildon_banner_show_information (NULL, NULL, dgettext("hildon-common-strings", "ckct_ib_min_zoom_level_reached")); + hildon_banner_show_information (NULL, NULL, + _CS("ckct_ib_min_zoom_level_reached")); return FALSE; } else if (zoom_level <= 0.8) { zoom_level = 0.5; @@ -1566,6 +1593,10 @@ modest_msg_view_window_zoom_minus (ModestWindow *window) } /* set zoom level */ + int_zoom = (gint) rint (zoom_level*100.0+0.1); + banner_text = g_strdup_printf (_HL("wdgt_ib_zoom"), int_zoom); + modest_platform_information_banner (GTK_WIDGET (window), NULL, banner_text); + g_free (banner_text); modest_zoomable_set_zoom (MODEST_ZOOMABLE (priv->msg_view), zoom_level); return TRUE; @@ -1603,7 +1634,7 @@ modest_msg_view_window_key_event (GtkWidget *window, if (event->type == GDK_KEY_PRESS) { GtkScrollType scroll_type; - + switch (event->keyval) { case GDK_Up: case GDK_KP_Up: @@ -1625,7 +1656,7 @@ modest_msg_view_window_key_event (GtkWidget *window, scroll_type = GTK_SCROLL_END; break; default: scroll_type = GTK_SCROLL_NONE; } - + /* g_signal_emit_by_name (G_OBJECT (priv->main_scroll), "scroll-child", */ /* scroll_type, FALSE, &return_value); */ return FALSE; @@ -1776,6 +1807,7 @@ message_reader_performer (gboolean canceled, info = (MsgReaderInfo *) user_data; if (canceled || err) { + update_window_title (MODEST_MSG_VIEW_WINDOW (parent_window)); goto frees; } @@ -1786,7 +1818,7 @@ message_reader_performer (gboolean canceled, mail_op = modest_mail_operation_new_with_error_handling (G_OBJECT(parent_window), modest_ui_actions_disk_operations_error_handler, NULL, NULL); - + modest_mail_operation_queue_add (modest_runtime_get_mail_operation_queue (), mail_op); modest_mail_operation_get_msg (mail_op, info->header, TRUE, view_msg_cb, info->row_reference); g_object_unref (mail_op); @@ -1830,6 +1862,11 @@ message_reader (ModestMsgViewWindow *window, mgr = modest_runtime_get_window_mgr (); /* Msg download completed */ if (!(tny_header_get_flags (header) & TNY_HEADER_FLAG_CACHED)) { + + /* We set the header from model while we're loading */ + tny_header_view_set_header (TNY_HEADER_VIEW (priv->msg_view), header); + gtk_window_set_title (GTK_WINDOW (window), _CS("ckdg_pb_updating")); + /* Ask the user if he wants to download the message if we're not online */ if (!tny_device_is_online (modest_runtime_get_device())) { @@ -1837,9 +1874,11 @@ message_reader (ModestMsgViewWindow *window, response = modest_platform_run_confirmation_dialog (GTK_WINDOW (window), _("mcen_nc_get_msg")); - if (response == GTK_RESPONSE_CANCEL) + if (response == GTK_RESPONSE_CANCEL) { + update_window_title (window); return FALSE; - + } + folder = tny_header_get_folder (header); info = g_slice_new (MsgReaderInfo); info->header = g_object_ref (header); @@ -1986,12 +2025,24 @@ view_msg_cb (ModestMailOperation *mail_op, row_reference = (GtkTreeRowReference *) user_data; if (canceled) { gtk_tree_row_reference_free (row_reference); + self = (ModestMsgViewWindow *) modest_mail_operation_get_source (mail_op); + if (self) { + /* Restore window title */ + update_window_title (self); + g_object_unref (self); + } return; } - + /* If there was any error */ if (!modest_ui_actions_msg_retrieval_check (mail_op, header, msg)) { - gtk_tree_row_reference_free (row_reference); + gtk_tree_row_reference_free (row_reference); + self = (ModestMsgViewWindow *) modest_mail_operation_get_source (mail_op); + if (self) { + /* Restore window title */ + update_window_title (self); + g_object_unref (self); + } return; } @@ -2119,7 +2170,7 @@ toolbar_resize (ModestMsgViewWindow *self) parent_priv = MODEST_WINDOW_GET_PRIVATE(self); mgr = modest_runtime_get_window_mgr (); - static_button_size = modest_window_mgr_get_fullscreen_mode (mgr)?118:108; + static_button_size = modest_window_mgr_get_fullscreen_mode (mgr)?120:120; if (parent_priv->toolbar) { /* left size buttons */ @@ -2139,13 +2190,12 @@ toolbar_resize (ModestMsgViewWindow *self) gtk_tool_item_set_expand (GTK_TOOL_ITEM (widget), FALSE); gtk_tool_item_set_homogeneous (GTK_TOOL_ITEM (widget), FALSE); gtk_widget_set_size_request (GTK_WIDGET (widget), static_button_size, -1); - + gtk_tool_item_set_homogeneous (GTK_TOOL_ITEM (priv->next_toolitem), TRUE); gtk_tool_item_set_expand (GTK_TOOL_ITEM (priv->next_toolitem), TRUE); gtk_tool_item_set_homogeneous (GTK_TOOL_ITEM (priv->prev_toolitem), TRUE); gtk_tool_item_set_expand (GTK_TOOL_ITEM (priv->prev_toolitem), TRUE); } - } static void @@ -2154,7 +2204,6 @@ modest_msg_view_window_show_toolbar (ModestWindow *self, { ModestMsgViewWindowPrivate *priv = NULL; ModestWindowPrivate *parent_priv; - GtkWidget *reply_button = NULL, *menu = NULL; parent_priv = MODEST_WINDOW_GET_PRIVATE(self); priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE(self); @@ -2165,6 +2214,7 @@ modest_msg_view_window_show_toolbar (ModestWindow *self, if (!parent_priv->toolbar) { parent_priv->toolbar = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar"); + gtk_toolbar_set_icon_size (GTK_TOOLBAR (parent_priv->toolbar), HILDON_ICON_SIZE_FINGER); gtk_widget_set_no_show_all (parent_priv->toolbar, TRUE); priv->next_toolitem = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar/ToolbarMessageNext"); @@ -2175,13 +2225,6 @@ modest_msg_view_window_show_toolbar (ModestWindow *self, hildon_window_add_toolbar (HILDON_WINDOW (self), GTK_TOOLBAR (parent_priv->toolbar)); - /* Set reply button tap and hold menu */ - reply_button = gtk_ui_manager_get_widget (parent_priv->ui_manager, - "/ToolBar/ToolbarMessageReply"); - menu = gtk_ui_manager_get_widget (parent_priv->ui_manager, - "/ToolbarReplyCSM"); - if (menu && reply_button) - gtk_widget_tap_and_hold_setup (GTK_WIDGET (reply_button), menu, NULL, 0); } if (show_toolbar) { @@ -2260,7 +2303,7 @@ on_account_removed (TnyAccountStore *account_store, parent_acc = modest_tny_account_get_parent_modest_account_name_for_server_account (account); /* Close this window if I'm showing a message of the removed account */ - if (strcmp (parent_acc, our_acc) == 0) + if (our_acc && parent_acc && strcmp (parent_acc, our_acc) == 0) modest_ui_actions_on_close_window (NULL, MODEST_WINDOW (user_data)); } } @@ -2281,7 +2324,7 @@ on_mail_operation_started (ModestMailOperation *mail_op, tmp = priv->progress_widgets; source = modest_mail_operation_get_source(mail_op); if (G_OBJECT (self) == source) { - if (op_type == MODEST_MAIL_OPERATION_TYPE_RECEIVE ) { + if (op_type == MODEST_MAIL_OPERATION_TYPE_RECEIVE) { set_toolbar_transfer_mode(self); while (tmp) { modest_progress_object_add_operation ( @@ -2308,7 +2351,7 @@ on_mail_operation_finished (ModestMailOperation *mail_op, op_type = modest_mail_operation_get_type_operation (mail_op); tmp = priv->progress_widgets; - if (op_type == MODEST_MAIL_OPERATION_TYPE_RECEIVE ) { + if (op_type == MODEST_MAIL_OPERATION_TYPE_RECEIVE) { while (tmp) { modest_progress_object_remove_operation (MODEST_PROGRESS_OBJECT (tmp->data), mail_op); @@ -2319,15 +2362,15 @@ on_mail_operation_finished (ModestMailOperation *mail_op, if (observers_empty (self)) { set_progress_hint (self, FALSE); } - - /* Update dimming rules. We have to do this right here - and not in view_msg_cb because at that point the - transfer mode is still enabled so the dimming rule - won't let the user delete the message that has been - readed for example */ - modest_ui_actions_check_toolbar_dimming_rules (MODEST_WINDOW (self)); - modest_ui_actions_check_menu_dimming_rules (MODEST_WINDOW (self)); } + + /* Update dimming rules. We have to do this right here + and not in view_msg_cb because at that point the + transfer mode is still enabled so the dimming rule + won't let the user delete the message that has been + readed for example */ + check_dimming_rules_after_change (self); + } static void @@ -2374,28 +2417,12 @@ modest_msg_view_window_get_attachments (ModestMsgViewWindow *win) g_return_val_if_fail (MODEST_IS_MSG_VIEW_WINDOW (win), NULL); priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (win); - selected_attachments = modest_msg_view_get_selected_attachments (MODEST_MSG_VIEW (priv->msg_view)); + /* In Hildon 2.2 as there's no selection we assume we have all attachments selected */ + selected_attachments = modest_msg_view_get_attachments (MODEST_MSG_VIEW (priv->msg_view)); return selected_attachments; } -typedef struct { - gchar *filepath; - GtkWidget *banner; - guint banner_idle_id; -} DecodeAsyncHelper; - -static gboolean -decode_async_banner_idle (gpointer user_data) -{ - DecodeAsyncHelper *helper = (DecodeAsyncHelper *) user_data; - - helper->banner_idle_id = 0; - helper->banner = hildon_banner_show_animation (NULL, NULL, _("mail_me_opening")); - - return FALSE; -} - static void on_decode_to_stream_async_handler (TnyMimePart *mime_part, gboolean cancelled, @@ -2403,32 +2430,25 @@ on_decode_to_stream_async_handler (TnyMimePart *mime_part, GError *err, gpointer user_data) { - DecodeAsyncHelper *helper = (DecodeAsyncHelper *) user_data; + gchar *filepath = (gchar *) user_data; - if (helper->banner_idle_id > 0) { - g_source_remove (helper->banner_idle_id); - helper->banner_idle_id = 0; - } - if (helper->banner) { - gtk_widget_destroy (helper->banner); - helper->banner = NULL; - } if (cancelled || err) { - modest_platform_information_banner (NULL, NULL, - _("mail_ib_file_operation_failed")); + if (err) { + modest_platform_information_banner (NULL, NULL, + _KR("cerm_device_memory_full")); + } goto free; } /* make the file read-only */ - g_chmod(helper->filepath, 0444); + g_chmod(filepath, 0444); /* Activate the file */ - modest_platform_activate_file (helper->filepath, tny_mime_part_get_content_type (mime_part)); + modest_platform_activate_file (filepath, tny_mime_part_get_content_type (mime_part)); free: /* Frees */ - g_free (helper->filepath); - g_slice_free (DecodeAsyncHelper, helper); + g_free (filepath); } void @@ -2468,18 +2488,17 @@ modest_msg_view_window_view_attachment (ModestMsgViewWindow *window, mime_part = (TnyMimePart *) tny_iterator_get_current (iter); g_object_unref (iter); } - g_object_unref (selected_attachments); + if (selected_attachments) + g_object_unref (selected_attachments); if (error) - return; + goto frees; } else { g_object_ref (mime_part); } - if (tny_mime_part_is_purged (mime_part)) { - g_object_unref (mime_part); - return; - } + if (tny_mime_part_is_purged (mime_part)) + goto frees; if (!modest_tny_mime_part_is_msg (mime_part)) { gchar *filepath = NULL; @@ -2488,16 +2507,12 @@ modest_msg_view_window_view_attachment (ModestMsgViewWindow *window, TnyFsStream *temp_stream = NULL; temp_stream = modest_utils_create_temp_stream (att_filename, attachment_uid, &filepath); - + if (temp_stream != NULL) { - DecodeAsyncHelper *helper = g_slice_new (DecodeAsyncHelper); - helper->filepath = g_strdup (filepath); - helper->banner = NULL; - helper->banner_idle_id = g_timeout_add (1000, decode_async_banner_idle, helper); tny_mime_part_decode_to_stream_async (mime_part, TNY_STREAM (temp_stream), on_decode_to_stream_async_handler, - NULL, - helper); + NULL, + g_strdup (filepath)); g_object_unref (temp_stream); /* NOTE: files in the temporary area will be automatically * cleaned after some time if they are no longer in use */ @@ -2536,16 +2551,25 @@ modest_msg_view_window_view_attachment (ModestMsgViewWindow *window, /* it's not found, so create a new window for it */ modest_window_mgr_register_header (mgr, header, attachment_uid); /* register the uid before building the window */ gchar *account = g_strdup (modest_window_get_active_account (MODEST_WINDOW (window))); + const gchar *mailbox = modest_window_get_active_mailbox (MODEST_WINDOW (window)); if (!account) account = modest_account_mgr_get_default_account (modest_runtime_get_account_mgr ()); - msg_win = modest_msg_view_window_new_for_attachment (TNY_MSG (mime_part), account, attachment_uid); + msg_win = modest_msg_view_window_new_for_attachment (TNY_MSG (mime_part), account, + mailbox, attachment_uid); modest_window_set_zoom (MODEST_WINDOW (msg_win), modest_window_get_zoom (MODEST_WINDOW (window))); - modest_window_mgr_register_window (mgr, msg_win, MODEST_WINDOW (window)); - gtk_widget_show_all (GTK_WIDGET (msg_win)); + if (modest_window_mgr_register_window (mgr, msg_win, MODEST_WINDOW (window))) + gtk_widget_show_all (GTK_WIDGET (msg_win)); + else + gtk_widget_destroy (GTK_WIDGET (msg_win)); } } - g_object_unref (mime_part); + + frees: + if (attachment_uid) + g_free (attachment_uid); + if (mime_part) + g_object_unref (mime_part); } typedef struct @@ -2557,7 +2581,6 @@ typedef struct typedef struct { GList *pairs; - GtkWidget *banner; GnomeVFSResult result; } SaveMimePartInfo; @@ -2566,11 +2589,11 @@ static gboolean idle_save_mime_part_show_result (SaveMimePartInfo *info); static gpointer save_mime_part_to_file (SaveMimePartInfo *info); static void save_mime_parts_to_file_with_checks (SaveMimePartInfo *info); -static void +static void save_mime_part_info_free (SaveMimePartInfo *info, gboolean with_struct) { - GList *node; + for (node = info->pairs; node != NULL; node = g_list_next (node)) { SaveMimePartPair *pair = (SaveMimePartPair *) node->data; g_free (pair->filename); @@ -2580,7 +2603,6 @@ save_mime_part_info_free (SaveMimePartInfo *info, gboolean with_struct) g_list_free (info->pairs); info->pairs = NULL; if (with_struct) { - gtk_widget_destroy (info->banner); g_slice_free (SaveMimePartInfo, info); } } @@ -2599,8 +2621,8 @@ idle_save_mime_part_show_result (SaveMimePartInfo *info) if (info->result == GNOME_VFS_OK) { hildon_banner_show_information (NULL, NULL, _CS("sfil_ib_saved")); } else if (info->result == GNOME_VFS_ERROR_NO_SPACE) { - hildon_banner_show_information (NULL, NULL, dgettext("ke-recv", - "cerm_device_memory_full")); + hildon_banner_show_information (NULL, NULL, + _KR("cerm_device_memory_full")); } else { hildon_banner_show_information (NULL, NULL, _("mail_ib_file_operation_failed")); } @@ -2623,8 +2645,14 @@ save_mime_part_to_file (SaveMimePartInfo *info) stream = tny_vfs_stream_new (handle); if (tny_mime_part_decode_to_stream (pair->part, stream, &error) < 0) { g_warning ("modest: could not save attachment %s: %d (%s)\n", pair->filename, error?error->code:-1, error?error->message:"Unknown error"); - - info->result = GNOME_VFS_ERROR_IO; + + if ((error->domain == TNY_ERROR_DOMAIN) && + (error->code == TNY_IO_ERROR_WRITE) && + (errno == ENOSPC)) { + info->result = GNOME_VFS_ERROR_NO_SPACE; + } else { + info->result = GNOME_VFS_ERROR_IO; + } } g_object_unref (G_OBJECT (stream)); g_object_unref (pair->part); @@ -2667,9 +2695,6 @@ save_mime_parts_to_file_with_checks (SaveMimePartInfo *info) if (!is_ok) { save_mime_part_info_free (info, TRUE); } else { - GtkWidget *banner = hildon_banner_show_animation (NULL, NULL, - _CS("sfil_ib_saving")); - info->banner = banner; g_thread_create ((GThreadFunc)save_mime_part_to_file, info, FALSE, NULL); } @@ -2683,6 +2708,7 @@ save_attachments_response (GtkDialog *dialog, TnyList *mime_parts; gchar *chooser_uri; GList *files_to_save = NULL; + gchar *current_folder; mime_parts = TNY_LIST (user_data); @@ -2690,10 +2716,21 @@ save_attachments_response (GtkDialog *dialog, goto end; chooser_uri = gtk_file_chooser_get_uri (GTK_FILE_CHOOSER (dialog)); + current_folder = gtk_file_chooser_get_current_folder_uri (GTK_FILE_CHOOSER (dialog)); + if (current_folder && current_folder != '\0') { + GError *err = NULL; + modest_conf_set_string (modest_runtime_get_conf (), MODEST_CONF_LATEST_SAVE_ATTACHMENT_PATH, + current_folder,&err); + if (err != NULL) { + g_debug ("Error storing latest used folder: %s", err->message); + g_error_free (err); + } + } + g_free (current_folder); if (!modest_utils_folder_writable (chooser_uri)) { hildon_banner_show_information - (NULL, NULL, dgettext("hildon-fm", "sfil_ib_readonly_location")); + (NULL, NULL, _FM("sfil_ib_readonly_location")); } else { TnyIterator *iter; @@ -2705,7 +2742,7 @@ save_attachments_response (GtkDialog *dialog, !tny_mime_part_is_purged (mime_part) && (tny_mime_part_get_filename (mime_part) != NULL)) { SaveMimePartPair *pair; - + pair = g_slice_new0 (SaveMimePartPair); if (tny_list_get_length (mime_parts) > 1) { @@ -2739,11 +2776,12 @@ save_attachments_response (GtkDialog *dialog, } void -modest_msg_view_window_save_attachments (ModestMsgViewWindow *window, TnyList *mime_parts) +modest_msg_view_window_save_attachments (ModestMsgViewWindow *window, + TnyList *mime_parts) { ModestMsgViewWindowPrivate *priv; GtkWidget *save_dialog = NULL; - gchar *folder = NULL; + gchar *conf_folder = NULL; gchar *filename = NULL; gchar *save_multiple_str = NULL; @@ -2751,9 +2789,20 @@ modest_msg_view_window_save_attachments (ModestMsgViewWindow *window, TnyList *m priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (window); if (mime_parts == NULL) { - mime_parts = modest_msg_view_get_selected_attachments (MODEST_MSG_VIEW (priv->msg_view)); - if (mime_parts == NULL || tny_list_get_length (mime_parts) == 0) + /* In Hildon 2.2 save and delete operate over all the attachments as there's no + * selection available */ + mime_parts = modest_msg_view_get_attachments (MODEST_MSG_VIEW (priv->msg_view)); + if (mime_parts && !modest_maemo_utils_select_attachments (GTK_WINDOW (window), mime_parts, FALSE)) { + g_object_unref (mime_parts); return; + } + if (mime_parts == NULL || tny_list_get_length (mime_parts) == 0) { + if (mime_parts) { + g_object_unref (mime_parts); + mime_parts = NULL; + } + return; + } } else { g_object_ref (mime_parts); } @@ -2780,14 +2829,22 @@ modest_msg_view_window_save_attachments (ModestMsgViewWindow *window, TnyList *m save_multiple_str = g_strdup_printf (_FM("sfil_va_number_of_objects_attachments"), tny_list_get_length (mime_parts)); } - + save_dialog = hildon_file_chooser_dialog_new (GTK_WINDOW (window), GTK_FILE_CHOOSER_ACTION_SAVE); /* set folder */ - folder = g_build_filename (g_get_home_dir (), g_getenv (MYDOCS_ENV), DOCS_FOLDER, NULL); - gtk_file_chooser_set_current_folder (GTK_FILE_CHOOSER (save_dialog), folder); - g_free (folder); + conf_folder = modest_conf_get_string (modest_runtime_get_conf (), MODEST_CONF_LATEST_SAVE_ATTACHMENT_PATH, NULL); + if (conf_folder && conf_folder[0] != '\0') { + gtk_file_chooser_set_current_folder_uri (GTK_FILE_CHOOSER (save_dialog), conf_folder); + } else { + gchar *docs_folder; + /* Set the default folder to images folder */ + docs_folder = g_build_filename (g_getenv (MYDOCS_ENV), DOCS_FOLDER, NULL); + gtk_file_chooser_set_current_folder (GTK_FILE_CHOOSER (save_dialog), docs_folder); + g_free (docs_folder); + } + g_free (conf_folder); /* set filename */ if (filename) { @@ -2847,10 +2904,10 @@ modest_msg_view_window_remove_attachments (ModestMsgViewWindow *window, gboolean g_return_if_fail (MODEST_IS_MSG_VIEW_WINDOW (window)); priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (window); - if (get_all) - mime_parts = modest_msg_view_get_attachments (MODEST_MSG_VIEW (priv->msg_view)); - else - mime_parts = modest_msg_view_get_selected_attachments (MODEST_MSG_VIEW (priv->msg_view)); + /* In hildon 2.2 we ignore the get_all flag as we always get all attachments. This is + * because we don't have selection + */ + mime_parts = modest_msg_view_get_attachments (MODEST_MSG_VIEW (priv->msg_view)); /* Remove already purged messages from mime parts list */ iter = tny_list_create_iterator (mime_parts); @@ -2864,7 +2921,8 @@ modest_msg_view_window_remove_attachments (ModestMsgViewWindow *window, gboolean } g_object_unref (iter); - if (tny_list_get_length (mime_parts) == 0) { + if (!modest_maemo_utils_select_attachments (GTK_WINDOW (window), mime_parts, TRUE) || + tny_list_get_length (mime_parts) == 0) { g_object_unref (mime_parts); return; } @@ -2943,11 +3001,18 @@ modest_msg_view_window_remove_attachments (ModestMsgViewWindow *window, gboolean static void update_window_title (ModestMsgViewWindow *window) { - ModestMsgViewWindowPrivate *priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (window); + ModestMsgViewWindowPrivate *priv; TnyMsg *msg = NULL; TnyHeader *header = NULL; gchar *subject = NULL; - + + priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (window); + + /* Note that if the window is closed while we're retrieving + the message, this widget could de deleted */ + if (!priv->msg_view) + return; + msg = tny_msg_view_get_msg (TNY_MSG_VIEW (priv->msg_view)); if (msg != NULL) { @@ -2966,9 +3031,10 @@ update_window_title (ModestMsgViewWindow *window) } -static void on_move_focus (GtkWidget *widget, - GtkDirectionType direction, - gpointer userdata) +static void +on_move_focus (GtkWidget *widget, + GtkDirectionType direction, + gpointer userdata) { g_signal_stop_emission_by_name (G_OBJECT (widget), "move-focus"); } @@ -3016,10 +3082,14 @@ on_fetch_image_idle_refresh_view (gpointer userdata) FetchImageData *fidata = (FetchImageData *) userdata; g_message ("REFRESH VIEW"); + + gdk_threads_enter (); if (GTK_WIDGET_DRAWABLE (fidata->msg_view)) { g_message ("QUEUING DRAW"); gtk_widget_queue_draw (fidata->msg_view); } + gdk_threads_leave (); + g_object_unref (fidata->msg_view); g_slice_free (FetchImageData, fidata); return FALSE; @@ -3033,12 +3103,37 @@ on_fetch_image_thread (gpointer userdata) TnyStream *cache_stream; cache = modest_runtime_get_images_cache (); - cache_stream = tny_stream_cache_get_stream (cache, fidata->cache_id, (TnyStreamCacheOpenStreamFetcher) fetch_image_open_stream, (gpointer) fidata->uri); + cache_stream = + tny_stream_cache_get_stream (cache, + fidata->cache_id, + (TnyStreamCacheOpenStreamFetcher) fetch_image_open_stream, + (gpointer) fidata->uri); g_free (fidata->cache_id); g_free (fidata->uri); if (cache_stream != NULL) { - tny_stream_write_to_stream (cache_stream, fidata->output_stream); + char buffer[4096]; + + while (G_LIKELY (!tny_stream_is_eos (cache_stream))) { + gssize nb_read; + + nb_read = tny_stream_read (cache_stream, buffer, sizeof (buffer)); + if (G_UNLIKELY (nb_read < 0)) { + break; + } else if (G_LIKELY (nb_read > 0)) { + gssize nb_written = 0; + + while (G_UNLIKELY (nb_written < nb_read)) { + gssize len; + + len = tny_stream_write (fidata->output_stream, buffer + nb_written, + nb_read - nb_written); + if (G_UNLIKELY (len < 0)) + break; + nb_written += len; + } + } + } tny_stream_close (cache_stream); g_object_unref (cache_stream); } @@ -3046,10 +3141,7 @@ on_fetch_image_thread (gpointer userdata) tny_stream_close (fidata->output_stream); g_object_unref (fidata->output_stream); - - gdk_threads_enter (); g_idle_add (on_fetch_image_idle_refresh_view, fidata); - gdk_threads_leave (); return NULL; } @@ -3084,7 +3176,7 @@ on_fetch_image (ModestMsgView *msgview, return FALSE; } - return TRUE;; + return TRUE; } static void @@ -3093,31 +3185,31 @@ setup_menu (ModestMsgViewWindow *self) g_return_if_fail (MODEST_IS_MSG_VIEW_WINDOW(self)); /* Settings menu buttons */ - modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_replytoall"), + modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_replytoall"), NULL, APP_MENU_CALLBACK (modest_ui_actions_on_reply_all), MODEST_DIMMING_CALLBACK (modest_ui_dimming_rules_on_reply_msg)); - modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_forward"), + modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_forward"), "d", APP_MENU_CALLBACK (modest_ui_actions_on_forward), MODEST_DIMMING_CALLBACK (modest_ui_dimming_rules_on_reply_msg)); - - modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_mark_as_read"), + + modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_mark_as_read"), NULL, APP_MENU_CALLBACK (modest_ui_actions_on_mark_as_read), MODEST_DIMMING_CALLBACK (modest_ui_dimming_rules_on_mark_as_read_msg_in_view)); - modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_mark_as_unread"), + modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_mark_as_unread"), NULL, APP_MENU_CALLBACK (modest_ui_actions_on_mark_as_unread), MODEST_DIMMING_CALLBACK (modest_ui_dimming_rules_on_mark_as_unread_msg_in_view)); - - modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_viewer_save_attachments"), + + modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_viewer_save_attachments"), NULL, APP_MENU_CALLBACK (modest_ui_actions_save_attachments), MODEST_DIMMING_CALLBACK (modest_ui_dimming_rules_on_save_attachments)); - modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_remove_attachments"), + modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_inbox_remove_attachments"), NULL, APP_MENU_CALLBACK (modest_ui_actions_remove_attachments), MODEST_DIMMING_CALLBACK (modest_ui_dimming_rules_on_remove_attachments)); - - modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_viewer_newemail"), + + modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_new_message"), "n", APP_MENU_CALLBACK (modest_ui_actions_on_new_msg), MODEST_DIMMING_CALLBACK (modest_ui_dimming_rules_on_new_msg)); - modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_viewer_addtocontacts"), + modest_hildon2_window_add_to_menu (MODEST_HILDON2_WINDOW (self), _("mcen_me_viewer_addtocontacts"), NULL, APP_MENU_CALLBACK (modest_ui_actions_add_to_contacts), MODEST_DIMMING_CALLBACK (modest_ui_dimming_rules_on_add_to_contacts)); } @@ -3132,8 +3224,18 @@ modest_msg_view_window_add_to_contacts (ModestMsgViewWindow *self) gboolean contacts_to_add = FALSE; msg = tny_msg_view_get_msg (TNY_MSG_VIEW (priv->msg_view)); - if (msg == NULL) return; - recipients = modest_tny_msg_get_all_recipients_list (msg); + if (msg == NULL) { + TnyHeader *header; + + header = modest_msg_view_window_get_header (self); + if (header == NULL) + return; + recipients = modest_tny_msg_header_get_all_recipients_list (header); + g_object_unref (header); + } else { + recipients = modest_tny_msg_get_all_recipients_list (msg); + g_object_unref (msg); + } if (recipients != NULL) { GtkWidget *picker_dialog; @@ -3180,5 +3282,19 @@ modest_msg_view_window_add_to_contacts (ModestMsgViewWindow *self) } if (recipients) {g_slist_foreach (recipients, (GFunc) g_free, NULL); g_slist_free (recipients);} - g_object_unref (msg); +} + +static gboolean +_modest_msg_view_window_map_event (GtkWidget *widget, + GdkEvent *event, + gpointer userdata) +{ + ModestMsgViewWindow *self = (ModestMsgViewWindow *) userdata; + ModestMsgViewWindowPrivate *priv = MODEST_MSG_VIEW_WINDOW_GET_PRIVATE (self); + + if (priv->progress_hint) { + hildon_gtk_window_set_progress_indicator (GTK_WINDOW (self), TRUE); + } + + return FALSE; }