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.
31 #include <glib/gi18n.h>
33 #include <glib/gstdio.h>
35 #include <tny-account-store.h>
36 #include <tny-fs-stream.h>
37 #include <tny-vfs-stream.h>
41 #include <modest-account-mgr.h>
42 #include <modest-account-mgr-helpers.h>
44 #include <widgets/modest-msg-edit-window.h>
45 #include <widgets/modest-combo-box.h>
46 #include <widgets/modest-recpt-editor.h>
47 #include <widgets/modest-attachments-view.h>
49 #include <modest-runtime.h>
51 #include "modest-platform.h"
52 #include "modest-icon-names.h"
53 #include "modest-widget-memory.h"
54 #include "modest-window-priv.h"
55 #include "modest-mail-operation.h"
56 #include "modest-tny-platform-factory.h"
57 #include "modest-tny-msg.h"
58 #include "modest-address-book.h"
59 #include "modest-text-utils.h"
60 #include <tny-simple-list.h>
61 #include <wptextview.h>
62 #include <wptextbuffer.h>
63 #include "modest-scroll-area.h"
65 #include "modest-hildon-includes.h"
66 #include "widgets/modest-msg-edit-window-ui.h"
67 #include <libgnomevfs/gnome-vfs-mime.h>
70 #define DEFAULT_FONT_SIZE 3
71 #define DEFAULT_FONT 2
72 #define DEFAULT_SIZE_BUTTON_FONT_FAMILY "Sans"
73 #define DEFAULT_SIZE_COMBOBOX_WIDTH 80
74 #define DEFAULT_MAIN_VBOX_SPACING 6
75 #define SUBJECT_MAX_LENGTH 1000
77 static void modest_msg_edit_window_class_init (ModestMsgEditWindowClass *klass);
78 static void modest_msg_edit_window_init (ModestMsgEditWindow *obj);
79 static void modest_msg_edit_window_finalize (GObject *obj);
81 static gboolean msg_body_focus (GtkWidget *focus, GdkEventFocus *event, gpointer userdata);
82 static void recpt_field_changed (GtkTextBuffer *buffer, ModestMsgEditWindow *editor);
83 static void send_insensitive_press (GtkWidget *widget, ModestMsgEditWindow *editor);
84 static void style_insensitive_press (GtkWidget *widget, ModestMsgEditWindow *editor);
85 static void remove_attachment_insensitive_press (GtkWidget *widget, ModestMsgEditWindow *editor);
86 static void zoom_insensitive_press (GtkWidget *widget, ModestMsgEditWindow *editor);
87 static void setup_insensitive_handlers (ModestMsgEditWindow *editor);
88 static void reset_modified (ModestMsgEditWindow *editor);
89 static gboolean is_modified (ModestMsgEditWindow *editor);
91 static void text_buffer_refresh_attributes (WPTextBuffer *buffer, ModestMsgEditWindow *window);
92 static void text_buffer_delete_range (GtkTextBuffer *buffer, GtkTextIter *start, GtkTextIter *end, gpointer userdata);
93 static void text_buffer_can_undo (GtkTextBuffer *buffer, gboolean can_undo, ModestMsgEditWindow *window);
94 static void text_buffer_delete_images_by_id (GtkTextBuffer *buffer, const gchar * image_id);
95 static void subject_field_changed (GtkEditable *editable, ModestMsgEditWindow *window);
96 static void modest_msg_edit_window_color_button_change (ModestMsgEditWindow *window,
98 static void modest_msg_edit_window_size_change (GtkCheckMenuItem *menu_item,
100 static void modest_msg_edit_window_font_change (GtkCheckMenuItem *menu_item,
102 static void modest_msg_edit_window_setup_toolbar (ModestMsgEditWindow *window);
103 static gboolean modest_msg_edit_window_window_state_event (GtkWidget *widget,
104 GdkEventWindowState *event,
106 static void modest_msg_edit_window_open_addressbook (ModestMsgEditWindow *window,
107 ModestRecptEditor *editor);
108 static void modest_msg_edit_window_add_attachment_clicked (GtkButton *button,
109 ModestMsgEditWindow *window);
111 /* ModestWindow methods implementation */
112 static void modest_msg_edit_window_set_zoom (ModestWindow *window, gdouble zoom);
113 static gdouble modest_msg_edit_window_get_zoom (ModestWindow *window);
114 static gboolean modest_msg_edit_window_zoom_minus (ModestWindow *window);
115 static gboolean modest_msg_edit_window_zoom_plus (ModestWindow *window);
116 static void modest_msg_edit_window_show_toolbar (ModestWindow *window,
117 gboolean show_toolbar);
118 static void modest_msg_edit_window_clipboard_owner_change (GtkClipboard *clipboard,
120 ModestMsgEditWindow *window);
121 static void modest_msg_edit_window_system_clipboard_owner_change (GtkClipboard *clipboard,
123 ModestMsgEditWindow *window);
124 static void update_window_title (ModestMsgEditWindow *window);
125 static void update_dimmed (ModestMsgEditWindow *window);
126 static void update_paste_dimming (ModestMsgEditWindow *window);
127 static void update_select_all_dimming (ModestMsgEditWindow *window);
128 static void update_zoom_dimming (ModestMsgEditWindow *window);
131 static void modest_msg_edit_window_find_toolbar_search (GtkWidget *widget,
132 ModestMsgEditWindow *window);
133 static void modest_msg_edit_window_find_toolbar_close (GtkWidget *widget,
134 ModestMsgEditWindow *window);
135 static void edit_menu_activated (GtkAction *action,
137 static void view_menu_activated (GtkAction *action,
140 /* list my signals */
147 typedef struct _ModestMsgEditWindowPrivate ModestMsgEditWindowPrivate;
148 struct _ModestMsgEditWindowPrivate {
150 GtkWidget *header_box;
152 ModestPairList *from_field_protos;
153 GtkWidget *from_field;
157 GtkWidget *bcc_field;
158 GtkWidget *subject_field;
159 GtkWidget *attachments_view;
160 GtkWidget *priority_icon;
161 GtkWidget *add_attachment_button;
163 GtkWidget *cc_caption;
164 GtkWidget *bcc_caption;
165 GtkWidget *attachments_caption;
167 GtkTextBuffer *text_buffer;
169 GtkWidget *font_size_toolitem;
170 GtkWidget *font_face_toolitem;
171 GtkWidget *font_color_button;
172 GSList *font_items_group;
173 GtkWidget *font_tool_button_label;
174 GSList *size_items_group;
175 GtkWidget *size_tool_button_label;
177 GtkWidget *find_toolbar;
184 TnyHeaderFlags priority_flags;
188 gulong clipboard_change_handler_id;
189 gulong system_clipboard_change_handler_id;
194 #define MODEST_MSG_EDIT_WINDOW_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE((o), \
195 MODEST_TYPE_MSG_EDIT_WINDOW, \
196 ModestMsgEditWindowPrivate))
198 static GtkWindowClass *parent_class = NULL;
200 /* uncomment the following if you have defined any signals */
201 /* static guint signals[LAST_SIGNAL] = {0}; */
204 modest_msg_edit_window_get_type (void)
206 static GType my_type = 0;
208 static const GTypeInfo my_info = {
209 sizeof(ModestMsgEditWindowClass),
210 NULL, /* base init */
211 NULL, /* base finalize */
212 (GClassInitFunc) modest_msg_edit_window_class_init,
213 NULL, /* class finalize */
214 NULL, /* class data */
215 sizeof(ModestMsgEditWindow),
217 (GInstanceInitFunc) modest_msg_edit_window_init,
220 my_type = g_type_register_static (MODEST_TYPE_WINDOW,
221 "ModestMsgEditWindow",
224 wp_text_buffer_library_init ();
230 save_state (ModestWindow *self)
232 modest_widget_memory_save (modest_runtime_get_conf(),
233 G_OBJECT(self), MODEST_CONF_EDIT_WINDOW_KEY);
238 restore_settings (ModestMsgEditWindow *self)
240 modest_widget_memory_restore (modest_runtime_get_conf(),
241 G_OBJECT(self), MODEST_CONF_EDIT_WINDOW_KEY);
246 modest_msg_edit_window_class_init (ModestMsgEditWindowClass *klass)
248 GObjectClass *gobject_class;
249 ModestWindowClass *modest_window_class;
250 gobject_class = (GObjectClass*) klass;
251 modest_window_class = (ModestWindowClass*) klass;
253 parent_class = g_type_class_peek_parent (klass);
254 gobject_class->finalize = modest_msg_edit_window_finalize;
256 modest_window_class->set_zoom_func = modest_msg_edit_window_set_zoom;
257 modest_window_class->get_zoom_func = modest_msg_edit_window_get_zoom;
258 modest_window_class->zoom_plus_func = modest_msg_edit_window_zoom_plus;
259 modest_window_class->zoom_minus_func = modest_msg_edit_window_zoom_minus;
260 modest_window_class->show_toolbar_func = modest_msg_edit_window_show_toolbar;
262 g_type_class_add_private (gobject_class, sizeof(ModestMsgEditWindowPrivate));
264 modest_window_class->save_state_func = save_state;
268 modest_msg_edit_window_init (ModestMsgEditWindow *obj)
270 ModestMsgEditWindowPrivate *priv;
271 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE(obj);
273 priv->msg_body = NULL;
274 priv->from_field = NULL;
275 priv->to_field = NULL;
276 priv->cc_field = NULL;
277 priv->bcc_field = NULL;
278 priv->subject_field = NULL;
279 priv->attachments = NULL;
281 priv->zoom_level = 1.0;
283 priv->cc_caption = NULL;
284 priv->bcc_caption = NULL;
286 priv->priority_flags = 0;
288 priv->find_toolbar = NULL;
290 priv->draft_msg = NULL;
291 priv->clipboard_change_handler_id = 0;
292 priv->system_clipboard_change_handler_id = 0;
296 /* FIXME: this is a dup from the one in gtk/ */
299 * @result: A ModestPairList, which must be freed with modest_pair_list_free().
301 static ModestPairList*
302 get_transports (void)
304 GSList *transports = NULL;
306 ModestAccountMgr *account_mgr = modest_runtime_get_account_mgr();
307 GSList *accounts = modest_account_mgr_account_names (account_mgr,
308 TRUE /* only enabled accounts. */);
310 GSList *cursor = accounts;
312 gchar *account_name = cursor->data;
313 gchar *from_string = NULL;
315 from_string = modest_account_mgr_get_from_string (account_mgr,
319 if (from_string && account_name) {
320 gchar *name = account_name;
321 ModestPair *pair = modest_pair_new ((gpointer) name,
322 (gpointer) from_string , TRUE);
323 transports = g_slist_prepend (transports, pair);
326 cursor = cursor->next;
328 g_slist_free (accounts); /* only free the accounts, not the elements,
329 * because they are used in the pairlist */
335 init_window (ModestMsgEditWindow *obj)
337 GtkWidget *from_caption, *to_caption, *subject_caption;
338 GtkWidget *main_vbox;
339 ModestMsgEditWindowPrivate *priv;
341 GtkSizeGroup *size_group;
343 GtkWidget *scroll_area;
344 GtkWidget *subject_box;
345 GtkWidget *attachment_icon;
346 GtkWidget *window_box;
348 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE(obj);
350 size_group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL);
352 /* Note: This ModestPairList* must exist for as long as the combo
353 * that uses it, because the ModestComboBox uses the ID opaquely,
354 * so it can't know how to manage its memory. */
355 priv->from_field_protos = get_transports ();
357 priv->from_field = modest_combo_box_new (priv->from_field_protos, g_str_equal);
359 priv->to_field = modest_recpt_editor_new ();
360 priv->cc_field = modest_recpt_editor_new ();
361 priv->bcc_field = modest_recpt_editor_new ();
362 subject_box = gtk_hbox_new (FALSE, 0);
363 priv->priority_icon = gtk_image_new ();
364 gtk_box_pack_start (GTK_BOX (subject_box), priv->priority_icon, FALSE, FALSE, 0);
365 priv->subject_field = gtk_entry_new_with_max_length (SUBJECT_MAX_LENGTH);
366 hildon_gtk_entry_set_input_mode (GTK_ENTRY (priv->subject_field),
367 HILDON_GTK_INPUT_MODE_FULL | HILDON_GTK_INPUT_MODE_AUTOCAP);
368 gtk_box_pack_start (GTK_BOX (subject_box), priv->subject_field, TRUE, TRUE, 0);
369 priv->add_attachment_button = gtk_button_new ();
370 GTK_WIDGET_UNSET_FLAGS (GTK_WIDGET (priv->add_attachment_button), GTK_CAN_FOCUS);
371 gtk_button_set_relief (GTK_BUTTON (priv->add_attachment_button), GTK_RELIEF_NONE);
372 gtk_button_set_focus_on_click (GTK_BUTTON (priv->add_attachment_button), FALSE);
373 gtk_button_set_alignment (GTK_BUTTON (priv->add_attachment_button), 1.0, 1.0);
374 attachment_icon = gtk_image_new_from_icon_name (MODEST_HEADER_ICON_ATTACH, GTK_ICON_SIZE_BUTTON);
375 gtk_container_add (GTK_CONTAINER (priv->add_attachment_button), attachment_icon);
376 gtk_box_pack_start (GTK_BOX (subject_box), priv->add_attachment_button, FALSE, FALSE, 0);
377 priv->attachments_view = modest_attachments_view_new (NULL);
379 priv->header_box = gtk_vbox_new (FALSE, 0);
381 from_caption = hildon_caption_new (size_group, _("mail_va_from"), priv->from_field, NULL, 0);
382 to_caption = hildon_caption_new (size_group, _("mail_va_to"), priv->to_field, NULL, 0);
383 priv->cc_caption = hildon_caption_new (size_group, _("mail_va_cc"), priv->cc_field, NULL, 0);
384 priv->bcc_caption = hildon_caption_new (size_group, _("mail_va_hotfix1"), priv->bcc_field, NULL, 0);
385 subject_caption = hildon_caption_new (size_group, _("mail_va_subject"), subject_box, NULL, 0);
386 priv->attachments_caption = hildon_caption_new (size_group, _("mail_va_attachment"), priv->attachments_view, NULL, 0);
387 g_object_unref (size_group);
389 size_group = gtk_size_group_new (GTK_SIZE_GROUP_HORIZONTAL);
390 modest_recpt_editor_set_field_size_group (MODEST_RECPT_EDITOR (priv->to_field), size_group);
391 modest_recpt_editor_set_field_size_group (MODEST_RECPT_EDITOR (priv->cc_field), size_group);
392 modest_recpt_editor_set_field_size_group (MODEST_RECPT_EDITOR (priv->bcc_field), size_group);
393 gtk_size_group_add_widget (size_group, priv->subject_field);
394 gtk_size_group_add_widget (size_group, priv->attachments_view);
395 g_object_unref (size_group);
397 gtk_box_pack_start (GTK_BOX (priv->header_box), from_caption, FALSE, FALSE, 0);
398 gtk_box_pack_start (GTK_BOX (priv->header_box), to_caption, FALSE, FALSE, 0);
399 gtk_box_pack_start (GTK_BOX (priv->header_box), priv->cc_caption, FALSE, FALSE, 0);
400 gtk_box_pack_start (GTK_BOX (priv->header_box), priv->bcc_caption, FALSE, FALSE, 0);
401 gtk_box_pack_start (GTK_BOX (priv->header_box), subject_caption, FALSE, FALSE, 0);
402 gtk_box_pack_start (GTK_BOX (priv->header_box), priv->attachments_caption, FALSE, FALSE, 0);
403 gtk_widget_set_no_show_all (priv->attachments_caption, TRUE);
406 priv->msg_body = wp_text_view_new ();
407 gtk_text_view_set_wrap_mode (GTK_TEXT_VIEW (priv->msg_body), GTK_WRAP_WORD_CHAR);
408 priv->text_buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (priv->msg_body));
409 g_object_set (priv->text_buffer, "font_scale", 1.0, NULL);
410 wp_text_buffer_enable_rich_text (WP_TEXT_BUFFER (priv->text_buffer), TRUE);
411 /* gtk_text_buffer_set_can_paste_rich_text (priv->text_buffer, TRUE); */
412 wp_text_buffer_reset_buffer (WP_TEXT_BUFFER (priv->text_buffer), TRUE);
414 priv->find_toolbar = hildon_find_toolbar_new (NULL);
415 gtk_widget_set_no_show_all (priv->find_toolbar, TRUE);
417 g_signal_connect (G_OBJECT (priv->text_buffer), "refresh_attributes",
418 G_CALLBACK (text_buffer_refresh_attributes), obj);
419 g_signal_connect (G_OBJECT (priv->text_buffer), "delete-range",
420 G_CALLBACK (text_buffer_delete_range), obj);
421 g_signal_connect (G_OBJECT (priv->text_buffer), "can-undo",
422 G_CALLBACK (text_buffer_can_undo), obj);
423 g_signal_connect (G_OBJECT (obj), "window-state-event",
424 G_CALLBACK (modest_msg_edit_window_window_state_event),
426 g_signal_connect_swapped (G_OBJECT (priv->to_field), "open-addressbook",
427 G_CALLBACK (modest_msg_edit_window_open_addressbook), obj);
428 g_signal_connect_swapped (G_OBJECT (priv->cc_field), "open-addressbook",
429 G_CALLBACK (modest_msg_edit_window_open_addressbook), obj);
430 g_signal_connect_swapped (G_OBJECT (priv->bcc_field), "open-addressbook",
431 G_CALLBACK (modest_msg_edit_window_open_addressbook), obj);
433 g_signal_connect (G_OBJECT (priv->add_attachment_button), "clicked",
434 G_CALLBACK (modest_msg_edit_window_add_attachment_clicked), obj);
436 g_signal_connect (G_OBJECT (priv->msg_body), "focus-in-event",
437 G_CALLBACK (msg_body_focus), obj);
438 g_signal_connect (G_OBJECT (priv->msg_body), "focus-out-event",
439 G_CALLBACK (msg_body_focus), obj);
440 g_signal_connect (G_OBJECT (modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->to_field))),
441 "changed", G_CALLBACK (recpt_field_changed), obj);
442 g_signal_connect (G_OBJECT (modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->cc_field))),
443 "changed", G_CALLBACK (recpt_field_changed), obj);
444 g_signal_connect (G_OBJECT (modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->bcc_field))),
445 "changed", G_CALLBACK (recpt_field_changed), obj);
446 recpt_field_changed (modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->to_field)), MODEST_MSG_EDIT_WINDOW (obj));
447 g_signal_connect (G_OBJECT (priv->subject_field), "changed", G_CALLBACK (subject_field_changed), obj);
449 g_signal_connect (G_OBJECT (priv->find_toolbar), "close", G_CALLBACK (modest_msg_edit_window_find_toolbar_close), obj);
450 g_signal_connect (G_OBJECT (priv->find_toolbar), "search", G_CALLBACK (modest_msg_edit_window_find_toolbar_search), obj);
452 priv->scroll = gtk_scrolled_window_new (NULL, NULL);
453 gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (priv->scroll), GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC);
454 gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (priv->scroll), GTK_SHADOW_NONE);
456 main_vbox = gtk_vbox_new (FALSE, DEFAULT_MAIN_VBOX_SPACING);
458 gtk_box_pack_start (GTK_BOX(main_vbox), priv->header_box, FALSE, FALSE, 0);
459 frame = gtk_frame_new (NULL);
460 gtk_box_pack_start (GTK_BOX(main_vbox), frame, TRUE, TRUE, 0);
462 gtk_scrolled_window_add_with_viewport (GTK_SCROLLED_WINDOW (priv->scroll), main_vbox);
463 gtk_container_set_focus_vadjustment (GTK_CONTAINER (main_vbox), gtk_scrolled_window_get_vadjustment (GTK_SCROLLED_WINDOW (priv->scroll)));
464 gtk_widget_show_all (GTK_WIDGET(priv->scroll));
466 if (!modest_conf_get_bool(modest_runtime_get_conf(), MODEST_CONF_SHOW_CC, NULL)) {
467 gtk_widget_set_no_show_all (priv->cc_caption, TRUE);
468 gtk_widget_hide (priv->cc_caption);
470 if (!modest_conf_get_bool(modest_runtime_get_conf(), MODEST_CONF_SHOW_BCC, NULL)) {
471 gtk_widget_set_no_show_all (priv->bcc_caption, TRUE);
472 gtk_widget_hide (priv->bcc_caption);
475 window_box = gtk_vbox_new (FALSE, 0);
476 gtk_box_pack_start (GTK_BOX (window_box), priv->scroll, TRUE, TRUE, 0);
477 gtk_box_pack_end (GTK_BOX (window_box), priv->find_toolbar, FALSE, FALSE, 0);
478 gtk_container_add (GTK_CONTAINER(obj), window_box);
479 scroll_area = modest_scroll_area_new (priv->scroll, priv->msg_body);
480 gtk_container_add (GTK_CONTAINER (frame), scroll_area);
481 gtk_container_set_focus_vadjustment (GTK_CONTAINER (scroll_area),
482 gtk_scrolled_window_get_vadjustment (GTK_SCROLLED_WINDOW (priv->scroll)));
484 priv->clipboard_change_handler_id = g_signal_connect (G_OBJECT (gtk_clipboard_get (GDK_SELECTION_PRIMARY)), "owner-change",
485 G_CALLBACK (modest_msg_edit_window_clipboard_owner_change), obj);
486 priv->system_clipboard_change_handler_id = g_signal_connect (G_OBJECT (gtk_clipboard_get (GDK_SELECTION_CLIPBOARD)), "owner-change",
487 G_CALLBACK (modest_msg_edit_window_system_clipboard_owner_change), obj);
493 modest_msg_edit_window_finalize (GObject *obj)
495 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (obj);
497 if (priv->clipboard_change_handler_id > 0) {
498 g_signal_handler_disconnect (gtk_clipboard_get (GDK_SELECTION_PRIMARY), priv->clipboard_change_handler_id);
499 priv->clipboard_change_handler_id = 0;
502 if (priv->system_clipboard_change_handler_id > 0) {
503 g_signal_handler_disconnect (gtk_clipboard_get (GDK_SELECTION_CLIPBOARD),
504 priv->system_clipboard_change_handler_id);
505 priv->system_clipboard_change_handler_id = 0;
508 /* This had to stay alive for as long as the combobox that used it: */
509 modest_pair_list_free (priv->from_field_protos);
511 G_OBJECT_CLASS(parent_class)->finalize (obj);
515 on_delete_event (GtkWidget *widget, GdkEvent *event, ModestMsgEditWindow *self)
517 GtkWidget *close_dialog;
518 ModestMsgEditWindowPrivate *priv;
521 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (self);
522 modest_window_save_state (MODEST_WINDOW (self));
523 if (is_modified (self)) {
524 close_dialog = hildon_note_new_confirmation (GTK_WINDOW (self), _("mcen_nc_no_email_message_modified_save_changes"));
525 response = gtk_dialog_run (GTK_DIALOG (close_dialog));
526 gtk_widget_destroy (close_dialog);
528 if (response != GTK_RESPONSE_CANCEL) {
529 modest_ui_actions_on_save_to_drafts (NULL, self);
532 /* /\* remove old message from drafts *\/ */
533 /* if (priv->draft_msg) { */
534 /* TnyHeader *header = tny_msg_get_header (priv->draft_msg); */
535 /* TnyAccount *account = modest_tny_account_store_get_server_account (modest_runtime_get_account_store(), */
537 /* TNY_ACCOUNT_TYPE_STORE); */
538 /* TnyFolder *folder = modest_tny_account_get_special_folder (account, TNY_FOLDER_TYPE_DRAFTS); */
539 /* g_return_val_if_fail (TNY_IS_HEADER (header), FALSE); */
540 /* g_return_val_if_fail (TNY_IS_FOLDER (folder), FALSE); */
541 /* tny_folder_remove_msg (folder, header, NULL); */
542 /* g_object_unref (folder); */
543 /* g_object_unref (header); */
544 /* g_object_unref (priv->draft_msg); */
545 /* priv->draft_msg = NULL; */
547 gtk_widget_destroy (GTK_WIDGET (self));
553 menubar_to_menu (GtkUIManager *ui_manager)
555 GtkWidget *main_menu;
559 /* Create new main menu */
560 main_menu = gtk_menu_new();
562 /* Get the menubar from the UI manager */
563 menubar = gtk_ui_manager_get_widget (ui_manager, "/MenuBar");
565 iter = gtk_container_get_children (GTK_CONTAINER (menubar));
569 menu = GTK_WIDGET (iter->data);
570 gtk_widget_reparent(menu, main_menu);
572 iter = g_list_next (iter);
579 set_msg (ModestMsgEditWindow *self, TnyMsg *msg)
582 const gchar *to, *cc, *bcc, *subject;
584 ModestMsgEditWindowPrivate *priv;
586 TnyHeaderFlags priority_flags;
588 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (self));
589 g_return_if_fail (TNY_IS_MSG (msg));
591 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (self);
593 header = tny_msg_get_header (msg);
594 to = tny_header_get_to (header);
595 cc = tny_header_get_cc (header);
596 bcc = tny_header_get_bcc (header);
597 subject = tny_header_get_subject (header);
598 priority_flags = tny_header_get_flags (header) & TNY_HEADER_FLAG_PRIORITY;
601 modest_recpt_editor_set_recipients (MODEST_RECPT_EDITOR (priv->to_field), to);
603 modest_recpt_editor_set_recipients (MODEST_RECPT_EDITOR (priv->cc_field), cc);
605 modest_recpt_editor_set_recipients (MODEST_RECPT_EDITOR (priv->bcc_field), bcc);
607 gtk_entry_set_text (GTK_ENTRY(priv->subject_field), subject);
608 modest_msg_edit_window_set_priority_flags (MODEST_MSG_EDIT_WINDOW(self),
611 update_window_title (self);
613 /* gtk_text_buffer_set_can_paste_rich_text (priv->text_buffer, TRUE); */
614 wp_text_buffer_reset_buffer (WP_TEXT_BUFFER (priv->text_buffer), TRUE);
615 body = modest_tny_msg_get_body (msg, TRUE);
617 if ((body == NULL)||(body[0] == '\0')) {
619 body = modest_text_utils_convert_to_html ("");
621 wp_text_buffer_load_document_begin (WP_TEXT_BUFFER (priv->text_buffer), TRUE);
622 wp_text_buffer_load_document_write (WP_TEXT_BUFFER (priv->text_buffer),
625 wp_text_buffer_load_document_end (WP_TEXT_BUFFER (priv->text_buffer));
628 /* Get the default format required from configuration */
629 if (!modest_conf_get_bool (modest_runtime_get_conf (), MODEST_CONF_PREFER_FORMATTED_TEXT, NULL)) {
630 wp_text_buffer_enable_rich_text (WP_TEXT_BUFFER (priv->text_buffer), FALSE);
633 /* Set the default focus depending on having already a To: field or not */
634 if ((!to)||(*to == '\0')) {
635 modest_recpt_editor_grab_focus (MODEST_RECPT_EDITOR (priv->to_field));
637 gtk_widget_grab_focus (priv->msg_body);
640 /* TODO: lower priority, select in the From: combo to the
641 value that comes from msg <- not sure, should it be
644 /* Add attachments to the view */
645 modest_attachments_view_set_message (MODEST_ATTACHMENTS_VIEW (priv->attachments_view), msg);
646 priv->attachments = modest_attachments_view_get_attachments (MODEST_ATTACHMENTS_VIEW (priv->attachments_view));
647 if (priv->attachments == NULL) {
648 gtk_widget_hide (priv->attachments_caption);
650 gtk_widget_set_no_show_all (priv->attachments_caption, FALSE);
651 gtk_widget_show_all (priv->attachments_caption);
654 gtk_text_buffer_get_start_iter (priv->text_buffer, &iter);
655 gtk_text_buffer_place_cursor (priv->text_buffer, &iter);
657 reset_modified (self);
659 update_dimmed (self);
660 text_buffer_can_undo (priv->text_buffer, FALSE, self);
662 priv->draft_msg = msg;
666 menu_tool_button_clicked_popup (GtkMenuToolButton *item,
669 GList *item_children, *node;
670 GtkWidget *bin_child;
672 bin_child = gtk_bin_get_child (GTK_BIN(item));
674 item_children = gtk_container_get_children (GTK_CONTAINER (bin_child));
676 for (node = item_children; node != NULL; node = g_list_next (node)) {
677 if (GTK_IS_TOGGLE_BUTTON (node->data)) {
678 gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (node->data), TRUE);
681 g_list_free (item_children);
685 menu_tool_button_dont_expand (GtkMenuToolButton *item)
688 GList *item_children, *node;
690 box = gtk_bin_get_child (GTK_BIN (item));
691 gtk_box_set_homogeneous (GTK_BOX (box), TRUE);
692 item_children = gtk_container_get_children (GTK_CONTAINER (box));
694 for (node = item_children; node != NULL; node = g_list_next (node)) {
695 gtk_box_set_child_packing (GTK_BOX (box), GTK_WIDGET (node->data), TRUE, TRUE, 0, GTK_PACK_START);
696 if (GTK_IS_TOGGLE_BUTTON (node->data))
697 gtk_button_set_alignment (GTK_BUTTON (node->data), 0.0, 0.5);
698 else if (GTK_IS_BUTTON (node->data))
699 gtk_button_set_alignment (GTK_BUTTON (node->data), 1.0, 0.5);
701 g_list_free (item_children);
706 modest_msg_edit_window_setup_toolbar (ModestMsgEditWindow *window)
708 ModestWindowPrivate *parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
709 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
710 GtkWidget *placeholder;
711 GtkWidget *tool_item;
716 GtkWidget *sizes_menu;
717 GtkWidget *fonts_menu;
718 GSList *radio_group = NULL;
723 parent_priv->toolbar = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar");
724 hildon_window_add_toolbar (HILDON_WINDOW (window), GTK_TOOLBAR (parent_priv->toolbar));
726 /* should we hide the toolbar? */
727 if (!modest_conf_get_bool (modest_runtime_get_conf (), MODEST_CONF_SHOW_TOOLBAR, NULL))
728 gtk_widget_hide (parent_priv->toolbar);
730 /* Font color placeholder */
731 placeholder = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar/FontColor");
732 insert_index = gtk_toolbar_get_item_index(GTK_TOOLBAR (parent_priv->toolbar), GTK_TOOL_ITEM(placeholder));
735 tool_item = GTK_WIDGET (gtk_tool_item_new ());
736 priv->font_color_button = hildon_color_button_new ();
737 GTK_WIDGET_UNSET_FLAGS (tool_item, GTK_CAN_FOCUS);
738 GTK_WIDGET_UNSET_FLAGS (priv->font_color_button, GTK_CAN_FOCUS);
739 gtk_container_add (GTK_CONTAINER (tool_item), priv->font_color_button);
740 gtk_tool_item_set_expand (GTK_TOOL_ITEM (tool_item), TRUE);
741 gtk_tool_item_set_homogeneous (GTK_TOOL_ITEM (tool_item), TRUE);
742 gtk_toolbar_insert(GTK_TOOLBAR(parent_priv->toolbar), GTK_TOOL_ITEM (tool_item), insert_index);
743 g_signal_connect_swapped (G_OBJECT (priv->font_color_button), "notify::color", G_CALLBACK (modest_msg_edit_window_color_button_change), window);
745 /* Font size and face placeholder */
746 placeholder = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar/FontAttributes");
747 insert_index = gtk_toolbar_get_item_index(GTK_TOOLBAR (parent_priv->toolbar), GTK_TOOL_ITEM(placeholder));
749 tool_item = GTK_WIDGET (gtk_menu_tool_button_new (NULL, NULL));
750 priv->size_tool_button_label = gtk_label_new (NULL);
751 snprintf(size_text, sizeof(size_text), "%d", wp_font_size[DEFAULT_FONT_SIZE]);
752 markup = g_strconcat ("<span font_family='", DEFAULT_SIZE_BUTTON_FONT_FAMILY, "'>",
753 size_text,"</span>", NULL);
754 gtk_label_set_markup (GTK_LABEL (priv->size_tool_button_label), markup);
756 gtk_tool_button_set_label_widget (GTK_TOOL_BUTTON (tool_item), priv->size_tool_button_label);
757 sizes_menu = gtk_menu_new ();
758 priv->size_items_group = NULL;
760 for (size_index = 0; size_index < WP_FONT_SIZE_COUNT; size_index++) {
761 GtkWidget *size_menu_item;
763 snprintf(size_text, sizeof(size_text), "%d", wp_font_size[size_index]);
764 size_menu_item = gtk_radio_menu_item_new_with_label (radio_group, size_text);
765 radio_group = gtk_radio_menu_item_get_group (GTK_RADIO_MENU_ITEM (size_menu_item));
766 gtk_menu_shell_append (GTK_MENU_SHELL (sizes_menu), size_menu_item);
767 gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM (size_menu_item), (wp_font_size[size_index] == 12));
768 gtk_widget_show (size_menu_item);
770 priv->size_items_group = g_slist_prepend (priv->size_items_group, size_menu_item);
774 for (node = radio_group; node != NULL; node = g_slist_next (node)) {
775 GtkWidget *item = (GtkWidget *) node->data;
776 g_signal_connect (G_OBJECT (item), "toggled", G_CALLBACK (modest_msg_edit_window_size_change),
780 priv->size_items_group = g_slist_reverse (priv->size_items_group);
781 gtk_menu_tool_button_set_menu (GTK_MENU_TOOL_BUTTON (tool_item), sizes_menu);
782 g_signal_connect (G_OBJECT (tool_item), "clicked", G_CALLBACK (menu_tool_button_clicked_popup), NULL);
783 gtk_toolbar_insert (GTK_TOOLBAR (parent_priv->toolbar), GTK_TOOL_ITEM (tool_item), insert_index);
784 gtk_tool_item_set_expand (GTK_TOOL_ITEM (tool_item), TRUE);
785 gtk_tool_item_set_homogeneous (GTK_TOOL_ITEM (tool_item), TRUE);
786 menu_tool_button_dont_expand (GTK_MENU_TOOL_BUTTON (tool_item));
787 priv->font_size_toolitem = tool_item;
790 tool_item = GTK_WIDGET (gtk_menu_tool_button_new (NULL, NULL));
791 priv->font_tool_button_label = gtk_label_new (NULL);
792 markup = g_strconcat ("<span font_family='", wp_get_font_name(DEFAULT_FONT), "'>Tt</span>", NULL);
793 gtk_label_set_markup (GTK_LABEL (priv->font_tool_button_label), markup);
795 gtk_tool_button_set_label_widget (GTK_TOOL_BUTTON (tool_item), priv->font_tool_button_label);
796 fonts_menu = gtk_menu_new ();
797 priv->font_items_group = NULL;
799 for (font_index = 0; font_index < wp_get_font_count (); font_index++) {
800 GtkWidget *font_menu_item;
801 GtkWidget *child_label;
803 font_menu_item = gtk_radio_menu_item_new_with_label (radio_group, "");
804 child_label = gtk_bin_get_child (GTK_BIN (font_menu_item));
805 markup = g_strconcat ("<span font_family='", wp_get_font_name (font_index),"'>",
806 wp_get_font_name (font_index), "</span>", NULL);
807 gtk_label_set_markup (GTK_LABEL (child_label), markup);
810 radio_group = gtk_radio_menu_item_get_group (GTK_RADIO_MENU_ITEM (font_menu_item));
811 gtk_menu_shell_append (GTK_MENU_SHELL (fonts_menu), font_menu_item);
812 gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM (font_menu_item), (font_index == DEFAULT_FONT));
813 gtk_widget_show (font_menu_item);
815 priv->font_items_group = g_slist_prepend (priv->font_items_group, font_menu_item);
818 for (node = radio_group; node != NULL; node = g_slist_next (node)) {
819 GtkWidget *item = (GtkWidget *) node->data;
820 g_signal_connect (G_OBJECT (item), "toggled", G_CALLBACK (modest_msg_edit_window_font_change),
823 priv->font_items_group = g_slist_reverse (priv->font_items_group);
824 gtk_menu_tool_button_set_menu (GTK_MENU_TOOL_BUTTON (tool_item), fonts_menu);
825 g_signal_connect (G_OBJECT (tool_item), "clicked", G_CALLBACK (menu_tool_button_clicked_popup), NULL);
826 gtk_toolbar_insert (GTK_TOOLBAR (parent_priv->toolbar), GTK_TOOL_ITEM (tool_item), insert_index);
827 gtk_tool_item_set_expand (GTK_TOOL_ITEM (tool_item), TRUE);
828 gtk_tool_item_set_homogeneous (GTK_TOOL_ITEM (tool_item), TRUE);
829 menu_tool_button_dont_expand (GTK_MENU_TOOL_BUTTON (tool_item));
830 priv->font_face_toolitem = tool_item;
832 /* Set expand and homogeneous for remaining items */
833 tool_item = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar/ToolbarSend");
834 gtk_tool_item_set_expand (GTK_TOOL_ITEM (tool_item), TRUE);
835 gtk_tool_item_set_homogeneous (GTK_TOOL_ITEM (tool_item), TRUE);
836 tool_item = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar/ActionsBold");
837 gtk_tool_item_set_expand (GTK_TOOL_ITEM (tool_item), TRUE);
838 gtk_tool_item_set_homogeneous (GTK_TOOL_ITEM (tool_item), TRUE);
839 tool_item = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar/ActionsItalics");
840 gtk_tool_item_set_expand (GTK_TOOL_ITEM (tool_item), TRUE);
841 gtk_tool_item_set_homogeneous (GTK_TOOL_ITEM (tool_item), TRUE);
849 modest_msg_edit_window_new (TnyMsg *msg, const gchar *account_name)
852 ModestWindowPrivate *parent_priv;
853 ModestMsgEditWindowPrivate *priv;
854 GtkActionGroup *action_group;
855 GError *error = NULL;
856 GdkPixbuf *window_icon = NULL;
859 gboolean prefer_formatted;
861 ModestPair *account_pair = NULL;
863 g_return_val_if_fail (msg, NULL);
864 g_return_val_if_fail (account_name, NULL);
866 obj = g_object_new(MODEST_TYPE_MSG_EDIT_WINDOW, NULL);
868 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (obj);
869 parent_priv = MODEST_WINDOW_GET_PRIVATE (obj);
871 parent_priv->ui_manager = gtk_ui_manager_new();
872 action_group = gtk_action_group_new ("ModestMsgEditWindowActions");
873 gtk_action_group_set_translation_domain (action_group, GETTEXT_PACKAGE);
875 /* Add common actions */
876 gtk_action_group_add_actions (action_group,
877 modest_msg_edit_action_entries,
878 G_N_ELEMENTS (modest_msg_edit_action_entries),
880 gtk_action_group_add_toggle_actions (action_group,
881 modest_msg_edit_toggle_action_entries,
882 G_N_ELEMENTS (modest_msg_edit_toggle_action_entries),
884 gtk_action_group_add_radio_actions (action_group,
885 modest_msg_edit_alignment_radio_action_entries,
886 G_N_ELEMENTS (modest_msg_edit_alignment_radio_action_entries),
888 G_CALLBACK (modest_ui_actions_on_change_justify),
890 gtk_action_group_add_radio_actions (action_group,
891 modest_msg_edit_zoom_action_entries,
892 G_N_ELEMENTS (modest_msg_edit_zoom_action_entries),
894 G_CALLBACK (modest_ui_actions_on_change_zoom),
896 gtk_action_group_add_radio_actions (action_group,
897 modest_msg_edit_priority_action_entries,
898 G_N_ELEMENTS (modest_msg_edit_priority_action_entries),
900 G_CALLBACK (modest_ui_actions_msg_edit_on_change_priority),
902 gtk_action_group_add_radio_actions (action_group,
903 modest_msg_edit_file_format_action_entries,
904 G_N_ELEMENTS (modest_msg_edit_file_format_action_entries),
905 modest_conf_get_bool (modest_runtime_get_conf (), MODEST_CONF_PREFER_FORMATTED_TEXT, NULL),
906 G_CALLBACK (modest_ui_actions_msg_edit_on_change_file_format),
908 gtk_ui_manager_insert_action_group (parent_priv->ui_manager, action_group, 0);
909 g_object_unref (action_group);
911 /* Load the UI definition */
912 gtk_ui_manager_add_ui_from_file (parent_priv->ui_manager, MODEST_UIDIR "modest-msg-edit-window-ui.xml",
915 g_warning ("Could not merge modest-msg-edit-window-ui.xml: %s", error->message);
916 g_clear_error (&error);
919 /* Add accelerators */
920 gtk_window_add_accel_group (GTK_WINDOW (obj),
921 gtk_ui_manager_get_accel_group (parent_priv->ui_manager));
924 parent_priv->menubar = menubar_to_menu (parent_priv->ui_manager);
925 hildon_window_set_menu (HILDON_WINDOW (obj), GTK_MENU (parent_priv->menubar));
928 init_window (MODEST_MSG_EDIT_WINDOW(obj));
930 restore_settings (MODEST_MSG_EDIT_WINDOW(obj));
932 gtk_window_set_icon_from_file (GTK_WINDOW(obj), MODEST_APP_ICON, NULL);
934 g_signal_connect (G_OBJECT(obj), "delete-event",
935 G_CALLBACK(on_delete_event), obj);
937 modest_window_set_active_account (MODEST_WINDOW(obj), account_name);
939 modest_msg_edit_window_setup_toolbar (MODEST_MSG_EDIT_WINDOW (obj));
941 setup_insensitive_handlers (MODEST_MSG_EDIT_WINDOW (obj));
943 account_pair = modest_pair_list_find_by_first_as_string (priv->from_field_protos, account_name);
944 if (account_pair != NULL)
945 modest_combo_box_set_active_id (MODEST_COMBO_BOX (priv->from_field), account_pair->first);
947 set_msg (MODEST_MSG_EDIT_WINDOW (obj), msg);
949 text_buffer_refresh_attributes (WP_TEXT_BUFFER (priv->text_buffer), MODEST_MSG_EDIT_WINDOW (obj));
951 /* Set window icon */
952 window_icon = modest_platform_get_icon (MODEST_APP_MSG_EDIT_ICON);
953 gtk_window_set_icon (GTK_WINDOW (obj), window_icon);
955 /* Dim at start clipboard actions */
956 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/EditMenu/CutMenu");
957 gtk_action_set_sensitive (action, FALSE);
958 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/EditMenu/CopyMenu");
959 gtk_action_set_sensitive (action, FALSE);
960 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/AttachmentsMenu/RemoveAttachmentsMenu");
961 gtk_action_set_sensitive (action, FALSE);
963 /* Update select all */
964 update_select_all_dimming (MODEST_MSG_EDIT_WINDOW (obj));
965 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/EditMenu");
966 g_signal_connect (G_OBJECT (action), "activate", G_CALLBACK (edit_menu_activated), obj);
967 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/ViewMenu");
968 g_signal_connect (G_OBJECT (action), "activate", G_CALLBACK (view_menu_activated), obj);
970 /* set initial state of cc and bcc */
971 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/ViewMenu/ViewCcFieldMenu");
972 gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (action),
973 modest_conf_get_bool(modest_runtime_get_conf(), MODEST_CONF_SHOW_CC, NULL));
974 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/ViewMenu/ViewBccFieldMenu");
975 gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (action),
976 modest_conf_get_bool(modest_runtime_get_conf(), MODEST_CONF_SHOW_BCC, NULL));
978 /* Setup the file format */
979 conf = modest_runtime_get_conf ();
980 prefer_formatted = modest_conf_get_bool (conf, MODEST_CONF_PREFER_FORMATTED_TEXT, &error);
982 g_clear_error (&error);
983 file_format = MODEST_FILE_FORMAT_FORMATTED_TEXT;
985 file_format = (prefer_formatted) ?
986 MODEST_FILE_FORMAT_FORMATTED_TEXT :
987 MODEST_FILE_FORMAT_PLAIN_TEXT;
988 modest_msg_edit_window_set_file_format (MODEST_MSG_EDIT_WINDOW (obj), file_format);
990 update_paste_dimming (MODEST_MSG_EDIT_WINDOW (obj));
992 return (ModestWindow*) obj;
996 get_formatted_data_cb (const gchar *buffer, gpointer user_data)
998 GString **string_buffer = (GString **) user_data;
1000 *string_buffer = g_string_append (*string_buffer, buffer);
1006 * @result: A new string which should be freed with g_free().
1009 get_formatted_data (ModestMsgEditWindow *edit_window)
1011 ModestMsgEditWindowPrivate *priv;
1012 GString *string_buffer = g_string_new ("");
1014 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (edit_window);
1016 wp_text_buffer_save_document (WP_TEXT_BUFFER(priv->text_buffer), get_formatted_data_cb, &string_buffer);
1018 return g_string_free (string_buffer, FALSE);
1023 modest_msg_edit_window_get_msg_data (ModestMsgEditWindow *edit_window)
1026 const gchar *account_name;
1027 ModestMsgEditWindowPrivate *priv;
1029 g_return_val_if_fail (MODEST_IS_MSG_EDIT_WINDOW (edit_window), NULL);
1031 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (edit_window);
1033 account_name = modest_combo_box_get_active_id (MODEST_COMBO_BOX (priv->from_field));
1034 g_return_val_if_fail (account_name, NULL);
1037 /* don't free these (except from) */
1038 data = g_slice_new0 (MsgData);
1039 data->from = modest_account_mgr_get_from_string (modest_runtime_get_account_mgr(),
1041 data->account_name = g_strdup (account_name);
1042 data->to = g_strdup (modest_recpt_editor_get_recipients (MODEST_RECPT_EDITOR (priv->to_field)));
1043 data->cc = g_strdup (modest_recpt_editor_get_recipients (MODEST_RECPT_EDITOR (priv->cc_field)));
1044 data->bcc = g_strdup (modest_recpt_editor_get_recipients (MODEST_RECPT_EDITOR (priv->bcc_field)));
1045 data->subject = g_strdup (gtk_entry_get_text (GTK_ENTRY (priv->subject_field)));
1046 if (priv->draft_msg) {
1047 data->draft_msg = g_object_ref (priv->draft_msg);
1049 data->draft_msg = NULL;
1052 GtkTextBuffer *buf = gtk_text_view_get_buffer (GTK_TEXT_VIEW (priv->msg_body));
1054 gtk_text_buffer_get_bounds (buf, &b, &e);
1055 data->plain_body = g_strdup (gtk_text_buffer_get_text (priv->text_buffer, &b, &e, FALSE)); /* returns a copy */
1057 if (wp_text_buffer_is_rich_text (WP_TEXT_BUFFER (priv->text_buffer)))
1058 data->html_body = get_formatted_data (edit_window); /* returns a copy. */
1060 data->html_body = NULL;
1062 data->attachments = priv->attachments; /* TODO: copy and free ? */
1063 data->priority_flags = priv->priority_flags;
1068 /* TODO: We must duplicate this implementation for GNOME and Maemo, but that is unwise. */
1070 modest_msg_edit_window_free_msg_data (ModestMsgEditWindow *edit_window,
1073 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (edit_window));
1081 g_free (data->subject);
1082 g_free (data->plain_body);
1083 g_free (data->html_body);
1084 if (data->draft_msg != NULL) {
1085 g_object_unref (data->draft_msg);
1086 data->draft_msg = NULL;
1088 g_free (data->account_name);
1090 /* TODO: Free data->attachments? */
1092 g_slice_free (MsgData, data);
1096 modest_msg_edit_window_get_format (ModestMsgEditWindow *self)
1099 ModestMsgEditWindowPrivate *priv = NULL;
1100 g_return_val_if_fail (MODEST_IS_MSG_EDIT_WINDOW (self), MODEST_MSG_EDIT_FORMAT_HTML);
1102 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (self);
1104 rich_text = wp_text_buffer_is_rich_text (WP_TEXT_BUFFER (priv->text_buffer));
1106 return MODEST_MSG_EDIT_FORMAT_HTML;
1108 return MODEST_MSG_EDIT_FORMAT_TEXT;
1112 modest_msg_edit_window_set_format (ModestMsgEditWindow *self,
1113 ModestMsgEditFormat format)
1115 ModestMsgEditWindowPrivate *priv;
1117 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (self));
1118 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (self);
1121 case MODEST_MSG_EDIT_FORMAT_HTML:
1122 wp_text_buffer_enable_rich_text (WP_TEXT_BUFFER (priv->text_buffer), TRUE);
1124 case MODEST_MSG_EDIT_FORMAT_TEXT:
1125 wp_text_buffer_enable_rich_text (WP_TEXT_BUFFER (priv->text_buffer), FALSE);
1128 g_return_if_reached ();
1132 ModestMsgEditFormatState *
1133 modest_msg_edit_window_get_format_state (ModestMsgEditWindow *self)
1135 ModestMsgEditFormatState *format_state = NULL;
1136 ModestMsgEditWindowPrivate *priv;
1137 WPTextBufferFormat *buffer_format = g_new0 (WPTextBufferFormat, 1);
1139 g_return_val_if_fail (MODEST_IS_MSG_EDIT_WINDOW (self), NULL);
1140 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (self);
1142 wp_text_buffer_get_attributes (WP_TEXT_BUFFER (priv->text_buffer), buffer_format, TRUE);
1144 format_state = g_new0 (ModestMsgEditFormatState, 1);
1145 format_state->bold = buffer_format->bold&0x1;
1146 format_state->italics = buffer_format->italic&0x1;
1147 format_state->bullet = buffer_format->bullet&0x1;
1148 format_state->color = buffer_format->color;
1149 format_state->font_size = buffer_format->font_size;
1150 format_state->font_family = wp_get_font_name (buffer_format->font);
1151 format_state->justification = buffer_format->justification;
1152 g_free (buffer_format);
1154 return format_state;
1159 modest_msg_edit_window_set_format_state (ModestMsgEditWindow *self,
1160 const ModestMsgEditFormatState *format_state)
1162 ModestMsgEditWindowPrivate *priv;
1163 WPTextBufferFormat *buffer_format = g_new0 (WPTextBufferFormat, 1);
1164 WPTextBufferFormat *current_format = g_new0 (WPTextBufferFormat, 1);
1165 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (self));
1166 g_return_if_fail (format_state != NULL);
1168 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (self);
1169 gtk_widget_grab_focus (priv->msg_body);
1170 buffer_format->bold = (format_state->bold != FALSE);
1171 buffer_format->italic = (format_state->italics != FALSE);
1172 buffer_format->color = format_state->color;
1173 buffer_format->font_size = format_state->font_size;
1174 buffer_format->font = wp_get_font_index (format_state->font_family, 0);
1175 buffer_format->justification = format_state->justification;
1176 buffer_format->bullet = format_state->bullet;
1178 wp_text_buffer_get_attributes (WP_TEXT_BUFFER (priv->text_buffer), current_format, TRUE);
1180 buffer_format->cs.bold = ((buffer_format->bold&0x1) != (current_format->bold&0x1));
1181 buffer_format->cs.italic = ((buffer_format->italic&0x1) != (current_format->italic&0x1));
1182 buffer_format->cs.color = gdk_color_equal(&(buffer_format->color), &(current_format->color));
1183 buffer_format->cs.font_size = (buffer_format->font_size != current_format->font_size);
1184 buffer_format->cs.font = (buffer_format->font != current_format->font);
1185 buffer_format->cs.justification = (buffer_format->justification != current_format->justification);
1186 buffer_format->cs.bullet = (buffer_format->bullet != current_format->bullet);
1188 wp_text_buffer_freeze (WP_TEXT_BUFFER (priv->text_buffer));
1189 if (buffer_format->cs.bold) {
1190 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_BOLD, (gpointer) (buffer_format->bold&0x1));
1192 if (buffer_format->cs.italic) {
1193 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_ITALIC, (gpointer) (buffer_format->italic&0x1));
1195 if (buffer_format->cs.color) {
1196 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_FORECOLOR, (gpointer) (&(buffer_format->color)));
1198 if (buffer_format->cs.font_size) {
1199 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_BOLD, (gpointer) (buffer_format->font_size));
1201 if (buffer_format->cs.justification) {
1202 switch (buffer_format->justification) {
1203 case GTK_JUSTIFY_LEFT:
1204 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_LEFT, (gpointer) TRUE);
1206 case GTK_JUSTIFY_CENTER:
1207 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_CENTER, (gpointer) TRUE);
1209 case GTK_JUSTIFY_RIGHT:
1210 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_RIGHT, (gpointer) TRUE);
1217 if (buffer_format->cs.font) {
1218 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_BOLD, (gpointer) (buffer_format->font));
1220 if (buffer_format->cs.bullet) {
1221 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_BULLET, (gpointer) ((int)buffer_format->bullet));
1223 /* wp_text_buffer_set_format (WP_TEXT_BUFFER (priv->text_buffer), buffer_format); */
1224 wp_text_buffer_thaw (WP_TEXT_BUFFER (priv->text_buffer));
1226 g_free (current_format);
1231 toggle_action_set_active_block_notify (GtkToggleAction *action,
1234 GSList *proxies = NULL;
1236 for (proxies = gtk_action_get_proxies (GTK_ACTION (action));
1237 proxies != NULL; proxies = g_slist_next (proxies)) {
1238 GtkWidget *widget = (GtkWidget *) proxies->data;
1239 gtk_action_block_activate_from (GTK_ACTION (action), widget);
1242 gtk_toggle_action_set_active (action, value);
1244 for (proxies = gtk_action_get_proxies (GTK_ACTION (action));
1245 proxies != NULL; proxies = g_slist_next (proxies)) {
1246 GtkWidget *widget = (GtkWidget *) proxies->data;
1247 gtk_action_unblock_activate_from (GTK_ACTION (action), widget);
1252 text_buffer_refresh_attributes (WPTextBuffer *buffer, ModestMsgEditWindow *window)
1254 WPTextBufferFormat *buffer_format = g_new0 (WPTextBufferFormat, 1);
1256 ModestWindowPrivate *parent_priv;
1257 ModestMsgEditWindowPrivate *priv;
1258 GtkWidget *new_size_menuitem;
1259 GtkWidget *new_font_menuitem;
1261 parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
1262 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1264 if (wp_text_buffer_is_rich_text (WP_TEXT_BUFFER (priv->text_buffer))) {
1265 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/FormatMenu/FileFormatMenu/FileFormatFormattedTextMenu");
1266 if (!gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (action)))
1267 toggle_action_set_active_block_notify (GTK_TOGGLE_ACTION (action), TRUE);
1269 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/FormatMenu/FileFormatMenu/FileFormatPlainTextMenu");
1270 if (!gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (action)))
1271 toggle_action_set_active_block_notify (GTK_TOGGLE_ACTION (action), TRUE);
1274 wp_text_buffer_get_attributes (WP_TEXT_BUFFER (priv->text_buffer), buffer_format, FALSE);
1276 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/ToolBar/ActionsBold");
1277 toggle_action_set_active_block_notify (GTK_TOGGLE_ACTION (action), buffer_format->bold);
1279 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/ToolBar/ActionsItalics");
1280 toggle_action_set_active_block_notify (GTK_TOGGLE_ACTION (action), buffer_format->italic);
1282 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/FormatMenu/BulletedListMenu");
1283 toggle_action_set_active_block_notify (GTK_TOGGLE_ACTION (action), buffer_format->bullet);
1285 g_signal_handlers_block_by_func (G_OBJECT (priv->font_color_button),
1286 G_CALLBACK (modest_msg_edit_window_color_button_change),
1288 hildon_color_button_set_color (HILDON_COLOR_BUTTON (priv->font_color_button), & (buffer_format->color));
1289 g_signal_handlers_unblock_by_func (G_OBJECT (priv->font_color_button),
1290 G_CALLBACK (modest_msg_edit_window_color_button_change),
1293 new_size_menuitem = GTK_WIDGET ((g_slist_nth (priv->size_items_group,
1294 buffer_format->font_size))->data);
1295 if (!gtk_check_menu_item_get_active (GTK_CHECK_MENU_ITEM (new_size_menuitem))) {
1299 label = gtk_bin_get_child (GTK_BIN (new_size_menuitem));
1300 markup = g_strconcat ("<span font_family='Serif'>", gtk_label_get_text (GTK_LABEL (label)), "</span>", NULL);
1301 gtk_label_set_markup (GTK_LABEL (priv->size_tool_button_label), markup);
1303 g_signal_handlers_block_by_func (G_OBJECT (new_size_menuitem),
1304 G_CALLBACK (modest_msg_edit_window_size_change),
1306 gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM (new_size_menuitem), TRUE);
1307 g_signal_handlers_unblock_by_func (G_OBJECT (new_size_menuitem),
1308 G_CALLBACK (modest_msg_edit_window_size_change),
1312 new_font_menuitem = GTK_WIDGET ((g_slist_nth (priv->font_items_group,
1313 buffer_format->font))->data);
1314 if (!gtk_check_menu_item_get_active (GTK_CHECK_MENU_ITEM (new_font_menuitem))) {
1318 label = gtk_bin_get_child (GTK_BIN (new_font_menuitem));
1319 markup = g_strconcat ("<span font_family='", gtk_label_get_text (GTK_LABEL (label)),"'>Tt</span>", NULL);
1320 gtk_label_set_markup (GTK_LABEL (priv->font_tool_button_label), markup);
1322 g_signal_handlers_block_by_func (G_OBJECT (new_font_menuitem),
1323 G_CALLBACK (modest_msg_edit_window_font_change),
1325 gtk_check_menu_item_set_active (GTK_CHECK_MENU_ITEM (new_font_menuitem), TRUE);
1326 g_signal_handlers_unblock_by_func (G_OBJECT (new_font_menuitem),
1327 G_CALLBACK (modest_msg_edit_window_font_change),
1331 g_free (buffer_format);
1337 modest_msg_edit_window_select_color (ModestMsgEditWindow *window)
1340 WPTextBufferFormat *buffer_format = g_new0 (WPTextBufferFormat, 1);
1341 ModestMsgEditWindowPrivate *priv;
1342 GtkWidget *dialog = NULL;
1344 const GdkColor *new_color = NULL;
1346 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1347 wp_text_buffer_get_attributes (WP_TEXT_BUFFER (priv->text_buffer), buffer_format, FALSE);
1349 #ifdef MODEST_HILDON_VERSION_0
1350 dialog = hildon_color_selector_new (GTK_WINDOW (window));
1351 hildon_color_selector_set_color (HILDON_COLOR_SELECTOR (dialog), &(buffer_format->color));
1353 dialog = hildon_color_chooser_new ();
1354 hildon_color_chooser_set_color (HILDON_COLOR_CHOOSER (dialog), &(buffer_format->color));
1355 #endif /*MODEST_HILDON_VERSION_0*/
1356 g_free (buffer_format);
1358 response = gtk_dialog_run (GTK_DIALOG (dialog));
1360 case GTK_RESPONSE_OK: {
1361 #ifdef MODEST_HILDON_VERSION_0
1362 new_color = hildon_color_selector_get_color (HILDON_COLOR_SELECTOR (dialog));
1365 hildon_color_chooser_get_color (HILDON_COLOR_CHOOSER(dialog), &col);
1367 #endif /*MODEST_HILDON_VERSION_0*/
1374 gtk_widget_destroy (dialog);
1376 if (new_color != NULL)
1377 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_FORECOLOR, (gpointer) new_color);
1382 modest_msg_edit_window_select_background_color (ModestMsgEditWindow *window)
1385 ModestMsgEditWindowPrivate *priv;
1386 GtkWidget *dialog = NULL;
1388 GdkColor *old_color = NULL;
1389 const GdkColor *new_color = NULL;
1391 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1392 old_color = (GdkColor*)wp_text_buffer_get_background_color (WP_TEXT_BUFFER (priv->text_buffer));
1394 #ifdef MODEST_HILDON_VERSION_0
1395 dialog = hildon_color_selector_new (GTK_WINDOW (window));
1396 hildon_color_selector_set_color (HILDON_COLOR_SELECTOR (dialog),(GdkColor*)old_color);
1398 dialog = hildon_color_chooser_new ();
1399 hildon_color_chooser_set_color (HILDON_COLOR_CHOOSER (dialog),(GdkColor*)old_color);
1400 #endif /*MODEST_HILDON_VERSION_9*/
1402 response = gtk_dialog_run (GTK_DIALOG (dialog));
1404 case GTK_RESPONSE_OK: {
1405 #ifdef MODEST_HILDON_VERSION_0
1406 new_color = hildon_color_selector_get_color (HILDON_COLOR_SELECTOR (dialog));
1409 hildon_color_chooser_get_color (HILDON_COLOR_CHOOSER(dialog), &col);
1411 #endif /*MODEST_HILDON_VERSION_0*/
1417 gtk_widget_destroy (dialog);
1419 if (new_color != NULL)
1420 wp_text_buffer_set_background_color (WP_TEXT_BUFFER (priv->text_buffer), new_color);
1425 modest_msg_edit_window_insert_image (ModestMsgEditWindow *window)
1428 ModestMsgEditWindowPrivate *priv;
1429 GtkWidget *dialog = NULL;
1431 gchar *filename = NULL;
1433 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1435 dialog = hildon_file_chooser_dialog_new (GTK_WINDOW (window), GTK_FILE_CHOOSER_ACTION_OPEN);
1436 gtk_window_set_title (GTK_WINDOW (dialog), _("mcen_ia_select_inline_image_title"));
1438 response = gtk_dialog_run (GTK_DIALOG (dialog));
1440 case GTK_RESPONSE_OK:
1441 filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (dialog));
1446 gtk_widget_destroy (dialog);
1449 GdkPixbuf *pixbuf = NULL;
1450 GtkTextIter position;
1451 GtkTextMark *insert_mark;
1453 pixbuf = gdk_pixbuf_new_from_file (filename, NULL);
1456 GdkPixbufFormat *pixbuf_format;
1458 image_file_id = g_open (filename, O_RDONLY, 0);
1459 pixbuf_format = gdk_pixbuf_get_file_info (filename, NULL, NULL);
1460 if ((image_file_id != -1)&&(pixbuf_format != NULL)) {
1461 TnyMimePart *image_part;
1462 TnyStream *image_stream;
1468 mime_types = gdk_pixbuf_format_get_mime_types (pixbuf_format);
1469 if ((mime_types != NULL) && (mime_types[0] != NULL)) {
1470 mime_type = mime_types[0];
1472 mime_type = "image/unknown";
1474 image_part = tny_platform_factory_new_mime_part
1475 (modest_runtime_get_platform_factory ());
1476 image_stream = TNY_STREAM (tny_fs_stream_new (image_file_id));
1478 tny_mime_part_construct_from_stream (image_part, image_stream, mime_type);
1479 g_strfreev (mime_types);
1481 content_id = g_strdup_printf ("%d", priv->last_cid);
1482 tny_mime_part_set_content_id (image_part, content_id);
1483 g_free (content_id);
1486 basename = g_path_get_basename (filename);
1487 tny_mime_part_set_filename (image_part, basename);
1490 insert_mark = gtk_text_buffer_get_insert (GTK_TEXT_BUFFER (priv->text_buffer));
1491 gtk_text_buffer_get_iter_at_mark (GTK_TEXT_BUFFER (priv->text_buffer), &position, insert_mark);
1492 wp_text_buffer_insert_image (WP_TEXT_BUFFER (priv->text_buffer), &position, g_strdup (tny_mime_part_get_content_id (image_part)), pixbuf);
1493 priv->attachments = g_list_prepend (priv->attachments, image_part);
1494 modest_attachments_view_add_attachment (MODEST_ATTACHMENTS_VIEW (priv->attachments_view),
1496 gtk_text_buffer_set_modified (priv->text_buffer, TRUE);
1497 gtk_widget_set_no_show_all (priv->attachments_caption, FALSE);
1498 gtk_widget_show_all (priv->attachments_caption);
1499 } else if (image_file_id == -1) {
1500 close (image_file_id);
1509 modest_msg_edit_window_attach_file (ModestMsgEditWindow *window)
1512 ModestMsgEditWindowPrivate *priv;
1513 GtkWidget *dialog = NULL;
1515 GSList *uris = NULL;
1518 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1520 dialog = hildon_file_chooser_dialog_new (GTK_WINDOW (window), GTK_FILE_CHOOSER_ACTION_OPEN);
1521 gtk_file_chooser_set_select_multiple (GTK_FILE_CHOOSER (dialog), TRUE);
1523 response = gtk_dialog_run (GTK_DIALOG (dialog));
1525 case GTK_RESPONSE_OK:
1526 uris = gtk_file_chooser_get_uris (GTK_FILE_CHOOSER (dialog));
1531 gtk_widget_destroy (dialog);
1533 for (uri_node = uris; uri_node != NULL; uri_node = g_slist_next (uri_node)) {
1535 GnomeVFSHandle *handle = NULL;
1536 GnomeVFSResult result;
1538 uri = (const gchar *) uri_node->data;
1539 result = gnome_vfs_open (&handle, uri, GNOME_VFS_OPEN_READ);
1540 if (result == GNOME_VFS_OK) {
1541 TnyMimePart *mime_part;
1543 const gchar *mime_type = NULL;
1547 GnomeVFSFileInfo info;
1549 filename = g_filename_from_uri (uri, NULL, NULL);
1551 if (gnome_vfs_get_file_info_from_handle (handle, &info, GNOME_VFS_FILE_INFO_GET_MIME_TYPE) == GNOME_VFS_OK)
1552 mime_type = gnome_vfs_file_info_get_mime_type (&info);
1553 mime_part = tny_platform_factory_new_mime_part
1554 (modest_runtime_get_platform_factory ());
1555 stream = TNY_STREAM (tny_vfs_stream_new (handle));
1557 tny_mime_part_construct_from_stream (mime_part, stream, mime_type);
1559 content_id = g_strdup_printf ("%d", priv->last_cid);
1560 tny_mime_part_set_content_id (mime_part, content_id);
1561 g_free (content_id);
1564 basename = g_path_get_basename (filename);
1565 tny_mime_part_set_filename (mime_part, basename);
1568 priv->attachments = g_list_prepend (priv->attachments, mime_part);
1569 modest_attachments_view_add_attachment (MODEST_ATTACHMENTS_VIEW (priv->attachments_view),
1571 gtk_widget_set_no_show_all (priv->attachments_caption, FALSE);
1572 gtk_widget_show_all (priv->attachments_caption);
1573 gtk_text_buffer_set_modified (priv->text_buffer, TRUE);
1578 g_slist_foreach (uris, (GFunc) g_free, NULL);
1579 g_slist_free (uris);
1583 modest_msg_edit_window_attach_file_noninteractive (
1584 ModestMsgEditWindow *window,
1585 const gchar *file_uri)
1588 ModestMsgEditWindowPrivate *priv;
1590 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1595 /* TODO: We should probably try to use only the URI,
1596 * instead of using a filename.
1598 gchar* filename = g_filename_from_uri (file_uri, NULL, NULL);
1600 g_warning("%s: g_filename_from_uri(%s) failed.\n", __FUNCTION__, file_uri);
1603 file_id = g_open (filename, O_RDONLY, 0);
1604 if (file_id != -1) {
1605 TnyMimePart *mime_part;
1607 const gchar *mime_type;
1611 mime_type = gnome_vfs_get_file_mime_type_fast (filename, NULL);
1612 mime_part = tny_platform_factory_new_mime_part
1613 (modest_runtime_get_platform_factory ());
1614 stream = TNY_STREAM (tny_fs_stream_new (file_id));
1616 tny_mime_part_construct_from_stream (mime_part, stream, mime_type);
1618 content_id = g_strdup_printf ("%d", priv->last_cid);
1619 tny_mime_part_set_content_id (mime_part, content_id);
1620 g_free (content_id);
1623 basename = g_path_get_basename (filename);
1624 tny_mime_part_set_filename (mime_part, basename);
1627 priv->attachments = g_list_prepend (priv->attachments, mime_part);
1628 modest_attachments_view_add_attachment (MODEST_ATTACHMENTS_VIEW (priv->attachments_view),
1630 gtk_widget_set_no_show_all (priv->attachments_caption, FALSE);
1631 gtk_widget_show_all (priv->attachments_caption);
1632 } else if (file_id == -1) {
1634 g_warning("file to be attached does not exist: %s", filename);
1642 modest_msg_edit_window_remove_attachments (ModestMsgEditWindow *window,
1645 ModestMsgEditWindowPrivate *priv;
1646 gboolean clean_list = FALSE;
1648 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1649 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1651 if (att_list == NULL) {
1652 att_list = modest_attachments_view_get_selection (MODEST_ATTACHMENTS_VIEW (priv->attachments_view));
1656 if (att_list == NULL) {
1657 hildon_banner_show_information (NULL, NULL, _("TODO: no attachments selected to remove"));
1659 GtkWidget *confirmation_dialog = NULL;
1660 gboolean dialog_response;
1662 gchar *message = NULL;
1663 const gchar *filename = NULL;
1665 if (att_list->next == NULL) {
1666 filename = tny_mime_part_get_filename (TNY_MIME_PART (att_list->data));
1670 message = g_strdup_printf (ngettext("emev_nc_delete_attachment", "emev_nc_delete_attachments",
1671 att_list->next == NULL), filename);
1672 confirmation_dialog = hildon_note_new_confirmation (GTK_WINDOW (window), message);
1674 dialog_response = (gtk_dialog_run (GTK_DIALOG (confirmation_dialog))==GTK_RESPONSE_OK);
1675 gtk_widget_destroy (confirmation_dialog);
1676 if (!dialog_response) {
1678 g_list_free (att_list);
1681 hildon_banner_show_information (NULL, NULL, _("mcen_ib_removing_attachment"));
1683 for (node = att_list; node != NULL; node = g_list_next (node)) {
1684 TnyMimePart *mime_part = (TnyMimePart *) node->data;
1685 const gchar *att_id;
1686 priv->attachments = g_list_remove (priv->attachments, mime_part);
1688 modest_attachments_view_remove_attachment (MODEST_ATTACHMENTS_VIEW (priv->attachments_view),
1690 if (priv->attachments == NULL)
1691 gtk_widget_hide (priv->attachments_caption);
1692 att_id = tny_mime_part_get_content_id (mime_part);
1694 text_buffer_delete_images_by_id (gtk_text_view_get_buffer (GTK_TEXT_VIEW (priv->msg_body)),
1696 g_object_unref (mime_part);
1697 gtk_text_buffer_set_modified (priv->text_buffer, TRUE);
1702 g_list_free (att_list);
1706 modest_msg_edit_window_color_button_change (ModestMsgEditWindow *window,
1709 ModestMsgEditWindowPrivate *priv;
1710 GdkColor *new_color;
1711 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1713 #ifdef MODEST_HILDON_VERSION_0
1714 new_color = hildon_color_button_get_color (HILDON_COLOR_BUTTON (priv->font_color_button));
1717 hildon_color_button_get_color (HILDON_COLOR_BUTTON(priv->font_color_button), &col);
1719 #endif /*MODEST_HILDON_VERSION_0*/
1721 wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_FORECOLOR, (gpointer) new_color);
1723 gtk_window_set_focus (GTK_WINDOW (window), priv->msg_body);
1728 modest_msg_edit_window_size_change (GtkCheckMenuItem *menu_item,
1731 ModestMsgEditWindowPrivate *priv;
1732 gint new_size_index;
1733 ModestMsgEditWindow *window;
1736 window = MODEST_MSG_EDIT_WINDOW (userdata);
1737 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1738 gtk_widget_grab_focus (GTK_WIDGET (priv->msg_body));
1740 if (gtk_check_menu_item_get_active (menu_item)) {
1742 WPTextBufferFormat format;
1744 memset (&format, 0, sizeof (format));
1745 wp_text_buffer_get_current_state (WP_TEXT_BUFFER (priv->text_buffer), &format);
1747 label = gtk_bin_get_child (GTK_BIN (menu_item));
1749 new_size_index = atoi (gtk_label_get_text (GTK_LABEL (label)));
1750 format.cs.font_size = TRUE;
1751 format.cs.text_position = TRUE;
1752 format.cs.font = TRUE;
1753 format.font_size = wp_get_font_size_index (new_size_index, DEFAULT_FONT_SIZE);
1754 wp_text_buffer_set_format (WP_TEXT_BUFFER (priv->text_buffer), &format);
1756 /* if (!wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_FONT_SIZE, */
1757 /* (gpointer) wp_get_font_size_index (new_size_index, 12))) */
1758 /* wp_text_view_reset_and_show_im (WP_TEXT_VIEW (priv->msg_body)); */
1760 text_buffer_refresh_attributes (WP_TEXT_BUFFER (priv->text_buffer), MODEST_MSG_EDIT_WINDOW (window));
1761 markup = g_strconcat ("<span font_family='Serif'>", gtk_label_get_text (GTK_LABEL (label)), "</span>", NULL);
1762 gtk_label_set_markup (GTK_LABEL (priv->size_tool_button_label), markup);
1768 modest_msg_edit_window_font_change (GtkCheckMenuItem *menu_item,
1771 ModestMsgEditWindowPrivate *priv;
1772 gint new_font_index;
1773 ModestMsgEditWindow *window;
1776 window = MODEST_MSG_EDIT_WINDOW (userdata);
1777 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1778 gtk_widget_grab_focus (GTK_WIDGET (priv->msg_body));
1780 if (gtk_check_menu_item_get_active (menu_item)) {
1783 label = gtk_bin_get_child (GTK_BIN (menu_item));
1785 new_font_index = wp_get_font_index (gtk_label_get_text (GTK_LABEL (label)), DEFAULT_FONT);
1787 if (!wp_text_buffer_set_attribute (WP_TEXT_BUFFER (priv->text_buffer), WPT_FONT,
1788 (gpointer) new_font_index))
1789 wp_text_view_reset_and_show_im (WP_TEXT_VIEW (priv->msg_body));
1791 text_buffer_refresh_attributes (WP_TEXT_BUFFER (priv->text_buffer), MODEST_MSG_EDIT_WINDOW (window));
1792 markup = g_strconcat ("<span font_family='",gtk_label_get_text (GTK_LABEL (label)),"'>Tt</span>", NULL);
1793 gtk_label_set_markup (GTK_LABEL (priv->font_tool_button_label), markup);
1799 modest_msg_edit_window_set_zoom (ModestWindow *window,
1802 ModestMsgEditWindowPrivate *priv;
1803 ModestWindowPrivate *parent_priv;
1804 GtkRadioAction *zoom_radio_action;
1806 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1808 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1809 parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
1810 priv->zoom_level = zoom;
1811 wp_text_buffer_set_font_scaling_factor (WP_TEXT_BUFFER (priv->text_buffer), zoom);
1813 /* Zoom level menu options should be updated with the current zoom level */
1814 parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
1815 zoom_radio_action = GTK_RADIO_ACTION (gtk_ui_manager_get_action (parent_priv->ui_manager,
1816 "/MenuBar/ViewMenu/ZoomMenu/Zoom50Menu"));
1817 gtk_radio_action_set_current_value (zoom_radio_action, (gint) (zoom*100.0+0.1));
1821 modest_msg_edit_window_get_zoom (ModestWindow *window)
1823 ModestMsgEditWindowPrivate *priv;
1825 g_return_val_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window), 1.0);
1827 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1828 return priv->zoom_level;
1832 zoom_allowed (ModestMsgEditWindow *window)
1836 focus = gtk_window_get_focus (GTK_WINDOW (window));
1837 return (focus != NULL && WP_IS_TEXT_VIEW (focus));
1841 modest_msg_edit_window_zoom_plus (ModestWindow *window)
1843 ModestWindowPrivate *parent_priv;
1844 GtkRadioAction *zoom_radio_action;
1845 GSList *group, *node;
1847 /* First we check if the text view is focused. If not, zooming is not allowed */
1848 if (!zoom_allowed (MODEST_MSG_EDIT_WINDOW (window))) {
1849 hildon_banner_show_information (NULL, NULL, dgettext("hildon-common-strings", "ckct_ib_cannot_zoom_here"));
1853 parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
1854 zoom_radio_action = GTK_RADIO_ACTION (gtk_ui_manager_get_action (parent_priv->ui_manager,
1855 "/MenuBar/ViewMenu/ZoomMenu/Zoom50Menu"));
1857 group = gtk_radio_action_get_group (zoom_radio_action);
1859 if (gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (group->data))) {
1860 hildon_banner_show_information (NULL, NULL, dgettext("hildon-common-strings", "ckct_ib_max_zoom_level_reached"));
1864 for (node = group; node != NULL; node = g_slist_next (node)) {
1865 if ((node->next != NULL) && gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (node->next->data))) {
1866 gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (node->data), TRUE);
1874 modest_msg_edit_window_zoom_minus (ModestWindow *window)
1876 ModestWindowPrivate *parent_priv;
1877 GtkRadioAction *zoom_radio_action;
1878 GSList *group, *node;
1880 /* First we check if the text view is focused. If not, zooming is not allowed */
1881 if (!zoom_allowed (MODEST_MSG_EDIT_WINDOW (window))) {
1882 hildon_banner_show_information (NULL, NULL, dgettext("hildon-common-strings", "ckct_ib_cannot_zoom_here"));
1886 parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
1887 zoom_radio_action = GTK_RADIO_ACTION (gtk_ui_manager_get_action (parent_priv->ui_manager,
1888 "/MenuBar/ViewMenu/ZoomMenu/Zoom50Menu"));
1890 group = gtk_radio_action_get_group (zoom_radio_action);
1892 for (node = group; node != NULL; node = g_slist_next (node)) {
1893 if (gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (node->data))) {
1894 if (node->next != NULL) {
1895 gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (node->next->data), TRUE);
1898 hildon_banner_show_information (NULL, NULL, dgettext("hildon-common-strings", "ckct_ib_min_zoom_level_reached"));
1906 modest_msg_edit_window_window_state_event (GtkWidget *widget, GdkEventWindowState *event, gpointer userdata)
1908 if (event->changed_mask & GDK_WINDOW_STATE_FULLSCREEN) {
1909 ModestWindowPrivate *parent_priv;
1910 ModestWindowMgr *mgr;
1911 gboolean is_fullscreen;
1912 GtkAction *fs_toggle_action;
1915 mgr = modest_runtime_get_window_mgr ();
1916 is_fullscreen = (modest_window_mgr_get_fullscreen_mode (mgr))?1:0;
1918 parent_priv = MODEST_WINDOW_GET_PRIVATE (widget);
1920 fs_toggle_action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/ViewMenu/ViewToggleFullscreenMenu");
1921 active = (gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (fs_toggle_action)))?1:0;
1922 if (is_fullscreen != active)
1923 gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (fs_toggle_action), is_fullscreen);
1931 modest_msg_edit_window_toggle_fullscreen (ModestMsgEditWindow *window)
1933 ModestWindowPrivate *parent_priv;
1934 GtkAction *fs_toggle_action;
1937 parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
1939 fs_toggle_action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/ViewMenu/ViewToggleFullscreenMenu");
1940 active = gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (fs_toggle_action));
1941 gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (fs_toggle_action), !active);
1945 modest_msg_edit_window_show_cc (ModestMsgEditWindow *window,
1948 ModestMsgEditWindowPrivate *priv = NULL;
1949 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1951 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1952 gtk_widget_set_no_show_all (priv->cc_caption, TRUE);
1954 gtk_widget_show (priv->cc_caption);
1956 gtk_widget_hide (priv->cc_caption);
1957 modest_conf_set_bool(modest_runtime_get_conf(), MODEST_CONF_SHOW_CC, show, NULL);
1961 modest_msg_edit_window_show_bcc (ModestMsgEditWindow *window,
1964 ModestMsgEditWindowPrivate *priv = NULL;
1965 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1967 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1968 gtk_widget_set_no_show_all (priv->bcc_caption, TRUE);
1970 gtk_widget_show (priv->bcc_caption);
1972 gtk_widget_hide (priv->bcc_caption);
1973 modest_conf_set_bool(modest_runtime_get_conf(), MODEST_CONF_SHOW_BCC, show, NULL);
1977 modest_msg_edit_window_open_addressbook (ModestMsgEditWindow *window,
1978 ModestRecptEditor *editor)
1980 ModestMsgEditWindowPrivate *priv;
1982 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
1983 g_return_if_fail ((editor == NULL) || (MODEST_IS_RECPT_EDITOR (editor)));
1984 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
1986 if (editor == NULL) {
1987 GtkWidget *view_focus;
1988 view_focus = gtk_window_get_focus (GTK_WINDOW (window));
1990 /* This code should be kept in sync with ModestRecptEditor. The
1991 textview inside the recpt editor is the one that really gets the
1992 focus. As it's inside a scrolled window, and this one inside the
1993 hbox recpt editor inherits from, we'll need to go up in the
1994 hierarchy to know if the text view is part of the recpt editor
1995 or if it's a different text entry */
1997 if (gtk_widget_get_parent (view_focus)) {
1998 GtkWidget *first_parent;
2000 first_parent = gtk_widget_get_parent (view_focus);
2001 if (gtk_widget_get_parent (first_parent) &&
2002 MODEST_IS_RECPT_EDITOR (gtk_widget_get_parent (first_parent))) {
2003 editor = MODEST_RECPT_EDITOR (gtk_widget_get_parent (first_parent));
2008 editor = MODEST_RECPT_EDITOR (priv->to_field);
2012 modest_address_book_select_addresses (editor);
2017 modest_msg_edit_window_select_contacts (ModestMsgEditWindow *window)
2019 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2021 modest_msg_edit_window_open_addressbook (window, NULL);
2025 modest_msg_edit_window_show_toolbar (ModestWindow *self,
2026 gboolean show_toolbar)
2028 ModestWindowPrivate *parent_priv;
2030 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (self));
2031 parent_priv = MODEST_WINDOW_GET_PRIVATE(self);
2033 /* FIXME: we can not just use the code of
2034 modest_msg_edit_window_setup_toolbar because it has a
2035 mixture of both initialization and creation code. */
2038 gtk_widget_show (GTK_WIDGET (parent_priv->toolbar));
2040 gtk_widget_hide (GTK_WIDGET (parent_priv->toolbar));
2044 modest_msg_edit_window_set_priority_flags (ModestMsgEditWindow *window,
2045 TnyHeaderFlags priority_flags)
2047 ModestMsgEditWindowPrivate *priv;
2048 ModestWindowPrivate *parent_priv;
2050 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2052 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2053 parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
2054 priority_flags = priority_flags & (TNY_HEADER_FLAG_PRIORITY);
2056 if (priv->priority_flags != priority_flags) {
2057 GtkAction *priority_action = NULL;
2059 priv->priority_flags = priority_flags;
2061 switch (priority_flags) {
2062 case TNY_HEADER_FLAG_HIGH_PRIORITY:
2063 gtk_image_set_from_icon_name (GTK_IMAGE (priv->priority_icon), "qgn_list_messaging_high", GTK_ICON_SIZE_MENU);
2064 gtk_widget_show (priv->priority_icon);
2065 priority_action = gtk_ui_manager_get_action (parent_priv->ui_manager,
2066 "/MenuBar/ToolsMenu/MessagePriorityMenu/MessagePriorityHighMenu");
2068 case TNY_HEADER_FLAG_LOW_PRIORITY:
2069 gtk_image_set_from_icon_name (GTK_IMAGE (priv->priority_icon), "qgn_list_messaging_low", GTK_ICON_SIZE_MENU);
2070 gtk_widget_show (priv->priority_icon);
2071 priority_action = gtk_ui_manager_get_action (parent_priv->ui_manager,
2072 "/MenuBar/ToolsMenu/MessagePriorityMenu/MessagePriorityLowMenu");
2075 gtk_widget_hide (priv->priority_icon);
2076 priority_action = gtk_ui_manager_get_action (parent_priv->ui_manager,
2077 "/MenuBar/ToolsMenu/MessagePriorityMenu/MessagePriorityNormalMenu");
2080 gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (priority_action), TRUE);
2081 gtk_text_buffer_set_modified (priv->text_buffer, TRUE);
2086 modest_msg_edit_window_set_file_format (ModestMsgEditWindow *window,
2089 ModestMsgEditWindowPrivate *priv;
2090 gint current_format;
2092 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2094 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2096 current_format = wp_text_buffer_is_rich_text (WP_TEXT_BUFFER (priv->text_buffer))
2097 ? MODEST_FILE_FORMAT_FORMATTED_TEXT : MODEST_FILE_FORMAT_PLAIN_TEXT;
2099 if (current_format != file_format) {
2100 switch (file_format) {
2101 case MODEST_FILE_FORMAT_FORMATTED_TEXT:
2102 wp_text_buffer_enable_rich_text (WP_TEXT_BUFFER (priv->text_buffer), TRUE);
2104 case MODEST_FILE_FORMAT_PLAIN_TEXT:
2108 dialog = hildon_note_new_confirmation (NULL, _("emev_nc_formatting_lost"));
2109 response = gtk_dialog_run (GTK_DIALOG (dialog));
2110 gtk_widget_destroy (dialog);
2111 if (response == GTK_RESPONSE_OK)
2112 wp_text_buffer_enable_rich_text (WP_TEXT_BUFFER (priv->text_buffer), FALSE);
2116 update_dimmed (window);
2121 modest_msg_edit_window_select_font (ModestMsgEditWindow *window)
2124 ModestMsgEditWindowPrivate *priv;
2125 WPTextBufferFormat oldfmt, fmt;
2126 gint old_position = 0;
2130 GdkColor *color = NULL;
2131 gboolean bold, bold_set, italic, italic_set;
2132 gboolean underline, underline_set;
2133 gboolean strikethrough, strikethrough_set;
2134 gboolean position_set;
2135 gboolean font_size_set, font_set, color_set;
2138 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2139 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2141 dialog = hildon_font_selection_dialog_new (GTK_WINDOW (window), NULL);
2143 /* First we get the currently selected font information */
2144 wp_text_buffer_get_attributes (WP_TEXT_BUFFER (priv->text_buffer), &oldfmt, TRUE);
2145 g_object_set (G_OBJECT (dialog), "font-scaling", priv->zoom_level, NULL);
2147 switch (oldfmt.text_position) {
2148 case TEXT_POSITION_NORMAL:
2151 case TEXT_POSITION_SUPERSCRIPT:
2159 g_object_set (G_OBJECT (dialog),
2160 "bold", oldfmt.bold != FALSE,
2161 "bold-set", !oldfmt.cs.bold,
2162 "underline", oldfmt.underline != FALSE,
2163 "underline-set", !oldfmt.cs.underline,
2164 "italic", oldfmt.italic != FALSE,
2165 "italic-set", !oldfmt.cs.italic,
2166 "strikethrough", oldfmt.strikethrough != FALSE,
2167 "strikethrough-set", !oldfmt.cs.strikethrough,
2168 "color", &oldfmt.color,
2169 "color-set", !oldfmt.cs.color,
2170 "size", wp_font_size[oldfmt.font_size],
2171 "size-set", !oldfmt.cs.font_size,
2172 "position", old_position,
2173 "position-set", !oldfmt.cs.text_position,
2174 "family", wp_get_font_name (oldfmt.font),
2175 "family-set", !oldfmt.cs.font,
2178 gtk_widget_show_all (dialog);
2179 response = gtk_dialog_run (GTK_DIALOG (dialog));
2180 if (response == GTK_RESPONSE_OK) {
2182 g_object_get( dialog,
2184 "bold-set", &bold_set,
2185 "underline", &underline,
2186 "underline-set", &underline_set,
2188 "italic-set", &italic_set,
2189 "strikethrough", &strikethrough,
2190 "strikethrough-set", &strikethrough_set,
2192 "color-set", &color_set,
2194 "size-set", &font_size_set,
2195 "family", &font_name,
2196 "family-set", &font_set,
2197 "position", &position,
2198 "position-set", &position_set,
2203 if (response == GTK_RESPONSE_OK) {
2204 memset(&fmt, 0, sizeof(fmt));
2210 fmt.italic = italic;
2211 fmt.cs.italic = TRUE;
2213 if (underline_set) {
2214 fmt.underline = underline;
2215 fmt.cs.underline = TRUE;
2217 if (strikethrough_set) {
2218 fmt.strikethrough = strikethrough;
2219 fmt.cs.strikethrough = TRUE;
2224 ? TEXT_POSITION_NORMAL
2225 : ( ( position == 1 )
2226 ? TEXT_POSITION_SUPERSCRIPT
2227 : TEXT_POSITION_SUBSCRIPT );
2228 fmt.cs.text_position = TRUE;
2232 fmt.cs.color = TRUE;
2235 fmt.font = wp_get_font_index(font_name,
2240 if (font_size_set) {
2241 fmt.font_size = wp_get_font_size_index(
2242 font_size, DEFAULT_FONT_SIZE);
2243 fmt.cs.font_size = TRUE;
2245 wp_text_buffer_set_format(WP_TEXT_BUFFER(priv->text_buffer), &fmt);
2247 gtk_widget_destroy (dialog);
2249 gtk_widget_grab_focus(GTK_WIDGET(priv->msg_body));
2253 modest_msg_edit_window_undo (ModestMsgEditWindow *window)
2255 ModestMsgEditWindowPrivate *priv;
2257 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2258 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2260 wp_text_buffer_undo (WP_TEXT_BUFFER (priv->text_buffer));
2262 update_dimmed (window);
2267 update_dimmed (ModestMsgEditWindow *window)
2269 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2270 ModestWindowPrivate *parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
2274 gboolean editor_focused;
2276 rich_text = wp_text_buffer_is_rich_text (WP_TEXT_BUFFER (priv->text_buffer));
2277 editor_focused = gtk_widget_is_focus (priv->msg_body);
2279 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/FormatMenu/SelectFontMenu");
2280 gtk_action_set_sensitive (action, rich_text && editor_focused);
2281 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/FormatMenu/BulletedListMenu");
2282 gtk_action_set_sensitive (action, rich_text && editor_focused);
2283 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/FormatMenu/AlignmentMenu");
2284 gtk_action_set_sensitive (action, rich_text && editor_focused);
2285 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/FormatMenu/AlignmentMenu/AlignmentLeftMenu");
2286 gtk_action_set_sensitive (action, rich_text && editor_focused);
2287 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/FormatMenu/AlignmentMenu/AlignmentCenterMenu");
2288 gtk_action_set_sensitive (action, rich_text && editor_focused);
2289 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/FormatMenu/AlignmentMenu/AlignmentRightMenu");
2290 gtk_action_set_sensitive (action, rich_text && editor_focused);
2291 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/AttachmentsMenu/InsertImageMenu");
2292 gtk_action_set_sensitive (action, rich_text && editor_focused);
2293 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/ToolBar/ActionsBold");
2294 gtk_action_set_sensitive (action, rich_text && editor_focused);
2295 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/ToolBar/ActionsItalics");
2296 gtk_action_set_sensitive (action, rich_text && editor_focused);
2297 widget = priv->font_color_button;
2298 gtk_widget_set_sensitive (widget, rich_text && editor_focused);
2299 widget = priv->font_size_toolitem;
2300 gtk_widget_set_sensitive (widget, rich_text && editor_focused);
2301 widget = priv->font_face_toolitem;
2302 gtk_widget_set_sensitive (widget, rich_text && editor_focused);
2306 setup_insensitive_handlers (ModestMsgEditWindow *window)
2308 ModestWindowPrivate *parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
2309 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2312 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar/ToolbarSend");
2313 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (send_insensitive_press), window);
2314 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/EmailMenu/SendMenu");
2315 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (send_insensitive_press), window);
2317 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/FormatMenu/SelectFontMenu");
2318 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2319 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/FormatMenu/BulletedListMenu");
2320 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2321 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/FormatMenu/AlignmentMenu");
2322 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2323 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/FormatMenu/AlignmentMenu/AlignmentLeftMenu");
2324 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2325 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/FormatMenu/AlignmentMenu/AlignmentCenterMenu");
2326 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2327 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/FormatMenu/AlignmentMenu/AlignmentRightMenu");
2328 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2329 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/AttachmentsMenu/InsertImageMenu");
2330 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2331 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar/ActionsBold");
2332 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2333 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/ToolBar/ActionsItalics");
2334 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2335 widget = priv->font_color_button;
2336 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2337 widget = priv->font_size_toolitem;
2338 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2339 widget = priv->font_face_toolitem;
2340 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (style_insensitive_press), window);
2342 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/AttachmentsMenu/RemoveAttachmentsMenu");
2343 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (remove_attachment_insensitive_press), window);
2344 widget = gtk_ui_manager_get_widget (parent_priv->ui_manager, "/MenuBar/ViewMenu/ZoomMenu");
2345 g_signal_connect (G_OBJECT (widget), "insensitive-press", G_CALLBACK (zoom_insensitive_press), window);
2349 text_buffer_can_undo (GtkTextBuffer *buffer, gboolean can_undo, ModestMsgEditWindow *window)
2351 ModestWindowPrivate *parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
2354 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/EditMenu/UndoMenu");
2355 gtk_action_set_sensitive (action, can_undo);
2359 text_buffer_delete_images_by_id (GtkTextBuffer *buffer, const gchar * image_id)
2362 GtkTextIter match_start, match_end;
2364 if (image_id == NULL)
2367 gtk_text_buffer_get_start_iter (buffer, &iter);
2369 while (gtk_text_iter_forward_search (&iter, "\xef\xbf\xbc", 0, &match_start, &match_end, NULL)) {
2370 GSList *tags = gtk_text_iter_get_tags (&match_start);
2372 for (node = tags; node != NULL; node = g_slist_next (node)) {
2373 GtkTextTag *tag = (GtkTextTag *) node->data;
2374 if (g_object_get_data (G_OBJECT (tag), "image-set") != NULL) {
2375 gchar *cur_image_id = g_object_get_data (G_OBJECT (tag), "image-index");
2376 if ((cur_image_id != NULL) && (strcmp (image_id, cur_image_id)==0)) {
2378 offset = gtk_text_iter_get_offset (&match_start);
2379 gtk_text_buffer_delete (buffer, &match_start, &match_end);
2380 gtk_text_buffer_get_iter_at_offset (buffer, &iter, offset);
2384 gtk_text_iter_forward_char (&iter);
2389 text_buffer_delete_range (GtkTextBuffer *buffer, GtkTextIter *start, GtkTextIter *end, gpointer userdata)
2391 ModestMsgEditWindow *window = (ModestMsgEditWindow *) userdata;
2392 GtkTextIter real_start, real_end;
2393 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2395 if (gtk_text_iter_compare (start, end) > 0) {
2399 real_start = *start;
2403 GSList *tags = gtk_text_iter_get_tags (&real_start);
2405 for (node = tags; node != NULL; node = g_slist_next (node)) {
2406 GtkTextTag *tag = (GtkTextTag *) node->data;
2407 if (g_object_get_data (G_OBJECT (tag), "image-set") != NULL) {
2408 gchar *image_id = g_object_get_data (G_OBJECT (tag), "image-index");
2410 modest_attachments_view_remove_attachment_by_id (MODEST_ATTACHMENTS_VIEW (priv->attachments_view),
2412 gtk_text_buffer_remove_tag (buffer, tag, start, end);
2415 } while (gtk_text_iter_forward_char (&real_start)&&
2416 (gtk_text_iter_compare (&real_start, &real_end)<=0));
2420 msg_body_focus (GtkWidget *focus,
2421 GdkEventFocus *event,
2425 update_dimmed (MODEST_MSG_EDIT_WINDOW (userdata));
2430 recpt_field_changed (GtkTextBuffer *buffer,
2431 ModestMsgEditWindow *editor)
2433 ModestWindowPrivate *parent_priv = MODEST_WINDOW_GET_PRIVATE (editor);
2434 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (editor);
2435 GtkTextBuffer *to_buffer, *cc_buffer, *bcc_buffer;
2436 gboolean dim = FALSE;
2439 to_buffer = modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->to_field));
2440 cc_buffer = modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->cc_field));
2441 bcc_buffer = modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->bcc_field));
2443 dim = ((gtk_text_buffer_get_char_count (to_buffer) +
2444 gtk_text_buffer_get_char_count (cc_buffer) +
2445 gtk_text_buffer_get_char_count (bcc_buffer)) == 0);
2447 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/ToolBar/ToolbarSend");
2448 gtk_action_set_sensitive (action, !dim);
2449 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/EmailMenu/SendMenu");
2450 gtk_action_set_sensitive (action, !dim);
2454 send_insensitive_press (GtkWidget *widget, ModestMsgEditWindow *editor)
2456 hildon_banner_show_information (NULL, NULL, _("mcen_ib_add_recipients_first"));
2460 zoom_insensitive_press (GtkWidget *widget, ModestMsgEditWindow *editor)
2462 hildon_banner_show_information (NULL, NULL, dgettext("hildon-common-strings", "ckct_ib_cannot_zoom_here"));
2466 remove_attachment_insensitive_press (GtkWidget *widget, ModestMsgEditWindow *editor)
2468 ModestWindowPrivate *parent_priv;
2469 ModestMsgEditWindowPrivate *priv;
2470 GList *selected_attachments = NULL;
2471 gint n_att_selected = 0;
2473 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (editor);
2474 parent_priv = MODEST_WINDOW_GET_PRIVATE (editor);
2476 selected_attachments = modest_attachments_view_get_selection (MODEST_ATTACHMENTS_VIEW (priv->attachments_view));
2477 n_att_selected = g_list_length (selected_attachments);
2478 g_list_free (selected_attachments);
2480 if (n_att_selected > 1)
2481 hildon_banner_show_information (NULL, NULL, _("mcen_ib_unable_to_display_more"));
2482 else if (n_att_selected == 0)
2483 hildon_banner_show_information (NULL, NULL, _("TODO: select one attachment"));
2488 style_insensitive_press (GtkWidget *widget, ModestMsgEditWindow *editor)
2490 gboolean rich_text, editor_focused;
2492 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (editor);
2493 rich_text = wp_text_buffer_is_rich_text (WP_TEXT_BUFFER (priv->text_buffer));
2494 editor_focused = gtk_widget_is_focus (priv->msg_body);
2497 hildon_banner_show_information (NULL, NULL, _("mcen_ib_item_unavailable_plaintext"));
2498 else if (!editor_focused)
2499 hildon_banner_show_information (NULL, NULL, _("mcen_ib_move_cursor_to_message"));
2503 reset_modified (ModestMsgEditWindow *editor)
2505 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (editor);
2506 GtkTextBuffer *buffer;
2508 buffer = modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR(priv->to_field));
2509 gtk_text_buffer_set_modified (buffer, FALSE);
2510 buffer = modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR(priv->cc_field));
2511 gtk_text_buffer_set_modified (buffer, FALSE);
2512 buffer = modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR(priv->bcc_field));
2513 gtk_text_buffer_set_modified (buffer, FALSE);
2514 gtk_text_buffer_set_modified (priv->text_buffer, FALSE);
2518 is_modified (ModestMsgEditWindow *editor)
2520 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (editor);
2521 GtkTextBuffer *buffer;
2523 buffer = modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR(priv->to_field));
2524 if (gtk_text_buffer_get_modified (buffer))
2526 buffer = modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR(priv->cc_field));
2527 if (gtk_text_buffer_get_modified (buffer))
2529 buffer = modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR(priv->bcc_field));
2530 if (gtk_text_buffer_get_modified (buffer))
2532 if (gtk_text_buffer_get_modified (priv->text_buffer))
2539 modest_msg_edit_window_check_names (ModestMsgEditWindow *window)
2541 ModestMsgEditWindowPrivate *priv = NULL;
2543 g_return_val_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window), FALSE);
2544 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2546 /* check if there's no recipient added */
2547 if ((gtk_text_buffer_get_char_count (modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->to_field))) == 0) &&
2548 (gtk_text_buffer_get_char_count (modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->cc_field))) == 0) &&
2549 (gtk_text_buffer_get_char_count (modest_recpt_editor_get_buffer (MODEST_RECPT_EDITOR (priv->bcc_field))) == 0)) {
2550 /* no recipient contents, then select contacts */
2551 modest_msg_edit_window_open_addressbook (window, NULL);
2555 if (!modest_address_book_check_names (MODEST_RECPT_EDITOR (priv->to_field)))
2557 if (!modest_address_book_check_names (MODEST_RECPT_EDITOR (priv->cc_field)))
2559 if (!modest_address_book_check_names (MODEST_RECPT_EDITOR (priv->bcc_field)))
2562 modest_recpt_editor_grab_focus (MODEST_RECPT_EDITOR (priv->to_field));
2569 modest_msg_edit_window_add_attachment_clicked (GtkButton *button,
2570 ModestMsgEditWindow *window)
2572 modest_msg_edit_window_attach_file (window);
2576 modest_msg_edit_window_clipboard_owner_change (GtkClipboard *clipboard,
2578 ModestMsgEditWindow *window)
2580 ModestWindowPrivate *parent_priv;
2581 ModestMsgEditWindowPrivate *priv;
2585 GList *selected_attachments = NULL;
2586 gint n_att_selected = 0;
2588 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2589 parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
2590 selection = gtk_clipboard_wait_for_text (clipboard);
2591 focused = gtk_window_get_focus (GTK_WINDOW (window));
2593 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/EditMenu/CutMenu");
2594 gtk_action_set_sensitive (action, (selection != NULL) && (!MODEST_IS_ATTACHMENTS_VIEW (focused)));
2595 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/EditMenu/CopyMenu");
2596 gtk_action_set_sensitive (action, (selection != NULL) && (!MODEST_IS_ATTACHMENTS_VIEW (focused)));
2598 selected_attachments = modest_attachments_view_get_selection (MODEST_ATTACHMENTS_VIEW (priv->attachments_view));
2599 n_att_selected = g_list_length (selected_attachments);
2600 g_list_free (selected_attachments);
2602 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/AttachmentsMenu/RemoveAttachmentsMenu");
2603 gtk_action_set_sensitive (action, n_att_selected == 1);
2606 update_paste_dimming (window);
2610 update_window_title (ModestMsgEditWindow *window)
2612 ModestMsgEditWindowPrivate *priv = NULL;
2613 const gchar *subject;
2615 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2616 subject = gtk_entry_get_text (GTK_ENTRY (priv->subject_field));
2617 if (subject == NULL || subject[0] == '\0')
2618 subject = _("mail_va_new_email");
2620 gtk_window_set_title (GTK_WINDOW (window), subject);
2625 subject_field_changed (GtkEditable *editable,
2626 ModestMsgEditWindow *window)
2628 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2629 update_window_title (window);
2630 gtk_text_buffer_set_modified (priv->text_buffer, TRUE);
2634 modest_msg_edit_window_toggle_find_toolbar (ModestMsgEditWindow *window,
2637 ModestMsgEditWindowPrivate *priv = NULL;
2639 g_return_if_fail (MODEST_IS_MSG_EDIT_WINDOW (window));
2640 priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2642 gtk_widget_set_no_show_all (priv->find_toolbar, FALSE);
2644 gtk_widget_show_all (priv->find_toolbar);
2645 hildon_find_toolbar_highlight_entry (HILDON_FIND_TOOLBAR (priv->find_toolbar), TRUE);
2647 gtk_widget_hide_all (priv->find_toolbar);
2648 gtk_widget_grab_focus (priv->msg_body);
2654 modest_msg_edit_window_find_toolbar_search (GtkWidget *widget,
2655 ModestMsgEditWindow *window)
2657 gchar *current_search = NULL;
2658 ModestMsgEditWindowPrivate *priv = MODEST_MSG_EDIT_WINDOW_GET_PRIVATE (window);
2660 GtkTextIter selection_start, selection_end;
2661 GtkTextIter match_start, match_end;
2663 g_object_get (G_OBJECT (widget), "prefix", ¤t_search, NULL);
2664 if ((current_search == NULL) && (strcmp (current_search, "") == 0)) {
2665 g_free (current_search);
2669 gtk_text_buffer_get_selection_bounds (priv->text_buffer, &selection_start, &selection_end);
2670 result = gtk_text_iter_forward_search (&selection_end, current_search, GTK_TEXT_SEARCH_VISIBLE_ONLY, &match_start, &match_end, NULL);
2672 GtkTextIter buffer_start;
2673 gtk_text_buffer_get_start_iter (priv->text_buffer, &buffer_start);
2674 result = gtk_text_iter_forward_search (&buffer_start, current_search, GTK_TEXT_SEARCH_VISIBLE_ONLY, &match_start, &match_end, &selection_start);
2677 gtk_text_buffer_select_range (priv->text_buffer, &match_start, &match_end);
2678 gtk_text_view_scroll_to_iter (GTK_TEXT_VIEW (priv->msg_body), &match_start, 0.0, TRUE, 0.0, 0.0);
2680 /* TODO: warning about non succesful search */
2682 g_free (current_search);
2686 modest_msg_edit_window_find_toolbar_close (GtkWidget *widget,
2687 ModestMsgEditWindow *window)
2689 GtkToggleAction *toggle;
2690 ModestWindowPrivate *parent_priv;
2691 parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
2693 toggle = GTK_TOGGLE_ACTION (gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/ToolsMenu/FindInMessageMenu"));
2694 gtk_toggle_action_set_active (toggle, FALSE);
2699 update_paste_dimming (ModestMsgEditWindow *window)
2701 ModestWindowPrivate *parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
2702 GtkAction *action = NULL;
2703 GtkClipboard *clipboard = NULL;
2705 clipboard = gtk_clipboard_get (GDK_SELECTION_CLIPBOARD);
2707 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/EditMenu/PasteMenu");
2708 gtk_action_set_sensitive (action, gtk_clipboard_wait_is_text_available (clipboard));
2713 modest_msg_edit_window_system_clipboard_owner_change (GtkClipboard *clipboard,
2715 ModestMsgEditWindow *window)
2717 update_paste_dimming (window);
2721 update_select_all_dimming (ModestMsgEditWindow *window)
2724 gboolean dimmed = FALSE;
2726 ModestWindowPrivate *parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
2728 focused = gtk_window_get_focus (GTK_WINDOW (window));
2729 if (GTK_IS_ENTRY (focused)) {
2730 const gchar *current_text;
2731 current_text = gtk_entry_get_text (GTK_ENTRY (focused));
2732 dimmed = ((current_text == NULL) || (current_text[0] == '\0'));
2733 } else if (GTK_IS_TEXT_VIEW (focused)) {
2734 GtkTextBuffer *buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (focused));
2735 dimmed = (gtk_text_buffer_get_char_count (buffer) < 1);
2736 } else if (MODEST_IS_ATTACHMENTS_VIEW (focused)) {
2739 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/EditMenu/SelectAllMenu");
2740 gtk_action_set_sensitive (action, !dimmed);
2744 update_zoom_dimming (ModestMsgEditWindow *window)
2747 gboolean dimmed = FALSE;
2749 ModestWindowPrivate *parent_priv = MODEST_WINDOW_GET_PRIVATE (window);
2751 focused = gtk_window_get_focus (GTK_WINDOW (window));
2752 dimmed = ! WP_IS_TEXT_VIEW (focused);
2753 action = gtk_ui_manager_get_action (parent_priv->ui_manager, "/MenuBar/ViewMenu/ZoomMenu");
2754 gtk_action_set_sensitive (action, !dimmed);
2758 edit_menu_activated (GtkAction *action,
2761 ModestMsgEditWindow *window = MODEST_MSG_EDIT_WINDOW (userdata);
2763 update_select_all_dimming (window);
2766 view_menu_activated (GtkAction *action,
2769 ModestMsgEditWindow *window = MODEST_MSG_EDIT_WINDOW (userdata);
2771 update_zoom_dimming (window);