diff options
Diffstat (limited to 'composer')
-rw-r--r-- | composer/.cvsignore | 22 | ||||
-rw-r--r-- | composer/ChangeLog | 399 | ||||
-rw-r--r-- | composer/ChangeLog.pre-1-4 | 4037 | ||||
-rw-r--r-- | composer/Composer.idl | 4 | ||||
-rw-r--r-- | composer/Evolution-Composer.idl | 141 | ||||
-rw-r--r-- | composer/Makefile.am | 87 | ||||
-rw-r--r-- | composer/bad-icon.xpm | 53 | ||||
-rw-r--r-- | composer/e-msg-composer-attachment-bar.c | 850 | ||||
-rw-r--r-- | composer/e-msg-composer-attachment-bar.h | 77 | ||||
-rw-r--r-- | composer/e-msg-composer-attachment.c | 457 | ||||
-rw-r--r-- | composer/e-msg-composer-attachment.glade | 237 | ||||
-rw-r--r-- | composer/e-msg-composer-attachment.h | 77 | ||||
-rw-r--r-- | composer/e-msg-composer-hdrs.c | 1342 | ||||
-rw-r--r-- | composer/e-msg-composer-hdrs.h | 152 | ||||
-rw-r--r-- | composer/e-msg-composer-select-file.c | 136 | ||||
-rw-r--r-- | composer/e-msg-composer-select-file.h | 35 | ||||
-rw-r--r-- | composer/e-msg-composer.c | 5055 | ||||
-rw-r--r-- | composer/e-msg-composer.h | 226 | ||||
-rw-r--r-- | composer/evolution-composer.c | 397 | ||||
-rw-r--r-- | composer/evolution-composer.h | 75 | ||||
-rw-r--r-- | composer/listener.c | 275 | ||||
-rw-r--r-- | composer/listener.h | 51 |
22 files changed, 0 insertions, 14185 deletions
diff --git a/composer/.cvsignore b/composer/.cvsignore deleted file mode 100644 index 730f98b91f..0000000000 --- a/composer/.cvsignore +++ /dev/null @@ -1,22 +0,0 @@ -.deps -.libs -.pure -evolution-msg-composer -Makefile -Makefile.in -*.lo -*.la -Composer-stubs.c -Composer-skels.c -Composer-common.c -Composer.h -Editor-stubs.c -Editor-skels.c -Editor.h -Editor-common.c -Evolution-Addressbook-SelectNames-common.c -Evolution-Addressbook-SelectNames-skels.c -Evolution-Addressbook-SelectNames-stubs.c -Evolution-Addressbook-SelectNames.h -HTMLEditor*.[ch] -composer-marshal.[ch]
\ No newline at end of file diff --git a/composer/ChangeLog b/composer/ChangeLog deleted file mode 100644 index 7ba1e67a3a..0000000000 --- a/composer/ChangeLog +++ /dev/null @@ -1,399 +0,0 @@ -2003-12-04 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (create_headers): Unifdef out the post-to - code and fix it to use the new folder selection button. - (e_msg_composer_hdrs_set_post_to): Same. - (e_msg_composer_hdrs_get_post_to): Same. - -2003-12-03 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer-hdrs.c: Do not #include - <evolution-folder-selector-button.h>. - (e_msg_composer_hdrs_set_post_to): #if 0 out for now. - (e_msg_composer_hdrs_get_post_to): Likewise. - -2003-12-01 Rodney Dawes <dobey@ximian.com> - - * e-msg-composer-hdrs.h: Use BASE_VERSION for repo_ids and OAFIIDs - -2003-11-11 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (e_msg_composer_set_autosaved): new method to - wrap autosaved flag setting - (e_msg_composer_unset_autosaved): ditto - (e_msg_composer_is_autosaved): new method, says if composer was - autosaved only - (autosave_save_draft): unset changed so that we don't autosave all - the time when anything else than gtkhtml control changed - -2003-11-06 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (autosave_save_draft): call gtkhtml's saved - command to clean is-saved flag, set composer's autosaved flag - (do_exit): complain if last save was just autosave - (e_msg_composer_unset_changed): reset autosaved flag - (save): reset autosaved flag - - * e-msg-composer.h: added autosaved flag, it tells whether last - save was autosave or regular save, when changed flag is reset the - autosaved one is reset too - -2003-11-30 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer-hdrs.c (create_headers): #if 0 the "post to" - stuff for now (it requires the global_shell_client and the - evolution_folder_selector_button which we don't have anymore). - -2003-11-26 Chris Toshok <toshok@ximian.com> - - * e-msg-composer.c (build_message): switch from just checking - SMIME_SUPPORTED to checking both HAVE_NSS and SMIME_SUPPORTED. - -2003-11-26 JP Rosevear <jpr@ximian.com> - - * Makefile.am: turn on deprecated gtk widgets - -2003-11-03 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (build_message): changed to use ciphercontext - directly to sign the message, no multipart-signed usage. - (build_message): do the same for multipart/encryption for gpg encrypting. - -2003-11-03 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer-hdrs.h (SELECT_NAMES_OAFIID): Append "_2". - -2003-10-31 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (build_message): fix for e-account smime info - changes. Also enforce having a signing certificate set in - preferences before doing any signing. - (from_changed_cb): handle smime sign/encrypt default for account - (create_composer): force a from-changed when we start, to properly - setup signing options. - -2003-10-30 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c: Turn on SMIME_SUPPORTED. - (build_message): move some of the security code around, and fix - up smime code. - -2003-10-08 Chris Toshok <toshok@ximian.com> - - * evolution-composer.c (corba_recipientlist_to_destv): EDestination => - EABDestination, and e_destination => eab_destination. - (impl_Composer_set_headers): same. - - * e-msg-composer.c (update_auto_recipients): EDestination => - EABDestination, and e_destination => eab_destination. - (e_msg_composer_new_with_message): same. - (add_recipients): same. - (handle_mailto): same. - (e_msg_composer_set_headers): same. - (e_msg_composer_get_recipients): same. - (e_msg_composer_get_to): same. - (e_msg_composer_get_cc): same. - (e_msg_composer_get_bcc): same. - - * e-msg-composer.h: EDestination => EABDestination, and - e_destination => eab_destination. - - * e-msg-composer-hdrs.c (set_recipients_from_destv): EDestination - => EABDestination, and e_destination => eab_destination. - (e_msg_composer_hdrs_to_message_internal): same. - (e_msg_composer_hdrs_set_to): same. - (e_msg_composer_hdrs_set_cc): same. - (e_msg_composer_hdrs_set_bcc): same. - (e_msg_composer_hdrs_get_to): same. - (e_msg_composer_hdrs_get_cc): same. - (e_msg_composer_hdrs_get_bcc): same. - (e_msg_composer_hdrs_get_recipients): same. - - * e-msg-composer-hdrs.h: EDestination => EABDestination, and - e_destination => eab_destination. - -2003-09-26 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (save): Don't blindly claim that the file - exists and then ask the user if he/she would like to overwrite - it. First check that the file even exists, if not - then we've got - a different error. Fixes bug #48759. - - * e-msg-composer-select-file.c (e_msg_composer_select_file): Use - the proper selector title, otherwise it says "Attach files" when - we are trying to save a message. - -2003-09-24 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (get_default_charset): Same as - below. - - * e-msg-composer.c (composer_get_default_charset_setting): Handle - empty-string as the charset value gotten from gconf as this can - happen. Partial fix for bug #47638. - -2003-09-13 Charles Zhang <charles.zhang@sun.com> - - * e-msg-composer-attachment-bar.c (remove_attachment): Add some - assertion. Send Close response signal to the properties dialog - while removeing an attachment. - * e-msg-composer-attachment-bar.c (remove_selected): Fix a re- - remove-attachment bug. [#48466] - -2003-09-18 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c: updated for - CamelTransferEncoding namespace changes - - * e-msg-composer.c: updated for CamelTransferEncoding namespace - changes - -2003-09-18 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c: - * e-msg-composer-attachment.c: - * e-msg-composer.c: Updated for namespace changes in Camel. - -2003-09-17 Not Zed <NotZed@Ximian.com> - - ** Merge in mail-refactor-2-branch - -2003-09-15 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer-hdrs.c (header_new_recipient): Make the entry - non-focusable again. The right fix for A11Y is to add - accelerators. - -2003-09-11 Federico Mena Quintero <federico@ximian.com> - - * e-msg-composer.h (EMsgComposer): Added an entry_uic field for a - BonoboUIComponent for the non-control entries (e.g. the Subject - line). - - * e-msg-composer.c (create_composer): Set autoactivate to true on - the HTML control's BonoboControlFrame. - (setup_ui): Create the composer->entry_uic. - (destroy): Free the composer->entry_uic. - (entry_verbs): New array of verbs for the non-control entries. - Moved the Edit* verbs to here, as they should not be part of the - main set. - (composer_entry_focus_in_event_cb): Load - evolution-composer-entries.xml here for the non-control entries' UI. - (composer_entry_focus_out_event_cb): Remove the menu items. - -2003-09-10 Not Zed <NotZed@Ximian.com> - - * listener.c (impl_event): We want to use decode to stream for - attachment parts. - -2003-09-08 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (autosave_load_draft): ugh, direct linking to - evolution-mail suckage. Should these callbacks just be handled - internally? - (handle_multipart_encrypted, handle_multipart_signed) - (handle_multipart_alternative, handle_multipart) - (e_msg_composer_new_with_message): Use new em_utils stuff for - message formatting. - -2003-08-22 Antonio Xu <antonio.xu@sun.com> - - * e-msg-composer-attachment.c (): Connect response signal to - attachment properties dialog, fix bug #47950. - -2003-08-21 Antonio Xu <antonio.xu@sun.com> - - * Makefile.am (INCLUDES): add EVOLUTION_IMAGESDIR define - * e-msg-composer.c (create_composer): use EVOLUTION_IMAGESDIR - and composer icon name to get the path of composer icon. - [#47781] - -2003-08-19 Jeffrey Stedfast <fejj@ximian.com> - - * Original patch from David Woodhouse, but modified a bit by me. - - * e-msg-composer.c (handle_mailto): Fix insertion of arbitrary - headers from mailto: links. Ignore From: and Reply-To: headers. - -2003-08-13 Lorenzo Gil Sanchez <lgs@sicem.biz> - - * e-msg-composer-hdrs.c (account_removed_cb): fixed an insulting - error message. Fixes bug #47413. - -2003-08-13 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (update): This needs to use - camel_data_wrapper_decode_to_stream() rather than - write_to_stream(). Also simplify a bit - no sense looping to load - the pixbuf data into the gdk-pixbuf loader 4K at a time when we - have the whole thing in a memory buffer already. Once done, unref - the stream instead of closing it so we don't leak. - (attach_to_multipart): Use decode_to_stream(). - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - Avoid constructing thwe data-wrapper from the stream twice for - message/rfc822 parts. - -2003-07-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): don't set - the rawtext bit anymore. - - * e-msg-composer.c (build_message): Convert the plain part's - content stream from UTF-8 to whatever charset we want. - -2003-07-31 Antonio Xu <antonio.xu@sun.com> - - * e-msg-composer.c (drag_data_received): add the drop type of - mozilla browser link to make composer support to handle mozilla - DnD data. [#47131] - -2003-07-28 Antonio Xu <antonio.xu@sun.com> - - * e-msg-composer-attachment-bar.c (update): add - gdk_pixbuf_loader_close to close pix buffer loading. [#45908] - -2003-07-25 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (GNOME_GTKHTML_EDITOR_CONTROL_ID): require the - new composer control version. - -2003-07-17 Michel Daenzer <michel@daenzer.net> - - * e-msg-composer.c (autosave_manager_query_load_orphans): Set - default answer of dialog to 'yes' to try and prevent autosaved - messages from getting lost accidentally. - -2003-07-23 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): Revert my - previous changes here too. - - * e-msg-composer.c (build_message): Revert my previous changes. - -2003-07-23 Dan Winship <danw@ximian.com> - - * bad-icon.xpm: Remove this. It was only used by e-icon-list, - which is no longer there. - - * composer-marshal.list: Likewise - - * Makefile.am: Update - -2003-07-21 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Init charset to NULL. - -2003-07-21 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (build_message): Make this work again. - -2003-07-17 Maxx Cao <maxx.cao@sun.com> - - ** For bug #46013 - - * e-msg-composer-hdrs.c (header_new_recipient): To/cc/bcc buttons - made focusable. - -2003-07-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): don't set - the rawtext bit anymore. - - * e-msg-composer.c (build_message): Convert the plain part's - content stream from UTF-8 to whatever charset we want. - -2003-07-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (popup_menu_event): Fix warnings - and other breakage introduced by Maxx. - -2002-07-14 Maxx Cao <maxx.cao@sun.com> - - ** For bug #45826 - - * e-msg-composer-attachment-bar.c (class_init): connect the - "popup_menu" signal, so that S-F10 keybinding will work. - (popup_menu_event): funcion added to handle "popup_menu" (S-F10 key). - (popup_menu_placement_callback): function added to place the popup - menu to the center of attachment icon, in case it is activated by - keyboard. - -2003-07-07 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Updated to - use camel_strcase_hash/equal. - -2003-07-01 Dan Winship <danw@ximian.com> - - * e-msg-composer-attachment-bar.c (pixbuf_for_mime_type): Gone. - (update): Use e_icon_for_mime_type instead. - - * Makefile.am (INCLUDES): remove EVOLUTION_IMAGESDIR define - -2003-06-25 Antonio Xu <antonio.xu@sun.com> - - * e-msg-composer.c (handle_mailto): Change file url to absolute - path. Fixes bug #44065. - -2003-07-01 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (autosave_load_draft): Connect to the - save-draft signal too. Fixes bug #45531. - -2003-06-27 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Set the rawtext bits for the - 'plain' and 'html' data wrappers to FALSE. - -2003-06-19 Larry Ewing <lewing@ximian.com> - - * listener.c (insert_paragraph_after): free the return value. - (impl_event): free the return value. - -2003-06-17 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (best_encoding): Use e_iconv_open/close so that - we get charset aliasing for free. Fixes bug #44991. - -2003-06-16 Jeffrey Stedfast <fejj@ximian.com> - - Fixes bug #44139. - - * e-msg-composer-hdrs.c (attach_couple): Set the vertical and - horizontal padding to 3 always. - (create_from_optionmenu): Change the hbox spacing to 6 pixels. - - * e-msg-composer.c (create_composer): Set the border width around - the composer's vbox to HIG specification and make the box_spacing - 6 pixels as well. - -2003-06-10 Larry Ewing <lewing@ximian.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_and_string_free): - free the structure as well. - -2003-06-09 Larry Ewing <lewing@ximian.com> - - * listener.c (insert_paragraph_before): free the return values. - -2003-05-21 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (composer_get_default_charset_setting): Same as - the rest. - (setup_ui): We didn't even seem to be using the gconf client - here. Removed. - (e_msg_composer_load_config): Unref the gconf client after we're - finished. - (e_msg_composer_new): Same. - (e_msg_composer_new_post): Here too. - (e_msg_composer_set_view_from): And here. - (e_msg_composer_set_view_replyto): And here. - (e_msg_composer_set_view_cc): Here too. - (e_msg_composer_set_view_bcc): Again here. - - * e-msg-composer-hdrs.c (create_from_optionmenu): Same as below. - (e_msg_composer_hdrs_set_from_account): Here too. - - * e-msg-composer-attachment-bar.c (get_default_charset): Unref the - gconf client. diff --git a/composer/ChangeLog.pre-1-4 b/composer/ChangeLog.pre-1-4 deleted file mode 100644 index 58f0eebec1..0000000000 --- a/composer/ChangeLog.pre-1-4 +++ /dev/null @@ -1,4037 +0,0 @@ -2003-05-20 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (composer_settings_update): set the various - bonobo properties that are composer preferences. - (create_composer): add notification of gconf changes. - (destroy): disconnect notification. - - * e-msg-composer.h: keep the gcond notify handler id. - -2003-05-15 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_edit): - Don't connect to the focus-out-event in order to update the - mime-type. Simply don't update the mime-type ever. Fixes bug - #42798. - -2003-04-28 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (autosave_manager_query_load_orphans): Change - the "would you like to recover unsaved drafts?" dialog a QUESTION - dialog rather than an ERROR dialog. Fixes bug #42024. - -2003-04-25 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (pixbuf_for_mime_type): If we - fail to load the icon that gnome_vfs_get_icon() gave us, the - default back to gnome-unknown.png. This is the only POSSIBLE way - for Anna to be getting a NULL pixbuf if she has gnome-unknown.png - that I can see. Should fix bug #41513. - -2003-04-23 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (map_default_cb): removed debug printfs. - -2003-04-22 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (add_attachments_handle_mime_part): added - related argument, TRUE means that container of mime_part is - multipart/related - (add_attachments_handle_mime_part): add images as inline when - related is TRUE - (add_attachments_from_multipart): pass related to - add_attachments_handle_mime_part - -2003-04-21 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (add_attachments_handle_mime_part): Don't ever - attach non-inlined text or message parts. Reverts a prior fix. - -2003-04-21 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.glade: Change the order of the - ok/cancel buttons. - -2003-04-19 Chris Toshok <toshok@ximian.com> - - [ fixes #40694 ] - * e-msg-composer-hdrs.c (create_addressbook_entry): this can't - hurt - set the frame to autoactivate so if by some chance the - widget is focused the control will end up being activated. - - * e-msg-composer.c (map_default_cb): activate the To: control - instead of focusing the widget. - -2003-04-18 Rodney Dawes <dobey@ximian.com> - - * Makefile.am: - * e-msg-composer.c: - Use PREFIX instead of EVOLUTION_DATADIR for bonobo_ui_util_set_ui (). - Fixes bug #21499. - -2003-04-14 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (file_name_focus_out_cb): Return - FALSE so the signal gets propogated further up the chain. Fixes - bug #41238. - (e_msg_composer_attachment_edit): The focus-out-event signal name - changed (although the old name still works...for now?). - -2003-04-11 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.glade: Updated to comply with the - HIG. Fixes bug #41239 and bug #41241. - -2003-04-09 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (composer_get_default_charset_setting): Use - e_iconv_locale_charset() instead of e_iconv_locale_name(), dunno - what I was thinking. locale_name() doesn't even exist. - (setup_ui): Don't free the default_charset, it's a const char*. - - * e-msg-composer-attachment-bar.c (get_default_charset): Same. - -2003-04-09 Chris Toshok <toshok@ximian.com> - - * e-msg-composer.c (setup_ui): fix build, it's - composer_get_default_charset_setting. - -2003-04-09 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (composer_get_default_charset_setting): Same as - with attachment-bar's get_default_charset(). - (setup_ui): Instead of pulling the default charset from gconf, - call our helper function above. - - * e-msg-composer-attachment-bar.c (get_default_charset): If gconf - returns a NULL string, default back to the locale charset. - -2003-04-08 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (map_default_cb): Added some debug printfs. - (create_composer): Call map_default_cb directly instead of having - it in a "map" callback. Ettore says we shouldn't be doing this - *shrug*. Still doesn't work tho. - -2003-04-07 Chris Toshok <toshok@ximian.com> - - [ fixes bug #39763 ] - * e-msg-composer.c (setup_cut_copy_paste): remove the - control_entry_focus_{in,out}_event_cb signal stuff. - (control_entry_focus_in_event_cb): nuke - (control_entry_focus_in_event_cb): same. - - * e-msg-composer-hdrs.c (create_addressbook_entry): pass the - contain to bonobo_widget_new_control_from_objref when creating the - entries. - -2003-04-04 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (autosave_save_draft): If the composer isn't - 'dirty', then don't autosave the draft (no need to). Fixes bug - #40764. - -2003-04-03 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (menu_edit_select_all_cb): Add a select-all - callback and verb. - (composer_entry_focus_in_event_cb): Set our bonobo-ui verbs. - -2003-04-02 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-select-file.c (e_msg_composer_select_file): Guard - against the filesel's selection being NULL. Fixes bug #40679. - -2003-04-01 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (composer_entry_focus_in_event_cb): Keep track - of which entry widget has focus. - (composer_entry_focus_out_event_cb): Same. - (control_entry_focus_in_event_cb): Same idea, but since this is in - another component, tell that component that its widget has focus - so it can merge bonoboui cut/copy/paste (and anything else) menus. - (control_entry_focus_out_event_cb): Same. - (setup_cut_copy_paste): Connect to the focus-in and focus-out - events for all the entry widgets and the html editor. - (menu_edit_cut_cb): New callback function since the composer will - now own the Cut/Copy/Paste menu items sometimes (depending on - which widget is in focus... confused yet? good). - - * e-msg-composer-hdrs.c (from_changed): Update the Reply-To entry - to be a normal GtkEntry. - (create_headers): Same. - (e_msg_composer_hdrs_set_reply_to): Here too. - (e_msg_composer_hdrs_get_reply_to): And finally here. - -2003-04-01 Not Zed <NotZed@Ximian.com> - - ** See bug #40300 & probably others. - - * e-msg-composer.c (autosave_manager_query_load_orphans): make the - composer arg a parent arg, its only used parent the dialogue. - Fix caller casts. - (e_msg_composer_check_autosave): new function, checks for - autosave files, and recovers them per user instructions. - -2003-03-31 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.glade: Convert to libglade-2's format. - - * e-msg-composer.c (set_editor_signature): E_MSG_COMPOSER_HDRS - (composer->hdrs)->account->id can never be NULL anymore. - -2003-03-25 Dan Winship <danw@ximian.com> - - * e-msg-composer.c: Update for e_notice move - -2003-03-20 Jeffrey Stedfast <fejj@ximian.com> - - Fixes for bug #39813 - - * e-msg-composer.c (composer_finalise): Don't unregister the - signature event handler here. - (destroy): Unregister it here instead. - -2003-03-19 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (add_attachments_handle_mime_part): Change the - logic to attach text parts when appropriate. - (map_default_cb): Grab the focus of the To entry widget. Fixes bug - #39800. Fixes another #warning too. - -2003-03-18 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (do_exit): e_msg_composer_hdrs_get_subject() - now returns const so don't g_free() it :-) - (map_default_cb): Same as above. Also, the subject entry no longer - derives from GnomeCanvas so eliminate the now unneeded casting to - grab the focus of the subject widget. - (e_msg_composer_get_subject): Return a const char * now. - - * e-msg-composer-hdrs.c (create_headers): Make the subject entry - into a GtkEntry so we don't have to worry about i18n and other - EEntry bugs anymore. Fixes numerous bugs (including #39924). - (e_msg_composer_hdrs_set_subject): Use gtk_entry_set_text(). - (e_msg_composer_hdrs_to_message_internal): - e_msg_composer_hdrs_get_subject() now returns const. - (e_msg_composer_hdrs_get_subject): Return a const char *. - (entry_changed): e_msg_composer_hdrs_get_subject() now returns - const. - -2003-03-13 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (create_composer): Default the composer's title - to "Create a message". Fixes bug #39696. - -2003-03-11 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c: Use GnomeIconList instead of - EIconList so we don't have to maintain an exact copy/paste of - GnomeIconList ourselves. I don't udnerstand why we ever did. - - * e-icon-list.[c,h]: Removed. - -2003-03-11 Not Zed <NotZed@Ximian.com> - - * evolution-composer.c (evolution_composer_new): add - send_cb/save_draft_cb arguments. - (impl_Composer_send): use the local send_cb. - (evolution_composer_init): dont init send, save-draft signals - here. - (evolution_composer_new): init signals here, fix params to - composer_construct(). - (evolution_composer_factory_init): remove, part of mailer now. - (factory_fn): same. - (finalise): disconnect from callbacks first. - - * evolution-composer.h: add send_cb/save_draft_cb to composer object. - -2003-03-10 Not Zed <NotZed@Ximian.com> - - * evolution-composer.c (finalise): from destroy. - (evolution_composer_class_init): gtkobject->gobject stuff. - (evolution_composer_new): remove old redundant stuff. - -2003-03-04 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (composer_get_default_charset_setting): Don't - allow the returned charset to be NULL. - (get_file_content): Make sure there is buffered data before trying - to convert it to UTF-8. - -2003-03-04 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-hdrs.c (destroy): disconnect any signal handlers - on the accounts object. For bug #37873. - -2003-02-25 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c: Same as below. - - * e-msg-composer-attachment-bar.c: Go back to using - e_iconv_charset_name(). - -2003-02-24 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (drag_data_received): Make sure the url is != - NULL? I can't think of anything else in this code that could - possibly cause bug #38382. - - * e-msg-composer-attachment-bar.c (pixbuf_for_mime_type): Fixed a - memory leak. - -2003-02-22 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_set_send_html): Don't save the - HTML format setting to gconf. This option menu is meant for a - per-essage setting (ie. once the composer closes, the next - composer will again use the default and not what the user chose - last time). - -2003-02-21 Dan Winship <danw@ximian.com> - - * Makefile.am: build libcomposer as a shared library so it can be - linked into libevolution-mail.so without portability problems - -2003-02-20 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (composer_get_default_charset_setting): Same as - below. - - * e-msg-composer-attachment-bar.c (get_default_charset): Use - camel_charset_canonical_name() rather than e_iconv_charset_name() - as the latter will be removed shortly. - -2003-02-18 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_set_from_account): - default_account is now a string value, not an int. - (create_from_optionmenu): Same. - (header_new_recipient): Use g_signal_connect_data() instead of the - now deprecated gtk_signal_connect_full(). - -2003-02-06 Dan Winship <danw@ximian.com> - - * Makefile.am: clean up - - * e-msg-composer.c (autosave_manager_query_load_orphans): #include - string.h - (menu_file_send_cb): s/gtk_signal_emit/g_signal_emit/ - - * e-msg-composer-attachment.c: #include string.h - (e_msg_composer_attachment_edit): s/E_GLADEDIR/EVOLUTION_GLADEDIR - - * e-msg-composer-attachment-bar.c: #include string.h - (pixbuf_for_mime_type): s/ICONSDIR/IMAGESDIR/ - - * e-msg-composer-hdrs.c: #include string.h - - * e-msg-composer-select-file.c (run_selector): Remove unused var - - * evolution-composer.c: #include string.h - (evolution_composer_init): Remove unused var - - * listener.c: #include string.h - (listener_new): Remove unused var - -2003-02-05 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_from_url): Split out the - mailto handling code from here so we can use it in the drag-n-drop - code too. - (drag_data_received): If we find a mailto: url in the - text/uri-list drop, pass that off to handle_mailto() so it can - fill in the fields for us. - -2003-02-03 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c: Just use - gnome_vfs_get_mime_type_from_name(). - -2003-02-01 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (update_mime_type): Give - gnome_vfs_get_uri_from_local_path a full path. - -2003-01-27 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_from_url): If the subject - or body components of the mailto url are not in UTF-8, convert - them to UTF-8. - - * e-msg-composer-attachment.c (update_mime_type): Fixed a #warning - by converting the filename into a uri before passing it into - gnome_vfs_get_mime_type() since that function really needs a uri. - -2003-01-22 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (init): Get the list of accounts here and - ref the account-list. - (destroy): Unref the accounts list here. - (create_from_optionmenu): Connect to the added/changed/removed - account-list signals here. - (account_added_cb): New callback function that adds the newly - added account to the from-dropdown menu. - (account_changed_cb): New callback that changes the label for the - account that got changed in the dropdown menu. - (account_removed_cb): Removes the account from the from dropdown - menu. - -2003-01-24 Ettore Perazzoli <ettore@ximian.com> - - * Makefile.am (iconsdir): Remove, this is now defined in - configure.in. - -2003-01-23 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_load_config): Load the view - menu states from gconf. - (e_msg_composer_set_send_html): Save the setting via gconf instead - of bonobo-config. - (e_msg_composer_set_view_from): Same. - (e_msg_composer_set_view_replyto): Here too. - (e_msg_composer_set_view_cc): Again here. - (e_msg_composer_set_view_bcc): And finally here. - (setup_ui): Fixed a #warning - use gconf instead of bonobo-conf. - (destroy): No need to sync/destroy the bonobo-conf db, we don't - use it anymore. - -2003-01-16 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer.c (setup_ui): Get evolution-message-composer.xml - from EVOLUTION_UI_DIRECTORY. - - * Makefile.am (gladedir): Version it using $(BASE_VERSION). - (iconsdir): Likewise. - (libcomposerincludedir): Removed. - -2003-01-17 Jeffrey Stedfast <fejj@ximian.com> - - * evolution-composer.c (impl_Composer_set_headers): Updated to use - EAccountList and iterators. - (evolution_composer_init): Updated to use EAccount. - - * e-msg-composer.c (from_changed_cb): Updated to use the EAccount - object. - (e_msg_composer_new_with_message): Same. - (e_msg_composer_get_preferred_account): Updated to return an - EAccount object. - (set_editor_signature): Updated to use an EAccountIdentity pointer. - (get_signature_html): Same. - - * e-msg-composer-hdrs.c (create_from_optionmenu): Updated to use - EAccount and EAccountList foo. - (destroy): Same here. - (e_msg_composer_hdrs_set_from_account): Here too. - (e_msg_composer_hdrs_get_from): Updated. - -2003-01-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (signature_cb): mail_config_get_signature_list - now returns a GSList. - (setup_signatures_menu): Same. - (set_signature_gui): Here too. - -2003-01-14 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer.c (do_exit): Make dialog HIG compliant - [Discard/Cancel/Save]. - -2003-01-09 Chris Toshok <toshok@ximian.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_set_to): don't pass - NULL to bonobo_widget_set_property. - (e_msg_composer_hdrs_set_cc): same. - (e_msg_composer_hdrs_set_bcc): same. - -2003-01-09 Chris Toshok <toshok@ximian.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_new): need to - ref/sink "new" so that the g_object_unref doesn't spew a warning. - -2003-01-08 Ettore Perazzoli <ettore@ximian.com> - - * Makefile.am: Icons are now in $(datadir)/evolution/images - instead of $(datadir)/images/evolution. - -2003-01-08 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (create_from_optionmenu): Use gconf to get - the default account index. - (e_msg_composer_hdrs_set_from_account): Same. - -2003-01-07 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (get_default_charset): New - convenience function. - (attach_to_multipart): Use get_default_charset(). - - * e-msg-composer.c (composer_get_default_charset): Convenience - function. - (get_file_content): Use the convenience function to get the - default charset setting. - (best_charset): Same. - (e_msg_composer_new): Use gconf to get the send_html setting. - (e_msg_composer_new_post): Same. - -2003-01-06 Dan Winship <danw@ximian.com> - - * Makefile.am: Remove idldir definition. (It's defined in - configure.in now) - -2002-12-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (get_signature_html): Use camel_text_to_html(). - (e_msg_composer_new_from_url): Same. - - * evolution-composer.c (impl_Composer_set_body): Use - camel_text_to_html(). - -2002-12-07 Jeffrey Stedfast <fejj@ximian.com> - - Fix for bug #33295 - - * e-msg-composer-attachment.c: Change the parent_class to a - GObjectClass pointer instead of a GtkObjectClass pointer. - (e_msg_composer_attachment_edit): Ref the attachment object so - that if the attachment is removed while it is still being edited, - the attachment object will still exist and therefor foil the - user's attempt to make Evolution crash when they close the - properties dialog for this attachment. - (close_cb): Unref the attachment object. - -2002-12-03 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (message_rfc822_dnd): Get rid of the unused - exception variable. - -2002-11-27 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (save): removed warning about e_notice. its - used too much, its here to stay. - - * *.[ch]: run fix.sh over everything. - -2002-12-01 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c: s/g_str[n]casecmp/str[n]casecmp - -2002-11-26 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (composer_finalise): properly chain finalise. - -2002-11-25 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-attachment-bar.c (init): Remove the window size - setting. - (e_msg_composer_attachment_bar_new): Move the window size setting - here. Also set icon width based on 15 approximate characters, so - the icon text is more readable. - -2002-11-22 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-select-file.c: rewrote most of this. Just use - gtkfileselection directly, no e-file-selector, much - smaller/simpler. - -2002-11-21 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-attachment-bar.c (remove_attachment): fix - g_signal_emit params, detail in wrong spot. - (add_common): Same. - - * e-icon-list.c (icon_new_from_pixbuf): remove the - 'use_broken_event_handling' set. - (emit_select): Add detail to signal emit. - (text_changed): Same. - - * e-msg-composer.c (subject_changed_cb): Duh! dont free subject & - simplify logic a little. - -2002-11-20 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-hdrs.c (entry_changed): duh, emit the signal - using an initialised value(!). - -2002-11-19 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (e_msg_composer_get_sig_file_content): use - CAMEL_MIME_FILTER_TOHTML_PRESERVE_8BIT flag - -2002-11-19 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-attachment-bar.c (add_from_file): dont unref - after destroy. duh. - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_set_to): Add type - code to set_property call. - (e_msg_composer_hdrs_set_cc): " - (e_msg_composer_hdrs_set_bcc): " - (e_msg_composer_hdrs_get_to): Do the same for get_property calls. - (init): ref/sink the tooltip object. - (e_msg_composer_hdrs_get_type): fix return type. - - * e-msg-composer.c (GNOME_GTKHTML_EDITOR_CONTROL_ID): we want - version 3.0 not 1.1. - (create_composer): Add type code to set property call. - (autosave_manager_query_load_orphans): my bad, we dont unref - dialog's once we've destroyed 'em. - (build_message): " - (get_file_content): " - (save): " - (do_exit): " - (composer_dispose): moved the autosave shutdown here. - -2002-11-18 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (create_composer): Remove check for - gtk_main_level(). as far as i can tell it serves no real purpose, - and i think gtkmain is now redundant. - (e_msg_composer_new_with_message): Same here. - (destroy): moved some stuff into finalise, and made destroy - mulitcall safe. - -2002-11-13 Ettore Perazzoli <ettore@ximian.com> - - * listener.h: Removed {BEGIN,END}_GNOME_DECLS. - - * e-msg-composer-select-file.c: Do not #include - <libgnome/gnome-defs.h>. - * e-msg-composer.c: Likewise. - * listener.h: Likewise. - -2002-11-13 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (setup_ui): bonobo api changes. - - * e-icon-list.c (e_icon_list_new): Use the right object_new method. - - * e-icon-list.h: get rid of BEGIN/END_GNOME_DECLS stuff. - -2002-11-11 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c: Remove some unused ehaders and - ones that cause compilation failures (such as gnome-defs.h). - - * e-icon-list.h: Same. - -2002-11-08 Not Zed <NotZed@Ximian.com> - - * listener.c: Fix bonobo object setup. - - * e-msg-composer-hdrs.c: Remove oaf stuff, fix destroy to be - multi-call safe. - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - Remove utf8 from locale conversions, & glib api changes. - (ok_cb): " - - * e-msg-composer-attachment-bar.c (add_from_file): gtk message - dialog. - (pixbuf_for_mime_type): glib,gnome-vfs api changes. - (init): Estimate the icon_height based on the pango font - description size, this is probably not correct. - (properties_cb): - (remove_cb): Changed signature for gnomeui callbacks. - (popup_icon_context_menu): - (popup_context_menu): popup_menu api change - (destroy): Protect from multiple calls. - (e_msg_composer_attachment_bar_new): Remove push/pop - visual/colormap stuff. - - * composer-marshal.list: The list of marshallers used by the - composer. - - * Makefile.am (composer-marshal.h): Added composer marshal builder. - - * evolution-composer.c (class_init): bonobo object epv setup change. - (factory_fn): Fix changes to factory callback. - - * e-icon-list.c: (icon_get_height): Use bounding box to calc - height. - (icon_event): drop gtk_selection_extended. - (e_icon_list_remove): " - (select_icon): - (unselect_icon): " - - * e-msg-composer.c (autosave_save_draft): Dup fd rather than poke - camel_stream_fd's data. Also, use camel_stream_close() rather - than flush. - (autosave_manager_query_load_orphans): Port to gtk dialog. - (autosave_query_cb): Removed, redundant. - (save): Port to gtkdialog. - (prepare_engine): Fix bonobo-object-client code. - (get_file_content): gtk dialog - (do_exit): gtk dialog. - (setup_signatures_menu): dump gtkutf8 stuff. - (marshal_NONE__NONE_INT): What WAS jeff thinking? Removed :) - (class_init): g object setup. - (e_msg_composer_get_type): " - (create_composer): remove bonobo_window_construct, use create - property instead. g_signal stuff. bonobo stuff. - (is_special_header): Use ascii_strncasecmp - (e_msg_composer_set_pending_body): gtk->g_object_get/set_data. - (e_msg_composer_set_body): use ascii_strncasecmp - (e_msg_composer_add_inline_image_from_mime_part): make cid const. - (autosave_manager_register): - (autosave_manager_unregister): Use g_path_get_basename() & account - for differences. - (composer_shutdown): rename to finalise/etc. - (class_init): Use object:finalize instead of shutdown. - (e_msg_composer_set_body): Use _() rather than U_(). - (build_message): gtk dialog. - -2002-11-06 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-attachment-bar.c (pixbuf_for_mime_type): Add - error return to gdk_pixbuf_new_from_file(). - -2002-11-01 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_from_url): Add support for - an attach option in the mailto: url. - -2002-10-29 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Make sure to - save References and In-Reply-To headers. Fixes bug #32932. - -2002-10-26 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): Don't set - the charset param on text parts nor tha rawtext bit on the content - if a charset for the part is already specified. - -2002-10-25 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer-attachment-bar.c (size_to_string): Return NULL - instead of the empty string if the size is less than one K. - (update): Only put the size if size_to_string() doesn't return - NULL. [#32751] - -2002-10-18 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (create_from_optionmenu): Only add the - account address to the list of addresses if it is non-NULL. Fixes - bug #32446 although it shouldn't ever happen anyway (an account - address is not allowed to be NULL). - -2002-10-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): We - need to treat message/rfc822 streams differently. Fixes bug - #32378. - -2002-10-16 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-select-file.c (select_file_internal): Mark the - file selector modal. Quick fix for bug #32256. - -2002-10-04 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): Set - content->rawtext to TRUE for text parts because the content is in - its raw form (since we didn't know the charset when we created - it). Also only write out the content-object to discover the best - encoding, we don't want to include the headers of the MIME - part. Second half of the fix for bug #31655. - -2002-10-02 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (get_file_content): Don't create a new file if - the file doesn't exist. - -2002-10-01 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): If the user hits cancel when - signing/encrypting, don't continue constructing the message, - instead abort (and just don't pop up a dialog). - -2002-10-01 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): When signing/encrypting a - part, if a USER_CANCEL occurs, re-use the part otherwise unref it - and replace it with the new part. - -2002-09-30 Aaron Weber <aaron@ximian.com> - - * evolution-composer.c (evolution_composer_factory_init): adjust - string on line 391 - - * e-msg-composer.c (create_composer): adjust string on 2872 - -2002-09-27 Dan Winship <danw@ximian.com> - - * Evolution-Composer.idl (setHeaders): let the caller set the - "From" account too (by name or address). - - * evolution-composer.c (impl_Composer_set_headers): Update for - that. - -2002-09-27 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Don't reuse the part that - we've signed and/or encrypted, create a new part container - instead. Fixes bug #31379. - -2002-09-25 Dan Winship <danw@ximian.com> - - * e-msg-composer-hdrs.c (create_headers): Use "mail/*" for the - allowed_types for the posting folder selector. - -2002-09-24 Dan Winship <danw@ximian.com> - - * e-msg-composer-hdrs.c (create_from_optionmenu): Only append the - account name to the end of the From menu item if the email address - is not unique. (That was added for people who have multiple - accounts with the same email address but different transports. The - rest of us don't need to be reminded of the account name, and - having it there can make the window very wide.) - -2002-09-24 Zbigniew Chyla <cyba@gnome.pl> - - * e-msg-composer-attachment-bar.c (size_to_string): - Don't mark empty string with _(). - -2002-09-23 Ettore Perazzoli <ettore@ximian.com> - - * e-icon-list.c (icon_new_from_pixbuf): Removed a #warning. - - * e-msg-composer-attachment-bar.c (size_to_string): Don't use dots - here so we don't get funny wrapping from GnomeIconList. [#236] - -2002-09-22 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (save): Fix non-ANSI switch statement - -2002-09-19 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (signature_cb): allow to select last 2 menu - items - -2002-09-17 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (add_attachments_from_multipart): Handle - multipart/signed and multipart/encrypted parts in a more expected - way. Fixes bug #28453. - -2002-09-15 Kjartan Maraas <kmaraas@gnome.org> - - * e-msg-composer.c: Mark a string for translation. - -2002-09-05 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer.c (composer_key_pressed): Don't chain the event - handler here -- that's just wrong! Also stop emission of the - signal when we catch Escape. - -2002-09-04 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (create_composer): Make it so that the composer - will close when the user hits Escape. - -2002-08-27 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (signature_cb): removed "Set as default" menu item - -2002-08-26 Peter Williams <peterw@ximian.com> - - * e-msg-composer.c (handle_multipart): Oops, we were overwriting - 'multipart' with our child multipart. Fixes 29399. - (handle_multipart_alternative): Here too. - -2002-08-22 Jeffrey Stedfast <fejj@ximian.com> - - Fixes bug #29016 - - * e-msg-composer.c (e_msg_composer_new_with_message): If the - X-Evolution-PostTo header exists, then treat this message composer - as a PostTo composer rather than a mail composer. - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_to_message_internal): - Set the X-Evolution-PostTo header if that is the mdoe we are in. - -2002-08-16 Dan Winship <danw@ximian.com> - - * e-msg-composer-hdrs.c (create_headers): Use an - EvolutionFolderSelectorButton instead of a label to indicate the - posting destination. #27920. - (e_msg_composer_hdrs_set_post_to): Use - evolution_folder_button_set_uri. - (e_msg_composer_hdrs_get_post_to): Use - evolution_folder_button_get_folder. - -2002-08-14 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (from_changed_cb): Don't turn on pgp signing if - this is an iMIP message and pgp_no_imip_sign is set. - (e_msg_composer_set_body): If setting a text/calendar body and - pgp_no_imip_sign is true, turn off signing. - -2002-08-13 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (do_exit): Make the warning dialog display the - message subject so that it is more clear which composer the dialog - is referring to. Fixes bug #25467. - -2002-08-12 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-select-file.c (create_file_selection): Set the - file-selection window icon. Fixes the mailer part of bug #7368. - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - Don't call new_from_mime_part() since that function now does some - copying of the mime part rather than simply reffing it. - (e_msg_composer_attachment_new_from_mime_part): Make a copy of the - MIME part so that if the message that this part belongs to gets - deleted from the the remote store, the composer will still have a - copy of it. Fixes bug #20308. - -2002-07-31 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Parse the - auto-cc/bcc recipients and then later when parsing the cc/bcc - recipients into EDestination objects, if the address is an - auto-*cc address, then set auto_recipient to TRUE on that - EDestination. This fixes bug #28339. - -2002-07-29 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (encode_signature_name): new helper function - (decode_signature_name): new helper function - (get_signature_html): use encode_signature_name - (set_signature_gui): use decode_signature_name - -2002-07-26 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (do_exit): don't assert on default, when ESC is - pressed, the dialog is closed as well and we get button number -1 - (set_signature_gui): new helper method to set signature from draft - message - (e_msg_composer_new_with_message): use set_signature_gui - -2002-07-26 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer-attachment-bar.c (pixbuf_for_mime_type): - Special-case message/digest, multipart/digest and message/rfc822 - and give them a nice icon. [#9786] - - * Makefile.am (INCLUDES): Add -D for EVOLUTION_ICONSDIR. - -2002-07-24 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (create_headers): Create the Post-To - header. - (headers_set_visibility): Possibly show the Post-To header. - (attach_headers): Attach the Post-To header. - (e_msg_composer_hdrs_set_post_to): Set the text for the Post-To - header. - (e_msg_composer_hdrs_get_post_to_label): Return the label widget - for this header pair. - (e_msg_composer_hdrs_set_visible_mask): New function to set the - visible mask (so we can disallow certain headers to be shown). - (e_msg_composer_hdrs_new): Save the visible mask argument. - (setup_headers): To: does not always have to be visible anymore. - (e_msg_composer_hdrs_get_post_to): New function to get the url for - the Post-To folder. - - * e-msg-composer.c (e_msg_composer_get_visible_flags): Set the - Post-To bit when it is supposed to be visible. - (e_msg_composer_new_post): Set the visible_mask to only allow the - headers needed for Posting. - -2002-07-25 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (e_msg_composer_set_body): Fix spelling. - -2002-07-23 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (autosave_run): restart automanager to avoid - multiple dialog apearing - -2002-07-23 Not Zed <NotZed@Ximian.com> - - * Applied patch below. - -2002-07-19 Christian Kreibich <christian@whoop.org> - - * e.msg-composer.c (get_signature_html): Test for the signature - delimiter not only at the beginning of a signature file, but also - inside the signature. - -2002-07-23 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_set_view_bcc): Reverted some - code that got committed by accident. - (e_msg_composer_set_view_cc): Same. - (e_msg_composer_set_view_replyto): Here too. - (e_msg_composer_set_view_from): And here. - -2002-07-22 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c: Removed a lot of extra g_return_if_fail's that - we don't need (if we are going to check if the pointer is a a - composer widget using the gtk type-check macros, then there is no - need to first check that it isn't NULL). - (get_file_content): Signatures are now supposed to be in UTF-8 and - not the user's locale charset, so we must first read in the - content, then check that it is valid UTF-8. If it isn't, then we - need to try to convert it to UTF-8. - -2002-07-22 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c: removed Insert File menu item - -2002-07-19 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_to_message_internal): - This should use address_encode, since its an rfc822 address, not - address_format which is for display. - -2002-07-17 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (save): use "saved" gtkhtml command - (e_msg_composer_is_dirty): use "is-saved" gtkhtml command - -2002-07-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_set_headers): Set the - from-account last so that auto-cc/bcc recipients don't get - overwritten when setting the cc/bcc recipient fields. - -2002-07-16 Peter Williams <peterw@ximian.com> - - * e-msg-composer.c (create_composer): Instead of doing this with a - weakref, do it by connecting to the destroy signal. The weakref was - not getting notified in certain conditions that I could never really - pin down, and this caused problems at exit. - - * e-msg-composer-hdrs.c (create_headers): Reorder to create reply_to - before from, because create_from_optionmenu causes from_changed to - be called, which expects reply_to.entry to exist. - -2002-07-15 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (build_message): added save_html_object_data - parameter, use gtkhtml command to save object data when wanted - -2002-07-08 Peter Williams <peterw@ximian.com> - - * Makefile.am (INCLUDES): Fix cflags for ebook header namespacing. - -2002-07-05 Jeffrey Stedfast <fejj@ximian.com> - - * evolution-composer.c (init): Don't connect to the postpone - signal, but do connect to the save-draft signal. - (evolution_composer_factory_init): No longer takes a postpone_cb - argument, but does now take a save_draft_cb argument. - - * e-msg-composer.c (menu_file_send_later_cb): Removed. - (class_init): Removed the POSTPONE signal. - (setup_ui): Don't need to swap the Send/SendLater tooltips and - accels anymore, since SendLater no longer exists. - -2002-06-26 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Use the new - CamelMultipartEncrypted class to do our encryption work for us. We - also need to always get the user's userid before encrypting since - pgp/gpg need that. - (e_msg_composer_new_with_message): Handle multipart/signed and - multipart/encrypted parts by adding the (decrypted) content and - setting the composer to pgp sign/encrypt the message when the user - re-sends it. - -2002-06-25 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Use - mail_crypto_get_pgp_cipher_context() so that the PGP/GPG decision - is done for us. - -2002-06-21 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Use the new gpg cipher context - rather than the old pgp context. - -2002-06-19 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (get_signature_html): don't convert text to - html twice - -2002-06-10 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (signature_cb): added "Set as default" menu - item - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_get_from_omenu): new - method - (e_msg_composer_hdrs_set_from_account): use - e_msg_composer_hdrs_get_from_omenu - -2002-06-07 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (get_signature_html): use new script signature - interface - -2002-06-06 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_set_from_account): - Agh, priv->from.entry is no longer a GtkOptionMenu - it is an hbox - containing the GtkOptionMenu. - - * e-msg-composer.c (setup_ui): Remove the customize toolbar thingy - since Michael said that this would fix bug #17952. - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_set_from_account): - Clean up the logic in this. For one, we don't need to do strstr - using the account address (wtf??). - -2002-06-05 Radek Doulik <rodo@ximian.com> - - * e-msg-composer-hdrs.c (create_from_optionmenu): put option menu - to hbox to make space for signatures menu - (e_msg_composer_hdrs_get_from_hbox): new helper function - - * e-msg-composer.c: moved signatures from menu to option menu next - to From: - -2002-06-03 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (build_message): Properly handle user - cancellation for signing/encrypting, just dont sign but create - anyway. - (e_msg_composer_get_subject): Wrapper function to get the subject - from the header object. - (e_msg_composer_get_to): - (e_msg_composer_get_cc): - (e_msg_composer_get_bcc): Same for the destination types. - -2002-06-03 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_guess_mime_type): Allocate a - new FileInfo struct here rather than using and unref it when we're - finished with it. - -2002-05-30 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (build_message): Changes for multipart/signed - api changes. - -2002-05-16 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer.c: New local `all_composers'; keeps a list of all - the composer windows created. Changed type of `parent_class' to - BonoboWindowClass *. - (do_exit): Cleaned up a bit. Raise the composer window before - showing the message box dialog. - (exit_dialog_cb): Removed. - (e_msg_composer_request_close_all): New. - (create_composer): Add the composer to the all_composers list and - weakref it. - (msg_composer_destroy_notify): GtkDestroyNotify function for the - composer's weakref; remove the composer from the all_composers - list. - -2002-05-15 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - Just use g_basename. - -2002-04-26 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Check for empty-string pgp-key - ids and don't use them. - -2002-04-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (destroy): Unref the priv->tooltips object - here. - - * e-msg-composer-attachment-bar.c (destroy): Free the priv struct. - - * e-msg-composer.c (set_editor_signature): We don't need a 'name'? - So don't strdup it. - -2002-04-12 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (from_changed): Change the Reply-To header - contents. - (e_msg_composer_hdrs_set_reply_to): The Reply-To entry was an - EEntry, not a bonobo control so fix this to set the text using - e_entry_set_text. - (e_msg_composer_hdrs_get_reply_to): Use e_entry_get_text here for - the same reason. - -2002-04-08 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (set_editor_text): No need to query for the - persist-stream interface here, just re-use - composer->persist_stream_interface - this might improve the speed - at which a reply action brings up the composer. - -2002-04-09 Not Zed <NotZed@Ximian.com> - - * e-msg-composer-hdrs.c (set_recipients_from_destv): Use decode - rather than unformat - the e_destination was changed (long time - ago) to rfc2047 encode the addresses, so we should decode - likewise. Should fix #16158. - - * e-msg-composer.c (next_word): g_utf8_next_char never returns - NULL, it just skips to the next character. So like normal string - code, we just check for a nul explicitly. Fixes a bug found while - checking #16158. - -2002-04-05 Jeffrey Stedfast <fejj@ximian.com> - - Fixes bug #3980. - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_set_cc): If a Cc list - is set to something non-empty, make sure to show the Cc widgets. - (e_msg_composer_hdrs_set_bcc): Same but for Bcc. - (e_msg_composer_hdrs_set_reply_to): And here. - -2002-03-28 Christopher James Lahey <clahey@ximian.com> - - * e-msg-composer-select-file.c: Switch to using EFileSelection - here instead of GtkFileSelection. - -2002-03-27 Larry Ewing <lewing@ximian.com> - - * Makefile.am: fix for the changes to GTKHTML_DATADIR that include - the release number. - -2002-03-18 Dan Winship <danw@ximian.com> - - * Evolution-Composer.idl, evolution-composer.c - (impl_Composer_show): "Forward as iCalendar" uses set_body, so we - can't make the composer un-showable after doing that. So get rid - of the "cannot show" exception. - - * e-msg-composer.c (e_msg_composer_set_body): Prepare the composer - to be shown in its weird state: Put an explanatory message in the - body, then call disable_editor. - (disable_editor): Common editor-disabling code - makes the editor - and attachment bar insensitive and disables any menu items that - could be used to modify them. - (e_msg_composer_new_redirect): Use disable_editor here now. - -2002-03-15 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c: use gtkhtml editor API version 1.1 - -2002-03-11 Dan Winship <danw@ximian.com> - - * listener.c (impl_event): Remove the extremely verbose printf - here. - -2002-03-07 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (destroy): ops, unregister and not register new - one sig_event_client - -2002-03-04 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (build_message): Fix a dumb bug in previous - commit that broke iMIP containing 8-bit data. - -2002-02-25 Dan Winship <danw@ximian.com> - - Mailer side of 14705. - - * Evolution-Composer.idl (setBody): Change setBodyText to setBody - and take a MIME type as well. - (show): Add an exception. - - * evolution-composer.c (impl_Composer_set_body, etc): Update for - IDL change. While I'm here, fix this to DTRT with both plaintext - and HTML bodies. (It claimed to take plain text before, but then - passed it to the composer as HTML.) - (impl_Composer_show): Raise an exception if setBody has been - called, since the composer window will not display the real data - in that case. - - * e-msg-composer.c (e_msg_composer_set_body): interface for - impl_Composer_set_body. - (build_message): If e_msg_composer_set_body has been called, use - the body and MIME type supplied to it rather than the contents of - the HTML editor. - -2002-02-14 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (delete_old_signature): don't insert paragraph - here, also delete paragraph where signature was - (e_msg_composer_show_sig_file): test if we are in empty document - and if so, insert new paragraph for signature - -2002-02-12 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_flush_pending_body): Use - set_editor_text() - (e_msg_composer_new_from_url): Same. - (e_msg_composer_set_body_text): Re-Show the signature. - -2002-02-12 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (e_msg_composer_is_dirty): reflect gtkhtml API - change - -2002-02-11 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (e_msg_composer_drop_editor_undo): new method, - drops undo in editor and resets dirty flag in editor - (do_exit): remove TRUE from condition as dirty flag in editor - should work now - (e_msg_composer_is_dirty): use new editor API for dirty flag - -2002-02-01 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (update_auto_recipients): Update the - auto-cc/bcc recipients in the composer header fields to match the - ones chosen in the account configuration. - -2002-01-31 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (e_msg_composer_ignore): new method, tells - composer to ignore all word in str string - (next_word): helper function to get next word from s, saves rest - of s to sr - -2002-01-29 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): If we are in redirect mode, - use the original message and set the resent-* headers using - e_msg_composer_hdrs_to_redirect() and then return. - (destroy): Unref the redirected message if it exists. - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_to_redirect): New - function for a composer in redirect mode. - -2002-01-27 Ettore Perazzoli <ettore@ximian.com> - - * Makefile.am: Use GNOME_FULL_CFLAGS. - -2002-01-10 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (get_file_content): Rewrote to use CamelStreams - and also convert the file contents to UTF-8 (assums the file - charset is the same charset that the composer is set to). - (menu_file_insert_file_cb): Pass the composer into - get_file_content(). - (e_msg_composer_get_sig_file_content): Pass NULL as the composer - argument. - -2002-01-09 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (class_init): Fixed the setup of the - "save-draft" signal so that it would actually work. - -2002-01-08 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (is_special_header): Greatly simplified. No - need to have a list of headers to not accept - we can just refuse - all headers that are not X-* headers (other than X-Evolution - headers). - -2002-01-07 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_get_message_draft): Set the - X-Evolution-Format header to text/plain if that is the editing - mode we are really in. This fixes bug #11499. - -2002-01-04 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_from_url): A few minor - fixes to make it more compliant with rfc2368. Should now be fully - rfc compliant as far as I can tell. - -2002-01-03 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_edit): - Only connect to the parent's destroy/hide signals while the - attachment editor dialog is "alive". - -2001-12-21 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-select-file.c (composer_hide_cb): Only cancel the - selection dialog if it is currently in use, otherwise we'll get an - extra gtk_main_quit and the mailer will exit :-( - -2001-12-17 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (read_file_content): Don't block forever if we - are reading a fifo with no data. - -2001-12-14 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (class_init): Setup the SAVE_DRAFT signal. - (menu_file_save_draft_cb): Emit the SAVE_DRAFT signal. - (exit_dialog_cb): Same here. - (save_draft): Removed. This code is now a signal that - mail-callbacks will connect to. - -2001-12-11 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_edit): - Attach to the parent widget's destroy signal - when that gets - destroyed, we need to cancel the editor dialog too. Also connect - to our parent window's "hide" signal so that when the composer - gets hidden (ie, it's being sent), we also close the dialogs. - - * e-msg-composer.c (init): Default composer->enable_autosave to - TRUE. - -2001-12-11 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-select-file.c (confirm): If multiple-selection is - enabled but nothing is slected, fall back to using the filename in - the entry box as the "selected" file. - (create_file_selection): If the composer gets hidden (ie it's - being "sent") then cancel the file selection dialog. - -2001-12-11 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-select-file.c - (file_selection_info_destroy_notify): If the widget is non-NULL, - then gtk_widget_destroy that bad boy... - -2001-12-10 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (add_from_user): - select_file_attachments now returns a GPtrArray so handle that and - loop until we've added all the attachment files. - - * e-msg-composer-select-file.c (confirm): Add an evil kludge to - get a list of filenames from the GtkFileSelection widget based on - the label in the history option menu item and the base filenames - of the selected items in the filename clist. - (create_file_selection): Setup the clist to allow multiple - selection. - (file_selection_info_destroy_notify): Destroy the GPtrArray - containing the list of xselected files. - (select_file_internal): Return a GPtrArray of files instead of a - char *. - -2001-12-10 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer.c (get_file_content): Only execute an executable - sig file if a magic environment variable is set. - -2001-12-06 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer.c (executed_file_output): Added. Executes the - given file and returns its output as a string. - (get_file_content): Stats the file to see if it is executable. - If it is, execute it and return the string. If not, just read - the file and return the contents. - -2001-11-30 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (setup_ui): Change the FileSend tooltip the be - the same as the FileSendLater tooltip if we are in offline mode. - -2001-11-11 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (drag_data_received): Allow drag & drop for - vcards. - -2001-11-30 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (setup_ui): Change the FileSend tooltip the be - the same as the FileSendLater tooltip if we are in offline mode. - -2001-11-14 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (create_composer): popup failure dialog if we - cannot get a valid editor_engine. - (prepare_engine): make the checks robust and make sure that we - unset the engine if any part fails. - -2001-11-02 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (add_inlined_images): use hash table to - eliminate duplicates - -2001-11-02 <NotZed@Ximian.com> - - * e-msg-composer.c (e_msg_composer_set_enable_autosave): New - function, enable/disable autosave for the composer temporarily. - (autosave_run_foreach_cb): Only save if we have enable autosave - turned on. In other cases we want to save it regardless. - -2001-10-30 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (build_message): Add back the "remove - Content-Disposition when sending itip" hack. - - * Evolution-Composer.idl (setMultipartType): New. - - * evolution-composer.c (impl_Composer_set_multipart_type): Allow - caller to specify a multipart/alternative rather than - multipart/mixed. - - * e-msg-composer.c (build_message): Revert yesterday's changes. - Add new ones for sending multipart/alternative. - -2001-10-30 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.h: add dirty prototype. - - * e-msg-composer.c: add dirty implementation. - -2001-10-30 Radek Doulik <rodo@ximian.com> - - * listener.c (insert_paragraph_before): new helper function, - extracted - (insert_paragraph_after): ditto - (impl_event): process command_before and command_after, use new - functions - (clear_signature): reset style to be sure - (reply_indent): ditto - -2001-10-30 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (build_message): Remove Content-Disposition in - the no_body case. (More kludging around Outlook iCalendar - brokenness.) - -2001-10-29 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer.c (setup_ui): Put the charset encoding submenu in - the EncodingPlaceholder. - -2001-10-29 Dan Winship <danw@ximian.com> - - * evolution-composer.c (init): Set the (new) "no_body" flag on the - composer. - (impl_Composer_set_body_text): And unset it here. - (unset_no_body): And here (called if/when the composer is - realized). - - * e-msg-composer.c (build_message): If the composer has the - "no_body" flag set, and a single attachment, promote that - attachment to be the message body. - -2001-10-30 Radek Doulik <rodo@ximian.com> - - * listener.c (reply_indent): simplified, requires new gtkhtml - -2001-10-29 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.h: add GList to hold the current images. - - * listener.c (resolve_image_url): keep track of the images that - the editor is currently uses in current_images as well as storing - the images in the hash. - - * e-msg-composer.c (clear_current_images): clear the list of - images actually in the message. - (add_inlined_images): use the current image list rather than the - hash tables. - (build_message): clear the current image list when appropriate. - (init): initialize current_images. - -2001-10-24 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (add_attachments_from_multipart): New function - that replaces handle_multpart() and handle_multipart_alternative() - for add_message_attachments(). - (e_msg_composer_add_message_attachments): Call - add_attachments_from_multipart(). - (handle_multipart_alternative): Now only used by - new_with_message() and is really only designed to work well with - messages generated by Evolution (ie for editing Drafts and such). - (handle_multipart): Same. - (e_msg_composer_new_with_message): No longer calls - add_message_attachments() because we can't ever have this fail and - the logic in add_message_attachments() is impossible - logic. Instead do like what we used to do before the addition of - add_message_attachments() came along. - -2001-10-24 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c - (e_msg_composer_add_inline_image_from_mime_part): rework this so - that we don't end up freeing the cid then reading from it. - -2001-10-22 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer-hdrs.c (create_from_optionmenu): Check that - account->id->address != NULL. - -2001-10-21 Dan Winship <danw@ximian.com> - - Make inline images used for replies not show up as - attachments. Also, I think this should make replies to HTML - messages containing inline images referenced via Content-Location - work, but that's not tested. - - * e-msg-composer.c (various): Keep two hash tables of inline image - data: one mapping from cid: URLs to CamelMimeParts for all - attachments, the other mapping from file: and Content-Location - urls to CamelMimeParts (for those inline images that came from a - file or have a Content-Location). - (add_inlined_images): Simplify. Most of this code is in - e_msg_composer_add_inline_image_from_file() now. - (e_msg_composer_add_message_attachments, handle_multipart): Change - "attach_all" arg to "just_inlines". If it is set, call - e_msg_composer_add_inline_image_from_mime_part on any attachment - with a Content-Id or Content-Location. - (e_msg_composer_add_inline_image_from_file): Create a mime part - from a file and add it to the inline images hash. - (e_msg_composer_add_inline_image_from_mime_part): Add a mime part - directly to the inline images hash. - - * listener.c (resolve_image_url): If asked to resolve a file: URL - that isn't in the inline images hash, call - e_msg_composer_add_inline_image_from_file to get a cid for it. - (impl_event): Look up the URL in the inline_images and - inline_images_by_url hashes. - - * e-msg-composer-attachment-bar.c - (e_msg_composer_attachment_bar_find_message): Gone. No longer - used. - -2001-10-19 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (handle_multipart): Now takes a 'attach_all' - argument. If !attach_all, then only attach the attachment if the - part has a content-id, otherwise we can safely assume that nothing - references it thus we don't need to attach it. - (e_msg_composer_add_message_attachments): Now takes a 'attach_all' - argument that overrides the "only attach attachments if they have - a content-id header" behavior. - (e_msg_composer_new_with_message): Pass TRUE as the attach_all - argument to add_message_attachments. - -2001-10-18 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (best_encoding): Don't use a - g_return_val_if_fail after iconv_open, this is a valid error - condition and so should use check it for real. - - * e-msg-composer-attachment-bar.c (attach_to_multipart): Correctly - set the charset parameter and use camel's bestenc filter to - determine which content transfer encoding to use. - -2001-10-15 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (e_msg_composer_add_message_attachments): - s/apply/flush/. - (e_msg_composer_flush_pending_body): renamed from apply now takes - apply as an argument. - (e_msg_composer_show_sig_file): s/g_assert/g_return_if_fail/ - warnings make for less painful bugs than crashes. - (set_editor_text): s/g_assert/g_return_if_fail/ - -2001-10-13 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (autosave_manager_unregister): Don't pop up an - "unable to retrieve message" if the composer never finished - initializing. - (init): Don't call autosave_manager_register here: wait until the - end of create_composer. - (create_composer): Remove the distinction between this and - e_msg_composer_construct since there's no need for the latter. Use - e_activation_failure_dialog if either the selectnames component or - the gtkhtml editor fails. - - * e-msg-composer-hdrs.c (setup_corba): Don't g_warn if the oaf - activation fails. create_composer() will tell the user. - -2001-10-11 Jeffrey Stedfast <fejj@ximian.com> - - * listener.c (impl_event): Deleted declaration of len. - - * e-msg-composer.c (e_msg_composer_add_message_attachments): Take - a settext argument. - (e_msg_composer_new_with_message): Updated to pass the settext argument. - -2001-10-10 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_set_from_account): - Check for either a matching account name, or for a matching e-mail - address embedded in the passed-in string. (Fixes half of bug - #3255) - (destroy): Call bonobo_object_release_unref on corba_select_names, - not CORBA_Object_release. Otherwise we leak stuff all over the - place. (Bug #11878) - - * e-msg-composer.c (e_msg_composer_new_with_message): If our message - doesn't contain an X-Evolution-Account header, pass in the From - header as the account name. (Fixes the other half of #3255) - -2001-10-10 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.h: add prototype. - - * e-msg-composer.c (e_msg_composer_add_message_attachments): new - function to copy attachments from the a message to a composer. - (e_msg_composer_set_pending_body): make simple function to - abstract this. - (e_msg_composer_apply_pending_body): apply the pending body to - the composer. - (e_msg_composer_new_with_message): use - e_msg_composer_add_message_attachments to copy attachments. - -2001-10-09 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (add_from_file): If the - attachment fails, report the error to the user. - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): Now - takes a CamelException argument. - - * e-msg-composer.c (setup_ui): Pass /menu/Edit as the menu path to - e_charset_picker thingy. - -2001-10-05 Larry Ewing <lewing@ximian.com> - - * e-msg-composer-attachment-bar.c - (e_msg_composer_attachment_bar_find_message): fix cut&pasteo. - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - remove unused variable. - - * e-msg-composer-attachment-bar.c - (e_msg_composer_attachment_bar_find_message): generalize this to - lookup content locations as well. - - * e-msg-composer-attachment-bar.h: change prototype to match the - new function. - - * listener.c (impl_event): handle the url_requested event, look up - parts in the attachment part and feed them down the stream if it - is found. - - * e-msg-composer.c (handle_multipart_alternative): delay setting - the body text. - (handle_multipart): delay setting body text - (e_msg_composer_new_with_message): set the body text from the - object data. Doing this ensures that we will have the attachments - processed before we try to look them up. - -2001-10-04 Larry Ewing <lewing@ximian.com> - - * e-msg-composer-attachment-bar.c - (e_msg_composer_attachment_bar_find_content_id): change to return - a CamelMimePart. - - * e-msg-composer-attachment-bar.h: update prototype. - - * e-msg-composer-attachment-bar.c - (e_msg_composer_attachment_bar_find_content_id): look up an - attachment by it's content id. - - * e-msg-composer-attachment-bar.h: add prototype for - e_msg_composer_attachment_bar_find_content_id. - -2001-10-03 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (autosave_save_draft): Make sure to unref the - message object so we don't leak it or any references to - attachments (child mime parts). - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - Unref the mime part after passing it along to new_from_mime_part. - -2001-10-02 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (save_draft): Pass an empty flags argument to - mail_get_folder. - -2001-10-02 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer.c (setup_ui): Use - `bonobo_ui_component_new_default()', not - `bonobo_ui_component_new()'. - -2001-09-27 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - Don't set Content-Ids on these parts since they are not contained - within a multipart/related - this fixes bug #10032. - -2001-09-26 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_from_url): Fixes glitch in - mailto: url parsing that caused it to fail when recipient names - contained commas. (Bug #10796) - -2001-09-20 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (save_draft): Update to reflect changes to - mail_get_folder. - -2001-09-20 Iain Holmes <iain@ximian.com> - - * e-msg-composer.c (get_file_content): Open the file with O_CREAT so - that if it doesn't exist, it's created. Never return a NULL as this - could potentially crash on Solaris. - -2001-09-18 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Attach an X-Evolution-Format - header so if people re-edit a message in say their Sent folder, we - will preserve format preferences. - (e_msg_composer_get_message_draft): Don't attach - X-Evolution-Format headers here since it is now done in - build_message(). - (e_msg_composer_new_with_message): Make sure to remove *all* - X-Evolution headers by using the mail-tools functions. - -2001-09-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (update): Don't - gtk_object_destroy() the pixbuf loader, unref it instead. - - * e-msg-composer-hdrs.c (destroy): Don't forget to free the - private structure. - -2001-09-14 Ettore Perazzoli <ettore@ximian.com> - - [Automake 1.5 fixes pointed out by Richard Boulton - <richard@tartarus.org>, as per #9258.] - - * Makefile.am (CLEANFILES): Set directly with `=' instead of `+='. - -2001-09-13 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (map_default_cb): free the text values we get - from the property bag and release the property bag properly. - -2001-09-12 JP Rosevear <jpr@ximian.com> - - * evolution-composer.c (corba_recipientlist_to_destv): null - terminate the destination vector - -2001-09-10 Jeffrey Stedfast <fejj@ximian.com> - - * evolution-composer.c (init): Don't call new_with_sig_file, it no - longer exists. - - * e-msg-composer.c (setup_ui): Make sure that the session is - non-NULL. - (menu_file_send_cb): And here too. - (e_msg_composer_new_with_sig_file): Removed. - -2001-09-10 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Wrap the S/MIME code in ifdef - SMIME_SUPPORTED which isn't defined but by some later version will - be. - (setup_ui): And again here. - -2001-09-09 Maciej Stachowiak <mjs@noisehavoc.org> - - * Makefile.am: Add VFS_CFLAGS so things don't break when the - gnome-vfs headers move. - -2001-09-08 Jon Trowbridge <trow@ximian.com> - - * evolution-composer.c (corba_recipientlist_to_destv): Originally - was corba_recipientlist_to_glist. - (impl_Composer_set_headers): Use corba_recipientlist_to_destv, new - destination-based api. - - * e-msg-composer.c (build_message): Get rid of that 'sending' - stuff. That was a bad idea. - (e_msg_composer_new_with_message): Apply the revised api and work - with vectors of destinations rather than just lists. - (e_msg_composer_get_recipients): Added. Returns the full set of - recipient destinations in a vector. - - * e-msg-composer-hdrs.c: Removed free_destv function. We use - e_destination_freev instead. - (e_msg_composer_hdrs_get_to): Changed to return a vector of - EDestinations. This function now works. - (e_msg_composer_hdrs_get_cc): Ditto. - (e_msg_composer_hdrs_get_bcc): Ditto. - (e_msg_composer_hdrs_get_recipients): Added. Returns a vector of - EDestinations that is the union of the to, cc and bcc lines. - (e_msg_composer_hdrs_set_to): Changed to take a vector of - EDestinations, rather than a GList. - (e_msg_composer_hdrs_set_cc): Ditto. - (e_msg_composer_hdrs_set_bcc): Ditto. - (e_msg_composer_hdrs_to_message): Use our new, improved API, rather - than a bunch of poking around in BonoboPropertyBags, etc. - -2001-09-07 Dan Winship <danw@ximian.com> - - * e-msg-composer-hdrs.c (set_recipients_from_destv): Remove some - debugging messages that don't check for NULL strings and crash - Solaris. - -2001-09-06 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (save): Have to specify a mode when using - O_CREAT. - (handle_multipart_alternative, handle_multipart, - e_msg_composer_new_with_message): Update for mail_get_message_body - change. - -2001-09-05 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer.c (autosave_manager_query_load_orphans): - s/Evolution/Ximian Evolution/. - (do_exit): Set the title to be "Warning: Modified Message". - -2001-08-29 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer.c (e_msg_composer_get_message_draft): Pass - in FALSE as the 'sending' arg to e_msg_composer_get_message. - (build_message): Added a 'sending' arg, which is passed to - e_msg_composer_get_message. - (e_msg_composer_get_message): Added a 'sending' arg, - which gets passed directly on to build_message. - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_to_message): Added - a "sending" arg, which should be TRUE if the message is being - sent now (rather than being autosaved, etc.). The address - use scores are only updated when sending. (Bug #8332) - Removed obsolete (#if 0/#endif-ed) code. - -2001-08-22 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer-hdrs.c (set_recipients_from_destv): Added. Try - to properly handle contact lists in which the addresses of the - list members should be hidden. - (e_msg_composer_hdrs_to_message): Changed to extract the - destination data from the entries and pass it along to - set_recipients_from_destv. - -2001-08-22 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (save): When reporting an error, use - my_file_name instead of file_name since file_name can be NULL. - -2001-08-21 Ettore Perazzoli <ettore@ximian.com> - - * e-msg-composer.c (autosave_manager_query_load_orphans): - s/attempt recovery/try to recover them/. - -2001-08-19 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (save_draft): Reset the "changed" state to - FALSE after a successful save. - -2001-08-17 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (show_attachments): Toggle the - View->Attachments menu item. This fixes bug #6107. - -2001-07-12 Peter Williams <peterw@ximian.com> - - * e-msg-composer.c (map_default_cb): New function. Figure out - which widget gets the default and assign it. Harder to do than - it sounds. - (e_msg_composer_construct): Hook map_default_cb up to the "map" - signal. - (set_focus_to_editor): Removed. - (set_focus_to_editor_idle): Removed. - -2001-08-10 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer-hdrs.c (set_recipients): Removed comment about - the need to resolve nicknames properly, because we now do that. - -2001-08-09 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (set_focus_to_editor): new helper function, - just setup idle callback to grab focus - (set_focus_to_editor_idle): grab focus for editor, before we have - better solution, it run grab-focus command on editor control - (e_msg_composer_construct): call prepare_engine here, set focus to - editor - -2001-08-10 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (autosave_manager_query_load_orphans): Don't - forget to closedir() when we finish with dir. - -2001-08-09 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (from_changed_cb): Set the smime/pgp - always-sign options when here so it updates when the user changes - his/her identity. - -2001-08-08 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_get_message_draft): Set the - PGP/MIME and S/MIME options to FALSE before getting the message - draft and restore the values afterward. - -2001-08-06 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (add_inlined_image): Use g_basename(). - (setup_ui): Get the default charset from the mail config db. - -2001-08-06 Radek Doulik <rodo@ximian.com> - - * listener.c (impl_event): handle delete event - -2001-07-31 Peter Williams <peterw@ximian.com> - - * e-msg-composer.c (setup_ui): Set the config path for the composer so - that the customize toolbar command works. - -2001-07-31 Jason Leach <jleach@ximian.com> - - * e-msg-composer.c: Use Tuomas' and Jakub's new (and beautiful) - icons for Send and Send Later in the toolbar and menus. - -2001-07-30 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (message_rfc822_dnd): Properly add the - message/rfc822 part. - -2001-07-27 Jason Leach <jleach@ximian.com> - - * e-msg-composer.c (get_signature_html): "-- \n" is 4 chars long, - so when checking if it's already in the sig, strncmp should check - 4 chars, not 3. - -2001-07-26 Peter Williams <peterw@ximian.com> - - * e-msg-composer.c (get_signature_html): Correct our manually inserted - signature dash thingie (it was missing the space). - -2001-07-26 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer-hdrs.c (set_recipients): Get "destinations", - rather than "text" from the entry_widget. (The getters/setters in - the control have been made more symmetric.) - -2001-07-18 Jason Leach <jleach@ximian.com> - - * e-msg-composer-hdrs.c (create_from_optionmenu): Update to the - new way of finding the default account. - -2001-07-18 Iain Holmes <iain@ximian.com> - - * e-msg-composer.c (do_exit): Use a messagebox. - -2001-07-17 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (drag_data_received): Correctly handle - text/uri-list's that contain more than a single file reference. - -2001-07-12 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (menu_changed_charset_cb): Removed a warning - that I don't need anymore. This code is working wonderfully ;-) - -2001-07-10 Kjartan Maraas <kmaraas@gnome.org> - - * e-msg-composer.c: Fix typo. s/sesiion/session/ - -2001-07-09 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (autosave_manager_query_load_orphans): Only ask - once about recovery, assume if they want to recover one file they - want to recover all of them. - -2001-07-09 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Use - camel_internet_address_format_address rather than - camel_address_encode since we want display-friendly addresses. - -2001-07-09 Iain Holmes <iain@ximian.com> - - * e-msg-composer-select-file.c (file_selection_info_destroy_notify): - Unref the file selection dialog when the data is destroyed. - -2001-07-09 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (composer_shutdown): Do the - autosave_manager_unregister at shutdown time instead of destroy - time (by which point the contents of the window, including the - remote editor control, will have already been destroyed). - -2001-07-09 Zbigniew Chyla <cyba@gnome.pl> - - * e-msg-composer-select-file.c: Added missing #include <config.h> to - make translations working. - -2001-07-07 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer-hdrs.c (set_recipients): Make sure that our - destination string (dest_str) is not the empty string before we - try to use it. - -2001-07-06 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (autosave_manager_new): add missing static. - (best_encoding): make sure we don't try to call iconv_open with a - NULL tocode. - (autosave_manager_query_load_orphans): remove zero length orphans - so that they don't clutter things up. - -2001-07-06 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - Convert the filename string to UTF8 before setting it on the - CamelMimePart because that code expects it to be in UTF8. - -2001-07-06 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (autosave_manager_query_load_orphans): only ask - if there are actually contents in the file. Asking about an - emptry fil is not very useful. - (autosave_load_draft): add some sanity chacks. - (autosave_run_foreach_cb): remove debugging warning. - (autosave_manager_new): add a missing static. - -2001-07-06 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (autosave_manager_unregister): make sure we - only remove the file if we think we saved it properly. - (autosave_manager_stop): make sure we set the timeout back to 0 so - that we will restart next time since we stop the timer when there - are no active composers. - (destroy): move this to the beginning of the destroy process. - (autosave_save_draft): add a return value indicating success. - (autosave_manager_register): go ahead and ask next time. - -2001-07-05 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c: add ask argment. - (autosave_manager_query_load_orphans): move the load loop out of - the dir reading loop. - (autosave_manager_new): move initialization out or register. - (autosave_manager_register): protect against recursion with ask. - (init): call new, this still needs to be moved. - -2001-07-05 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (save): Play the "File exists, overwrite?" - game. - (autosave_run_foreach_cb): Change the return val from a gboolean - to void. - -2001-07-04 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (autosave_load_draft): attach send and postpone - handlers. and be more tolerant of errors. - -2001-07-03 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (autosave_save_draft): make sure we seek to the - begining. - - * e-msg-composer.h: remove the timer id. - - * e-msg-composer.c: use autosave manager. - (autosave_save_draft): moved initialization to - autosave_init_file. Only save the buffer if we get a valid - message. - (autosave_load_draft): unlink the old file, we own it now. and - unref the stream when we are done with it. - (autosave_is_owned): check if we own the file, this needs to be - extended to check for other valid processes. - (autosave_query_load_orphans): make this search through the - managers list as it walks the dir. - (autosave_query_load_orphans): make sure we use the full path. - (autosave_run_foreach_cb): timeout foreach handler. - (autosave_run): the timeout function. - (autosave_start): start timer. - (autosave_stop): stop timer. - (autosave_register): register a composer with the autosave manager. - (autosave_unregister): unregister a composer. - (destroy): unregister the composer, everything is okay. - (init): register the composer. - -2001-07-02 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.h: add autosave members. - - * e-msg-composer.c (autosave_query_load_orphans): query the user to - check if they want to load any orphans we've found. - (autosave_query_cb): the dialog callback. - (autosave_is_orphan): test if if a particular file is orphaned. - (autosave_load_draft): load a message from an autosave file. - (autosave_save_draft): save the current buffer to the autosave file. - -2001-07-02 Christopher James Lahey <clahey@ximian.com> - - * Makefile.am (INCLUDES): Added $(BONOBO_CONF_CFLAGS). - -2001-07-02 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): Set the - user-chosen charset. - - * e-msg-composer.c (menu_change_charset_cb): New callback function - to get the user-set charset. - (init): Set the charset to NULL. - (best_charset): Take a default_charset param that holds the value - the user set for this particular message using the menu. - (destroy): Free the charset. - -2001-07-02 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (setup_ui): Construct an e-charset-picker - bonobo-ui menu. - (menu_change_charset_cb): - -2001-06-30 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer-hdrs.c (set_recipients): Touch all of our - EDestinations before we unref them, updating the last-use records - in the addressbook. - -2001-06-29 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (e_msg_composer_show_sig_file): remove now - invalid argument in the documentation. - -2001-06-28 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c: removed obsolete e_msg_composer_get_sig_file - - * e-msg-composer.h: removed sig_file field from EMsgComposer - - * e-msg-composer.c (e_msg_composer_get_sig_file_content): exported - (get_file_content): make it const safe - (e_msg_composer_get_sig_file_content): refactored, don't try to be - clever about signature filename, as it's exact now - (get_signature_html): use has_html_signature flag - (e_msg_composer_show_sig_file): renamed from - e_msg_composer_set_sig_file, removed sig_file parameter as it's - obsolete now - (e_msg_composer_new_with_sig_file): removed obsolete parameters - -2001-06-27 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (menu_file_insert_file_cb): make hook this up. - (get_sig_file_content): use get_file_content. - (get_file_content): make this usable for both insertion and - signatures. - (read_file_content): added helper function to read file. - -2001-06-27 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c: Added a pixcache array for special pixmaps to - use in the composer. - (setup_ui): Set the pixcache. - -2001-06-21 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (menu_file_send_cb): Emit the POSTPONE signal - if we are offline. - (setup_ui): If we are offline, change the Control+Enter accel to - be on the SendLater menu item. - -2001-06-20 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (save_draft): Save the formatting preference - for this message draft using a X-Evolution-Format header. - (e_msg_composer_new_with_message): Restore the format editing - preference and also remove any other X-Evolution-* headers that we - may have set. - -2001-06-20 Dave Camp <dave@ximian.com> - - * Evolution-Composer.idl: Changed attachData to accept a sequence of - chars rather than a string. - - * evolution-composer.c (impl_Composer_attach_data): Changed the 'data' - argument to a GNOME_Evolution_Composer_AttachmentData, and pass - data->_buffer and data->_length to camel_mime_part_set_content(). - -2001-06-19 JP Rosevear <jpr@ximian.com> - - * evolution-composer.c (impl_Composer_send): send the message - - * Evolution-Composer.idl: add a "send" method to send a message - without showing the editor - -2001-06-19 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_construct): Don't define the - drop_types here. - (drag_data_received): Implement message/rfc822 dnd drop type - handling. - -2001-06-12 Dan Winship <danw@ximian.com> - - * e-msg-composer-attachment.glade: Replace the disposition option - menu with a checkbox. - - * e-msg-composer-select-file.c - (e_msg_composer_select_file_attachment): New function to select a - file to attach. Adds a "suggest inline disposition" checkbox. - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): Add - a disposition argument rather than always defaulting to - "attachment". - (struct _DialogData, ok_cb, e_msg_composer_attachment_edit): - Update for optionmenu->checkbox change for disposition. - - * e-msg-composer-attachment-bar.c (add_from_file): Add a - disposition argument. - (add_from_user): Use e_msg_composer_select_file_attachment, pass - chosen disposition to add_from_file. - (e_msg_composer_attachment_bar_attach): Pass "attachment" to - add_from_file for the disposition. - -2001-06-11 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (best_charset): Fix again... don't leave - *encoding uninitialized in the US-ASCII case. - -2001-06-11 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer.c (e_msg_composer_construct): Rearranged - gtk_widget_show()s a bit to fix Bug#3204. The composer is now - (like the rest of Evo) properly network transparent. - -2001-06-08 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer.c (save_draft): When saving a draft, attach - information about the From: identity via X-Evolution-Account. - This lets us select the correct identity when we edit it later. - (e_msg_composer_new_with_message): If the message we are editting - is tagged with an account (via X-Evolution-Account), make sure - that the composer chooses that account's identity by default. - -2001-06-08 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (best_charset): Don't use the default charset - if the message is US-ASCII. - -2001-06-07 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_with_sig_file): just set - sig_file field, but don't actualy insert signature, it will be - done by format menu item callback - (e_msg_composer_set_body_text): don't set signature here - -2001-06-01 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): If user is trying to sign - his/her message, try first to use the key that they might have - provided in their account settings. If that was never set, default - to their email address. Also respect their config option to - encrypt-to-self. - -2001-05-31 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Oops. Fix a few compile problems. - -2001-05-31 Christopher James Lahey <clahey@ximian.com> - - * Makefile.am (HTML_EDITOR_GENERATED): Use GTKHTML_DATADIR here. - -2001-05-31 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Fixed up the S/MIME - signing/encrypting code to work with the new API. - -2001-05-31 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (best_encoding): Add a missing iconv_close - -2001-05-30 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (build_message): Use the config-specified - default character set (which in turn defaults to the locale - character set) as the default for encoding non-US-ASCII messages, - assuming it works. Fall back to camel_charset_best() if it fails. - Also, pick the Content-Transfer-Encoding based on how the data - looks in the destination charset, not in UTF8. - - While I was here, I also refactored a bunch and tried to reduce - redundant code. There are still too many places that set the - transfer-encoding on the plaintext part though... Also, I think - some more cleanliness could happen if the sign/encrypt interfaces - returned CamelMultiparts instead of CamelMimeParts. - -2001-05-28 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (update): Use - e_utf8_to_gtk_string() on the description of the attachment since - camel stores these as utf-8 strings. - -2001-05-28 Jason Leach <jleach@ximian.com> - - * Makefile.am (INCLUDES): srcdir != builddir fix. - -2001-05-24 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Populate the - extra_hdr_* arrays with any non-special-case headers. - (is_special_header): New convenience function to determine if a - header is a "special" header or not. - -2001-05-24 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (menu_edit_delete_all_cb): new callback - (menu_edit_delete_all_cb): set orig to 0 too - (menu_edit_delete_all_cb): be more careful about text color and - style - -2001-05-23 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (e_msg_composer_set_sig_file): set orig to 0 - -2001-05-18 Jon Trowbridge <trow@ximian.com> - - * e-msg-composer-hdrs.c (set_recipients): Properly unserialize the - string returned by the "text" property of the bonobo control, - convert it into EDestinations, and use them to get the e-mail - addresses of our recipients. - -2001-05-17 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (save_draft): Draft messages should be marked - read. - -2001-05-16 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Added S/MIME sign/encrypt code. - (init): Initalize smime_sign/encrypt. - (e_msg_composer_get_smime_encrypt): new - (e_msg_composer_set_smime_encrypt): new - (e_msg_composer_get_smime_sign): new - (e_msg_composer_set_smime_sign): new - (menu_security_smime_sign_cb): new - (menu_security_smime_encrypt_cb): new - (setup_ui): Setup the UI for S/MIME stuff. - -2001-05-10 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): If we are creating a message - with only a single part (ie no attachments and we will not be - signing/encrypting the part) then `part = CAMEL_MIME_PART(message)` - otherwise create a new MIME part and set it's content-object as the - message's content-object at a later date. - -2001-05-09 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (add_inlined_image): Don't wrap content-id with - brackets here as it is now done internally in camel. - -2001-05-03 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (get_signature_html): put signature in 100% - width table - (delete_old_signature): look only for first flow with signature == 1 - (e_msg_composer_new): don't insert <BR> - (e_msg_composer_new_with_sig_file): ditto - (delete_old_signature): don't delete whole signature paragraph, - but just it's content - (delete_old_signature): if signature isn't found, insert new empty - paragraph to end of document for new signature - (e_msg_composer_set_sig_file): delete signature always - (e_msg_composer_set_sig_file): don't place signature to the end of - document, but place it where previous one was (if there wasn't - then new one is appended to the document) - -2001-05-02 Radek Doulik <rodo@ximian.com> - - * listener.c (impl_event): do automagic indenting only when - in_signature_insert is FALSE - - * e-msg-composer.c (e_msg_composer_set_sig_file): do indent-zero - before signature inserting - (e_msg_composer_set_sig_file): use in_signature_insert flag - -2001-05-01 Radek Doulik <rodo@ximian.com> - - * listener.c (impl_event): set signature to 0 in newly created - empty paragraphs - (clear_signature): new helper function - -2001-04-26 Dan Winship <danw@ximian.com> - - * Makefile.am (INCLUDES): Remove UNICODE_CFLAGS - -2001-04-25 Radek Doulik <rodo@ximian.com> - - * e-msg-composer.c (e_msg_composer_set_send_html): block/unblock - redraw - - * listener.c (impl_event): reflect object data type change - - * e-msg-composer.c (get_sig_file_content): renamed from - get_signature - (get_signature_html): new helper function, uses - get_sig_file_content - (set_editor_text): removed signature parameters - (from_changed_cb): new signal handler, sets signature by identity - change - (delete_old_signature): new function, deletes old signature from - the document - (e_msg_composer_set_sig_file): new method, set's signature - filename - (e_msg_composer_mark_text_orig): removed (obsolete) - - * e-msg-composer-hdrs.c: added signal FROM_CHANGED - -2001-04-21 Duncan Mak <duncan@ximian.com> - - * e-msg-composer.c (e_msg_composer_construct): Set window_icon to - "compose-message.png" for the composer window. - - Did #include <libgnomeui/gnome-window-icon.h> so we could use - gnome_window_icon_set_from_file() here. - -2001-04-17 Radek Doulik <rodo@ximian.com> - - * listener.c (reply_indent): more auto-indentation magic - -2001-04-12 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Use the mail-crypto pgp-mime - wrappers. - (build_message): s/CAMEL_PGP_HASH_TYPE_SHA1/CAMEL_CIPHER_HASH_SHA1 - -2001-04-11 Dan Winship <danw@ximian.com> - - * e-msg-composer-select-file.c (create_file_selection): Fix - previous. - -2001-04-11 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-select-file.c (create_file_selection): Set the - default filename to the user's homedir. - -2001-04-04 Kjartan Maraas <kmaraas@gnome.org> - - * e-msg-composer-attachment.c: Fix headers. - * e-msg-composer-hdrs.c: Same here. - -2001-03-29 Kjartan Maraas <kmaraas@gnome.org> - - * e-icon-list.c: Replace #include <gtk/gtk.h> - * e-msg-composer-attachment-bar.c: Replace #include <gnome.h> - * e-msg-composer-attachment-bar.h: Remove #include <gnome.h> - * e-msg-composer-attachment.c: Remove #include <gnome.h> - * e-msg-composer-attachment.h: Same here. - * e-msg-composer-hdrs.c: Replace #include <gnome.h> and <bonobo.h> - * e-msg-composer-hdrs.h: Replace #include <gnome.h> - * e-msg-composer-file.c: #include <gtk/gtkmain.h>, <gtk/gtksignal.h> - * e-msg-composer.c: Replace #include <bonobo.h>, <gnome.h> - * e-msg-composer.h: Replace #include <gnome.h> and <bonobo.h> - * evolution-composer.c: Replace #include <bonobo.h> - * listener.c: Same here. - -2001-03-28 Dan Winship <danw@ximian.com> - - * e-msg-composer.c (save_draft): Use the drafts folder specified - by the account, if possible. Also, fix the setting of "send_html" - after saving the draft in case the user plans to keep editting... - -2001-03-27 Larry Ewing <lewing@ximian.com> - - * e-msg-composer.c (e_msg_composer_set_send_html): set the - FormatHTML property on the editor to let it know the mode. - (e_msg_composer_construct): set the property at construct time. - -2001-03-26 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): Set - the mime part content-id. - -2001-03-19 Radek Doulik <rodo@ximian.com> - - * listener.c (reply_indent): set default text color - -2001-03-17 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_get_reply_to): Make - sure the reply_to text is non-NULL before trying to pass it off to - the address parser. - -2001-03-13 Dan Winship <danw@ximian.com> - - * e-msg-composer-attachment.c (update_mime_type): Use - gnome_vfs_mime_type_from_name rather than gnome_vfs_mime_info, - since the entered filename doesn't have to be a real file on disk. - Deal with it returning NULL too. - (e_msg_composer_attachment_edit): Select the right item in the - inline/attachment menu. - - * e-msg-composer-hdrs.c: s/Pair/EMsgComposerHdrPair/. Namespace! - -2001-03-12 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.h: Added view_replyto member. - - * e-msg-composer.c (e_msg_composer_get_visible_flags): Find out if - we want to view the Reply-To header. - (e_msg_composer_set_view_replyto): A new function to set the state - of the replyto header. - (menu_view_replyto_cb): Callback for setting the ReplyTo state. - (set_config): Make static. - (setup_ui): Setup the ReplyTo bonobo stuff. - (load_from_property_bag): More defaults for the ReplyTo, yay. - (load_from_gnome_config): Again... - (e_msg_composer_get_view_bcc): Implemented. - (e_msg_composer_get_view_cc): Implemented. - (e_msg_composer_get_view_from): Implemented. - (e_msg_composer_get_view_replyto): Implemented. - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_get_reply_to_entry): - New function, yay. - (e_msg_composer_hdrs_get_reply_to): Another new function. - (e_msg_composer_hdrs_set_reply_to): Yet another new function... - (create_headers): Create the reply-to header. - (attach_headers): Attach the reply_to. - (headers_set_visibility): Set the reply_to visibility. - (e_msg_composer_hdrs_to_message): Set the message's reply-to here - based on the user-set reply-to header. - -2001-03-06 Miguel de Icaza <miguel@ximian.com> - - * e-msg-composer.c (set_config): New function. Used to store - integer values into the configuration engine. Handles the case of - Bonobo-conf being installed, or falls back to gnome_config. - - * e-msg-composer-hdrs.c (add_header): Renamed to be - header_new_recipient(). Now we take care of the other cases in - create_headers, which is a lot nicer now. - - (create_optionmenu): Removed extra "name" argument which was not - being used anyways (the only arg passed was From:). - (init): Removed all the redundant NULL initialization by using - nice g_new0 - - (create_headers): New function, much cleaner. - - Use of Pair structure everywhere instead of individual widgets to - keep track of which ones are visible and which ones are not. - - * e-msg-composer.c (setup_ui): Handle ViewFrom and ViewBCC - commands. - (menu_view_bcc_cb, menu_view_from_cb): New functions that - implement the features described. - - (menu_format_html_cb): Removed unrequired test, as - e_msg_composer_set_send_html already optimizes the case of the - state being the same. - (menu_security_pgp_encrypt_cb): Remove redundant code. - (menu_security_pgp_sign_cb): ditto. - -2001-03-02 Jeffrey Stedfast <fejj@ximian.com> - - * e-icon-list.c (icon_new_from_pixbuf): Added a comment reminding - us that we should probably not force a particular font in the icon - caption. - -2001-02-27 Dan Winship <danw@ximian.com> - - * evolution-composer.c (factory_fn): If - !mail_config_is_configured(), give an error and return NULL. - -2001-02-22 Ettore Perazzoli <ettore@ximian.com> - - * Makefile.am (INCLUDES): Add `-I$(top_srcdir)/shell'. - -2001-02-21 Not Zed <NotZed@Ximian.com> - - * e-msg-composer.c (menu_file_save_draft_cb): - (exit_dialog_cb): Use mail_append_mail to save to drafts instead - of custom thread handler. - -2001-02-19 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Handle exceptions a little - nicer and pop up a nice GnomeDialog with the error message - also, - don't return a CamelMimeMessage if it fails to sign/decrypt - because we want to let the user decide what to do based on the - error message he/she gets. - -2001-02-15 Dan Winship <danw@ximian.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_set_from_account): If - @account_name is NULL, pick the default account rather than giving - a g_warning. - - * e-msg-composer.c (e_msg_composer_set_headers): Note in the - doc comment that @from can be NULL if you want the default account - (since there is code that expects this). - -2001-02-13 Jeffrey Stedfast <fejj@ximian.com> - - * evolution-composer.c (corba_recipientlist_to_glist): Use the - camel-internet-address code to format the address rather than - doing it the broken way. - -2001-02-10 Jeffrey Stedfast <fejj@ximian.com> - - * evolution-composer.c (impl_Composer_set_headers): Updated. We - might want to change the corba interface for this to allow setting - the from-address as well. - - * e-msg-composer.c (e_msg_composer_new_with_message): Updated. - (e_msg_composer_set_headers): Now takes a 'From' argument so that - we can try to pre-determine the account the user will want to send - from. - -2001-02-11 Gediminas Paulauskas <menesis@delfi.lt> - - * e-msg-composer-attachment.glade.h: removed. - * e-msg-composer-attachment.glade: do not write strings to above. - * Makefile.am: don't include glade.h in EXTRA_DIST. - -2001-02-10 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): - multipart/* is another mime type we DO NOT want to encode ;-) - -2001-02-06 Christopher James Lahey <clahey@ximian.com> - - * e-msg-composer-hdrs.c (address_button_clicked_cb, add_header): - Set the default argument to - GNOME_Evolution_Addressbook_SelectNames_activateDialog correctly. - -2001-01-30 Larry Ewing <lewing@ximian.com> - - * e-msg-composer-hdrs.c (create_optionmenu): make sure we convert - from utf-8 before creating the option menu items. - -2001-01-25 Jason Leach <jasonleach@usa.net> - - (Moving the flag for has_changed from the Hdrs to the Composer - itself. Providing public methods to set/unset a composer as - changed. Adding attachments now flags the composer as changed) - - * e-msg-composer.c (e_msg_composer_unset_changed): New function. - (e_msg_composer_set_changed): New function. - - * e-msg-composer.c (hdrs_changed_cb): Callback to the new signal, - uses the new composer_set_changed. - (attachment_bar_changed_cb): Add a call to the new - composer_set_changed. - - * e-msg-composer-hdrs.c (class_init): New signal "hdrs_changed" to - tell the parent composer that any of the headers have changed. - (addressbook_entry_changed): emit the new signal here. - (entry_changed): And here. - -2001-01-24 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (menu_security_pgp_encrypt_cb): New callback. - (menu_security_pgp_sign_cb): Another new callback. - (setup_ui): Added initialization for the PGP sign and encrypt - bonobo menu items. - (e_msg_composer_set_pgp_encrypt): Change the Bonobo UI name to - SecurityPGPEncrypt. - (e_msg_composer_set_pgp_sign): Change the Bonobo UI name to - SecurityPGPSign. - -2001-01-21 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Fixed some memory leaks - dealing with content-type temp strings. Also implemented code to - sign and/or encrypt the message if the user has specified that it - should. - -2001-01-20 Jason Leach <jasonleach@usa.net> - - (Fix #1222: doing File->New->Mail Message doesn't include .sig) - - * evolution-composer.c (init): Get the users account information, - see if they've specified a sig file, if they do, create a composer - with that sig. - -2001-01-19 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (create_optionmenu): Use "Full Name - <address>" for the label in the menu rather than the account - name. Specify the account name only if it's not the same as the - address. - -2001-01-19 Jason Leach <jasonleach@usa.net> - - * e-msg-composer-hdrs.c (create_addressbook_entry): Listen for - property bag changes to "entry_changed" on here, which means on - the To, Cc, and Bcc entries. - (addressbook_entry_changed): New function that gets called when - "entry_changed" property is changed (to TRUE). - -2001-01-18 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer.c (build_message): Updated to reflect changes to - e_msg_composer_hdrs_get_from(). - - * e-msg-composer-hdrs.c (set_recipients): Don't do anymore utf8 - conversions, the widget already does this (or should unless there - is brokenness). - (e_msg_composer_hdrs_get_from): Return a CamelInternetAddress like - we should. - (e_msg_composer_hdrs_to_message): Update to reflect changes made - the the above function. - -2001-01-12 Miguel de Icaza <miguel@gnu.org> - - * Makefile.am: Make the composer a standard library, not a libtool - one. Nobody ever uses it as a shared library and it is not - installed. - -2001-01-17 Jason Leach <jasonleach@usa.net> - - (Bug #1192: Set the Composer window title to something useful) - - * e-msg-composer.c (e_msg_composer_construct): Connect up the new - signal here. - (subject_changed_cb): Set the composer window title to the subject - as it's changed, or if it goes blank make it the default "Compose - a message". - - * e-msg-composer-hdrs.c (class_init): Create a new signal - "subject_changed". - (entry_changed): Emit the signal here when the subject entry is - changed. - -2001-01-17 Iain Holmes <iain@ximian.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_edit): - Get the option menu from the XML file. - (ok_cb): Set the attachment disposition depending on the option - menu results. - (option_menu_get_history): Really should have been in GTK at some - point. - - * e-msg-composer-attachment.glade: Add the option menu. - -2001-01-17 Michael Meeks <michael@helixcode.com> - - * evolution-composer.c (enum_objects): comment out for now - to ease compat issues. - (evolution_composer_construct): pass in NULL for the item - handler enum_objects fn + calm warning. - -2001-01-17 JP Rosevear <jpr@ximian.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Use the - to/cc/bcc addresses insted of just the to. - -2001-01-17 Federico Mena Quintero <federico@ximian.com> - - * e-icon-list.[ch]: Ximianified email addresses. - -2001-01-16 Radek Doulik <rodo@helixcode.com> - - * e-msg-composer.c (e_msg_composer_mark_text_orig): publicate - mark_orig_text - (set_editor_text): don't call mark_orig_text, let it for reply - -2001-01-15 Jason Leach <jasonleach@usa.net> - - (Plug leaking the subject string on each message sent) - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_get_subject): Don't - strdup before returning the subject, it's already been strdup'd - from the gtk_object_get(). - -2001-01-13 Jason Leach <jasonleach@usa.net> - - (Fix Bug #1083: Composer IDLs not getting installed) - - * Makefile.am: add @idl and @idl_DATA vars. - -2001-01-12 Jeffrey Stedfast <fejj@ximian.com> - - * e-msg-composer-hdrs.c (create_optionmenu): Oops. Make sure to - attach the item to the menu ;-) - -2001-01-12 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (build_message): Call set_from_account which - means we no longer have to do all the crap involved in formatting - strings into an internet-address. - (e_msg_composer_get_preferred_account): New access function. - - * e-msg-composer-hdrs.c (add_header): case COMBOBOX has changed to - OPTIOMENU. - (create_optionmenu): Update to use an optionmenu of accounts. - (from_changed): New callback for the From optionmenu. - (setup_headers): s/COMBOBOX/OPTIONMENU - (init): Set the account and from_options to NULL. - (e_msg_composer_hdrs_get_from): Updated. - (destroy): free the from_options. - (e_msg_composer_hdrs_set_from_address): Renamed from set_from - because it no longer takes a string arg but rather an account arg. - -2001-01-12 Miguel de Icaza <miguel@ximian.com> - - * e-msg-composer-hdrs.c (add_header): Only attach to "changed" if - the widget is an EEntry. The HEADER_COMBOBOX and the - HEADER_ADDRBOOK are a ComboBox and a remote Bonobo control - respectively. - - * evolution-composer.c (get_object): Move getObject functionality - here from e-msg-composer.c - -2001-01-11 Miguel de Icaza <miguel@ximian.com> - - * e-msg-composer-hdrs.c (create_dropdown_entry): Only set the - popdown strings if we have anything to popdown. - -2001-01-10 Miguel de Icaza <miguel@helixcode.com> - - * evolution-composer.c (evolution_composer_construct): Add an - ItemContainer Bonobo interface to allow client applications to - locate the Message Composer component. - -2001-01-11 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (menu_file_save_draft_cb): New callback to save - draft. Fixes bug #1045. - -2001-01-10 Miguel de Icaza <miguel@helixcode.com> - - * e-msg-composer.c: Removed more UNSAFE stuff. Maybe we should - kill this macro, and have people that want these broken things - define their own macros. - (setup_item_container): Add an ItemContainer bonobo interface to - handle options to the window component. - -2001-01-08 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-hdrs.c (create_dropdown_entry): Updated for new - config code - this time it works! - -2001-01-08 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-hdrs.c (create_dropdown_entry): Reverted back to - old config code temporarily until I get the new config code - working 100%. - -2001-01-07 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-hdrs.c (create_dropdown_entry): Updated to - reflect changes to the mail-config API. - -2001-01-05 Radek Doulik <rodo@helixcode.com> - - * listener.c (impl_event): disable indenting for now, it crashes - editor - -2001-01-03 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (do_exit): If the headers have changed, then - continue with the prompt else just destroy the window. - - * e-msg-composer-hdrs.c (init): Initialize has_changed to FALSE. - (entry_changed): New callback to set the value of has_changed. - (add_header): Attach the "changed" signal. - -2001-01-02 Dan Winship <danw@helixcode.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_edit): - * e-msg-composer-attachment-bar.c (update): Use - header_content_type_simple, not header_content_type_format. - - * e-msg-composer-hdrs.c (create_dropdown_entry): Call - e_utf8_to_gtk_string on the combobox strings. - -2000-12-28 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (handle_multipart_alternative, - handle_multipart, e_msg_composer_new_with_message): Use - CamelContentType instead of GMimeContentField. - - * e-msg-composer-attachment.c (e_msg_composer_attachment_edit): - * e-msg-composer-attachment-bar.c (update, attach_to_multipart): - Use CamelContentType, and use the header_content_type_* functions - rather than operating on the structure by hand. - -2000-12-15 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (e_msg_composer_get_pgp_encrypt): New function - to get whether or not to encrypt the message. - (e_msg_composer_set_pgp_encrypt): New function to set encryption. - (e_msg_composer_get_pgp_sign): New function to get whether or not - to sign the message. - (e_msg_composer_set_pgp_sign): New function to set pgp_sign. - (init): Initialize pgp_sign and pgp_encrypt to FALSE. - -2000-12-14 Christopher James Lahey <clahey@helixcode.com> - - * e-msg-composer-hdrs.c (add_header): Made it so that carriage - return doesn't insert a newline in the subject entry. - -2000-12-12 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-hdrs.c (set_entry): Don't convert the utf-8 - string to a gtkstring because the widget expects to get a utf-8 - string. - -2000-12-12 Dan Winship <danw@helixcode.com> - - * Makefile.am (EXTRA_DIST): Add $(IDLS). (From campd.) - -2000-12-07 Radek Doulik <rodo@helixcode.com> - - * e-msg-composer.c (prepare_engine): added warnings - (prepare_engine): updated to IDL:GNOME/GtkHTML/Editor/Engine:1.0 - - * Makefile.am: renamed HTMLEditor* to Editor*, added Editor-common.c: - $(HTML_EDITOR_GENERATED) rule - -2000-12-05 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (add_recipients): Use camel to construct the - list of recipients rather than just strchr(recips, ',') which is - very prone to errors. - -2000-11-03 Iain Holmes <iain@helixcode.com> - - * e-msg-composer-attachment-bar.c (update): Pass NULL - instead of icon_name to the e_icon_list_append_pixbuf - function. - (init) Take the font size into account when setting the - height of the bar. - -2000-11-02 Iain Holmes <iain@helixcode.com> - - * e-msg-composer-attachment-bar.c (update): Use the - pixbuf_for_mime_type function to get the icon. - (pixbuf_for_mime_type): Functino that searches nautilus/ - and mc/ for icon files. - -2000-11-15 Radek Doulik <rodo@helixcode.com> - - * e-msg-composer.c (prepare_engine): update namespace - - * updates for HTMLEditor API changes - - * e-msg-composer.c: added #include <libgnomevfs/gnome-vfs.h> - - * e-msg-composer.h: e_msg_composer_guess_mime_type renamed and - moved mime_guess_type_from_file_name from camel as it uses VFS - -2000-11-14 Radek Doulik <rodo@helixcode.com> - - * listener.c (reply_indent): rename command to runCommand - - * e-msg-composer.c: updated to HTMLEditor API changes - - * listener.c: updated to HTMLEditor API changes - -2000-11-13 Radek Doulik <rodo@helixcode.com> - - * listener.c (reply_indent): extracted function, does reply - indentation, use updated editor engine api - -2000-11-10 Michael Meeks <michael@helixcode.com> - - * Makefile.am ($(HTML_EDITOR_GENERATED)): rearrnace - includes. - -2000-11-10 Larry Ewing <lewing@helixcode.com> - - * e-msg-composer.c (build_message): set the HTML charset to utf-8 - for all the html message parts. - (build_message): make sure we set the proper encoding on the html - part now that it may contain utf-8 characters - -2000-11-08 Radek Doulik <rodo@helixcode.com> - - * e-msg-composer.c (e_msg_composer_clear_inlined_table): new - function - (destroy): use e_msg_composer_clear_inlined_table, destroy - inlined_images hash table - (get_signature): added in_html arg, it tells if we should use HTML - signature - (set_editor_text): try to use HTML signature - (e_msg_composer_new_with_sig_file): added send_html arg to be able - to use HTML signature - - * listener.c (resolve_image_url): don't add inlined images to - attachement bar - - * e-msg-composer.c (add_inlined_images): new function, adds - inlined images to multipart - (add_inlined_image): helper function, adds one image to multipart - (build_message): store HTML messages with inlined images to - multipart/related - - * e-msg-composer-attachment-bar.c (add_from_file): removed - content_id arg - (e_msg_composer_attachment_bar_attach): likewise - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - removed content_id arg - -2000-11-06 Not Zed <NotZed@HelixCode.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_to_message): Changed - for message api changes. Use camel_address_unformat to convert - the editable->usable. - (set_recipients): Same. Now we set the recipients as - camel_internet_address's. Fixed a memleak indirectly. - (decode_addresses): Removed, no longer needed. - (create_dropdown_entry): We dont want to use _encode(), we want to - _format, as we are displaying the result. We can use the static - function too to avoid the object creation, and the memory leak! - (set_entry): Convert the args to gtk-safe characters, since the - entry doesn't understand utf8. - (set_recipients): And likewise do the reverse when retrieving the - contents of the widget. - -2000-11-06 Larry Ewing <lewing@helixcode.com> - - * e-msg-composer.c (build_message): set the content type on the - plain part of outgoing messages. - (best_content): a helper function to get the best content type for - the attachment. This should probably use the helper functions in - the future. - -2000-11-06 Kjartan Maraas <kmaraas@gnome.org> - - * e-msg-composer-attachment.c: Added #include <config.h> - * e-msg-composer-hdrs.c: s/_HAVE_CONFIG_H/HAVE_CONFIG_H for - working i18n. - -2000-11-04 Radek Doulik <rodo@helixcode.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): fix - test for regular file to !S_ISREG (statbuf.st_mode) - - * listener.c (resolve_image_url): use inline images hash table - - * e-msg-composer.c (init): create inlined images hash table - (destroy): destroy it - (clear_inline_images): helper function, used from - g_hash_table_foreach_remove to destroy one inline image record - - * e-msg-composer.h: added hash table with inlined images url -> - cid info - -2000-11-03 Radek Doulik <rodo@helixcode.com> - - * listener.c (impl_event): updated for API changed - implemented image_url event - (resolve_image_url): new helper function, attaches image to mail - and returns new (resolved) url pointing to mime component - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - added conponent_id parameter - - * e-msg-composer-attachment-bar.c - (e_msg_composer_attachment_bar_attach): added parameter content_id - (add_from_file): likewise - -2000-11-03 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-attachment.c (e_msg_composer_attachment_new): - Don't allow attaching anything but regular files. - -2000-11-03 Federico Mena Quintero <federico@helixcode.com> - - * Makefile.am: Clean the idl-generated files properly. - -2000-11-02 Peter Williams <peterw@helixcode.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): CamelStreamMem - steals our byte array; we can't destroy the byte array explicitly, and - we must unref the stream only when done using the array. - -2000-11-01 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Don't create - the To, Cc, and Bcc lists based only on the address, use both the - name and address and camel_address_encode() them. - -2000-11-01 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): Fix the - CTE kludge, calculate the best mime transfer encoding for the mime - part and use that. Include e-msg-composer-select-file.h - -2000-10-31 Radek Doulik <rodo@helixcode.com> - - * e-msg-composer.c (prepare_engine): new function, tries prepare - editor engine - (mark_orig_text): marks original text in editor - (set_editor_text): call mark_orig_text - (create_composer): call prepare_engine - - * Makefile.am (IDL_GENERATED): added HTMLEditor generated files to - IDL_GENERATED - ($(IDL_GENERATED)): generate also files from HTMLEditor.idl - (libcomposer_la_SOURCES): added listener.[ch] - - * e-msg-composer.h: added editor_engine and editor_listener to - EMsgComposer - - * listener.[ch]: new files, implementation of HTMLEditor::Listener - -2000-10-27 Ettore Perazzoli <ettore@helixcode.com> - - * Makefile.am ($(IDL_GENERATED)): Get `Composer.idl' from - `$(srcdir)' so that it builds with builddir != srcdir. - -2000-10-27 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Fixed my - not-quite-right logic so that we don't accidently set the body - contents using a plain text attachment instead of the actual body - of the message :-) - -2000-10-25 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Populate the - composer with any attachments. - -2000-10-25 Iain Holmes <iain@helixcode.com> - - * e-msg-composer-select-file.c (create_file_selection): Set the - wmclass and wmclass_name for the file selectors so that Sawfish - doesn't make the dialogs the same size as the parent. - -2000-10-25 Dan Winship <danw@helixcode.com> - - * evolution-composer.c (init): Attach send/postpone signal - handlers to the EMsgComposer. - (evolution_composer_factory_init): Take send/postpone signal - handlers as arguments. - -2000-10-23 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c, e-msg-composer-attachment-bar.c: add some - missing _()s. - - * e-msg-composer-address-dialog.*, e-msg-composer-address-entry.*: - Old cruft. Remove. - - * Makefile.am: Update for removed files. - - * e-msg-composer-hdrs.c: Remove e-msg-composer-address-entry.h - include. - - * e-msg-composer.c: Remove e-msg-composer-address-dialog.h include - -2000-10-23 Ariel Rios <ariel@arcavia.com> - - * e-msg-composer-hdrs.c: Include Composer.h - instead of volution-Addressbook-SelectNames.h - -2000-10-22 Dan Winship <danw@helixcode.com> - - * .cvsignore: No, don't ignore Evolution-Addressbook-SelectNames*. - They're not supposed to be there any more. - -2000-10-22 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer-attachment-bar.c (attach_cb): Removed. - (add_from_user): Use `e_msg_composer_select_file()' instead of - doing the file selector widget magic by yourself. - -2000-10-20 Jeffrey Stedfast <fejj@helixcode.com> - - * .cvsignore: Ignore Evolution-Addressbook-SelectNames* - -2000-10-20 Dan Winship <danw@helixcode.com> - - * Evolution-Composer.idl: Evolution::Composer interface - - * evolution-composer.[ch]: Implementation and factory. So - entirely not tested. - - * Makefile.am (libcomposer_la_SOURCES): Add - evolution-composer.[ch] - (IDLS): Update this for Evolution-Composer.idl / Composer.idl - - * main.c: Removed. (Old, dead code) - -2000-10-19 Ettore Perazzoli <ettore@helixcode.com> - - * Makefile.am (glade_data): Add `e-msg-composer-attachment.glade'. - (glade_messages): New. - (EXTRA_DIST): Add `$(glade_messages)'. - -2000-10-19 Michael Meeks <michael@helixcode.com> - - * e-msg-composer.c (create_menubar_file, create_menubar_edit), - (create_menubar_format, create_menubar_view, create_menubar): kill. - (create_toolbar): die. - (setup_ui): impl. - (e_msg_composer_construct): hook in. - (menu_format_html_cb): update. - (menu_view_attachments_activate_cb): ditto. - (destroy): upd. - (e_msg_composer_construct): upd. - (e_msg_composer_set_send_html): upd. - -2000-10-16 Iain Holmes <iain@helixcode.com> - - * e-msg-composer-hdrs.c (init): Don't need the ID anymore. - -2000-10-17 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): If the body - text was NULL, then don't bother turning it into HTML (besides, it - causes a nasty segfault). - -2000-10-15 Dan Winship <danw@helixcode.com> - - * Makefile.am: Move CPPFLAGS flags to INCLUDES to avoid bashing - any CPPFLAGS set at configure time. - -2000-10-14 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-attachment.c (set_entry): If the entry widget is - NULL, obviously we can't set any text on it. - -2000-10-14 Iain Holmes <iain@helixcode.com> - - * e-msg-composer-hdrs.c (init): Create a unique-ish id for this set - of headers, so that only one select-names dialog will be created for - a given set of headers. - (address_button_clicked_cb): Pass the unique-ish id to the activate - dialog command. - -2000-10-13 Larry Ewing <lewing@helixcode.com> - - * e-msg-composer.c (build_message): stop using format_text, - gtkhtml handles this now. - (format_text): function removed. - -2000-10-10 Iain Holmes <iain@helixcode.com> - - * e-icon-list.c: Allow NULL pixbufs, and load the "broken" image - - * e-msg-composer-attachment-bar.c (update): If the image isn't - found load the default text/plain icon. - -2000-10-02 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (build_message): If the body of the message has - 8-bit chars, set the Content-Transfer-Encoding type to the best - encoding. - -2000-10-02 Dan Winship <danw@helixcode.com> - - * e-icon-list.c: fix #include of gnome-canvas-pixbuf.h - -2000-10-02 Iain Holmes <iain@helixcode.com> - - * e-msg-composer-attachment-bar.c: If the description of an attachment - is a blank string, revert to displaying the filename. - -2000-10-01 Iain Holmes <iain@helixcode.com> - - * e-icon-list.c: If you try to add an icon from a file that doesn't - exist put a "Broken icon" image. - - * bad-icon.xpm: Broken icon image. - -2000-10-01 Iain Holmes <iain@helixcode.com> - - * e-msg-composer-attachment-bar.[ch] (update): If the attachment is - an image, then make a thumbnail for it. - Base the attachment bar on e-icon-list instead of gnome-icon-list. - - * e-icon-list.[ch]: New files. These are modified versions of - gnome-icon-list from gnome-libs HEAD that uses gdk-pixbuf instead - of the evil Imlib. - - * e-msg-composer-attachment.[ch]: Add a pixbuf_cache member, to - save us having to generate a thumbnail for the attachment every - time the bar changes. - - * e-msg-composer.c (e_msg_composer_construct): Add dnd support for - files. Drag a file to the composer to add it as an attachment. - -2000-09-28 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (build_message): Check to see if the body has - 8bit chars, if so - set the Content-Transfer-Encoding to 8bit. - Addresses Bugzilla bug #652. - -2000-09-25 Dan Winship <danw@helixcode.com> - - * e-msg-composer-hdrs.c (setup_headers): fix typo in tooltip. - * e-msg-composer.c (create_menubar_file): fix accelerator for - "Save as" to be different from "Save". (Both problems pointed out - by menthos@menthos.com.) - -2000-09-24 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (get_signature): Updated to handle FIFO - streams. - -2000-09-19 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (e_msg_composer_construct): Don't g_error out - if the html-editor-control fails. - (create_composer): New internal function to create and construct a - msg_composer and pop up an error message if it fails. - (e_msg_composer_new, e_msg_composer_new_with_sig_file, - e_msg_composer_new_with_message, e_msg_composer_new_from_url): Use - create_composer, return if it fails, change return type to - EMsgComposer *. - -2000-09-18 Dan Winship <danw@helixcode.com> - - * e-msg-composer-attachment.c (get_mime_type): Use - gnome_vfs_get_file_info. - - * e-msg-composer-attachment-bar.c (update): Use gnome_vfs_mime - functions, not old gnome_mime. - -2000-09-18 Christopher James Lahey <clahey@helixcode.com> - - * Makefile.am: Added $(EXTRA_GNOME_CFLAGS) and - $(EXTRA_GNOME_LIBS). Removed unneeded libraries. - - * e-msg-composer-address-dialog.c, e-msg-composer-address-entry.c, - e-msg-composer-attachment.c, e-msg-composer-hdrs.c, - e-msg-composer.c: Fixed the #include lines to deal properly with - gal. - -2000-09-12 Michael Meeks <michael@helixcode.com> - - * e-msg-composer.c: Update for new UI handler. - -2000-09-12 Larry Ewing <lewing@helixcode.com> - - * e-msg-composer-attachment-bar.c (add_common): add a make sure - the attachment isn't NULL. A more complete fix coming soon. - -2000-09-12 Ettore Perazzoli <ettore@helixcode.com> - - * Makefile.am ($(IDL_GENERATED)): Add space after `-I'. - -2000-09-05 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer.c (create_menubar_format): Accelerate the - `Format' menu with an `o' instead of an `f' [the `f' is already - taken by the "File" menu]. - -2000-09-04 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_with_sig_file): Applied - Jesse's patch that sets the composer's sig_file - -2000-09-02 Lauris Kaplinski <lauris@helixcode.com> - - * e-msg-composer-address-dialog.c: Use e_utf8 wrappers - -2000-09-01 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (e_msg_composer_get_sig_file): This needs to - return a const char * and not a char *, because we're not actually - allocating memory here. - (create_menubar_file): Changed "Send" to "Send Now" and added - "Send Later" - (menu_file_send_later_cb): New callback that emits the POSTPONE - signal (equivalent to "Send Later" - -2000-08-28 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Always - request to import the HTML version if at all possible so that we - maintain formatting and other nifty stuff :-) - -2000-08-28 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_to_message): Set the - "From" address in the CamelMimeMessage. Also updated to use - get_subject to both make our lives easier and prepare for using UTF8 - (e_msg_composer_hdrs_get_subject): Updated to behave similarly to - get_from and return allocated memory (it will have to return - allocated memory once it's converted to use UTF8 anyways) - - * e-msg-composer.c (setup_save_draft): Always set - composer->send_html = TRUE so that formatting is preserved. - -2000-08-24 Lauris Kaplinski <lauris@helixcode.com> - - * e-msg-composer-address-entry.c: Use e_utf8 wrappers - - * e-msg-composer-attachment.c: Use e_utf8 wrappers - - * e-msg-composer-hdrs.c: Use e_utf8 wrappers - -2000-08-24 Peter Williams <peterw@helixcode.com> - - * Makefile.am (INCLUDES): Add builddir/shell so we can - get Evolution.h - -2000-08-12 Michael Meeks <michael@helixcode.com> - - * e-msg-composer.c (get_text): get_text not get_txt. - -2000-08-11 JP Rosevear <jpr@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Use - new config accessors - -2000-08-10 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c: Remove unneeded e-setup.h include - -2000-08-10 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (exit_dialog_cb): Made async - -2000-08-10 Peter Williams <peterw@helixcode.com> - - * e-msg-composer.c (do_exit): Temporarily disable draft saving - while we figure out how to work around Zucchi's new append_message. - -2000-08-10 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_get_from): Return the - text in GtkCombo->entry - -2000-08-09 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-hdrs.c (create_dropdown_entry): Fixed the GList - identity stuff, should now display all configured identities. - -2000-08-09 Christopher James Lahey <clahey@helixcode.com> - - * e-msg-composer-address-dialog.c: Fixed some warnings. - - * e-msg-composer-hdrs.c: Switched the composer to use an EEntry - for the subject field. - - * e-msg-composer.c: Changed the non scaling objects in this vbox - to be FALSE, FALSE instead of FALSE, TRUE. - -2000-08-09 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-hdrs.c (add_header): Modified to allow dropdown - entry-boxes as well (for headers like From:) - (setup_headers): Modified to use the correct enum type. - (create_dropdown_entry): New convenience function to add a - drop-down combo box and fill it in with identities - (init): Set from_entry to NULL - (e_msg_composer_hdrs_get_from): New convenience function to get - the text in the From widget in the composer - (e_msg_composer_hdrs_set_from): New convenience function to set - the From header in the composer - -2000-08-08 JP Rosevear <jpr@helixcode.com> - - * Makefile.am: Fix build by allowing includes for e-table dir - -2000-08-07 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): - s/strcasecmp/g_strcasecmp - - * e-msg-composer.c: s/strncasecmp/g_strncasecmp - this will help - later with building on different platforms :-) - -2000-08-07 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_with_message): Added code - to set the body text based on the CamelMimeMessage. - (set_editor_text): Use lowercase html tags... - -2000-08-07 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c (do_exit): Prompt the user to save their - composition in Drafts. - (set_editor_text): Uhm, use "-- \n" not "--\n" because the space - is called for in the standard - (e_msg_composer_new_with_message): New convenience function that - takes a CamelMimeMessage as an argument. This will be useful when - we code the ability to resume the editing of a message draft (like - in the Drafts folder). - -2000-08-01 JP Rosevear <jpr@helixcode.com> - - * e-msg-composer.h: Constify param - - * e-msg-composer.c (get_signature): Constify param - (set_editor_text): ditto - (e_msg_composer_new_with_sig_file): ditto - -2000-08-01 Peter Williams <peterw@helixcode.com> - - * e-msg-composer.c (set_editor_text): sizeof("--\") != - strlen("--\n"), breaking the test for the signature prefix. - -2000-07-28 JP Rosevear <jpr@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_with_sig_file): New - function to create composer with sig file set. - (e_msg_composer_get_sig_file): New function to get sig file - (e_msg_composer_set_sig_file): New function to set sig file - -2000-07-25 Michael Meeks <michael@helixcode.com> - - * e-msg-composer.c (get_text): add textual exception printout. - (set_editor_text): close pre tags & check for pre-existing - sig separator. - -2000-07-25 Peter Williams <peterw@helixcode.com> - - * e-msg-composer.c (menu_file_insert_file_cb): Mark this function - as FIXME because we're waiting for the HTML Editor Control to - support paste commands. Also some updates for when that happens. - -2000-07-24 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c: Remove GOAD support. - (create_editor): Try to give a more helpful error message when - failing to load the editor control. - -2000-07-23 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer.c (menu_format_html_cb): New callback for the - "Send HTML" menu toggle item. - (create_menubar_format): New. - (create_menubar): Call it. - (create_menubar_options): Removed. - (init): Initialize `send_html' and `attachment_bar_visible' to - FALSE. - (get_signature): Add `void' to the declaration. This is C, not - C++. - (menu_file_close_cb): Renamed from `exit_cb'. - (menu_file_send_cb): Renamed from `send_cb'. - (menu_file_save_as_cb): Renamed from `save_as_cb'. - (menu_file_save_cb): Renamed from `save_cb'. - (menu_file_open_cb): Renamed from `open_cb'. - (menu_file_add_attachment_cb): Renamed from `add_attachment_cb'. - (menu_file_insert_file_cb): Renamed from `insert_file_cb'. - (e_msg_composer_set_send_html): New. - (build_message): Use the `send_html' flag instead of peeking the - `msg_format' gnome-config value directly. - - * e-msg-composer.h: New member `send_html' in `EMsgComposer'. - -2000-07-23 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer.c: Changed to use BonoboUIHandler stuff directly - instead of translating from GnomeUIInfo. - (create_menubar_file): New. - (create_menubar_edit): New. - (create_menubar_view): New. - (create_menubar_options): New. - (create_menubar): Use these functions to set up the menu bar. - (create_toolbar): Use BonoboUIHandler directly instead of - converting from GnomeUIInfo. - (toolbar_view_attachments_clicked_cb): Removed. - (address_dialog_cb): Removed. - (address_dialog_destroy_cb): Removed. - (address_dialog_apply_cb): Removed. - (setup_address_dialog): Removed. - -2000-07-12 Peter Williams <peterw@helixcode.com> - - * e-msg-composer.c: (view_tree) Make the "View Attachments" item - a toggleitem ... so that it can be toggled... - (menu_view_attachments_activate_cb): Treat the widget correctly - and toggle correctly. - -2000-07-10 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer.c (exit_cb): Use it. - (delete_event): New, handler for the "delete_event" signal. - -2000-07-09 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (set_editor_text): Don't load "" into the - editor, because it will cause the editor component to g_warning. - -2000-07-09 Christopher James Lahey <clahey@helixcode.com> - - * e-msg-composer-hdrs.c: Removed the extra frame here. - -2000-07-08 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (create_menubar): Create an empty "Edit" menu - for the editor control to insert itself into. - -2000-07-08 Jeffrey Stedfast <fejj@helixcode.com> - - * .cvsignore: Ignore dynamically created source files - -2000-07-08 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer-hdrs.c (set_entry): New. - (e_msg_composer_hdrs_set_to): Use it. - (e_msg_composer_hdrs_set_cc): Likewise - (e_msg_composer_hdrs_set_bcc): Likewise. - (e_msg_composer_hdrs_get_to): Replace implementation with a - `g_assert_not_reached()'. - (e_msg_composer_hdrs_get_cc): Likewise. - (e_msg_composer_hdrs_get_bcc): Likewise. - - * e-msg-composer.c: Get rid of cut/copy/paste/undo as they - duplicate the editor toolbar and cannot be made to work for all - the widgets anyway. - -2000-07-08 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer-hdrs.c: New member `corba_select_names' in - `EMsgComposerHdrsPrivate'. - (destroy): If not `CORBA_OBJECT_NIL', release. - (init): Init to `CORBA_OBJECT_NIL'. - (setup_corba): New. - (e_msg_composer_hdrs_new): Call it. - (add_entry): Create the entries by using the ::SelectNames - interface. - (address_button_clicked_cb): Activate the dialog through the - ::SelectNames interface. - -2000-06-29 Jeffrey Stedfast <fejj@helixcode.com> - - * e-msg-composer.c: Changed "Exit" to "Close" in the File menu. - This is a little more intuitive as it does not suggest exiting - the application, just says "close this window". - -2000-06-26 Christopher James Lahey <clahey@helixcode.com> - - * Makefile.am: Added e-msg-composer-select-file.h for make - distcheck. - -2000-06-26 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer.c - (load): New. - (open_cb): Use it. - (save): New function. - (save_cb): Implemented by using it. - (save_as_cb): Likewise. - -2000-06-17 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer.c (e_msg_composer_construct): I18N the title bar. - - * Makefile.am (libcomposerinclude_HEADERS): Removed. Move all the - `.h' files into `libcomposer_la_SOURCES' so that they get - distributed, but not installed. - - * e-msg-composer.c (open_cb): New; implement the `Open' command. - (save_as_cb): New; implement the `Save as' command. - (init): Initialize the `persist_file_interface' and - `persist_stream_interface' members to NULL. - (destroy): Release the PersistStream and PersistFile interfaces. - (e_msg_composer_construct): Query the PersistFile and - PersistStream interfaces on the control and save them in the - `persist_file_interface' and `persist_stream_interface' members. - (get_text): Renamed from `get_editor_text'. Get a - @persist_stream_interface instead of querying it a the control. - (build_message): Return NULL if `persist_stream_interface' is nil. - - * e-msg-composer.h: New member `persist_file_interface' in - `EMsgComposer'. - - * e-msg-composer-select-file.c: New. - * e-msg-composer-select-file.h: New. - - * e-msg-composer.c (e_msg_composer_construct): Make the `To:' - entry grab the keyboard focus. - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_get_to_entry): New. - (e_msg_composer_hdrs_get_cc_entry): New. - (e_msg_composer_hdrs_get_bcc_entry): New. - (e_msg_composer_hdrs_get_subject_entry): New. - - * e-msg-composer.c (e_msg_composer_construct): Set the scroll - frame's shadow type to `GTK_SHADOW_IN'. - (format_text): Initialize `tabbing' to zero to shut down the - compiler. - -2000-06-14 Dan Winship <danw@helixcode.com> - - * e-msg-composer-attachment-bar.c (add_from_user): keep the - GtkFileSelection around between calls so we start up in the same - directory we ended up in last time around. (Also fixes a big - memory leak in that the code was already keeping the - GtkFileSelection around, it just wasn't remembering to reuse it.) - - * e-msg-composer.c (format_text): Don't line-wrap lines that start - with ">". - -2000-06-12 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (format_text): If a paragraph starts with TABs, - indent the whole paragraph to that tab level. - -2000-06-12 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer.c: Make the `attachment_scroll_frame' an - `EScrollFrame'. - (exit_cb): I18N the quit message. - - * e-msg-composer.h: `attachment_scrolled_window' renamed to - `attachment_scroll_frame'. - -2000-06-12 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (format_text): Don't break on non-breaking - spaces, don't keep non-breaking spaces that fall after a line - wrap, and translate non-breaking spaces to regular ones after - wrapping. - -2000-06-05 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (e_msg_composer_attach): New convenience - function. - - * e-msg-composer-attachment.c: Store a CamelMimePart rather than - filename/description/mime_type info. Also record whether we were - told or guessed the MIME type. - (e_msg_composer_attachment_new_from_mime_part): New constructor. - (e_msg_composer_attachment_edit): Remove the "browse" button. (If - the user wants to change the actual file that the attachment is - based on, he should delete the attachment and create a new one...) - Remove the "Apply" button, because it's not all that useful. Make - the MIME type only track the filename if it was guessed rather - than being provided. - - * e-msg-composer-attachment.glade: Remove "browse" and "apply" - buttons. Make filename editable. - - * e-msg-composer-attachment-bar.c (sort): Removed. Send the - attachments in the order the user attached them in. - (text_changed): Removed, since we weren't enabling the relevant - GnomeIconList functionality that would have used this. - (update): Don't print the size if it's 0. - (attach_to_multipart, etc): adjust for EMsgComposerAttachment - changes. - (attach_to_multipart): Use 7bit encoding for message/ subparts. - (e_msg_composer_attachment_bar_attach_mime_part): New convenience - function. - - -2000-06-02 Christopher James Lahey <clahey@helixcode.com> - - * e-msg-composer.c: Added the ability to save plain text mail. - -2000-05-29 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (get_editor_text): add a "format" argument so - we can fetch different kinds of text. - (format_text): New function to do line wrapping on plain text. - (build_message): Build multipart/alternative messages rather than - HTML-only ones. Yay. We don't suck (as much) any more! - -2000-05-28 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c: #include <errno.h> - -2000-05-26 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (get_editor_text, set_editor_text): Update for - PersistStream changes - (build_message): Update for CamelMultipart changes. - - * e-msg-composer.c (get_signature): routine to read the user's - signature file. - (set_editor_text): If the user has configured a signature, append - it to the set text. - (e_msg_composer_new): Call set_editor_text with "" to load the - signature (if any). - -2000-05-25 Not Zed <NotZed@HelixCode.com> - - * e-msg-composer.c (build_message): Use camel_data_wrapper_new - instead of camel_simple_data_wrapper_new. - -2000-05-17 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (build_message): Use - camel_simple_data_wrapper_new rather than camel_data_wrapper_new. - -2000-05-13 Valek Filippov <frob@df.ru> - - * e-msg-composer-attachment.glade: save translatable strings - * e-msg-composer-attachment.glade.h: file with strings - * e-msg-composer-address-dialog.glade: save translatable strings - * e-msg-composer-address-dialog.glade.h: file with strings - -2000-05-12 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (get_editor_text): NUL-terminate the data - extracted from the BonoboStream. - -2000-05-10 Dan Winship <danw@helixcode.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): deal with - Content-Transfer-Encoding a little bit at least. - -2000-05-07 Mathieu Lacage <mathieu@gnu.org> - - * e-msg-composer.c (create_editor): remove FIXME and hardcoded - string. You can write mails with OAF now. - -2000-05-07 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (build_message): unref content, etc. after - attaching it to message. - - * e-msg-composer-attachment-bar.c (attach_to_multipart): unref - part after attaching it. - -2000-05-06 Christopher James Lahey <clahey@helixcode.com> - - * e-msg-composer-hdrs.c: Turned off focus in the To, Cc, and Bcc - buttons. - -2000-05-02 Matt Loper <matt@helixcode.com> - - * Makefile.am: set G_LOG_DOMAIN. - -2000-04-28 Dan Winship <danw@helixcode.com> - - * e-msg-composer-hdrs.c (set_recipients): Update (minimally) for - Camel recipient changes. - -2000-04-27 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new_from_url): New routine, to - process mailto URLs. - -2000-04-26 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (build_message): Only generate a multipart - message if there are attachments. Otherwise generate a single - part. - - * Update for CamelMimeBodyPart -> CamelMimePart - -2000-04-26 Dan Winship <danw@helixcode.com> - - * e-msg-composer-attachment-bar.c (attach_to_multipart): add a - s/SIMPLE_// that notzed missed. Update to use - camel_mime_part_set_content. - * e-msg-composer.c (build_message): remove a now-unused variable. - Update for camel_mime_part_set_content. - -2000-04-26 NotZed <NotZed@HelixCode.com> - - * e-msg-composer.c (build_message): Use camel_mime_part_set_text() - to set the text rather than messing with data wrappers. - - * e-msg-composer-attachment-bar.c (attach_to_multipart): Change - for new camel-stream interfaces. - (attach_to_multipart): Also set base64 encoding by default. - -2000-04-25 Radek Doulik <rodo@helixcode.com> - - * e-msg-composer.c (create_editor): use uih here - (e_msg_composer_construct): create menubar/toolbar before creating - editor control - -2000-04-23 Dan Winship <danw@helixcode.com> - - * Makefile.am: build libcomposer static and don't install it. - - * e-msg-composer-attachment-bar.c (attach_to_multipart): This was - only half-implemented. Finish it, mostly. - -2000-04-22 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (e_msg_composer_add_header): new function to - make the composer record additional headers it should output. - (In-Reply-To), etc. - (build_message): output them - -2000-04-21 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (e_msg_composer_set_headers): - (e_msg_composer_set_body_text): new functions - (exit_cb): Connect "Exit" menu item finally. - - * e-msg-composer-hdrs.c: const poisoning - (e_msg_composer_hdrs_set_subject): - (e_msg_composer_hdrs_get_subject): new functions - - * e-msg-composer-address-entry.c: const poisoning - -2000-04-20 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (get_editor_text, set_editor_text): new - functions to get and set the contents of the HTML editor via - Bonobo::PersistStream. - (build_message): use get_editor_text. This works again. - -2000-04-17 Dan Winship <danw@helixcode.com> - - * e-msg-composer.c (build_message): Change - camel_mime_message_new_with_session to camel_mime_message_new - -2000-03-17 bertrand <bertrand@helixcode.com> - - * e-msg-composer.c (create_menubar): Pass the composer as the data - for the menubar callbacks. - -2000-03-12 Matt Loper <matt@helixcode.com> - - * Makefile.am: Modified to make the composer into a library, to be - used by the mail component. - -2000-03-07 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer.c (create_toolbar): Pass the composer as the data - for the toolbar callbacks. - (e_msg_composer_construct): Connect the "changed" signal of the - attachment bar to `attachment_bar_changed()'. - (attachment_bar_changed): Renamed to `attachment_bar_changed_cb'. - -2000-03-02 Ettore Perazzoli <ettore@helixcode.com> - - * e-msg-composer.c (e_msg_composer_new): Precondition: - gtk_main_level() greater than zero. - (e_msg_composer_construct): Likewise. - (create_menus): New function. Set up menus through - BonoboUIHandler. - (e_msg_composer_construct): Use it. - - * main.c (main): Initialize Bonobo. - - * e-msg-composer.c (init): Initialize `uih' and `editor' to NULL. - Do not init `text' and `text_scrolled_window' anymore. - (destroy): Unref `uih'. - (e_msg_composer_construct): Create a new BonoboUIHandler and put - it into `uih'. - (create_editor): New helper function. - (e_msg_composer_construct): Use it to set up the editor. - - * e-msg-composer.h: New member `uih' in `EMsgComposer'. Removed - members `text', `text_scrolled_window'. New member `editor'. - - * Makefile.am (INCLUDES): Add `$(BONOBO_GNOME_CFLAGS)'. - (evolution_msg_composer_LDADD): Add `$(BONOBO_GNOME_LIBS)'. - - * e-msg-composer.c (glade_connect): Removed. - (setup_signals): Removed. - (e_msg_composer_construct): Do not use libglade to set the toolbar - and menubar up. - (destroy): Removed libglade stuff. - (init): Likewise. - - * e-msg-composer.h: Removed `menubar_gui', `toolbar_gui', - `appbar_gui'. - - * e-msg-composer.glade: Removed. - -2000-01-12 bertrand <bertrand@helixcode.com> - - * Makefile.am (evolution_msg_composer_LDADD): - use $(EXTRA_GNOME_LIBS_THREADS) to link with gthread - -1999-11-17 Ettore Perazzoli <ettore@gnu.org> - - * Makefile.am: New Makefile to compile the message composer - executable. - - * main.c: New file. - - * e-msg-composer-hdrs.c (e_msg_composer_hdrs_to_message): Use - `CAMEL_RECIPIENT*' macros instead of the old `RECIPIENT*' ones - that do not exist anymore. - - * e-msg-composer-address-dialog.c - (e_msg_composer_address_dialog_construct): Use `E_GLADEDIR' - instead of `E_GUIDIR'. - * e-msg-composer-attachment.c (e_msg_composer_attachment_edit): - Likewise. - * e-msg-composer.c (e_msg_composer_construct): Likewise. - -(See `$(top_srcdir)/widgets/ChangeLog' for previous changes to the -message composer.) diff --git a/composer/Composer.idl b/composer/Composer.idl deleted file mode 100644 index a6cb35c037..0000000000 --- a/composer/Composer.idl +++ /dev/null @@ -1,4 +0,0 @@ -/* -*- Mode: IDL; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ - -#include <Evolution-Addressbook-SelectNames.idl> -#include <Evolution-Composer.idl> diff --git a/composer/Evolution-Composer.idl b/composer/Evolution-Composer.idl deleted file mode 100644 index 5dc62a3317..0000000000 --- a/composer/Evolution-Composer.idl +++ /dev/null @@ -1,141 +0,0 @@ -/* -*- Mode: IDL; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* - * Evolution-Composer.idl: Mail composer interfaces for Evolution - * - * Author: - * Dan Winship <danw@ximian.com> - * - * (C) 2000 Ximian, Inc. - */ - -#include <Bonobo.idl> - -module GNOME { -module Evolution { - - interface Composer : Bonobo::Unknown { - struct Recipient { - string name; /* UTF-8 */ - string address; - }; - typedef sequence<Recipient> RecipientList; - - typedef sequence<char> AttachmentData; - - enum MultipartType { - MIXED, - ALTERNATIVE - }; - - /** - * setHeaders: - * @from: the "From" account or address - * @to: the "To" recipients - * @cc: the "CC" recipients - * @bcc: the "Bcc" recipients - * @subject: the subject of the message - * - * Sets the composer headers. Any of @to, @cc, and - * @bcc may be an empty list, and @subject may be an - * empty string. If @from is empty or invalid, the - * default account will be used. Otherwise is - * specifies an account name or email address to send - * from. - **/ - void setHeaders (in string from, in RecipientList to, - in RecipientList cc, in RecipientList bcc, - in string subject); - - /** - * setMultipartType: - * @type: a multipart subtype - * - * Sets the kind of multipart message that is being - * created. - * - * If @type is MIXED (the default), setBody() - * will create the body, and attachMIME() and - * attachData() will create attachments. - * - * If @type is ALTERNATIVE, setBody() will create - * text/plain alternative, and each following - * attachMIME() or attachData() call will create - * another alternative. - * - * Other values of @type are not currently supported, - * although "related" probably should be. - **/ - void setMultipartType (in MultipartType type); - - /** - * setBody: - * @body: the body - * @mime_type: the MIME type of @body - * - * Sets the body of the composer to @body. If - * @mime_type is something other than "text/plain" or - * "text/html", the composer will not be editable - * and it will not attempt to assign a non-UTF8 - * character set to the data. However, @mime_type may - * include parameters in that case. - **/ - void setBody (in string body, in string mime_type); - - /** - * attachMIME: - * @data: the attachment data - * - * This adds an attachment to the composer. @data - * should be a fully-formed MIME body part. - **/ - exception CouldNotParse {}; - void attachMIME (in string data) - raises (CouldNotParse); - - /** - * attachData: - * @content_type: the Content-Type header - * @filename: the suggested filename, or "" - * @description: a description of the data, or "" - * @show_inline: whether the attachment should be - * displayed inline or not. - * @data: the raw attachment data - * - * This adds @data as an attachment, using the provided - * information to generate MIME headers. @content_type - * may contain just a MIME content type, or it may - * contain a complete Content-Type header. @filename - * is a filename for the Content-Disposition header - * @description (if not "") provides the - * Content-Description, and @show_inline determines if the - * Content-Disposition is "inline" or "attachment". - * - * If you need to specify headers or values other than - * what this function can do, you will need to generate - * all of the MIME headers yourself and use - * add_attachment (). - **/ - void attachData (in string content_type, - in string filename, - in string description, - in boolean show_inline, - in AttachmentData data); - - /** - * show: - * - * Shows the composer and lets the user edit things - * and send the message. - **/ - void show (); - - - /** - * send: - * - * Send the message without showing the user the composer - **/ - void send (); - }; -}; -}; diff --git a/composer/Makefile.am b/composer/Makefile.am deleted file mode 100644 index fcd91d787c..0000000000 --- a/composer/Makefile.am +++ /dev/null @@ -1,87 +0,0 @@ -## CORBA stuff - -IDLS = \ - Evolution-Composer.idl \ - Composer.idl - -IDL_GENERATED = \ - Composer.h \ - Composer-common.c \ - Composer-skels.c \ - Composer-stubs.c - -HTML_EDITOR_GENERATED = \ - Editor.h \ - Editor-common.c \ - Editor-skels.c \ - Editor-stubs.c - -selectnamesdir = $(top_srcdir)/addressbook/gui/component/select-names - -$(IDL_GENERATED): $(IDLS) $(selectnamesdir)/Evolution-Addressbook-SelectNames.idl - $(ORBIT_IDL) -I $(srcdir) -I $(datadir)/idl $(IDL_INCLUDES) \ - -I $(selectnamesdir) $(srcdir)/Composer.idl - -Editor-commmon.c: $(GTKHTML_DATADIR)/Editor.idl - -$(HTML_EDITOR_GENERATED): $(GTKHTML_DATADIR)/Editor.idl - $(ORBIT_IDL) -I $(srcdir) $(IDL_INCLUDES) -I $(GTKHTML_DATADIR)/gtkhtml $(GTKHTML_DATADIR)/Editor.idl - -## - -idl_DATA = $(IDLS) - -glade_DATA = \ - e-msg-composer-attachment.glade - -noinst_LTLIBRARIES = libcomposer.la - -INCLUDES = \ - -I$(top_srcdir) \ - -I$(top_builddir) \ - -I$(top_srcdir)/widgets \ - -I$(top_builddir)/widgets \ - -I$(top_srcdir)/camel \ - -I$(top_builddir)/camel \ - -I$(top_srcdir)/addressbook/backend \ - -I$(top_builddir)/addressbook/backend \ - -I$(top_builddir)/addressbook/gui/component/select-names \ - -I$(top_builddir)/shell \ - -I$(top_srcdir)/shell \ - -DEVOLUTION_DATADIR=\"$(datadir)\" \ - -DEVOLUTION_IMAGESDIR=\"$(imagesdir)\" \ - -DEVOLUTION_UIDIR=\"$(evolutionuidir)\" \ - -DEVOLUTION_GLADEDIR=\"$(gladedir)\" \ - -DPREFIX=\"$(prefix)\" \ - -DG_LOG_DOMAIN=\"composer\" \ - -DG_DISABLE_DEPRECATED \ - $(EVOLUTION_MAIL_CFLAGS) - -libcomposer_la_SOURCES = \ - $(IDL_GENERATED) \ - $(HTML_EDITOR_GENERATED) \ - e-msg-composer-attachment-bar.c \ - e-msg-composer-attachment-bar.h \ - e-msg-composer-attachment.c \ - e-msg-composer-attachment.h \ - e-msg-composer-hdrs.c \ - e-msg-composer-hdrs.h \ - e-msg-composer-select-file.c \ - e-msg-composer-select-file.h \ - e-msg-composer.c \ - e-msg-composer.h \ - evolution-composer.c \ - evolution-composer.h \ - listener.c \ - listener.h - -EXTRA_DIST = \ - $(glade_DATA) \ - $(IDLS) \ - ChangeLog.pre-1-4 - -BUILT_SOURCES = $(IDL_GENERATED) $(HTML_EDITOR_GENERATED) -CLEANFILES = $(BUILT_SOURCES) - -dist-hook: - cd $(distdir); rm -f $(BUILT_SOURCES) diff --git a/composer/bad-icon.xpm b/composer/bad-icon.xpm deleted file mode 100644 index 0a9cac23cd..0000000000 --- a/composer/bad-icon.xpm +++ /dev/null @@ -1,53 +0,0 @@ -/* XPM */ -static char * bad_icon_xpm[] = { -"48 48 2 1", -" g None", -". g #000000", -"................................................", -". .", -". .", -". .", -". .", -". .", -". .", -". .", -". .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". .. .", -". .. .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". . . .", -". .", -". .", -". .", -". .", -". .", -". .", -"................................................"}; diff --git a/composer/e-msg-composer-attachment-bar.c b/composer/e-msg-composer-attachment-bar.c deleted file mode 100644 index 9e7b42dfca..0000000000 --- a/composer/e-msg-composer-attachment-bar.c +++ /dev/null @@ -1,850 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* - * Authors: Ettore Perazzoli <ettore@ximian.com> - * Jeffrey Stedfast <fejj@ximian.com> - * - * Copyright 1999-2002 Ximian, Inc. (www.ximian.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA. - * - */ - - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <string.h> -#include <gtk/gtk.h> -#include <glade/glade.h> -#include <gconf/gconf.h> -#include <gconf/gconf-client.h> -#include <libgnome/gnome-util.h> -#include <libgnomeui/gnome-app.h> -#include <libgnomeui/gnome-app-helper.h> -#include <libgnomeui/gnome-popup-menu.h> -#include <libgnomevfs/gnome-vfs-mime-handlers.h> - -#include "e-msg-composer.h" -#include "e-msg-composer-select-file.h" -#include "e-msg-composer-attachment.h" -#include "e-msg-composer-attachment-bar.h" - -#include <gal/util/e-iconv.h> - -#include <camel/camel-data-wrapper.h> -#include <camel/camel-stream-fs.h> -#include <camel/camel-stream-null.h> -#include <camel/camel-stream-filter.h> -#include <camel/camel-mime-filter-bestenc.h> -#include <camel/camel-mime-part.h> - -#include "e-util/e-gui-utils.h" - -#define ICON_WIDTH 64 -#define ICON_SEPARATORS " /-_" -#define ICON_SPACING 2 -#define ICON_ROW_SPACING ICON_SPACING -#define ICON_COL_SPACING ICON_SPACING -#define ICON_BORDER 2 -#define ICON_TEXT_SPACING 2 - - -static GnomeIconListClass *parent_class = NULL; - -struct _EMsgComposerAttachmentBarPrivate { - GList *attachments; - guint num_attachments; - - GtkWidget *context_menu; - GtkWidget *icon_context_menu; -}; - - -enum { - CHANGED, - LAST_SIGNAL -}; - -static guint signals[LAST_SIGNAL] = { 0 }; - - -static void update (EMsgComposerAttachmentBar *bar); - - -static char * -size_to_string (gulong size) -{ - char *size_string; - - /* FIXME: The following should probably go into a separate module, as - we might have to do the same thing in other places as well. Also, - I am not sure this will be OK for all the languages. */ - - if (size < 1e3L) { - size_string = NULL; - } else { - gdouble displayed_size; - - if (size < 1e6L) { - displayed_size = (gdouble) size / 1.0e3; - size_string = g_strdup_printf (_("%.0fK"), displayed_size); - } else if (size < 1e9L) { - displayed_size = (gdouble) size / 1.0e6; - size_string = g_strdup_printf (_("%.0fM"), displayed_size); - } else { - displayed_size = (gdouble) size / 1.0e9; - size_string = g_strdup_printf (_("%.0fG"), displayed_size); - } - } - - return size_string; -} - -/* Attachment handling functions. */ - -static void -free_attachment_list (EMsgComposerAttachmentBar *bar) -{ - EMsgComposerAttachmentBarPrivate *priv; - GList *p; - - priv = bar->priv; - - for (p = priv->attachments; p != NULL; p = p->next) - g_object_unref (p->data); - - priv->attachments = NULL; -} - -static void -attachment_changed_cb (EMsgComposerAttachment *attachment, - gpointer data) -{ - update (E_MSG_COMPOSER_ATTACHMENT_BAR (data)); -} - -static void -add_common (EMsgComposerAttachmentBar *bar, - EMsgComposerAttachment *attachment) -{ - g_return_if_fail (attachment != NULL); - - g_signal_connect (attachment, "changed", - G_CALLBACK (attachment_changed_cb), - bar); - - bar->priv->attachments = g_list_append (bar->priv->attachments, - attachment); - bar->priv->num_attachments++; - - update (bar); - - g_signal_emit (bar, signals[CHANGED], 0); -} - -static void -add_from_mime_part (EMsgComposerAttachmentBar *bar, - CamelMimePart *part) -{ - add_common (bar, e_msg_composer_attachment_new_from_mime_part (part)); -} - -static void -add_from_file (EMsgComposerAttachmentBar *bar, - const char *file_name, - const char *disposition) -{ - EMsgComposerAttachment *attachment; - EMsgComposer *composer; - CamelException ex; - GtkWidget *dialog; - - camel_exception_init (&ex); - attachment = e_msg_composer_attachment_new (file_name, disposition, &ex); - if (attachment) { - add_common (bar, attachment); - } else { - composer = E_MSG_COMPOSER (gtk_widget_get_toplevel (GTK_WIDGET (bar))); - dialog = gtk_message_dialog_new(GTK_WINDOW(composer), - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT, - GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, - "%s", camel_exception_get_description (&ex)); - gtk_dialog_run(GTK_DIALOG(dialog)); - gtk_widget_destroy(dialog); - camel_exception_clear (&ex); - } -} - -static void -remove_attachment (EMsgComposerAttachmentBar *bar, - EMsgComposerAttachment *attachment) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT_BAR (bar)); - g_return_if_fail (g_list_find (bar->priv->attachments, attachment) != NULL); - - bar->priv->attachments = g_list_remove (bar->priv->attachments, - attachment); - bar->priv->num_attachments--; - if (attachment->editor_gui != NULL) { - GtkWidget *dialog = glade_xml_get_widget (attachment->editor_gui, "dialog"); - g_signal_emit_by_name (dialog, "response", GTK_RESPONSE_CLOSE); - } - - g_object_unref(attachment); - - g_signal_emit (bar, signals[CHANGED], 0); -} - - -/* Icon list contents handling. */ - -static void -update (EMsgComposerAttachmentBar *bar) -{ - EMsgComposerAttachmentBarPrivate *priv; - GnomeIconList *icon_list; - GList *p; - - priv = bar->priv; - icon_list = GNOME_ICON_LIST (bar); - - gnome_icon_list_freeze (icon_list); - - gnome_icon_list_clear (icon_list); - - /* FIXME could be faster, but we don't care. */ - for (p = priv->attachments; p != NULL; p = p->next) { - EMsgComposerAttachment *attachment; - CamelContentType *content_type; - char *size_string, *label; - GdkPixbuf *pixbuf; - gboolean image; - const char *desc; - - attachment = p->data; - content_type = camel_mime_part_get_content_type (attachment->body); - /* Get the image out of the attachment - and create a thumbnail for it */ - image = camel_content_type_is (content_type, "image", "*"); - - if (image && attachment->pixbuf_cache == NULL) { - CamelDataWrapper *wrapper; - CamelStreamMem *mstream; - GdkPixbufLoader *loader; - gboolean error = TRUE; - - wrapper = camel_medium_get_content_object (CAMEL_MEDIUM (attachment->body)); - mstream = (CamelStreamMem *) camel_stream_mem_new (); - - camel_data_wrapper_decode_to_stream (wrapper, (CamelStream *) mstream); - - /* Stream image into pixbuf loader */ - loader = gdk_pixbuf_loader_new (); - error = !gdk_pixbuf_loader_write (loader, mstream->buffer->data, mstream->buffer->len, NULL); - gdk_pixbuf_loader_close (loader, NULL); - - if (!error) { - int ratio, width, height; - - /* Shrink pixbuf */ - pixbuf = gdk_pixbuf_loader_get_pixbuf (loader); - width = gdk_pixbuf_get_width (pixbuf); - height = gdk_pixbuf_get_height (pixbuf); - if (width >= height) { - if (width > 48) { - ratio = width / 48; - width = 48; - height = height / ratio; - } - } else { - if (height > 48) { - ratio = height / 48; - height = 48; - width = width / ratio; - } - } - - attachment->pixbuf_cache = gdk_pixbuf_scale_simple - (pixbuf, - width, - height, - GDK_INTERP_BILINEAR); - } else { - g_warning ("GdkPixbufLoader Error"); - image = FALSE; - } - - /* Destroy everything */ - g_object_unref (loader); - camel_object_unref (mstream); - } - - desc = camel_mime_part_get_description (attachment->body); - if (!desc || *desc == '\0') - desc = camel_mime_part_get_filename (attachment->body); - - if (!desc) - desc = _("attachment"); - - if (attachment->size - && (size_string = size_to_string (attachment->size))) { - label = g_strdup_printf ("%s (%s)", desc, size_string); - g_free (size_string); - } else - label = g_strdup (desc); - - if (image) { - gnome_icon_list_append_pixbuf (icon_list, attachment->pixbuf_cache, NULL, label); - } else { - char *mime_type; - - mime_type = camel_content_type_simple (content_type); - pixbuf = e_icon_for_mime_type (mime_type, 48); - g_free (mime_type); - gnome_icon_list_append_pixbuf (icon_list, pixbuf, NULL, label); - if (pixbuf) - g_object_unref (pixbuf); - } - - g_free (label); - } - - gnome_icon_list_thaw (icon_list); -} - -static void -remove_selected (EMsgComposerAttachmentBar *bar) -{ - GnomeIconList *icon_list; - EMsgComposerAttachment *attachment; - GList *attachment_list, *p; - int num; - - icon_list = GNOME_ICON_LIST (bar); - - /* Weee! I am especially proud of this piece of cheesy code: it is - truly awful. But unless one attaches a huge number of files, it - will not be as greedy as intended. FIXME of course. */ - - attachment_list = NULL; - p = gnome_icon_list_get_selection (icon_list); - for ( ; p != NULL; p = p->next) { - num = GPOINTER_TO_INT (p->data); - attachment = E_MSG_COMPOSER_ATTACHMENT (g_list_nth_data (bar->priv->attachments, num)); - - /* We need to check if there are duplicated index in the return list of - gnome_icon_list_get_selection() because of gnome bugzilla bug #122356. - FIXME in the future. */ - - if (g_list_find (attachment_list, attachment) == NULL) { - attachment_list = g_list_prepend (attachment_list, attachment); - } - } - - for (p = attachment_list; p != NULL; p = p->next) - remove_attachment (bar, E_MSG_COMPOSER_ATTACHMENT (p->data)); - - g_list_free (attachment_list); - - update (bar); -} - -static void -edit_selected (EMsgComposerAttachmentBar *bar) -{ - GnomeIconList *icon_list; - EMsgComposerAttachment *attachment; - GList *selection; - int num; - - icon_list = GNOME_ICON_LIST (bar); - - selection = gnome_icon_list_get_selection (icon_list); - num = GPOINTER_TO_INT (selection->data); - attachment = g_list_nth (bar->priv->attachments, num)->data; - - e_msg_composer_attachment_edit (attachment, GTK_WIDGET (bar)); -} - - -/* "Attach" dialog. */ - -static void -add_from_user (EMsgComposerAttachmentBar *bar) -{ - EMsgComposer *composer; - GPtrArray *file_list; - gboolean is_inline = FALSE; - int i; - - composer = E_MSG_COMPOSER (gtk_widget_get_toplevel (GTK_WIDGET (bar))); - - file_list = e_msg_composer_select_file_attachments (composer, &is_inline); - if (!file_list) - return; - - for (i = 0; i < file_list->len; i++) { - add_from_file (bar, file_list->pdata[i], is_inline ? "inline" : "attachment"); - g_free (file_list->pdata[i]); - } - - g_ptr_array_free (file_list, TRUE); -} - - -/* Callbacks. */ - -static void -add_cb (GtkWidget *widget, gpointer data, GtkWidget *for_widget) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT_BAR (data)); - - add_from_user (E_MSG_COMPOSER_ATTACHMENT_BAR (data)); -} - -static void -properties_cb (GtkWidget *widget, gpointer data, GtkWidget *for_widget) -{ - EMsgComposerAttachmentBar *bar; - - g_return_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT_BAR (data)); - - bar = E_MSG_COMPOSER_ATTACHMENT_BAR (data); - edit_selected (data); -} - -static void -remove_cb (GtkWidget *widget, gpointer data, GtkWidget *for_widget) -{ - EMsgComposerAttachmentBar *bar; - - g_return_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT_BAR (data)); - - bar = E_MSG_COMPOSER_ATTACHMENT_BAR (data); - remove_selected (bar); -} - - -/* Popup menu handling. */ - -static GnomeUIInfo icon_context_menu_info[] = { - GNOMEUIINFO_ITEM (N_("Remove"), - N_("Remove selected items from the attachment list"), - remove_cb, NULL), - GNOMEUIINFO_MENU_PROPERTIES_ITEM (properties_cb, NULL), - GNOMEUIINFO_END -}; - -static GtkWidget * -get_icon_context_menu (EMsgComposerAttachmentBar *bar) -{ - EMsgComposerAttachmentBarPrivate *priv; - - priv = bar->priv; - if (priv->icon_context_menu == NULL) - priv->icon_context_menu = gnome_popup_menu_new (icon_context_menu_info); - - return priv->icon_context_menu; -} - -static void -popup_icon_context_menu (EMsgComposerAttachmentBar *bar, - gint num, - GdkEventButton *event) -{ - GtkWidget *menu; - - menu = get_icon_context_menu (bar); - gnome_popup_menu_do_popup (menu, NULL, NULL, event, bar, NULL); -} - -static GnomeUIInfo context_menu_info[] = { - GNOMEUIINFO_ITEM (N_("Add attachment..."), - N_("Attach a file to the message"), - add_cb, NULL), - GNOMEUIINFO_END -}; - -static GtkWidget * -get_context_menu (EMsgComposerAttachmentBar *bar) -{ - EMsgComposerAttachmentBarPrivate *priv; - - priv = bar->priv; - if (priv->context_menu == NULL) - priv->context_menu = gnome_popup_menu_new (context_menu_info); - - return priv->context_menu; -} - -static void -popup_context_menu (EMsgComposerAttachmentBar *bar, - GdkEventButton *event) -{ - GtkWidget *menu; - - menu = get_context_menu (bar); - gnome_popup_menu_do_popup (menu, NULL, NULL, event, bar, NULL); -} - - -/* GtkObject methods. */ - -static void -destroy (GtkObject *object) -{ - EMsgComposerAttachmentBar *bar; - - bar = E_MSG_COMPOSER_ATTACHMENT_BAR (object); - - if (bar->priv) { - free_attachment_list (bar); - g_free (bar->priv); - bar->priv = NULL; - } - - if (GTK_OBJECT_CLASS (parent_class)->destroy != NULL) - (* GTK_OBJECT_CLASS (parent_class)->destroy) (object); -} - - -/* GtkWidget methods. */ - - -static void -popup_menu_placement_callback (GtkMenu *menu, int *x, int *y, gboolean *push_in, gpointer user_data) -{ - EMsgComposerAttachmentBar *bar; - GnomeIconList *icon_list; - GList *selection; - GnomeCanvasPixbuf *image; - - bar = E_MSG_COMPOSER_ATTACHMENT_BAR (user_data); - icon_list = GNOME_ICON_LIST (user_data); - - gdk_window_get_origin (((GtkWidget*) bar)->window, x, y); - - selection = gnome_icon_list_get_selection (icon_list); - if (selection == NULL) - return; - - image = gnome_icon_list_get_icon_pixbuf_item (icon_list, (gint)selection->data); - if (image == NULL) - return; - - /* Put menu to the center of icon. */ - *x += (int)(image->item.x1 + image->item.x2) / 2; - *y += (int)(image->item.y1 + image->item.y2) / 2; -} - -static gboolean -popup_menu_event (GtkWidget *widget) -{ - EMsgComposerAttachmentBar *bar = E_MSG_COMPOSER_ATTACHMENT_BAR (widget); - GnomeIconList *icon_list = GNOME_ICON_LIST (widget); - GList *selection = gnome_icon_list_get_selection (icon_list); - GtkWidget *menu; - - if (selection == NULL) - menu = get_context_menu (bar); - else - menu = get_icon_context_menu (bar); - - gnome_popup_menu_do_popup (menu, popup_menu_placement_callback, - widget, NULL, widget, NULL); - - return TRUE; -} - - -static int -button_press_event (GtkWidget *widget, - GdkEventButton *event) -{ - EMsgComposerAttachmentBar *bar; - GnomeIconList *icon_list; - int icon_number; - - bar = E_MSG_COMPOSER_ATTACHMENT_BAR (widget); - icon_list = GNOME_ICON_LIST (widget); - - if (event->button != 3) - return GTK_WIDGET_CLASS (parent_class)->button_press_event (widget, event); - - icon_number = gnome_icon_list_get_icon_at (icon_list, event->x, event->y); - - if (icon_number >= 0) { - gnome_icon_list_select_icon (icon_list, icon_number); - popup_icon_context_menu (bar, icon_number, event); - } else { - popup_context_menu (bar, event); - } - - return TRUE; -} - - -/* Initialization. */ - -static void -class_init (EMsgComposerAttachmentBarClass *klass) -{ - GtkObjectClass *object_class; - GtkWidgetClass *widget_class; - GnomeIconListClass *icon_list_class; - - object_class = GTK_OBJECT_CLASS (klass); - widget_class = GTK_WIDGET_CLASS (klass); - icon_list_class = GNOME_ICON_LIST_CLASS (klass); - - parent_class = g_type_class_ref (gnome_icon_list_get_type ()); - - object_class->destroy = destroy; - - widget_class->button_press_event = button_press_event; - widget_class->popup_menu = popup_menu_event; - - - /* Setup signals. */ - - signals[CHANGED] = - g_signal_new ("changed", - E_TYPE_MSG_COMPOSER_ATTACHMENT_BAR, - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (EMsgComposerAttachmentBarClass, changed), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); -} - -static void -init (EMsgComposerAttachmentBar *bar) -{ - EMsgComposerAttachmentBarPrivate *priv; - - priv = g_new (EMsgComposerAttachmentBarPrivate, 1); - - priv->attachments = NULL; - priv->context_menu = NULL; - priv->icon_context_menu = NULL; - - priv->num_attachments = 0; - - bar->priv = priv; -} - - -GType -e_msg_composer_attachment_bar_get_type (void) -{ - static GType type = 0; - - if (type == 0) { - static const GTypeInfo info = { - sizeof (EMsgComposerAttachmentBarClass), - NULL, NULL, - (GClassInitFunc) class_init, - NULL, NULL, - sizeof (EMsgComposerAttachmentBar), - 0, - (GInstanceInitFunc) init, - }; - - type = g_type_register_static (GNOME_TYPE_ICON_LIST, "EMsgComposerAttachmentBar", &info, 0); - } - - return type; -} - -GtkWidget * -e_msg_composer_attachment_bar_new (GtkAdjustment *adj) -{ - EMsgComposerAttachmentBar *new; - GnomeIconList *icon_list; - int width, height, icon_width, window_height; - PangoFontMetrics *metrics; - PangoContext *context; - - new = g_object_new (e_msg_composer_attachment_bar_get_type (), NULL); - - icon_list = GNOME_ICON_LIST (new); - - context = gtk_widget_get_pango_context ((GtkWidget *) new); - metrics = pango_context_get_metrics (context, ((GtkWidget *) new)->style->font_desc, pango_context_get_language (context)); - width = PANGO_PIXELS (pango_font_metrics_get_approximate_char_width (metrics)) * 15; - /* This should be *2, but the icon list creates too much space above ... */ - height = PANGO_PIXELS (pango_font_metrics_get_ascent (metrics) + pango_font_metrics_get_descent (metrics)) * 3; - pango_font_metrics_unref (metrics); - - icon_width = ICON_WIDTH + ICON_SPACING + ICON_BORDER + ICON_TEXT_SPACING; - icon_width = MAX (icon_width, width); - - gnome_icon_list_construct (icon_list, icon_width, adj, 0); - - window_height = ICON_WIDTH + ICON_SPACING + ICON_BORDER + ICON_TEXT_SPACING + height; - gtk_widget_set_size_request (GTK_WIDGET (new), icon_width * 4, window_height); - - gnome_icon_list_set_separators (icon_list, ICON_SEPARATORS); - gnome_icon_list_set_row_spacing (icon_list, ICON_ROW_SPACING); - gnome_icon_list_set_col_spacing (icon_list, ICON_COL_SPACING); - gnome_icon_list_set_icon_border (icon_list, ICON_BORDER); - gnome_icon_list_set_text_spacing (icon_list, ICON_TEXT_SPACING); - gnome_icon_list_set_selection_mode (icon_list, GTK_SELECTION_MULTIPLE); - - return GTK_WIDGET (new); -} - -static const char * -get_default_charset (void) -{ - GConfClient *gconf; - const char *charset; - char *buf; - - gconf = gconf_client_get_default (); - buf = gconf_client_get_string (gconf, "/apps/evolution/mail/composer/charset", NULL); - if (buf && buf[0] == '\0') { - g_free (buf); - buf = NULL; - } - - g_object_unref (gconf); - - if (buf != NULL) { - charset = e_iconv_charset_name (buf); - g_free (buf); - } else - charset = e_iconv_locale_charset (); - - return charset; -} - -static void -attach_to_multipart (CamelMultipart *multipart, - EMsgComposerAttachment *attachment, - const char *default_charset) -{ - CamelContentType *content_type; - CamelDataWrapper *content; - - content_type = camel_mime_part_get_content_type (attachment->body); - content = camel_medium_get_content_object (CAMEL_MEDIUM (attachment->body)); - - if (!CAMEL_IS_MULTIPART (content)) { - if (camel_content_type_is (content_type, "text", "*")) { - CamelTransferEncoding encoding; - CamelStreamFilter *filter_stream; - CamelMimeFilterBestenc *bestenc; - CamelStream *stream; - const char *charset; - char *type; - - charset = camel_content_type_param (content_type, "charset"); - - stream = camel_stream_null_new (); - filter_stream = camel_stream_filter_new_with_stream (stream); - bestenc = camel_mime_filter_bestenc_new (CAMEL_BESTENC_GET_ENCODING); - camel_stream_filter_add (filter_stream, CAMEL_MIME_FILTER (bestenc)); - camel_object_unref (stream); - - camel_data_wrapper_decode_to_stream (content, CAMEL_STREAM (filter_stream)); - camel_object_unref (filter_stream); - - encoding = camel_mime_filter_bestenc_get_best_encoding (bestenc, CAMEL_BESTENC_8BIT); - camel_mime_part_set_encoding (attachment->body, encoding); - - if (encoding == CAMEL_TRANSFER_ENCODING_7BIT) { - /* the text fits within us-ascii so this is safe */ - /* FIXME: check that this isn't iso-2022-jp? */ - default_charset = "us-ascii"; - } else if (!charset) { - if (!default_charset) - default_charset = get_default_charset (); - - /* FIXME: We should really check that this fits within the - default_charset and if not find one that does and/or - allow the user to specify? */ - } - - if (!charset) { - /* looks kinda nasty, but this is how ya have to do it */ - camel_content_type_set_param (content_type, "charset", default_charset); - type = camel_content_type_format (content_type); - camel_mime_part_set_content_type (attachment->body, type); - g_free (type); - } - - camel_object_unref (bestenc); - } else if (!CAMEL_IS_MIME_MESSAGE (content)) { - camel_mime_part_set_encoding (attachment->body, CAMEL_TRANSFER_ENCODING_BASE64); - } - } - - camel_multipart_add_part (multipart, attachment->body); -} - -void -e_msg_composer_attachment_bar_to_multipart (EMsgComposerAttachmentBar *bar, - CamelMultipart *multipart, - const char *default_charset) -{ - EMsgComposerAttachmentBarPrivate *priv; - GList *p; - - g_return_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT_BAR (bar)); - g_return_if_fail (CAMEL_IS_MULTIPART (multipart)); - - priv = bar->priv; - - for (p = priv->attachments; p != NULL; p = p->next) { - EMsgComposerAttachment *attachment; - - attachment = E_MSG_COMPOSER_ATTACHMENT (p->data); - attach_to_multipart (multipart, attachment, default_charset); - } -} - - -guint -e_msg_composer_attachment_bar_get_num_attachments (EMsgComposerAttachmentBar *bar) -{ - g_return_val_if_fail (bar != NULL, 0); - g_return_val_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT_BAR (bar), 0); - - return bar->priv->num_attachments; -} - - -void -e_msg_composer_attachment_bar_attach (EMsgComposerAttachmentBar *bar, - const gchar *file_name) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT_BAR (bar)); - - if (file_name == NULL) - add_from_user (bar); - else - add_from_file (bar, file_name, "attachment"); -} - -void -e_msg_composer_attachment_bar_attach_mime_part (EMsgComposerAttachmentBar *bar, - CamelMimePart *part) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT_BAR (bar)); - - add_from_mime_part (bar, part); -} diff --git a/composer/e-msg-composer-attachment-bar.h b/composer/e-msg-composer-attachment-bar.h deleted file mode 100644 index a43b466633..0000000000 --- a/composer/e-msg-composer-attachment-bar.h +++ /dev/null @@ -1,77 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* msg-composer-attachment-bar.h - * - * Copyright (C) 1999 Ximian, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * published by the Free Software Foundation; either version 2 of the - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this program; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - * - * Author: Ettore Perazzoli - */ - -#ifndef __E_MSG_COMPOSER_ATTACHMENT_BAR_H__ -#define __E_MSG_COMPOSER_ATTACHMENT_BAR_H__ - -#include <libgnomeui/gnome-icon-list.h> - -#include <camel/camel-multipart.h> - -#ifdef __cplusplus -extern "C" { -#pragma } -#endif /* __cplusplus */ - -#define E_TYPE_MSG_COMPOSER_ATTACHMENT_BAR \ - (e_msg_composer_attachment_bar_get_type ()) -#define E_MSG_COMPOSER_ATTACHMENT_BAR(obj) \ - (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_MSG_COMPOSER_ATTACHMENT_BAR, EMsgComposerAttachmentBar)) -#define E_MSG_COMPOSER_ATTACHMENT_BAR_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_MSG_COMPOSER_ATTACHMENT_BAR, EMsgComposerAttachmentBarClass)) -#define E_IS_MSG_COMPOSER_ATTACHMENT_BAR(obj) \ - (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_MSG_COMPOSER_ATTACHMENT_BAR)) -#define E_IS_MSG_COMPOSER_ATTACHMENT_BAR_CLASS(klass) \ - (G_TYPE_CHECK_CLASS_TYPE ((obj), E_TYPE_MSG_COMPOSER_ATTACHMENT_BAR)) - -typedef struct _EMsgComposerAttachmentBar EMsgComposerAttachmentBar; -typedef struct _EMsgComposerAttachmentBarClass EMsgComposerAttachmentBarClass; -typedef struct _EMsgComposerAttachmentBarPrivate EMsgComposerAttachmentBarPrivate; - -struct _EMsgComposerAttachmentBar { - GnomeIconList parent; - - EMsgComposerAttachmentBarPrivate *priv; -}; - -struct _EMsgComposerAttachmentBarClass { - GnomeIconListClass parent_class; - - void (* changed) (EMsgComposerAttachmentBar *bar); -}; - - -GtkType e_msg_composer_attachment_bar_get_type (void); - -GtkWidget *e_msg_composer_attachment_bar_new (GtkAdjustment *adj); -void e_msg_composer_attachment_bar_to_multipart (EMsgComposerAttachmentBar *bar, CamelMultipart *multipart, - const char *default_charset); -guint e_msg_composer_attachment_bar_get_num_attachments (EMsgComposerAttachmentBar *bar); -void e_msg_composer_attachment_bar_attach (EMsgComposerAttachmentBar *bar, const char *file_name); -void e_msg_composer_attachment_bar_attach_mime_part (EMsgComposerAttachmentBar *bar, CamelMimePart *part); - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif /* __E_MSG_COMPOSER_ATTACHMENT_BAR_H__ */ diff --git a/composer/e-msg-composer-attachment.c b/composer/e-msg-composer-attachment.c deleted file mode 100644 index 2e8a0c61c5..0000000000 --- a/composer/e-msg-composer-attachment.c +++ /dev/null @@ -1,457 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* - * Authors: Ettore Perazzoli <ettore@ximian.com> - * Jeffrey Stedfast <fejj@ximian.com> - * - * Copyright 1999-2002 Ximian, Inc. (www.ximian.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA. - * - */ - - -/* This is the object representing an email attachment. It is implemented as a - GObject to make it easier for the application to handle it. For example, - the "changed" signal is emitted whenever something changes in the - attachment. Also, this contains the code to let users edit the - attachment manually. */ - -#include <sys/stat.h> -#include <string.h> -#include <errno.h> - -#include <camel/camel.h> -#include <gtk/gtknotebook.h> -#include <gtk/gtktogglebutton.h> -#include <libgnomevfs/gnome-vfs-mime.h> - -#include "e-util/e-mktemp.h" - -#include "e-msg-composer.h" -#include "e-msg-composer-attachment.h" - - -enum { - CHANGED, - LAST_SIGNAL -}; -static guint signals[LAST_SIGNAL] = { 0 }; - -static GObjectClass *parent_class = NULL; - - -static void -changed (EMsgComposerAttachment *attachment) -{ - g_signal_emit (attachment, signals[CHANGED], 0); -} - - -/* GtkObject methods. */ - -static void -finalise(GObject *object) -{ - EMsgComposerAttachment *attachment; - - attachment = E_MSG_COMPOSER_ATTACHMENT (object); - - camel_object_unref (attachment->body); - if (attachment->pixbuf_cache != NULL) - g_object_unref (attachment->pixbuf_cache); - - G_OBJECT_CLASS (parent_class)->finalize (object); -} - - -/* Signals. */ - -static void -real_changed (EMsgComposerAttachment *msg_composer_attachment) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT (msg_composer_attachment)); -} - - -static void -class_init (EMsgComposerAttachmentClass *klass) -{ - GObjectClass *object_class; - - object_class = (GObjectClass*) klass; - parent_class = g_type_class_ref (G_TYPE_OBJECT); - - object_class->finalize = finalise; - klass->changed = real_changed; - - signals[CHANGED] = g_signal_new ("changed", - E_TYPE_MSG_COMPOSER_ATTACHMENT, - G_SIGNAL_RUN_FIRST, - G_STRUCT_OFFSET (EMsgComposerAttachmentClass, changed), - NULL, - NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); -} - -static void -init (EMsgComposerAttachment *msg_composer_attachment) -{ - msg_composer_attachment->editor_gui = NULL; - msg_composer_attachment->body = NULL; - msg_composer_attachment->size = 0; - msg_composer_attachment->pixbuf_cache = NULL; -} - -GType -e_msg_composer_attachment_get_type (void) -{ - static GType type = 0; - - if (type == 0) { - static const GTypeInfo info = { - sizeof (EMsgComposerAttachmentClass), - NULL, - NULL, - (GClassInitFunc) class_init, - NULL, - NULL, - sizeof (EMsgComposerAttachment), - 0, - (GInstanceInitFunc) init, - }; - - type = g_type_register_static (G_TYPE_OBJECT, "EMsgComposerAttachment", &info, 0); - } - - return type; -} - - -/** - * e_msg_composer_attachment_new: - * @file_name: filename to attach - * @disposition: Content-Disposition of the attachment - * @ex: exception - * - * Return value: the new attachment, or %NULL on error - **/ -EMsgComposerAttachment * -e_msg_composer_attachment_new (const char *file_name, - const char *disposition, - CamelException *ex) -{ - EMsgComposerAttachment *new; - CamelMimePart *part; - CamelDataWrapper *wrapper; - CamelStream *stream; - struct stat statbuf; - char *mime_type; - char *filename; - - g_return_val_if_fail (file_name != NULL, NULL); - - if (stat (file_name, &statbuf) < 0) { - camel_exception_setv (ex, CAMEL_EXCEPTION_SYSTEM, - _("Cannot attach file %s: %s"), - file_name, g_strerror (errno)); - return NULL; - } - - /* return if it's not a regular file */ - if (!S_ISREG (statbuf.st_mode)) { - camel_exception_setv (ex, CAMEL_EXCEPTION_SYSTEM, - _("Cannot attach file %s: not a regular file"), - file_name); - return NULL; - } - - stream = camel_stream_fs_new_with_name (file_name, O_RDONLY, 0); - if (!stream) { - camel_exception_setv (ex, CAMEL_EXCEPTION_SYSTEM, - _("Cannot attach file %s: %s"), - file_name, g_strerror (errno)); - return NULL; - } - - mime_type = e_msg_composer_guess_mime_type (file_name); - if (mime_type) { - if (!strcasecmp (mime_type, "message/rfc822")) { - wrapper = (CamelDataWrapper *) camel_mime_message_new (); - } else { - wrapper = camel_data_wrapper_new (); - } - - camel_data_wrapper_construct_from_stream (wrapper, stream); - camel_data_wrapper_set_mime_type (wrapper, mime_type); - g_free (mime_type); - } else { - wrapper = camel_data_wrapper_new (); - camel_data_wrapper_construct_from_stream (wrapper, stream); - camel_data_wrapper_set_mime_type (wrapper, "application/octet-stream"); - } - - camel_object_unref (stream); - - part = camel_mime_part_new (); - camel_medium_set_content_object (CAMEL_MEDIUM (part), wrapper); - camel_object_unref (wrapper); - - camel_mime_part_set_disposition (part, disposition); - filename = g_path_get_basename (file_name); - camel_mime_part_set_filename (part, filename); - g_free (filename); - -#if 0 - /* Note: Outlook 2002 is broken with respect to Content-Ids on - non-multipart/related parts, so as an interoperability - workaround, don't set a Content-Id on these parts. Fixes - bug #10032 */ - /* set the Content-Id */ - content_id = camel_header_msgid_generate (); - camel_mime_part_set_content_id (part, content_id); - g_free (content_id); -#endif - - new = g_object_new (E_TYPE_MSG_COMPOSER_ATTACHMENT, NULL); - new->editor_gui = NULL; - new->body = part; - new->size = statbuf.st_size; - new->guessed_type = TRUE; - - return new; -} - - -/** - * e_msg_composer_attachment_new_from_mime_part: - * @part: a CamelMimePart - * - * Return value: a new EMsgComposerAttachment based on the mime part - **/ -EMsgComposerAttachment * -e_msg_composer_attachment_new_from_mime_part (CamelMimePart *part) -{ - EMsgComposerAttachment *new; - CamelMimePart *mime_part; - CamelStream *stream; - - g_return_val_if_fail (CAMEL_IS_MIME_PART (part), NULL); - - stream = camel_stream_mem_new (); - if (camel_data_wrapper_write_to_stream (CAMEL_DATA_WRAPPER (part), stream) == -1) { - camel_object_unref (stream); - return NULL; - } - - camel_stream_reset (stream); - mime_part = camel_mime_part_new (); - - if (camel_data_wrapper_construct_from_stream (CAMEL_DATA_WRAPPER (mime_part), stream) == -1) { - camel_object_unref (mime_part); - camel_object_unref (stream); - return NULL; - } - - camel_object_unref (stream); - - new = g_object_new (E_TYPE_MSG_COMPOSER_ATTACHMENT, NULL); - new->editor_gui = NULL; - new->body = mime_part; - new->guessed_type = FALSE; - new->size = 0; - - return new; -} - - -/* The attachment property dialog. */ - -typedef struct { - GtkWidget *dialog; - GtkEntry *file_name_entry; - GtkEntry *description_entry; - GtkEntry *mime_type_entry; - GtkToggleButton *disposition_checkbox; - EMsgComposerAttachment *attachment; -} DialogData; - -static void -destroy_dialog_data (DialogData *data) -{ - g_free (data); -} - -/* - * fixme: I am converting EVERYTHING to/from UTF-8, although mime types - * are in ASCII. This is not strictly necessary, but we want to be - * consistent and possibly check for errors somewhere. - */ - -static void -set_entry (GladeXML *xml, const char *widget_name, const char *value) -{ - GtkEntry *entry; - - entry = GTK_ENTRY (glade_xml_get_widget (xml, widget_name)); - if (entry == NULL) - g_warning ("Entry for `%s' not found.", widget_name); - else - gtk_entry_set_text (entry, value ? value : ""); -} - -static void -connect_widget (GladeXML *gui, const char *name, const char *signal_name, - GCallback func, gpointer data) -{ - GtkWidget *widget; - - widget = glade_xml_get_widget (gui, name); - g_signal_connect (widget, signal_name, func, data); -} - -static void -close_cb (GtkWidget *widget, gpointer data) -{ - EMsgComposerAttachment *attachment; - DialogData *dialog_data; - - dialog_data = (DialogData *) data; - attachment = dialog_data->attachment; - - gtk_widget_destroy (dialog_data->dialog); - g_object_unref (attachment->editor_gui); - attachment->editor_gui = NULL; - - g_object_unref (attachment); - - destroy_dialog_data (dialog_data); -} - -static void -ok_cb (GtkWidget *widget, gpointer data) -{ - DialogData *dialog_data; - EMsgComposerAttachment *attachment; - const char *str; - - dialog_data = (DialogData *) data; - attachment = dialog_data->attachment; - - str = gtk_entry_get_text (dialog_data->file_name_entry); - camel_mime_part_set_filename (attachment->body, str); - - str = gtk_entry_get_text (dialog_data->description_entry); - camel_mime_part_set_description (attachment->body, str); - - str = gtk_entry_get_text (dialog_data->mime_type_entry); - camel_mime_part_set_content_type (attachment->body, str); - - camel_data_wrapper_set_mime_type(camel_medium_get_content_object(CAMEL_MEDIUM (attachment->body)), str); - - switch (gtk_toggle_button_get_active (dialog_data->disposition_checkbox)) { - case 0: - camel_mime_part_set_disposition (attachment->body, "attachment"); - break; - case 1: - camel_mime_part_set_disposition (attachment->body, "inline"); - break; - default: - /* Hmmmm? */ - break; - } - - changed (attachment); - close_cb (widget, data); -} - -static void -response_cb (GtkWidget *widget, gint response, gpointer data) -{ - if (response == GTK_RESPONSE_OK) - ok_cb (widget, data); - else - close_cb (widget, data); -} - -void -e_msg_composer_attachment_edit (EMsgComposerAttachment *attachment, GtkWidget *parent) -{ - CamelContentType *content_type; - const char *disposition; - DialogData *dialog_data; - GladeXML *editor_gui; - char *type; - - g_return_if_fail (attachment != NULL); - g_return_if_fail (E_IS_MSG_COMPOSER_ATTACHMENT (attachment)); - - if (attachment->editor_gui != NULL) { - GtkWidget *window; - - window = glade_xml_get_widget (attachment->editor_gui, - "dialog"); - gdk_window_show (window->window); - return; - } - - editor_gui = glade_xml_new (EVOLUTION_GLADEDIR "/e-msg-composer-attachment.glade", - NULL, NULL); - if (editor_gui == NULL) { - g_warning ("Cannot load `e-msg-composer-attachment.glade'"); - return; - } - - attachment->editor_gui = editor_gui; - - gtk_window_set_transient_for - (GTK_WINDOW (glade_xml_get_widget (editor_gui, "dialog")), - GTK_WINDOW (gtk_widget_get_toplevel (parent))); - - dialog_data = g_new (DialogData, 1); - g_object_ref (attachment); - dialog_data->attachment = attachment; - dialog_data->dialog = glade_xml_get_widget (editor_gui, "dialog"); - dialog_data->file_name_entry = GTK_ENTRY ( - glade_xml_get_widget (editor_gui, "file_name_entry")); - dialog_data->description_entry = GTK_ENTRY ( - glade_xml_get_widget (editor_gui, "description_entry")); - dialog_data->mime_type_entry = GTK_ENTRY ( - glade_xml_get_widget (editor_gui, "mime_type_entry")); - dialog_data->disposition_checkbox = GTK_TOGGLE_BUTTON ( - glade_xml_get_widget (editor_gui, "disposition_checkbox")); - - set_entry (editor_gui, "file_name_entry", - camel_mime_part_get_filename (attachment->body)); - set_entry (editor_gui, "description_entry", - camel_mime_part_get_description (attachment->body)); - content_type = camel_mime_part_get_content_type (attachment->body); - type = camel_content_type_simple (content_type); - set_entry (editor_gui, "mime_type_entry", type); - g_free (type); - - disposition = camel_mime_part_get_disposition (attachment->body); - gtk_toggle_button_set_active (dialog_data->disposition_checkbox, - disposition && !g_ascii_strcasecmp (disposition, "inline")); - - connect_widget (editor_gui, "dialog", "response", (GCallback)response_cb, dialog_data); -#warning "signal connect while alive" - /* make sure that when the composer gets hidden/closed that our windows also close */ - parent = gtk_widget_get_toplevel (parent); - gtk_signal_connect_while_alive (GTK_OBJECT (parent), "destroy", (GCallback)close_cb, dialog_data, - GTK_OBJECT (dialog_data->dialog)); - gtk_signal_connect_while_alive (GTK_OBJECT (parent), "hide", (GCallback)close_cb, dialog_data, - GTK_OBJECT (dialog_data->dialog)); -} diff --git a/composer/e-msg-composer-attachment.glade b/composer/e-msg-composer-attachment.glade deleted file mode 100644 index dc228eef70..0000000000 --- a/composer/e-msg-composer-attachment.glade +++ /dev/null @@ -1,237 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-interface SYSTEM "http://glade.gnome.org/glade-2.0.dtd"> - -<glade-interface> - -<widget class="GtkDialog" id="dialog"> - <property name="border_width">6</property> - <property name="visible">True</property> - <property name="title" translatable="yes">Attachment Properties</property> - <property name="type">GTK_WINDOW_TOPLEVEL</property> - <property name="window_position">GTK_WIN_POS_NONE</property> - <property name="modal">False</property> - <property name="resizable">True</property> - <property name="destroy_with_parent">False</property> - <property name="has_separator">True</property> - - <child internal-child="vbox"> - <widget class="GtkVBox" id="dialog-vbox1"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">6</property> - - <child internal-child="action_area"> - <widget class="GtkHButtonBox" id="dialog-action_area1"> - <property name="visible">True</property> - <property name="layout_style">GTK_BUTTONBOX_END</property> - - <child> - <widget class="GtkButton" id="close_button"> - <property name="visible">True</property> - <property name="can_default">True</property> - <property name="has_default">True</property> - <property name="can_focus">True</property> - <property name="label">gtk-cancel</property> - <property name="use_stock">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="response_id">-6</property> - </widget> - </child> - - <child> - <widget class="GtkButton" id="ok_button"> - <property name="visible">True</property> - <property name="can_default">True</property> - <property name="can_focus">True</property> - <property name="label">gtk-ok</property> - <property name="use_stock">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="response_id">-5</property> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">True</property> - <property name="pack_type">GTK_PACK_END</property> - </packing> - </child> - - <child> - <widget class="GtkTable" id="table1"> - <property name="visible">True</property> - <property name="n_rows">4</property> - <property name="n_columns">2</property> - <property name="homogeneous">False</property> - <property name="row_spacing">6</property> - <property name="column_spacing">6</property> - - <child> - <widget class="GtkEntry" id="description_entry"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="editable">True</property> - <property name="visibility">True</property> - <property name="max_length">0</property> - <property name="text" translatable="yes"></property> - <property name="has_frame">True</property> - <property name="invisible_char" translatable="yes">*</property> - <property name="activates_default">False</property> - </widget> - <packing> - <property name="left_attach">1</property> - <property name="right_attach">2</property> - <property name="top_attach">1</property> - <property name="bottom_attach">2</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkEntry" id="mime_type_entry"> - <property name="visible">True</property> - <property name="sensitive">False</property> - <property name="can_focus">True</property> - <property name="editable">False</property> - <property name="visibility">True</property> - <property name="max_length">0</property> - <property name="text" translatable="yes"></property> - <property name="has_frame">True</property> - <property name="invisible_char" translatable="yes">*</property> - <property name="activates_default">False</property> - </widget> - <packing> - <property name="left_attach">1</property> - <property name="right_attach">2</property> - <property name="top_attach">2</property> - <property name="bottom_attach">3</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="mime_label"> - <property name="visible">True</property> - <property name="label" translatable="yes">MIME type:</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">1</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - </widget> - <packing> - <property name="left_attach">0</property> - <property name="right_attach">1</property> - <property name="top_attach">2</property> - <property name="bottom_attach">3</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="description_label"> - <property name="visible">True</property> - <property name="label" translatable="yes">Description:</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_CENTER</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">1</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - </widget> - <packing> - <property name="left_attach">0</property> - <property name="right_attach">1</property> - <property name="top_attach">1</property> - <property name="bottom_attach">2</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="filename_label"> - <property name="visible">True</property> - <property name="label" translatable="yes">File name:</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_CENTER</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">1</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - </widget> - <packing> - <property name="left_attach">0</property> - <property name="right_attach">1</property> - <property name="top_attach">0</property> - <property name="bottom_attach">1</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkEntry" id="file_name_entry"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="editable">True</property> - <property name="visibility">True</property> - <property name="max_length">0</property> - <property name="text" translatable="yes"></property> - <property name="has_frame">True</property> - <property name="invisible_char" translatable="yes">*</property> - <property name="activates_default">False</property> - </widget> - <packing> - <property name="left_attach">1</property> - <property name="right_attach">2</property> - <property name="top_attach">0</property> - <property name="bottom_attach">1</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkCheckButton" id="disposition_checkbox"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="label" translatable="yes">Suggest automatic display of attachment</property> - <property name="use_underline">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="active">False</property> - <property name="inconsistent">False</property> - <property name="draw_indicator">True</property> - </widget> - <packing> - <property name="left_attach">0</property> - <property name="right_attach">2</property> - <property name="top_attach">3</property> - <property name="bottom_attach">4</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - </widget> - </child> -</widget> - -</glade-interface> diff --git a/composer/e-msg-composer-attachment.h b/composer/e-msg-composer-attachment.h deleted file mode 100644 index caef6ebc58..0000000000 --- a/composer/e-msg-composer-attachment.h +++ /dev/null @@ -1,77 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* e-msg-composer-attachment.h - * - * Copyright (C) 1999 Ximian, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * published by the Free Software Foundation; either version 2 of the - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this program; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - * - * Author: Ettore Perazzoli - */ -#ifndef __E_MSG_COMPOSER_ATTACHMENT_H__ -#define __E_MSG_COMPOSER_ATTACHMENT_H__ - -#include <gdk-pixbuf/gdk-pixbuf.h> -#include <glade/glade-xml.h> -#include <camel/camel-mime-part.h> -#include <camel/camel-exception.h> - -#ifdef __cplusplus -extern "C" { -#pragma } -#endif /* __cplusplus */ - -#define E_TYPE_MSG_COMPOSER_ATTACHMENT (e_msg_composer_attachment_get_type ()) -#define E_MSG_COMPOSER_ATTACHMENT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_MSG_COMPOSER_ATTACHMENT, EMsgComposerAttachment)) -#define E_MSG_COMPOSER_ATTACHMENT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_MSG_COMPOSER_ATTACHMENT, EMsgComposerAttachmentClass)) -#define E_IS_MSG_COMPOSER_ATTACHMENT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_MSG_COMPOSER_ATTACHMENT)) -#define E_IS_MSG_COMPOSER_ATTACHMENT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((obj), E_TYPE_MSG_COMPOSER_ATTACHMENT)) - - -typedef struct _EMsgComposerAttachment EMsgComposerAttachment; -typedef struct _EMsgComposerAttachmentClass EMsgComposerAttachmentClass; - -struct _EMsgComposerAttachment { - GObject parent; - - GladeXML *editor_gui; - - CamelMimePart *body; - gboolean guessed_type; - gulong size; - - GdkPixbuf *pixbuf_cache; -}; - -struct _EMsgComposerAttachmentClass { - GObjectClass parent_class; - - void (*changed) (EMsgComposerAttachment *msg_composer_attachment); -}; - - -GType e_msg_composer_attachment_get_type (void); -EMsgComposerAttachment *e_msg_composer_attachment_new (const char *file_name, - const char *disposition, - CamelException *ex); -EMsgComposerAttachment *e_msg_composer_attachment_new_from_mime_part (CamelMimePart *part); -void e_msg_composer_attachment_edit (EMsgComposerAttachment *attachment, - GtkWidget *parent); - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif /* __E_MSG_COMPOSER_ATTACHMENT_H__ */ diff --git a/composer/e-msg-composer-hdrs.c b/composer/e-msg-composer-hdrs.c deleted file mode 100644 index 4e222b0bfd..0000000000 --- a/composer/e-msg-composer-hdrs.c +++ /dev/null @@ -1,1342 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* msg-composer-hdrs.c - * - * Copyright (C) 1999 Ximian, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * published by the Free Software Foundation; either version 2 of the - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this program; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - * - * Author: Ettore Perazzoli - */ - - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <string.h> - -#include <bonobo/bonobo-control.h> -#include <bonobo/bonobo-widget.h> - -#include <gtk/gtkmenuitem.h> -#include <gtk/gtkoptionmenu.h> -#include <gtk/gtktooltips.h> -#include <libgnomeui/gnome-uidefs.h> - -#include "Composer.h" - -#include <gtk/gtkmenuitem.h> -#include <gtk/gtkoptionmenu.h> -#include <gtk/gtktooltips.h> - -#include <gconf/gconf.h> -#include <gconf/gconf-client.h> - -#include <gal/e-text/e-entry.h> - -#include <camel/camel.h> -#include "e-msg-composer-hdrs.h" -#include "mail/mail-config.h" -#include "mail/em-folder-selection-button.h" - - - -/* Indexes in the GtkTable assigned to various items */ - -#define LINE_FROM 0 -#define LINE_REPLYTO 1 -#define LINE_TO 2 -#define LINE_CC 3 -#define LINE_BCC 4 -#define LINE_POSTTO 5 -#define LINE_SUBJECT 6 - - -typedef struct { - GtkWidget *label; - GtkWidget *entry; -} EMsgComposerHdrPair; - -struct _EMsgComposerHdrsPrivate { - GNOME_Evolution_Addressbook_SelectNames corba_select_names; - - /* ui component */ - BonoboUIComponent *uic; - - /* The tooltips. */ - GtkTooltips *tooltips; - - EAccountList *accounts; - GSList *from_options; - - /* Standard headers. */ - EMsgComposerHdrPair from, reply_to, to, cc, bcc, post_to, subject; -}; - - -static GtkTableClass *parent_class = NULL; - -enum { - SHOW_ADDRESS_DIALOG, - SUBJECT_CHANGED, - HDRS_CHANGED, - FROM_CHANGED, - LAST_SIGNAL -}; - -static int signals[LAST_SIGNAL]; - - -static gboolean -setup_corba (EMsgComposerHdrs *hdrs) -{ - EMsgComposerHdrsPrivate *priv; - CORBA_Environment ev; - - priv = hdrs->priv; - - g_assert (priv->corba_select_names == CORBA_OBJECT_NIL); - - CORBA_exception_init (&ev); - - priv->corba_select_names = bonobo_activation_activate_from_id (SELECT_NAMES_OAFIID, 0, NULL, &ev); - - /* OAF seems to be broken -- it can return a CORBA_OBJECT_NIL without - raising an exception in `ev'. */ - if (ev._major != CORBA_NO_EXCEPTION || priv->corba_select_names == CORBA_OBJECT_NIL) { - CORBA_exception_free (&ev); - return FALSE; - } - - CORBA_exception_free (&ev); - - return TRUE; -} - -typedef struct { - EMsgComposerHdrs *hdrs; - char *string; -} EMsgComposerHdrsAndString; - -static void -e_msg_composer_hdrs_and_string_free (EMsgComposerHdrsAndString *emchas) -{ - if (emchas->hdrs) - g_object_unref (emchas->hdrs); - g_free (emchas->string); - g_free (emchas); -} - -static EMsgComposerHdrsAndString * -e_msg_composer_hdrs_and_string_create (EMsgComposerHdrs *hdrs, const char *string) -{ - EMsgComposerHdrsAndString *emchas; - - emchas = g_new (EMsgComposerHdrsAndString, 1); - emchas->hdrs = hdrs; - emchas->string = g_strdup (string); - if (emchas->hdrs) - g_object_ref (emchas->hdrs); - - return emchas; -} - -static void -address_button_clicked_cb (GtkButton *button, gpointer data) -{ - EMsgComposerHdrsAndString *emchas; - EMsgComposerHdrs *hdrs; - EMsgComposerHdrsPrivate *priv; - CORBA_Environment ev; - - emchas = data; - hdrs = emchas->hdrs; - priv = hdrs->priv; - - CORBA_exception_init (&ev); - - GNOME_Evolution_Addressbook_SelectNames_activateDialog ( - priv->corba_select_names, emchas->string, &ev); - - CORBA_exception_free (&ev); -} - -static void -from_changed (GtkWidget *item, gpointer data) -{ - EMsgComposerHdrs *hdrs = E_MSG_COMPOSER_HDRS (data); - const char *reply_to; - - hdrs->account = g_object_get_data ((GObject *) item, "account"); - - /* we do this rather than calling e_msg_composer_hdrs_set_reply_to() - because we don't want to change the visibility of the header */ - reply_to = hdrs->account->id->reply_to; - gtk_entry_set_text (GTK_ENTRY (hdrs->priv->reply_to.entry), reply_to ? reply_to : ""); - - g_signal_emit (hdrs, signals [FROM_CHANGED], 0); -} - -static void -account_added_cb (EAccountList *accounts, EAccount *account, EMsgComposerHdrs *hdrs) -{ - GtkWidget *item, *menu, *omenu, *toplevel; - char *label; - - omenu = e_msg_composer_hdrs_get_from_omenu (hdrs); - menu = gtk_option_menu_get_menu (GTK_OPTION_MENU (omenu)); - - label = g_strdup_printf ("%s <%s>", account->id->name, account->id->address); - item = gtk_menu_item_new_with_label (label); - gtk_widget_show (item); - g_free (label); - - g_object_ref (account); - g_object_set_data ((GObject *) item, "account", account); - g_signal_connect (item, "activate", G_CALLBACK (from_changed), hdrs); - - /* this is so we can later set which one we want */ - hdrs->priv->from_options = g_slist_append (hdrs->priv->from_options, item); - - gtk_menu_shell_append (GTK_MENU_SHELL (menu), item); - - toplevel = gtk_widget_get_toplevel ((GtkWidget *) hdrs); - gtk_widget_set_sensitive (toplevel, TRUE); -} - -static void -account_changed_cb (EAccountList *accounts, EAccount *account, EMsgComposerHdrs *hdrs) -{ - GtkWidget *item, *label; - EAccount *acnt; - GSList *node; - char *text; - - node = hdrs->priv->from_options; - while (node != NULL) { - item = node->data; - acnt = g_object_get_data ((GObject *) item, "account"); - if (acnt == account) { - text = g_strdup_printf ("%s <%s>", account->id->name, account->id->address); - label = gtk_bin_get_child ((GtkBin *) item); - gtk_label_set_text ((GtkLabel *) label, text); - g_free (text); - break; - } - - node = node->next; - } -} - -static void -account_removed_cb (EAccountList *accounts, EAccount *account, EMsgComposerHdrs *hdrs) -{ - struct _EMsgComposerHdrsPrivate *priv = hdrs->priv; - GtkWidget *item, *omenu, *toplevel, *dialog; - EAccount *acnt; - GSList *node; - - node = priv->from_options; - while (node != NULL) { - item = node->data; - acnt = g_object_get_data ((GObject *) item, "account"); - if (acnt == account) { - if (hdrs->account == account) - hdrs->account = NULL; - - priv->from_options = g_slist_remove_link (priv->from_options, node); - g_slist_free_1 (node); - g_object_unref (account); - gtk_widget_destroy (item); - break; - } - - node = node->next; - } - - if (hdrs->account == NULL) { - if (priv->from_options) { - /* the previously selected account was removed, - default the new selection to the first account in - the menu list */ - omenu = e_msg_composer_hdrs_get_from_omenu (hdrs); - - item = priv->from_options->data; - gtk_option_menu_set_history (GTK_OPTION_MENU (omenu), 0); - g_signal_emit_by_name (item, "activate", hdrs); - } else { - toplevel = gtk_widget_get_toplevel ((GtkWidget *) hdrs); - gtk_widget_set_sensitive (toplevel, FALSE); - - dialog = gtk_message_dialog_new ((GtkWindow *) toplevel, GTK_DIALOG_MODAL | - GTK_DIALOG_DESTROY_WITH_PARENT, - GTK_MESSAGE_WARNING, GTK_BUTTONS_OK, "%s", - _("You need to configure an account before you can compose mail.")); - } - } -} - -static GtkWidget * -create_from_optionmenu (EMsgComposerHdrs *hdrs) -{ - struct _EMsgComposerHdrsPrivate *priv = hdrs->priv; - GtkWidget *hbox, *omenu, *menu, *item, *first = NULL; - int i = 0, history = 0, m, matches; - GPtrArray *addresses; - GConfClient *gconf; - EAccount *account; - EIterator *iter; - char *uid; - - omenu = gtk_option_menu_new (); - menu = gtk_menu_new (); - - gconf = gconf_client_get_default (); - uid = gconf_client_get_string (gconf, "/apps/evolution/mail/default_account", NULL); - g_object_unref (gconf); - - /* Make list of account email addresses */ - addresses = g_ptr_array_new (); - iter = e_list_get_iterator ((EList *) priv->accounts); - while (e_iterator_is_valid (iter)) { - account = (EAccount *) e_iterator_get (iter); - - if (account->id->address) - g_ptr_array_add (addresses, account->id->address); - - e_iterator_next (iter); - } - - e_iterator_reset (iter); - - while (e_iterator_is_valid (iter)) { - char *label; - - account = (EAccount *) e_iterator_get (iter); - - /* this should never ever fail */ - if (!account || !account->name || !account->id) { - g_assert_not_reached (); - continue; - } - - if (account->id->address && *account->id->address) { - /* If the account has a unique email address, just - * show that. Otherwise include the account name. - */ - for (m = matches = 0; m < addresses->len; m++) { - if (!strcmp (account->id->address, addresses->pdata[m])) - matches++; - } - - if (matches > 1) - label = g_strdup_printf ("%s <%s> (%s)", account->id->name, - account->id->address, account->name); - else - label = g_strdup_printf ("%s <%s>", account->id->name, account->id->address); - - item = gtk_menu_item_new_with_label (label); - g_free (label); - - g_object_ref (account); - g_object_set_data ((GObject *) item, "account", account); - g_signal_connect (item, "activate", G_CALLBACK (from_changed), hdrs); - - if (uid && !strcmp (account->uid, uid)) { - first = item; - history = i; - } - - /* this is so we can later set which one we want */ - hdrs->priv->from_options = g_slist_append (hdrs->priv->from_options, item); - - gtk_menu_shell_append (GTK_MENU_SHELL (menu), item); - gtk_widget_show (item); - i++; - } - - e_iterator_next (iter); - } - - g_free (uid); - g_object_unref (iter); - - g_ptr_array_free (addresses, TRUE); - - gtk_option_menu_set_menu (GTK_OPTION_MENU (omenu), menu); - - if (first) { - gtk_option_menu_set_history (GTK_OPTION_MENU (omenu), history); - g_signal_emit_by_name (first, "activate", hdrs); - } - - hbox = gtk_hbox_new (FALSE, 6); - gtk_box_pack_start_defaults (GTK_BOX (hbox), omenu); - gtk_widget_show (omenu); - gtk_widget_show (hbox); - - g_object_set_data ((GObject *) hbox, "from_menu", omenu); - - /* listen for changes to the account list so we can auto-update the from menu */ - g_signal_connect (priv->accounts, "account-added", G_CALLBACK (account_added_cb), hdrs); - g_signal_connect (priv->accounts, "account-changed", G_CALLBACK (account_changed_cb), hdrs); - g_signal_connect (priv->accounts, "account-removed", G_CALLBACK (account_removed_cb), hdrs); - - return hbox; -} - -static void -addressbook_entry_changed (BonoboListener *listener, - const char *event_name, - const CORBA_any *arg, - CORBA_Environment *ev, - gpointer user_data) -{ - EMsgComposerHdrs *hdrs = E_MSG_COMPOSER_HDRS (user_data); - - g_signal_emit (hdrs, signals[HDRS_CHANGED], 0); -} - -static GtkWidget * -create_addressbook_entry (EMsgComposerHdrs *hdrs, const char *name) -{ - EMsgComposerHdrsPrivate *priv; - GNOME_Evolution_Addressbook_SelectNames corba_select_names; - Bonobo_Control corba_control; - GtkWidget *control_widget; - CORBA_Environment ev; - BonoboControlFrame *cf; - Bonobo_PropertyBag pb = CORBA_OBJECT_NIL; - - priv = hdrs->priv; - corba_select_names = priv->corba_select_names; - - CORBA_exception_init (&ev); - - GNOME_Evolution_Addressbook_SelectNames_addSection ( - corba_select_names, name, name, &ev); - if (ev._major != CORBA_NO_EXCEPTION) { - CORBA_exception_free (&ev); - return NULL; - } - - corba_control = - GNOME_Evolution_Addressbook_SelectNames_getEntryBySection ( - corba_select_names, name, &ev); - - if (ev._major != CORBA_NO_EXCEPTION) { - CORBA_exception_free (&ev); - return NULL; - } - - CORBA_exception_free (&ev); - - control_widget = bonobo_widget_new_control_from_objref ( - corba_control, bonobo_ui_component_get_container (priv->uic)); - - cf = bonobo_widget_get_control_frame (BONOBO_WIDGET (control_widget)); - pb = bonobo_control_frame_get_control_property_bag (cf, NULL); - - bonobo_control_frame_set_autoactivate (cf, TRUE); - - bonobo_event_source_client_add_listener ( - pb, addressbook_entry_changed, - "Bonobo/Property:change:entry_changed", - NULL, hdrs); - - return control_widget; -} - -static EMsgComposerHdrPair -header_new_recipient (EMsgComposerHdrs *hdrs, const char *name, const char *tip) -{ - EMsgComposerHdrsPrivate *priv; - EMsgComposerHdrPair ret; - - priv = hdrs->priv; - - ret.label = gtk_button_new_with_label (name); - GTK_OBJECT_UNSET_FLAGS (ret.label, GTK_CAN_FOCUS); - g_signal_connect_data (ret.label, "clicked", - G_CALLBACK (address_button_clicked_cb), - e_msg_composer_hdrs_and_string_create (hdrs, name), - (GClosureNotify) e_msg_composer_hdrs_and_string_free, - 0); - - gtk_tooltips_set_tip (hdrs->priv->tooltips, ret.label, - _("Click here for the address book"), - NULL); - - ret.entry = create_addressbook_entry (hdrs, name); - - return ret; -} - -static void -entry_changed (GtkWidget *entry, EMsgComposerHdrs *hdrs) -{ - const char *subject; - - subject = e_msg_composer_hdrs_get_subject (hdrs); - g_signal_emit (hdrs, signals[SUBJECT_CHANGED], 0, subject); - g_signal_emit (hdrs, signals[HDRS_CHANGED], 0); -} - -static void -create_headers (EMsgComposerHdrs *hdrs) -{ - EMsgComposerHdrsPrivate *priv = hdrs->priv; - - /* - * Reply-To: - * - * Create this before we call create_from_optionmenu, - * because that causes from_changed to be called, which - * expects the reply_to fields to be initialized. - */ - priv->reply_to.label = gtk_label_new (_("Reply-To:")); - priv->reply_to.entry = gtk_entry_new (); - - /* - * From - */ - priv->from.label = gtk_label_new (_("From:")); - priv->from.entry = create_from_optionmenu (hdrs); - - /* - * Subject - */ - priv->subject.label = gtk_label_new (_("Subject:")); - priv->subject.entry = gtk_entry_new (); - g_signal_connect (priv->subject.entry, "changed", - G_CALLBACK (entry_changed), hdrs); - - /* - * To, CC, and Bcc - */ - priv->to = header_new_recipient ( - hdrs, _("To:"), - _("Enter the recipients of the message")); - - priv->cc = header_new_recipient ( - hdrs, _("Cc:"), - _("Enter the addresses that will receive a carbon copy of the message")); - - priv->bcc = header_new_recipient ( - hdrs, _("Bcc:"), - _("Enter the addresses that will receive a carbon copy of " - "the message without appearing in the recipient list of " - "the message.")); - - /* - * Post-To - */ - priv->post_to.label = gtk_label_new (_("Post To:")); - priv->post_to.entry = em_folder_selection_button_new (_("Posting destination"), _("Choose a folder to post the message to.")); -} - -static void -attach_couple (EMsgComposerHdrs *hdrs, EMsgComposerHdrPair *pair, int line) -{ - gtk_table_attach (GTK_TABLE (hdrs), - pair->label, 0, 1, - line, line + 1, - GTK_FILL, GTK_FILL, 3, 3); - - gtk_table_attach (GTK_TABLE (hdrs), - pair->entry, 1, 2, - line, line + 1, - GTK_FILL | GTK_EXPAND, 0, 3, 3); -} - -static void -attach_headers (EMsgComposerHdrs *hdrs) -{ - EMsgComposerHdrsPrivate *p = hdrs->priv; - - attach_couple (hdrs, &p->from, LINE_FROM); - attach_couple (hdrs, &p->reply_to, LINE_REPLYTO); - attach_couple (hdrs, &p->to, LINE_TO); - attach_couple (hdrs, &p->cc, LINE_CC); - attach_couple (hdrs, &p->bcc, LINE_BCC); - attach_couple (hdrs, &p->post_to, LINE_POSTTO); - attach_couple (hdrs, &p->subject, LINE_SUBJECT); -} - -static void -set_pair_visibility (EMsgComposerHdrs *h, EMsgComposerHdrPair *pair, int visible) -{ - if (visible & h->visible_mask) { - gtk_widget_show (pair->label); - gtk_widget_show (pair->entry); - } else { - gtk_widget_hide (pair->label); - gtk_widget_hide (pair->entry); - } -} - -static void -headers_set_visibility (EMsgComposerHdrs *h, int visible_flags) -{ - EMsgComposerHdrsPrivate *p = h->priv; - - /* To is always visible if we're not doing Post-To */ - if (!(h->visible_mask & E_MSG_COMPOSER_VISIBLE_POSTTO)) - visible_flags |= E_MSG_COMPOSER_VISIBLE_TO; - else - visible_flags |= E_MSG_COMPOSER_VISIBLE_POSTTO; - - set_pair_visibility (h, &p->from, visible_flags & E_MSG_COMPOSER_VISIBLE_FROM); - set_pair_visibility (h, &p->reply_to, visible_flags & E_MSG_COMPOSER_VISIBLE_REPLYTO); - set_pair_visibility (h, &p->to, visible_flags & E_MSG_COMPOSER_VISIBLE_TO); - set_pair_visibility (h, &p->cc, visible_flags & E_MSG_COMPOSER_VISIBLE_CC); - set_pair_visibility (h, &p->bcc, visible_flags & E_MSG_COMPOSER_VISIBLE_BCC); - set_pair_visibility (h, &p->post_to, visible_flags & E_MSG_COMPOSER_VISIBLE_POSTTO); - set_pair_visibility (h, &p->subject, visible_flags & E_MSG_COMPOSER_VISIBLE_SUBJECT); -} - -static void -headers_set_sensitivity (EMsgComposerHdrs *h) -{ - bonobo_ui_component_set_prop ( - h->priv->uic, "/commands/ViewFrom", "sensitive", - h->visible_mask & E_MSG_COMPOSER_VISIBLE_FROM ? "1" : "0", NULL); - - bonobo_ui_component_set_prop ( - h->priv->uic, "/commands/ViewReplyTo", "sensitive", - h->visible_mask & E_MSG_COMPOSER_VISIBLE_REPLYTO ? "1" : "0", NULL); - - bonobo_ui_component_set_prop ( - h->priv->uic, "/commands/ViewCC", "sensitive", - h->visible_mask & E_MSG_COMPOSER_VISIBLE_CC ? "1" : "0", NULL); - - bonobo_ui_component_set_prop ( - h->priv->uic, "/commands/ViewBCC", "sensitive", - h->visible_mask & E_MSG_COMPOSER_VISIBLE_BCC ? "1" : "0", NULL); -} - -void -e_msg_composer_hdrs_set_visible_mask (EMsgComposerHdrs *hdrs, int visible_mask) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - - hdrs->visible_mask = visible_mask; - headers_set_sensitivity (hdrs); -} - -void -e_msg_composer_hdrs_set_visible (EMsgComposerHdrs *hdrs, int visible_flags) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - - headers_set_visibility (hdrs, visible_flags); - gtk_widget_queue_resize (GTK_WIDGET (hdrs)); -} - -static void -setup_headers (EMsgComposerHdrs *hdrs, int visible_flags) -{ - create_headers (hdrs); - attach_headers (hdrs); - - headers_set_sensitivity (hdrs); - headers_set_visibility (hdrs, visible_flags); -} - - -/* GtkObject methods. */ - -static void -destroy (GtkObject *object) -{ - EMsgComposerHdrs *hdrs; - EMsgComposerHdrsPrivate *priv; - GSList *l, *n; - - hdrs = E_MSG_COMPOSER_HDRS (object); - priv = hdrs->priv; - - if (priv) { - if (priv->corba_select_names != CORBA_OBJECT_NIL) { - CORBA_Environment ev; - CORBA_exception_init (&ev); - bonobo_object_release_unref (priv->corba_select_names, &ev); - CORBA_exception_free (&ev); - priv->corba_select_names = CORBA_OBJECT_NIL; - } - - if (priv->tooltips) { - gtk_object_destroy (GTK_OBJECT (priv->tooltips)); - g_object_unref (priv->tooltips); - priv->tooltips = NULL; - } - - if (priv->accounts) { - g_signal_handlers_disconnect_matched(priv->accounts, G_SIGNAL_MATCH_DATA, 0, 0, NULL, NULL, hdrs); - g_object_unref (priv->accounts); - priv->accounts = NULL; - } - - l = priv->from_options; - while (l) { - EAccount *account; - GtkWidget *item = l->data; - - account = g_object_get_data ((GObject *) item, "account"); - g_object_unref (account); - - n = l->next; - g_slist_free_1 (l); - l = n; - } - - priv->from_options = NULL; - - g_free (priv); - hdrs->priv = NULL; - } - - if (GTK_OBJECT_CLASS (parent_class)->destroy != NULL) - (* GTK_OBJECT_CLASS (parent_class)->destroy) (object); -} - - -static void -class_init (EMsgComposerHdrsClass *class) -{ - GtkObjectClass *object_class; - - object_class = GTK_OBJECT_CLASS (class); - object_class->destroy = destroy; - - parent_class = g_type_class_ref (gtk_table_get_type ()); - - signals[SHOW_ADDRESS_DIALOG] = - g_signal_new ("show_address_dialog", - E_TYPE_MSG_COMPOSER_HDRS, - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET(EMsgComposerHdrsClass, show_address_dialog), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - - signals[SUBJECT_CHANGED] = - g_signal_new ("subject_changed", - E_TYPE_MSG_COMPOSER_HDRS, - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET(EMsgComposerHdrsClass, subject_changed), - NULL, NULL, - g_cclosure_marshal_VOID__STRING, - G_TYPE_NONE, - 1, G_TYPE_STRING); - - signals[HDRS_CHANGED] = - g_signal_new ("hdrs_changed", - E_TYPE_MSG_COMPOSER_HDRS, - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET(EMsgComposerHdrsClass, hdrs_changed), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - - signals[FROM_CHANGED] = - g_signal_new ("from_changed", - E_TYPE_MSG_COMPOSER_HDRS, - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET(EMsgComposerHdrsClass, from_changed), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); -} - -static void -init (EMsgComposerHdrs *hdrs) -{ - EMsgComposerHdrsPrivate *priv; - - priv = g_new0 (EMsgComposerHdrsPrivate, 1); - - priv->tooltips = gtk_tooltips_new (); - g_object_ref (priv->tooltips); - gtk_object_sink ((GtkObject *) priv->tooltips); - - priv->accounts = mail_config_get_accounts (); - g_object_ref (priv->accounts); - - hdrs->priv = priv; -} - - -GType -e_msg_composer_hdrs_get_type (void) -{ - static GType type = 0; - - if (type == 0) { - static const GTypeInfo info = { - sizeof (EMsgComposerHdrsClass), - NULL, - NULL, - (GClassInitFunc) class_init, - NULL, - NULL, - sizeof (EMsgComposerHdrs), - 0, - (GInstanceInitFunc) init, - }; - - type = g_type_register_static (gtk_table_get_type (), "EMsgComposerHdrs", &info, 0); - } - - return type; -} - -GtkWidget * -e_msg_composer_hdrs_new (BonoboUIComponent *uic, int visible_mask, int visible_flags) -{ - EMsgComposerHdrs *new; - EMsgComposerHdrsPrivate *priv; - - new = g_object_new (e_msg_composer_hdrs_get_type (), NULL); - priv = new->priv; - priv->uic = uic; - - g_object_ref (new); - gtk_object_sink (GTK_OBJECT (new)); - - if (!setup_corba (new)) { - g_object_unref (new); - return NULL; - } - - new->visible_mask = visible_mask; - - setup_headers (new, visible_flags); - - return GTK_WIDGET (new); -} - -static void -set_recipients_from_destv (CamelMimeMessage *msg, - EABDestination **to_destv, - EABDestination **cc_destv, - EABDestination **bcc_destv, - gboolean redirect) -{ - CamelInternetAddress *to_addr; - CamelInternetAddress *cc_addr; - CamelInternetAddress *bcc_addr; - CamelInternetAddress *target; - const char *text_addr, *header; - gboolean seen_hidden_list = FALSE; - int i; - - to_addr = camel_internet_address_new (); - cc_addr = camel_internet_address_new (); - bcc_addr = camel_internet_address_new (); - - if (to_destv) { - for (i = 0; to_destv[i] != NULL; ++i) { - text_addr = eab_destination_get_address (to_destv[i]); - - if (text_addr && *text_addr) { - target = to_addr; - if (eab_destination_is_evolution_list (to_destv[i]) - && !eab_destination_list_show_addresses (to_destv[i])) { - target = bcc_addr; - seen_hidden_list = TRUE; - } - - camel_address_decode (CAMEL_ADDRESS (target), text_addr); - } - } - } - - if (cc_destv) { - for (i = 0; cc_destv[i] != NULL; ++i) { - text_addr = eab_destination_get_address (cc_destv[i]); - if (text_addr && *text_addr) { - target = cc_addr; - if (eab_destination_is_evolution_list (cc_destv[i]) - && !eab_destination_list_show_addresses (cc_destv[i])) { - target = bcc_addr; - seen_hidden_list = TRUE; - } - - camel_address_decode (CAMEL_ADDRESS (target), text_addr); - } - } - } - - if (bcc_destv) { - for (i = 0; bcc_destv[i] != NULL; ++i) { - text_addr = eab_destination_get_address (bcc_destv[i]); - if (text_addr && *text_addr) { - camel_address_decode (CAMEL_ADDRESS (bcc_addr), text_addr); - } - } - } - - header = redirect ? CAMEL_RECIPIENT_TYPE_RESENT_TO : CAMEL_RECIPIENT_TYPE_TO; - if (camel_address_length (CAMEL_ADDRESS (to_addr)) > 0) { - camel_mime_message_set_recipients (msg, header, to_addr); - } else if (seen_hidden_list) { - camel_medium_set_header (CAMEL_MEDIUM (msg), header, "Undisclosed-Recipient:;"); - } - - header = redirect ? CAMEL_RECIPIENT_TYPE_RESENT_CC : CAMEL_RECIPIENT_TYPE_CC; - if (camel_address_length (CAMEL_ADDRESS (cc_addr)) > 0) { - camel_mime_message_set_recipients (msg, header, cc_addr); - } - - header = redirect ? CAMEL_RECIPIENT_TYPE_RESENT_BCC : CAMEL_RECIPIENT_TYPE_BCC; - if (camel_address_length (CAMEL_ADDRESS (bcc_addr)) > 0) { - camel_mime_message_set_recipients (msg, header, bcc_addr); - } - - camel_object_unref (to_addr); - camel_object_unref (cc_addr); - camel_object_unref (bcc_addr); -} - -static void -e_msg_composer_hdrs_to_message_internal (EMsgComposerHdrs *hdrs, - CamelMimeMessage *msg, - gboolean redirect) -{ - EABDestination **to_destv, **cc_destv, **bcc_destv; - CamelInternetAddress *addr; - const char *subject; - char *header; - - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - g_return_if_fail (CAMEL_IS_MIME_MESSAGE (msg)); - - subject = e_msg_composer_hdrs_get_subject (hdrs); - camel_mime_message_set_subject (msg, subject); - - addr = e_msg_composer_hdrs_get_from (hdrs); - if (redirect) { - header = camel_address_encode (CAMEL_ADDRESS (addr)); - camel_medium_set_header (CAMEL_MEDIUM (msg), "Resent-From", header); - g_free (header); - } else { - camel_mime_message_set_from (msg, addr); - } - camel_object_unref (addr); - - addr = e_msg_composer_hdrs_get_reply_to (hdrs); - if (addr) { - camel_mime_message_set_reply_to (msg, addr); - camel_object_unref (addr); - } - - if (hdrs->visible_mask & E_MSG_COMPOSER_VISIBLE_MASK_RECIPIENTS) { - to_destv = e_msg_composer_hdrs_get_to (hdrs); - cc_destv = e_msg_composer_hdrs_get_cc (hdrs); - bcc_destv = e_msg_composer_hdrs_get_bcc (hdrs); - - /* Attach destinations to the message. */ - - set_recipients_from_destv (msg, to_destv, cc_destv, bcc_destv, redirect); - - eab_destination_freev (to_destv); - eab_destination_freev (cc_destv); - eab_destination_freev (bcc_destv); - } - - if (hdrs->visible_mask & E_MSG_COMPOSER_VISIBLE_POSTTO) { - header = e_msg_composer_hdrs_get_post_to (hdrs); - camel_medium_set_header (CAMEL_MEDIUM (msg), "X-Evolution-PostTo", header); - g_free (header); - } -} - - -void -e_msg_composer_hdrs_to_message (EMsgComposerHdrs *hdrs, - CamelMimeMessage *msg) -{ - e_msg_composer_hdrs_to_message_internal (hdrs, msg, FALSE); -} - - -void -e_msg_composer_hdrs_to_redirect (EMsgComposerHdrs *hdrs, - CamelMimeMessage *msg) -{ - e_msg_composer_hdrs_to_message_internal (hdrs, msg, TRUE); -} - - -/* FIXME: yea, this could be better... but it's doubtful it'll be used much */ -void -e_msg_composer_hdrs_set_from_account (EMsgComposerHdrs *hdrs, - const char *account_name) -{ - GtkOptionMenu *omenu; - GConfClient *gconf; - GtkWidget *item; - char *uid = NULL; - GSList *l; - int i = 0; - - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - - omenu = GTK_OPTION_MENU (e_msg_composer_hdrs_get_from_omenu (hdrs)); - - if (!account_name) { - gconf = gconf_client_get_default (); - uid = gconf_client_get_string (gconf, "/apps/evolution/mail/default_account", NULL); - g_object_unref (gconf); - } - - /* find the item that represents the account and activate it */ - l = hdrs->priv->from_options; - while (l) { - EAccount *account; - item = l->data; - - account = g_object_get_data ((GObject *) item, "account"); - if (account_name) { - if (account->name && !strcmp (account_name, account->name)) { - /* set the correct optionlist item */ - gtk_option_menu_set_history (omenu, i); - g_signal_emit_by_name (item, "activate", hdrs); - g_free (uid); - - return; - } - } else if (uid && !strcmp (account->uid, uid)) { - /* set the default optionlist item */ - gtk_option_menu_set_history (omenu, i); - g_signal_emit_by_name (item, "activate", hdrs); - g_free (uid); - - return; - } - - l = l->next; - i++; - } - - g_free (uid); -} - -void -e_msg_composer_hdrs_set_reply_to (EMsgComposerHdrs *hdrs, - const char *reply_to) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - - gtk_entry_set_text (GTK_ENTRY (hdrs->priv->reply_to.entry), reply_to ? reply_to : ""); - - if (reply_to && *reply_to) - set_pair_visibility (hdrs, &hdrs->priv->cc, TRUE); -} - -void -e_msg_composer_hdrs_set_to (EMsgComposerHdrs *hdrs, - EABDestination **to_destv) -{ - char *str; - - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - - str = eab_destination_exportv (to_destv); - bonobo_widget_set_property (BONOBO_WIDGET (hdrs->priv->to.entry), "destinations", TC_CORBA_string, str ? str : "", NULL); - g_free (str); -} - -void -e_msg_composer_hdrs_set_cc (EMsgComposerHdrs *hdrs, - EABDestination **cc_destv) -{ - char *str; - - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - - str = eab_destination_exportv (cc_destv); - bonobo_widget_set_property (BONOBO_WIDGET (hdrs->priv->cc.entry), "destinations", TC_CORBA_string, str ? str :"", NULL); - if (str && *str) - set_pair_visibility (hdrs, &hdrs->priv->cc, TRUE); - g_free (str); -} - -void -e_msg_composer_hdrs_set_bcc (EMsgComposerHdrs *hdrs, - EABDestination **bcc_destv) -{ - char *str; - - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - - str = eab_destination_exportv (bcc_destv); - bonobo_widget_set_property (BONOBO_WIDGET (hdrs->priv->bcc.entry), "destinations", TC_CORBA_string, str ? str : "", NULL); - if (str && *str) - set_pair_visibility (hdrs, &hdrs->priv->bcc, TRUE); - g_free (str); -} - - -void -e_msg_composer_hdrs_set_post_to (EMsgComposerHdrs *hdrs, - const char *post_to) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - g_return_if_fail (post_to != NULL); - - em_folder_selection_button_set_selection ((EMFolderSelectionButton *) hdrs->priv->post_to.entry, post_to); -} - - -void -e_msg_composer_hdrs_set_subject (EMsgComposerHdrs *hdrs, - const char *subject) -{ - g_return_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs)); - g_return_if_fail (subject != NULL); - - gtk_entry_set_text ((GtkEntry *) hdrs->priv->subject.entry, subject); -} - - -CamelInternetAddress * -e_msg_composer_hdrs_get_from (EMsgComposerHdrs *hdrs) -{ - CamelInternetAddress *addr; - EAccount *account; - - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - if (!(account = hdrs->account)) { - /* FIXME: perhaps we should try the default account? */ - return NULL; - } - - addr = camel_internet_address_new (); - camel_internet_address_add (addr, account->id->name, account->id->address); - - return addr; -} - -CamelInternetAddress * -e_msg_composer_hdrs_get_reply_to (EMsgComposerHdrs *hdrs) -{ - CamelInternetAddress *addr; - const char *reply_to; - - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - reply_to = gtk_entry_get_text (GTK_ENTRY (hdrs->priv->reply_to.entry)); - - if (!reply_to || *reply_to == '\0') - return NULL; - - addr = camel_internet_address_new (); - if (camel_address_unformat (CAMEL_ADDRESS (addr), reply_to) == -1) { - camel_object_unref (CAMEL_OBJECT (addr)); - return NULL; - } - - return addr; -} - -EABDestination ** -e_msg_composer_hdrs_get_to (EMsgComposerHdrs *hdrs) -{ - char *str = NULL; - EABDestination **destv = NULL; - - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - bonobo_widget_get_property (BONOBO_WIDGET (hdrs->priv->to.entry), "destinations", TC_CORBA_string, &str, NULL); - - if (str != NULL) { - destv = eab_destination_importv (str); - g_free (str); - } - - return destv; -} - -EABDestination ** -e_msg_composer_hdrs_get_cc (EMsgComposerHdrs *hdrs) -{ - char *str = NULL; - EABDestination **destv = NULL; - - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - bonobo_widget_get_property (BONOBO_WIDGET (hdrs->priv->cc.entry), "destinations", TC_CORBA_string, &str, NULL); - - if (str != NULL) { - destv = eab_destination_importv (str); - g_free (str); - } - - return destv; -} - -EABDestination ** -e_msg_composer_hdrs_get_bcc (EMsgComposerHdrs *hdrs) -{ - char *str = NULL; - EABDestination **destv = NULL; - - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - bonobo_widget_get_property (BONOBO_WIDGET (hdrs->priv->bcc.entry), "destinations", TC_CORBA_string, &str, NULL); - - if (str != NULL) { - destv = eab_destination_importv (str); - g_free (str); - } - - return destv; -} - -EABDestination ** -e_msg_composer_hdrs_get_recipients (EMsgComposerHdrs *hdrs) -{ - EABDestination **to_destv; - EABDestination **cc_destv; - EABDestination **bcc_destv; - EABDestination **recip_destv; - int i, j, n; - - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - to_destv = e_msg_composer_hdrs_get_to (hdrs); - cc_destv = e_msg_composer_hdrs_get_cc (hdrs); - bcc_destv = e_msg_composer_hdrs_get_bcc (hdrs); - - n = 0; - - for (i = 0; to_destv && to_destv[i] != NULL; i++, n++); - for (i = 0; cc_destv && cc_destv[i] != NULL; i++, n++); - for (i = 0; bcc_destv && bcc_destv[i] != NULL; i++, n++); - - if (n == 0) - return NULL; - - recip_destv = g_new (EABDestination *, n + 1); - - j = 0; - - for (i = 0; to_destv && to_destv[i] != NULL; i++, j++) - recip_destv[j] = to_destv[i]; - for (i = 0; cc_destv && cc_destv[i] != NULL; i++, j++) - recip_destv[j] = cc_destv[i]; - for (i = 0; bcc_destv && bcc_destv[i] != NULL; i++, j++) - recip_destv[j] = bcc_destv[i]; - - g_assert (j == n); - recip_destv[j] = NULL; - - g_free (to_destv); - g_free (cc_destv); - g_free (bcc_destv); - - return recip_destv; -} - - -char * -e_msg_composer_hdrs_get_post_to (EMsgComposerHdrs *hdrs) -{ - const char *uri; - - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - uri = em_folder_selection_button_get_selection ((EMFolderSelectionButton *) hdrs->priv->post_to.entry); - - return g_strdup (uri); -} - - -const char * -e_msg_composer_hdrs_get_subject (EMsgComposerHdrs *hdrs) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - return gtk_entry_get_text ((GtkEntry *) hdrs->priv->subject.entry); -} - - -GtkWidget * -e_msg_composer_hdrs_get_reply_to_entry (EMsgComposerHdrs *hdrs) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - return hdrs->priv->reply_to.entry; -} - -GtkWidget * -e_msg_composer_hdrs_get_to_entry (EMsgComposerHdrs *hdrs) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - return hdrs->priv->to.entry; -} - -GtkWidget * -e_msg_composer_hdrs_get_cc_entry (EMsgComposerHdrs *hdrs) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - return hdrs->priv->cc.entry; -} - -GtkWidget * -e_msg_composer_hdrs_get_bcc_entry (EMsgComposerHdrs *hdrs) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - return hdrs->priv->bcc.entry; -} - -GtkWidget * -e_msg_composer_hdrs_get_post_to_label (EMsgComposerHdrs *hdrs) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - return hdrs->priv->post_to.entry; -} - -GtkWidget * -e_msg_composer_hdrs_get_subject_entry (EMsgComposerHdrs *hdrs) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - return hdrs->priv->subject.entry; -} - -GtkWidget * -e_msg_composer_hdrs_get_from_hbox (EMsgComposerHdrs *hdrs) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - return hdrs->priv->from.entry; -} - -GtkWidget * -e_msg_composer_hdrs_get_from_omenu (EMsgComposerHdrs *hdrs) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER_HDRS (hdrs), NULL); - - return GTK_WIDGET (g_object_get_data ((GObject *) hdrs->priv->from.entry, "from_menu")); -} diff --git a/composer/e-msg-composer-hdrs.h b/composer/e-msg-composer-hdrs.h deleted file mode 100644 index f3bedb1c34..0000000000 --- a/composer/e-msg-composer-hdrs.h +++ /dev/null @@ -1,152 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* msg-composer-hdrs.h - * - * Copyright (C) 1999 Ximian, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * published by the Free Software Foundation; either version 2 of the - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this program; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - * - * Author: Ettore Perazzoli - */ - - -#ifndef ___E_MSG_COMPOSER_HDRS_H__ -#define ___E_MSG_COMPOSER_HDRS_H__ - -#include <gtk/gtktable.h> - -#include <bonobo/bonobo-ui-component.h> - -#include <e-util/e-account.h> -#include <camel/camel-mime-message.h> -#include <addressbook/util/eab-destination.h> - -#ifdef __cplusplus -extern "C" { -#pragma } -#endif /* __cplusplus */ - -#define E_TYPE_MSG_COMPOSER_HDRS (e_msg_composer_hdrs_get_type ()) -#define E_MSG_COMPOSER_HDRS(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_MSG_COMPOSER_HDRS, EMsgComposerHdrs)) -#define E_MSG_COMPOSER_HDRS_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_MSG_COMPOSER_HDRS, EMsgComposerHdrsClass)) -#define E_IS_MSG_COMPOSER_HDRS(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_MSG_COMPOSER_HDRS)) -#define E_IS_MSG_COMPOSER_HDRS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((obj), E_TYPE_MSG_COMPOSER_HDRS)) - - -#define SELECT_NAMES_OAFIID "OAFIID:GNOME_Evolution_Addressbook_SelectNames:" BASE_VERSION - -typedef struct _EMsgComposerHdrs EMsgComposerHdrs; -typedef struct _EMsgComposerHdrsClass EMsgComposerHdrsClass; -typedef struct _EMsgComposerHdrsPrivate EMsgComposerHdrsPrivate; - -struct _EMsgComposerHdrs { - GtkTable parent; - - EMsgComposerHdrsPrivate *priv; - - EAccount *account; - - guint32 visible_mask; - - gboolean has_changed; -}; - -struct _EMsgComposerHdrsClass { - GtkTableClass parent_class; - - void (* show_address_dialog) (EMsgComposerHdrs *hdrs); - - void (* subject_changed) (EMsgComposerHdrs *hdrs, gchar *subject); - - void (* hdrs_changed) (EMsgComposerHdrs *hdrs); - - void (* from_changed) (EMsgComposerHdrs *hdrs); -}; - -typedef enum { - E_MSG_COMPOSER_VISIBLE_FROM = (1 << 0), - E_MSG_COMPOSER_VISIBLE_REPLYTO = (1 << 1), - E_MSG_COMPOSER_VISIBLE_TO = (1 << 2), - E_MSG_COMPOSER_VISIBLE_CC = (1 << 3), - E_MSG_COMPOSER_VISIBLE_BCC = (1 << 4), - E_MSG_COMPOSER_VISIBLE_POSTTO = (1 << 5), /* for posting to folders */ - E_MSG_COMPOSER_VISIBLE_NEWSGROUP = (1 << 6), /* for posting to newsgroups */ - E_MSG_COMPOSER_VISIBLE_SUBJECT = (1 << 7) -} EMsgComposerHeaderVisibleFlags; - -#define E_MSG_COMPOSER_VISIBLE_MASK_SENDER (E_MSG_COMPOSER_VISIBLE_FROM | E_MSG_COMPOSER_VISIBLE_REPLYTO) -#define E_MSG_COMPOSER_VISIBLE_MASK_BASIC (E_MSG_COMPOSER_VISIBLE_MASK_SENDER | E_MSG_COMPOSER_VISIBLE_SUBJECT) -#define E_MSG_COMPOSER_VISIBLE_MASK_RECIPIENTS (E_MSG_COMPOSER_VISIBLE_TO | E_MSG_COMPOSER_VISIBLE_CC | E_MSG_COMPOSER_VISIBLE_BCC) - -#define E_MSG_COMPOSER_VISIBLE_MASK_MAIL (E_MSG_COMPOSER_VISIBLE_MASK_BASIC | E_MSG_COMPOSER_VISIBLE_MASK_RECIPIENTS) -#define E_MSG_COMPOSER_VISIBLE_MASK_NEWS (E_MSG_COMPOSER_VISIBLE_MASK_BASIC | E_MSG_COMPOSER_VISIBLE_NEWSGROUP) -#define E_MSG_COMPOSER_VISIBLE_MASK_POST (E_MSG_COMPOSER_VISIBLE_MASK_BASIC | E_MSG_COMPOSER_VISIBLE_POSTTO) - - -GtkType e_msg_composer_hdrs_get_type (void); -GtkWidget *e_msg_composer_hdrs_new (BonoboUIComponent *uic, int visible_mask, int visible_flags); - -void e_msg_composer_hdrs_to_message (EMsgComposerHdrs *hdrs, - CamelMimeMessage *msg); - -void e_msg_composer_hdrs_to_redirect (EMsgComposerHdrs *hdrs, - CamelMimeMessage *msg); - - -void e_msg_composer_hdrs_set_from_account (EMsgComposerHdrs *hdrs, - const char *account_name); -void e_msg_composer_hdrs_set_reply_to (EMsgComposerHdrs *hdrs, - const char *reply_to); -void e_msg_composer_hdrs_set_to (EMsgComposerHdrs *hdrs, - EABDestination **to_destv); -void e_msg_composer_hdrs_set_cc (EMsgComposerHdrs *hdrs, - EABDestination **cc_destv); -void e_msg_composer_hdrs_set_bcc (EMsgComposerHdrs *hdrs, - EABDestination **bcc_destv); -void e_msg_composer_hdrs_set_post_to (EMsgComposerHdrs *hdrs, - const char *post_to); -void e_msg_composer_hdrs_set_subject (EMsgComposerHdrs *hdrs, - const char *subject); - -CamelInternetAddress *e_msg_composer_hdrs_get_from (EMsgComposerHdrs *hdrs); -CamelInternetAddress *e_msg_composer_hdrs_get_reply_to (EMsgComposerHdrs *hdrs); - -EABDestination **e_msg_composer_hdrs_get_to (EMsgComposerHdrs *hdrs); -EABDestination **e_msg_composer_hdrs_get_cc (EMsgComposerHdrs *hdrs); -EABDestination **e_msg_composer_hdrs_get_bcc (EMsgComposerHdrs *hdrs); -EABDestination **e_msg_composer_hdrs_get_recipients (EMsgComposerHdrs *hdrs); -char *e_msg_composer_hdrs_get_post_to (EMsgComposerHdrs *hdrs); -const char *e_msg_composer_hdrs_get_subject (EMsgComposerHdrs *hdrs); - -GtkWidget *e_msg_composer_hdrs_get_from_hbox (EMsgComposerHdrs *hdrs); -GtkWidget *e_msg_composer_hdrs_get_from_omenu (EMsgComposerHdrs *hdrs); -GtkWidget *e_msg_composer_hdrs_get_reply_to_entry (EMsgComposerHdrs *hdrs); -GtkWidget *e_msg_composer_hdrs_get_to_entry (EMsgComposerHdrs *hdrs); -GtkWidget *e_msg_composer_hdrs_get_cc_entry (EMsgComposerHdrs *hdrs); -GtkWidget *e_msg_composer_hdrs_get_bcc_entry (EMsgComposerHdrs *hdrs); -GtkWidget *e_msg_composer_hdrs_get_post_to_label (EMsgComposerHdrs *hdrs); -GtkWidget *e_msg_composer_hdrs_get_subject_entry (EMsgComposerHdrs *hdrs); - -void e_msg_composer_hdrs_set_visible_mask (EMsgComposerHdrs *hdrs, - int visible_mask); -void e_msg_composer_hdrs_set_visible (EMsgComposerHdrs *hdrs, - int visible_flags); - -#ifdef _cplusplus -} -#endif /* _cplusplus */ - - -#endif /* __E_MSG_COMPOSER_HDRS_H__ */ diff --git a/composer/e-msg-composer-select-file.c b/composer/e-msg-composer-select-file.c deleted file mode 100644 index 3726124837..0000000000 --- a/composer/e-msg-composer-select-file.c +++ /dev/null @@ -1,136 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* - * Authors: Ettore Perazzoli <ettore@ximian.com> - * Jeffrey Stedfast <fejj@ximian.com> - * Michael Zucchi <notzed@ximian.com> - * - * Copyright 2002 Ximian, Inc. (www.ximian.com) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA. - * - */ - - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <gtk/gtkbox.h> -#include <gtk/gtkcheckbutton.h> -#include <gtk/gtkfilesel.h> -#include <gtk/gtkmain.h> -#include <gtk/gtksignal.h> - -#include <libgnomeui/gnome-uidefs.h> -#include <libgnomeui/gnome-window-icon.h> - -#include "e-msg-composer-select-file.h" - -static GtkFileSelection * -run_selector(EMsgComposer *composer, const char *title, int multi, gboolean *showinline_p) -{ - GtkFileSelection *selection; - GtkWidget *showinline = NULL; - char *path; - - selection = (GtkFileSelection *)gtk_file_selection_new(title); - gtk_window_set_transient_for((GtkWindow *)selection, (GtkWindow *)composer); - gtk_window_set_wmclass((GtkWindow *)selection, "fileselection", "Evolution:composer"); - gtk_window_set_modal((GtkWindow *)selection, TRUE); - gnome_window_icon_set_from_file((GtkWindow *)selection, EVOLUTION_DATADIR "/images/evolution/compose-message.png"); - gtk_file_selection_set_select_multiple((GtkFileSelection *)selection, multi); - - /* restore last path used */ - path = g_object_get_data((GObject *)composer, "attach_path"); - if (path == NULL) { - path = g_strdup_printf("%s/", g_get_home_dir()); - gtk_file_selection_set_filename(selection, path); - g_free(path); - } else { - gtk_file_selection_set_filename(selection, path); - } - - if (showinline_p) { - showinline = gtk_check_button_new_with_label (_("Suggest automatic display of attachment")); - gtk_widget_show (showinline); - gtk_box_pack_end (GTK_BOX (selection->main_vbox), showinline, FALSE, FALSE, 4); - } - - if (gtk_dialog_run((GtkDialog *)selection) == GTK_RESPONSE_OK) { - if (showinline_p) - *showinline_p = gtk_toggle_button_get_active((GtkToggleButton *)showinline); - path = g_path_get_dirname(gtk_file_selection_get_filename(selection)); - g_object_set_data_full((GObject *)composer, "attach_path", g_strdup_printf("%s/", path), g_free); - g_free(path); - } else { - gtk_widget_destroy((GtkWidget *)selection); - selection = NULL; - } - - return selection; -} - -/** - * e_msg_composer_select_file: - * @composer: a composer - * @title: the title for the file selection dialog box - * - * This pops up a file selection dialog box with the given title - * and allows the user to select a file. - * - * Return value: the selected filename, or %NULL if the user - * cancelled. - **/ -char * -e_msg_composer_select_file (EMsgComposer *composer, const char *title) -{ - GtkFileSelection *selection; - char *name = NULL; - - selection = run_selector (composer, title, TRUE, NULL); - if (selection) { - name = g_strdup(gtk_file_selection_get_filename(selection)); - gtk_widget_destroy((GtkWidget *)selection); - } - - return name; -} - -GPtrArray * -e_msg_composer_select_file_attachments (EMsgComposer *composer, gboolean *showinline_p) -{ - GtkFileSelection *selection; - GPtrArray *list = NULL; - char **files; - int i; - - selection = run_selector(composer, _("Attach file(s)"), TRUE, showinline_p); - if (selection) { - files = gtk_file_selection_get_selections(selection); - - if (files != NULL) { - list = g_ptr_array_new (); - for (i = 0; files[i]; i++) - g_ptr_array_add (list, g_strdup (files[i])); - - g_strfreev (files); - } - - gtk_widget_destroy((GtkWidget *)selection); - } - - return list; -} - diff --git a/composer/e-msg-composer-select-file.h b/composer/e-msg-composer-select-file.h deleted file mode 100644 index 8216089130..0000000000 --- a/composer/e-msg-composer-select-file.h +++ /dev/null @@ -1,35 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* e-msg-composer-select-file.c - * - * Copyright (C) 2000 Ximian, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * published by the Free Software Foundation; either version 2 of the - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this program; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - * - * Author: Ettore Perazzoli - */ - -#ifndef E_MSG_COMPOSER_SELECT_FILE_H -#define E_MSG_COMPOSER_SELECT_FILE_H - -#include "e-msg-composer.h" - -char *e_msg_composer_select_file (EMsgComposer *composer, - const char *title); - -GPtrArray *e_msg_composer_select_file_attachments (EMsgComposer *composer, - gboolean *inline_p); - -#endif /* E_MSG_COMPOSER_SELECT_FILE_H */ diff --git a/composer/e-msg-composer.c b/composer/e-msg-composer.c deleted file mode 100644 index c5f59ae298..0000000000 --- a/composer/e-msg-composer.c +++ /dev/null @@ -1,5055 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* e-msg-composer.c - * - * Copyright (C) 1999-2003 Ximian, Inc. (www.ximian.com) - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * published by the Free Software Foundation; either version 2 of the - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this program; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - * - * Authors: - * Ettore Perazzoli (ettore@ximian.com) - * Jeffrey Stedfast (fejj@ximian.com) - * Miguel de Icaza (miguel@ximian.com) - * Radek Doulik (rodo@ximian.com) - * - */ - -/* - - TODO - - - Somehow users should be able to see if any file(s) are attached even when - the attachment bar is not shown. - - Should use EventSources to keep track of global changes made to configuration - values. Right now it ignores the problem olympically. Miguel. -*/ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#define SMIME_SUPPORTED 1 - -#include <string.h> -#include <stdlib.h> -#include <dirent.h> -#include <sys/time.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <sys/wait.h> -#include <unistd.h> -#include <errno.h> -#include <ctype.h> - -#include <gtk/gtkoptionmenu.h> -#include <gtk/gtkscrolledwindow.h> - -#include <gconf/gconf.h> -#include <gconf/gconf-client.h> - -#include <libgnome/gnome-exec.h> -#include <libgnomeui/gnome-uidefs.h> -#include <libgnomeui/gnome-window-icon.h> - -#include <bonobo/bonobo-exception.h> -#include <bonobo/bonobo-moniker-util.h> -#include <bonobo/bonobo-stream-memory.h> -#include <bonobo/bonobo-ui-util.h> -#include <bonobo/bonobo-widget.h> - -#include <libgnomevfs/gnome-vfs.h> - -#include <gtkhtml/htmlselection.h> - -#include <glade/glade.h> - -#include <gal/util/e-iconv.h> -#include <gal/e-text/e-entry.h> - -#include "e-util/e-dialog-utils.h" -#include "widgets/misc/e-charset-picker.h" - -#include <camel/camel-session.h> -#include <camel/camel-charset-map.h> -#include <camel/camel-stream-filter.h> -#include <camel/camel-mime-filter-charset.h> -#if defined (HAVE_NSS) && defined (SMIME_SUPPORTED) -#include <camel/camel-smime-context.h> -#endif - -#include "mail/em-utils.h" -#include "mail/mail-crypto.h" -#include "mail/mail-tools.h" -#include "mail/mail-ops.h" -#include "mail/mail-mt.h" -#include "mail/mail-session.h" - -#include "e-msg-composer.h" -#include "e-msg-composer-attachment-bar.h" -#include "e-msg-composer-hdrs.h" -#include "e-msg-composer-select-file.h" - -#include "evolution-shell-component-utils.h" - -#include "Editor.h" -#include "listener.h" - -#define GNOME_GTKHTML_EDITOR_CONTROL_ID "OAFIID:GNOME_GtkHTML_Editor:3.1" - -#define d(x) x - - -#define DEFAULT_WIDTH 600 -#define DEFAULT_HEIGHT 500 - -enum { - SEND, - SAVE_DRAFT, - LAST_SIGNAL -}; - -static guint signals[LAST_SIGNAL] = { 0 }; - -enum { - DND_TYPE_MESSAGE_RFC822, - DND_TYPE_TEXT_URI_LIST, - DND_TYPE_NETSCAPE_URL, - DND_TYPE_TEXT_VCARD, -}; - -static GtkTargetEntry drop_types[] = { - { "message/rfc822", 0, DND_TYPE_MESSAGE_RFC822 }, - { "text/uri-list", 0, DND_TYPE_TEXT_URI_LIST }, - { "_NETSCAPE_URL", 0, DND_TYPE_NETSCAPE_URL }, - { "text/x-vcard", 0, DND_TYPE_TEXT_VCARD }, -}; - -static int num_drop_types = sizeof (drop_types) / sizeof (drop_types[0]); - - -/* The parent class. */ -static BonoboWindowClass *parent_class = NULL; - -/* All the composer windows open, for bookkeeping purposes. */ -static GSList *all_composers = NULL; - - -/* local prototypes */ -static GList *add_recipients (GList *list, const char *recips, gboolean decode); - -static void handle_mailto (EMsgComposer *composer, const char *mailto); - -static void message_rfc822_dnd (EMsgComposer *composer, CamelStream *stream); - -/* used by e_msg_composer_add_message_attachments() */ -static void add_attachments_from_multipart (EMsgComposer *composer, CamelMultipart *multipart, - gboolean just_inlines, int depth); - -/* used by e_msg_composer_new_with_message() */ -static void handle_multipart (EMsgComposer *composer, CamelMultipart *multipart, int depth); -static void handle_multipart_alternative (EMsgComposer *composer, CamelMultipart *multipart, int depth); -static void handle_multipart_encrypted (EMsgComposer *composer, CamelMultipart *multipart, int depth); -static void handle_multipart_signed (EMsgComposer *composer, CamelMultipart *multipart, int depth); - -static void set_editor_signature (EMsgComposer *composer); - - -static GByteArray * -get_text (Bonobo_PersistStream persist, char *format) -{ - BonoboStream *stream; - BonoboStreamMem *stream_mem; - CORBA_Environment ev; - GByteArray *text; - - CORBA_exception_init (&ev); - - stream = bonobo_stream_mem_create (NULL, 0, FALSE, TRUE); - Bonobo_PersistStream_save (persist, (Bonobo_Stream)bonobo_object_corba_objref (BONOBO_OBJECT (stream)), - format, &ev); - if (ev._major != CORBA_NO_EXCEPTION) { - g_warning ("Exception getting mail '%s'", - bonobo_exception_get_text (&ev)); - return NULL; - } - - CORBA_exception_free (&ev); - - stream_mem = BONOBO_STREAM_MEM (stream); - text = g_byte_array_new (); - g_byte_array_append (text, stream_mem->buffer, stream_mem->pos); - bonobo_object_unref (BONOBO_OBJECT (stream)); - - return text; -} - -#define LINE_LEN 72 - -static CamelTransferEncoding -best_encoding (GByteArray *buf, const char *charset) -{ - char *in, *out, outbuf[256], *ch; - size_t inlen, outlen; - int status, count = 0; - iconv_t cd; - - if (!charset) - return -1; - - cd = e_iconv_open (charset, "utf-8"); - if (cd == (iconv_t) -1) - return -1; - - in = buf->data; - inlen = buf->len; - do { - out = outbuf; - outlen = sizeof (outbuf); - status = e_iconv (cd, (const char **) &in, &inlen, &out, &outlen); - for (ch = out - 1; ch >= outbuf; ch--) { - if ((unsigned char)*ch > 127) - count++; - } - } while (status == (size_t) -1 && errno == E2BIG); - e_iconv_close (cd); - - if (status == (size_t) -1) - return -1; - - if (count == 0) - return CAMEL_TRANSFER_ENCODING_7BIT; - else if (count <= buf->len * 0.17) - return CAMEL_TRANSFER_ENCODING_QUOTEDPRINTABLE; - else - return CAMEL_TRANSFER_ENCODING_BASE64; -} - -static const char * -composer_get_default_charset_setting (void) -{ - GConfClient *gconf; - const char *charset; - char *buf; - - gconf = gconf_client_get_default (); - buf = gconf_client_get_string (gconf, "/apps/evolution/mail/composer/charset", NULL); - - if (buf == NULL || buf[0] == '\0') { - g_free (buf); - buf = gconf_client_get_string (gconf, "/apps/evolution/mail/format/charset", NULL); - if (buf && buf[0] == '\0') { - g_free (buf); - buf = NULL; - } - } - - g_object_unref (gconf); - - if (buf != NULL) { - charset = e_iconv_charset_name (buf); - g_free (buf); - } else - charset = e_iconv_locale_charset (); - - return charset ? charset : "us-ascii"; -} - -static const char * -best_charset (GByteArray *buf, const char *default_charset, CamelTransferEncoding *encoding) -{ - const char *charset; - - /* First try US-ASCII */ - *encoding = best_encoding (buf, "US-ASCII"); - if (*encoding == CAMEL_TRANSFER_ENCODING_7BIT) - return NULL; - - /* Next try the user-specified charset for this message */ - charset = default_charset; - *encoding = best_encoding (buf, charset); - if (*encoding != -1) - return charset; - - /* Now try the user's default charset from the mail config */ - charset = composer_get_default_charset_setting (); - *encoding = best_encoding (buf, charset); - if (*encoding != -1) - return charset; - - /* Try to find something that will work */ - charset = camel_charset_best (buf->data, buf->len); - if (!charset) - *encoding = CAMEL_TRANSFER_ENCODING_7BIT; - else - *encoding = best_encoding (buf, charset); - - return charset; -} - -static gboolean -clear_inline_images (gpointer key, gpointer value, gpointer user_data) -{ - g_free (key); - camel_object_unref (value); - - return TRUE; -} - -static void -clear_current_images (EMsgComposer *composer) -{ - g_list_free (composer->current_images); - composer->current_images = NULL; -} - -static gboolean -clear_url (gpointer key, gpointer value, gpointer user_data) -{ - g_free (key); - - return TRUE; -} - -void -e_msg_composer_clear_inlined_table (EMsgComposer *composer) -{ - g_hash_table_foreach_remove (composer->inline_images, clear_inline_images, NULL); - g_hash_table_foreach_remove (composer->inline_images_by_url, clear_url, NULL); -} - -static void -add_inlined_images (EMsgComposer *composer, CamelMultipart *multipart) -{ - GList *d = composer->current_images; - GHashTable *added; - - added = g_hash_table_new (g_direct_hash, g_direct_equal); - while (d) { - CamelMimePart *part = d->data; - - if (!g_hash_table_lookup (added, part)) { - camel_multipart_add_part (multipart, part); - g_hash_table_insert (added, part, part); - } - d = d->next; - } - g_hash_table_destroy (added); -} - -/* This functions builds a CamelMimeMessage for the message that the user has - * composed in `composer'. - */ -static CamelMimeMessage * -build_message (EMsgComposer *composer, gboolean save_html_object_data) -{ - EMsgComposerAttachmentBar *attachment_bar = - E_MSG_COMPOSER_ATTACHMENT_BAR (composer->attachment_bar); - EMsgComposerHdrs *hdrs = E_MSG_COMPOSER_HDRS (composer->hdrs); - CamelDataWrapper *plain, *html, *current; - CamelTransferEncoding plain_encoding; - GPtrArray *recipients = NULL; - CamelMultipart *body = NULL; - CamelContentType *type; - CamelMimeMessage *new; - const char *charset = NULL; - CamelStream *stream; - CamelMimePart *part; - CamelException ex; - GByteArray *data; - int i; - - if (composer->persist_stream_interface == CORBA_OBJECT_NIL) - return NULL; - - /* evil kludgy hack for Redirect */ - if (composer->redirect) { - e_msg_composer_hdrs_to_redirect (hdrs, composer->redirect); - camel_object_ref (composer->redirect); - return composer->redirect; - } - - new = camel_mime_message_new (); - e_msg_composer_hdrs_to_message (hdrs, new); - for (i = 0; i < composer->extra_hdr_names->len; i++) { - camel_medium_add_header (CAMEL_MEDIUM (new), - composer->extra_hdr_names->pdata[i], - composer->extra_hdr_values->pdata[i]); - } - - if (composer->mime_body) { - plain_encoding = CAMEL_TRANSFER_ENCODING_7BIT; - for (i = 0; composer->mime_body[i]; i++) { - if ((unsigned char) composer->mime_body[i] > 127) { - plain_encoding = CAMEL_TRANSFER_ENCODING_QUOTEDPRINTABLE; - break; - } - } - data = g_byte_array_new (); - g_byte_array_append (data, composer->mime_body, strlen (composer->mime_body)); - type = camel_content_type_decode (composer->mime_type); - } else { - data = get_text (composer->persist_stream_interface, "text/plain"); - if (!data) { - /* The component has probably died */ - camel_object_unref (CAMEL_OBJECT (new)); - return NULL; - } - - /* FIXME: we may want to do better than this... */ - charset = best_charset (data, composer->charset, &plain_encoding); - type = camel_content_type_new ("text", "plain"); - if (charset) - camel_content_type_set_param (type, "charset", charset); - } - - stream = camel_stream_mem_new_with_byte_array (data); - - /* convert the stream to the appropriate charset */ - if (charset && strcasecmp (charset, "UTF-8") != 0) { - CamelStreamFilter *filter_stream; - CamelMimeFilterCharset *filter; - - filter_stream = camel_stream_filter_new_with_stream (stream); - camel_object_unref (stream); - - stream = (CamelStream *) filter_stream; - filter = camel_mime_filter_charset_new_convert ("UTF-8", charset); - camel_stream_filter_add (filter_stream, (CamelMimeFilter *) filter); - camel_object_unref (filter); - } - - /* construct the content object */ - plain = camel_data_wrapper_new (); - camel_data_wrapper_construct_from_stream (plain, stream); - camel_object_unref (stream); - - camel_data_wrapper_set_mime_type_field (plain, type); - camel_content_type_unref (type); - - if (composer->send_html) { - CORBA_Environment ev; - clear_current_images (composer); - - if (save_html_object_data) { - CORBA_exception_init (&ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "save-data-on", &ev); - } - data = get_text (composer->persist_stream_interface, "text/html"); - if (save_html_object_data) { - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "save-data-off", &ev); - CORBA_exception_free (&ev); - } - - if (!data) { - /* The component has probably died */ - camel_object_unref (new); - camel_object_unref (plain); - return NULL; - } - - html = camel_data_wrapper_new (); - - stream = camel_stream_mem_new_with_byte_array (data); - camel_data_wrapper_construct_from_stream (html, stream); - camel_object_unref (stream); - camel_data_wrapper_set_mime_type (html, "text/html; charset=utf-8"); - - /* Build the multipart/alternative */ - body = camel_multipart_new (); - camel_data_wrapper_set_mime_type (CAMEL_DATA_WRAPPER (body), - "multipart/alternative"); - camel_multipart_set_boundary (body, NULL); - - part = camel_mime_part_new (); - camel_medium_set_content_object (CAMEL_MEDIUM (part), plain); - camel_object_unref (plain); - camel_mime_part_set_encoding (part, plain_encoding); - camel_multipart_add_part (body, part); - camel_object_unref (part); - - part = camel_mime_part_new (); - camel_medium_set_content_object (CAMEL_MEDIUM (part), html); - camel_object_unref (html); - camel_multipart_add_part (body, part); - camel_object_unref (part); - - /* If there are inlined images, construct a - * multipart/related containing the - * multipart/alternative and the images. - */ - if (composer->current_images) { - CamelMultipart *html_with_images; - - html_with_images = camel_multipart_new (); - camel_data_wrapper_set_mime_type ( - CAMEL_DATA_WRAPPER (html_with_images), - "multipart/related; type=\"multipart/alternative\""); - camel_multipart_set_boundary (html_with_images, NULL); - - part = camel_mime_part_new (); - camel_medium_set_content_object (CAMEL_MEDIUM (part), CAMEL_DATA_WRAPPER (body)); - camel_object_unref (body); - camel_multipart_add_part (html_with_images, part); - camel_object_unref (part); - - add_inlined_images (composer, html_with_images); - clear_current_images (composer); - - current = CAMEL_DATA_WRAPPER (html_with_images); - } else - current = CAMEL_DATA_WRAPPER (body); - } else - current = plain; - - if (e_msg_composer_attachment_bar_get_num_attachments (attachment_bar)) { - CamelMultipart *multipart = camel_multipart_new (); - - if (composer->is_alternative) { - camel_data_wrapper_set_mime_type (CAMEL_DATA_WRAPPER (multipart), - "multipart/alternative"); - } - - /* Generate a random boundary. */ - camel_multipart_set_boundary (multipart, NULL); - - part = camel_mime_part_new (); - camel_medium_set_content_object (CAMEL_MEDIUM (part), current); - if (current == plain) - camel_mime_part_set_encoding (part, plain_encoding); - camel_object_unref (current); - camel_multipart_add_part (multipart, part); - camel_object_unref (part); - - e_msg_composer_attachment_bar_to_multipart (attachment_bar, multipart, composer->charset); - - if (composer->is_alternative) { - int i; - - for (i = camel_multipart_get_number (multipart); i > 1; i--) { - part = camel_multipart_get_part (multipart, i - 1); - camel_medium_remove_header (CAMEL_MEDIUM (part), "Content-Disposition"); - } - } - - current = CAMEL_DATA_WRAPPER (multipart); - } - - camel_exception_init (&ex); - - /* Setup working recipient list if we're encrypting */ - if (composer->pgp_encrypt -#if defined (HAVE_NSS) && defined (SMIME_SUPPORTED) - || composer->smime_encrypt -#endif - ) { - int i, j; - const char *types[] = { CAMEL_RECIPIENT_TYPE_TO, CAMEL_RECIPIENT_TYPE_CC, CAMEL_RECIPIENT_TYPE_BCC }; - - recipients = g_ptr_array_new(); - for (i=0; i < sizeof(types)/sizeof(types[0]); i++) { - const CamelInternetAddress *addr; - const char *address; - - addr = camel_mime_message_get_recipients(new, types[i]); - for (j=0;camel_internet_address_get(addr, j, NULL, &address); j++) - g_ptr_array_add(recipients, g_strdup (address)); - - } - } - - if (composer->pgp_sign || composer->pgp_encrypt) { - const char *pgp_userid; - CamelInternetAddress *from = NULL; - CamelCipherContext *cipher; - - part = camel_mime_part_new (); - camel_medium_set_content_object (CAMEL_MEDIUM (part), current); - if (current == plain) - camel_mime_part_set_encoding (part, plain_encoding); - camel_object_unref (current); - - if (hdrs->account && hdrs->account->pgp_key && *hdrs->account->pgp_key) { - pgp_userid = hdrs->account->pgp_key; - } else { - from = e_msg_composer_hdrs_get_from(hdrs); - camel_internet_address_get(from, 0, NULL, &pgp_userid); - } - - if (composer->pgp_sign) { - CamelMimePart *npart = camel_mime_part_new(); - - cipher = mail_crypto_get_pgp_cipher_context(hdrs->account); - camel_cipher_sign(cipher, pgp_userid, CAMEL_CIPHER_HASH_SHA1, part, npart, &ex); - camel_object_unref(cipher); - - if (camel_exception_is_set(&ex)) { - camel_object_unref(npart); - goto exception; - } - - camel_object_unref(part); - part = npart; - } - - if (composer->pgp_encrypt) { - CamelMimePart *npart = camel_mime_part_new(); - - /* check to see if we should encrypt to self, NB gets removed immediately after use */ - if (hdrs->account && hdrs->account->pgp_encrypt_to_self && pgp_userid) - g_ptr_array_add (recipients, (char *)pgp_userid); - - cipher = mail_crypto_get_pgp_cipher_context (hdrs->account); - camel_cipher_encrypt(cipher, pgp_userid, recipients, part, npart, &ex); - camel_object_unref (cipher); - - if (hdrs->account && hdrs->account->pgp_encrypt_to_self && pgp_userid) - g_ptr_array_set_size(recipients, recipients->len - 1); - - if (camel_exception_is_set (&ex)) { - camel_object_unref(npart); - goto exception; - } - - camel_object_unref (part); - part = npart; - } - - if (from) - camel_object_unref (from); - - current = camel_medium_get_content_object (CAMEL_MEDIUM (part)); - camel_object_ref (current); - camel_object_unref (part); - } - -#if defined (HAVE_NSS) && defined (SMIME_SUPPORTED) - if (composer->smime_sign || composer->smime_encrypt) { - CamelInternetAddress *from = NULL; - CamelCipherContext *cipher; - - part = camel_mime_part_new(); - camel_medium_set_content_object((CamelMedium *)part, current); - if (current == plain) - camel_mime_part_set_encoding(part, plain_encoding); - camel_object_unref(current); - - if (composer->smime_sign - && (hdrs->account == NULL || hdrs->account->smime_sign_key == NULL || hdrs->account->smime_sign_key[0] == 0)) { - camel_exception_setv(&ex, 1, _("Cannot sign outgoing message: No signing certificate set for from account")); - goto exception; - } - - if (composer->smime_encrypt - && (hdrs->account == NULL || hdrs->account->smime_sign_key == NULL || hdrs->account->smime_sign_key[0] == 0)) { - camel_exception_setv(&ex, 1, _("Cannot encrypt outgoing message: No encryption certificate set for from account")); - goto exception; - } - - if (composer->smime_sign) { - CamelMimePart *npart = camel_mime_part_new(); - - cipher = camel_smime_context_new(session); - - /* if we're also encrypting, envelope-sign rather than clear-sign */ - if (composer->smime_encrypt) { - camel_smime_context_set_sign_mode((CamelSMIMEContext *)cipher, CAMEL_SMIME_SIGN_ENVELOPED); - camel_smime_context_set_encrypt_key((CamelSMIMEContext *)cipher, TRUE, hdrs->account->smime_encrypt_key); - } else if (hdrs->account && hdrs->account->smime_encrypt_key && *hdrs->account->smime_encrypt_key) { - camel_smime_context_set_encrypt_key((CamelSMIMEContext *)cipher, TRUE, hdrs->account->smime_encrypt_key); - } - - camel_cipher_sign(cipher, hdrs->account->smime_sign_key, CAMEL_CIPHER_HASH_SHA1, part, npart, &ex); - camel_object_unref(cipher); - - if (camel_exception_is_set(&ex)) { - camel_object_unref(npart); - goto exception; - } - - camel_object_unref(part); - part = npart; - } - - if (composer->smime_encrypt) { - /* check to see if we should encrypt to self, NB removed after use */ - if (hdrs->account->smime_encrypt_to_self) - g_ptr_array_add(recipients, hdrs->account->smime_encrypt_key); - - cipher = camel_smime_context_new(session); - camel_smime_context_set_encrypt_key((CamelSMIMEContext *)cipher, TRUE, hdrs->account->smime_encrypt_key); - - camel_cipher_encrypt(cipher, NULL, recipients, part, (CamelMimePart *)new, &ex); - camel_object_unref(cipher); - - if (camel_exception_is_set(&ex)) - goto exception; - - if (hdrs->account->smime_encrypt_to_self) - g_ptr_array_set_size(recipients, recipients->len - 1); - } - - if (from) - camel_object_unref(from); - - /* we replaced the message directly, we don't want to do reparenting foo */ - if (composer->smime_encrypt) { - camel_object_unref(part); - goto skip_content; - } else { - current = camel_medium_get_content_object((CamelMedium *)part); - camel_object_ref(current); - camel_object_unref(part); - } - } -#endif /* HAVE_NSS */ - - camel_medium_set_content_object (CAMEL_MEDIUM (new), current); - if (current == plain) - camel_mime_part_set_encoding (CAMEL_MIME_PART (new), plain_encoding); - camel_object_unref (current); - -skip_content: - - if (recipients) { - for (i=0; i<recipients->len; i++) - g_free(recipients->pdata[i]); - g_ptr_array_free(recipients, TRUE); - } - - /* Attach whether this message was written in HTML */ - camel_medium_set_header (CAMEL_MEDIUM (new), "X-Evolution-Format", - composer->send_html ? "text/html" : "text/plain"); - - return new; - - exception: - - if (part != CAMEL_MIME_PART (new)) - camel_object_unref (part); - - camel_object_unref (new); - - if (ex.id != CAMEL_EXCEPTION_USER_CANCEL) { - GtkWidget *dialog; - - dialog = gtk_message_dialog_new(GTK_WINDOW(composer), - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT, - GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, - "%s", camel_exception_get_description (&ex)); - gtk_dialog_run(GTK_DIALOG(dialog)); - gtk_widget_destroy(dialog); - } - - camel_exception_clear (&ex); - - if (recipients) { - for (i=0; i<recipients->len; i++) - g_free(recipients->pdata[i]); - g_ptr_array_free(recipients, TRUE); - } - - return NULL; -} - - -static char * -get_file_content (EMsgComposer *composer, const char *file_name, gboolean want_html, guint flags, gboolean warn) -{ - CamelStreamFilter *filtered_stream; - CamelStreamMem *memstream; - CamelMimeFilter *html, *charenc; - CamelStream *stream; - GByteArray *buffer; - const char *charset; - char *content; - int fd; - - fd = open (file_name, O_RDONLY); - if (fd == -1) { - if (warn) { - GtkWidget *dialog; - - dialog = gtk_message_dialog_new(GTK_WINDOW(composer), - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT, - GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, - _("Error while reading file %s:\n%s"), - file_name, g_strerror (errno)); - gtk_dialog_run(GTK_DIALOG(dialog)); - gtk_widget_destroy(dialog); - } - return g_strdup (""); - } - - stream = camel_stream_fs_new_with_fd (fd); - - if (want_html) { - filtered_stream = camel_stream_filter_new_with_stream (stream); - camel_object_unref (stream); - - html = camel_mime_filter_tohtml_new (flags, 0); - camel_stream_filter_add (filtered_stream, html); - camel_object_unref (html); - - stream = (CamelStream *) filtered_stream; - } - - memstream = (CamelStreamMem *) camel_stream_mem_new (); - buffer = g_byte_array_new (); - camel_stream_mem_set_byte_array (memstream, buffer); - - camel_stream_write_to_stream (stream, (CamelStream *) memstream); - camel_object_unref (stream); - - /* The newer signature UI saves signatures in UTF-8, but we still need to check that - the signature is valid UTF-8 because it is possible that the user imported a - signature file that is in his/her locale charset. If it's not in UTF-8 and not in - the charset the composer is in (or their default mail charset) then fuck it, - there's nothing we can do. */ - if (buffer->len && !g_utf8_validate (buffer->data, buffer->len, NULL)) { - stream = (CamelStream *) memstream; - memstream = (CamelStreamMem *) camel_stream_mem_new (); - camel_stream_mem_set_byte_array (memstream, g_byte_array_new ()); - - filtered_stream = camel_stream_filter_new_with_stream (stream); - camel_object_unref (stream); - - charset = composer ? composer->charset : composer_get_default_charset_setting (); - charenc = (CamelMimeFilter *) camel_mime_filter_charset_new_convert (charset, "utf-8"); - camel_stream_filter_add (filtered_stream, charenc); - camel_object_unref (charenc); - - camel_stream_write_to_stream ((CamelStream *) filtered_stream, (CamelStream *) memstream); - camel_object_unref (filtered_stream); - g_byte_array_free (buffer, TRUE); - - buffer = memstream->buffer; - } - - camel_object_unref (memstream); - - g_byte_array_append (buffer, "", 1); - content = buffer->data; - g_byte_array_free (buffer, FALSE); - - return content; -} - -char * -e_msg_composer_get_sig_file_content (const char *sigfile, gboolean in_html) -{ - if (!sigfile || !*sigfile) { - return NULL; - } - - return get_file_content (NULL, sigfile, !in_html, CAMEL_MIME_FILTER_TOHTML_PRESERVE_8BIT, FALSE); -} - -static void -prepare_engine (EMsgComposer *composer) -{ - CORBA_Environment ev; - - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - /* printf ("prepare_engine\n"); */ - - CORBA_exception_init (&ev); - composer->editor_engine = (GNOME_GtkHTML_Editor_Engine) Bonobo_Unknown_queryInterface - (bonobo_widget_get_objref (BONOBO_WIDGET (composer->editor)), "IDL:GNOME/GtkHTML/Editor/Engine:1.0", &ev); - if ((composer->editor_engine != CORBA_OBJECT_NIL) && (ev._major == CORBA_NO_EXCEPTION)) { - - /* printf ("trying set listener\n"); */ - composer->editor_listener = BONOBO_OBJECT (listener_new (composer)); - if (composer->editor_listener != NULL) - GNOME_GtkHTML_Editor_Engine__set_listener (composer->editor_engine, - (GNOME_GtkHTML_Editor_Listener) - bonobo_object_dup_ref - (bonobo_object_corba_objref (composer->editor_listener), - &ev), - &ev); - - if ((ev._major != CORBA_NO_EXCEPTION) || (composer->editor_listener == NULL)) { - CORBA_Environment err_ev; - - CORBA_exception_init (&err_ev); - - Bonobo_Unknown_unref (composer->editor_engine, &err_ev); - CORBA_Object_release (composer->editor_engine, &err_ev); - - CORBA_exception_free (&err_ev); - - composer->editor_engine = CORBA_OBJECT_NIL; - g_warning ("Can't establish Editor Listener\n"); - } - } else { - composer->editor_engine = CORBA_OBJECT_NIL; - g_warning ("Can't get Editor Engine\n"); - } - - CORBA_exception_free (&ev); -} - -static gchar * -encode_signature_name (const gchar *name) -{ - const gchar *s; - gchar *ename, *e; - gint len = 0; - - s = name; - while (*s) { - len ++; - if (*s == '"' || *s == '.' || *s == '=') - len ++; - s ++; - } - - ename = g_new (gchar, len + 1); - - s = name; - e = ename; - while (*s) { - if (*s == '"') { - *e = '.'; - e ++; - *e = '1'; - e ++; - } else if (*s == '=') { - *e = '.'; - e ++; - *e = '2'; - e ++; - } else { - *e = *s; - e ++; - } - if (*s == '.') { - *e = '.'; - e ++; - } - s ++; - } - *e = 0; - - return ename; -} - -static gchar * -decode_signature_name (const gchar *name) -{ - const gchar *s; - gchar *dname, *d; - gint len = 0; - - s = name; - while (*s) { - len ++; - if (*s == '.') { - s ++; - if (!*s || !(*s == '.' || *s == '1' || *s == '2')) - return NULL; - } - s ++; - } - - dname = g_new (gchar, len + 1); - - s = name; - d = dname; - while (*s) { - if (*s == '.') { - s ++; - if (!*s || !(*s == '.' || *s == '1' || *s == '2')) { - g_free (dname); - return NULL; - } - if (*s == '1') - *d = '"'; - else if (*s == '2') - *d = '='; - else - *d = '.'; - } else - *d = *s; - d ++; - s ++; - } - *d = 0; - - return dname; -} - -#define CONVERT_SPACES CAMEL_MIME_FILTER_TOHTML_CONVERT_SPACES - -static char * -get_signature_html (EMsgComposer *composer) -{ - gboolean format_html = FALSE; - char *text = NULL, *html = NULL, *sig_file = NULL, *script = NULL; - - if (composer->signature) { - sig_file = composer->signature->filename; - format_html = composer->signature->html; - script = composer->signature->script; - } else if (composer->auto_signature) { - EAccountIdentity *id; - char *organization; - char *address; - char *name; - - id = E_MSG_COMPOSER_HDRS (composer->hdrs)->account->id; - address = id->address ? camel_text_to_html (id->address, CONVERT_SPACES, 0) : NULL; - name = id->name ? camel_text_to_html (id->name, CONVERT_SPACES, 0) : NULL; - organization = id->organization ? camel_text_to_html (id->organization, CONVERT_SPACES, 0) : NULL; - - text = g_strdup_printf ("-- <BR>%s%s%s%s%s%s%s%s", - name ? name : "", - (address && *address) ? " <<A HREF=\"mailto:" : "", - address ? address : "", - (address && *address) ? "\">" : "", - address ? address : "", - (address && *address) ? "</A>>" : "", - (organization && *organization) ? "<BR>" : "", - organization ? organization : ""); - g_free (address); - g_free (name); - g_free (organization); - format_html = TRUE; - } - - if (!text) { - if (script) - text = mail_config_signature_run_script (script); - else { - if (!sig_file) - return NULL; - /* printf ("sig file: %s\n", sig_file); */ - text = e_msg_composer_get_sig_file_content (sig_file, format_html); - } - } - - /* printf ("text: %s\n", text); */ - if (text) { - gchar *encoded_name = NULL; - - if (composer->signature) - encoded_name = encode_signature_name (composer->signature->name); - - /* The signature dash convention ("-- \n") is specified in the - * "Son of RFC 1036": http://www.chemie.fu-berlin.de/outerspace/netnews/son-of-1036.html, - * section 4.3.2. - */ - html = g_strdup_printf ("<!--+GtkHTML:<DATA class=\"ClueFlow\" key=\"signature\" value=\"1\">-->" - "<!--+GtkHTML:<DATA class=\"ClueFlow\" key=\"signature_name\" value=\"%s%s\">-->" - "<TABLE WIDTH=\"100%%\" CELLSPACING=\"0\" CELLPADDING=\"0\"><TR><TD>" - "%s%s%s%s" - "</TD></TR></TABLE>", - composer->signature ? "name:" : "auto", - composer->signature ? encoded_name : "", - format_html ? "" : "<PRE>\n", - format_html || (!strncmp ("-- \n", text, 4) || strstr(text, "\n-- \n")) ? "" : "-- \n", - text, - format_html ? "" : "</PRE>\n"); - g_free (text); - g_free (encoded_name); - text = html; - } - - return text; -} - -static void -set_editor_text (EMsgComposer *composer, const char *text) -{ - Bonobo_PersistStream persist; - BonoboStream *stream; - BonoboWidget *editor; - CORBA_Environment ev; - Bonobo_Unknown object; - - g_return_if_fail (composer->persist_stream_interface != CORBA_OBJECT_NIL); - - persist = composer->persist_stream_interface; - - editor = BONOBO_WIDGET (composer->editor); - - CORBA_exception_init (&ev); - - stream = bonobo_stream_mem_create (text, strlen (text), TRUE, FALSE); - object = bonobo_object_corba_objref (BONOBO_OBJECT (stream)); - Bonobo_PersistStream_load (persist, (Bonobo_Stream) object, "text/html", &ev); - if (ev._major != CORBA_NO_EXCEPTION) { - /* FIXME. Some error message. */ - bonobo_object_unref (BONOBO_OBJECT (stream)); - CORBA_exception_free (&ev); - return; - } - - CORBA_exception_free (&ev); - - bonobo_object_unref (BONOBO_OBJECT (stream)); -} - -/* Commands. */ - -static void -show_attachments (EMsgComposer *composer, - gboolean show) -{ - if (show) { - gtk_widget_show (composer->attachment_scrolled_window); - gtk_widget_show (composer->attachment_bar); - } else { - gtk_widget_hide (composer->attachment_scrolled_window); - gtk_widget_hide (composer->attachment_bar); - } - - composer->attachment_bar_visible = show; - - /* Update the GUI. */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/ViewAttach", - "state", show ? "1" : "0", NULL); -} - -static void -save (EMsgComposer *composer, const char *default_filename) -{ - CORBA_Environment ev; - char *filename; - int fd; - - if (default_filename != NULL) - filename = g_strdup (default_filename); - else - filename = e_msg_composer_select_file (composer, _("Save as...")); - - if (filename == NULL) - return; - - /* check to see if we already have the file and that we can create it */ - if ((fd = open (filename, O_RDONLY | O_CREAT | O_EXCL, 0777)) == -1) { - int resp, errnosav = errno; - GtkWidget *dialog; - struct stat st; - - if (stat (filename, &st) == 0 && S_ISREG (st.st_mode)) { - dialog = gtk_message_dialog_new (GTK_WINDOW (composer), - GTK_DIALOG_MODAL | GTK_DIALOG_DESTROY_WITH_PARENT, - GTK_MESSAGE_QUESTION, GTK_BUTTONS_YES_NO, - _("File exists, overwrite?")); - resp = gtk_dialog_run (GTK_DIALOG (dialog)); - gtk_widget_destroy (dialog); - if (resp != GTK_RESPONSE_YES) { - g_free (filename); - return; - } - } else { - dialog = gtk_message_dialog_new (GTK_WINDOW (composer), - GTK_DIALOG_MODAL | GTK_DIALOG_DESTROY_WITH_PARENT, - GTK_MESSAGE_ERROR, GTK_BUTTONS_CLOSE, - _("Error saving file: %s"), g_strerror (errnosav)); - gtk_dialog_run (GTK_DIALOG (dialog)); - gtk_widget_destroy (dialog); - g_free (filename); - return; - } - } else - close (fd); - - CORBA_exception_init (&ev); - - Bonobo_PersistFile_save (composer->persist_file_interface, filename, &ev); - - if (ev._major != CORBA_NO_EXCEPTION) { - char *tmp = g_path_get_basename (filename); - - e_notice (composer, GTK_MESSAGE_ERROR, _("Error saving file: %s"), tmp); - g_free(tmp); - } else { - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "saved", &ev); - e_msg_composer_unset_autosaved (composer); - } - CORBA_exception_free (&ev); - - g_free (filename); -} - -static void -load (EMsgComposer *composer, const char *file_name) -{ - CORBA_Environment ev; - - CORBA_exception_init (&ev); - - Bonobo_PersistFile_load (composer->persist_file_interface, file_name, &ev); - - if (ev._major != CORBA_NO_EXCEPTION) { - char *tmp = g_path_get_basename(file_name); - - e_notice (composer, GTK_MESSAGE_ERROR, - _("Error loading file: %s"), tmp); - g_free(tmp); - } - - CORBA_exception_free (&ev); -} - -#define AUTOSAVE_SEED ".evolution-composer.autosave-XXXXXX" -#define AUTOSAVE_INTERVAL 60000 - -typedef struct _AutosaveManager AutosaveManager; -struct _AutosaveManager { - GHashTable *table; - guint id; - gboolean ask; -}; - -static AutosaveManager *am = NULL; -static void autosave_manager_start (AutosaveManager *am); -static void autosave_manager_stop (AutosaveManager *am); - -static gboolean -autosave_save_draft (EMsgComposer *composer) -{ - CamelMimeMessage *message; - CamelStream *stream; - char *file; - int fd, camelfd; - gboolean success = TRUE; - - if (!e_msg_composer_is_dirty (composer)) - return TRUE; - - fd = composer->autosave_fd; - file = composer->autosave_file; - - if (fd == -1) { - e_notice (composer, GTK_MESSAGE_ERROR, - _("Error accessing file: %s"), file); - return FALSE; - } - - message = e_msg_composer_get_message_draft (composer); - - if (message == NULL) { - e_notice (composer, GTK_MESSAGE_ERROR, - _("Unable to retrieve message from editor")); - return FALSE; - } - - if (lseek (fd, (off_t)0, SEEK_SET) == -1) { - camel_object_unref (message); - e_notice (composer, GTK_MESSAGE_ERROR, - _("Unable to seek on file: %s\n%s"), file, g_strerror (errno)); - return FALSE; - } - - if (ftruncate (fd, (off_t)0) == -1) { - camel_object_unref (message); - e_notice (composer, GTK_MESSAGE_ERROR, - _("Unable to truncate file: %s\n%s"), file, g_strerror (errno)); - return FALSE; - } - - /* dup the fd because we dont want camel to close it when done */ - camelfd = dup(fd); - if (fd == -1) { - camel_object_unref (message); - e_notice (composer, GTK_MESSAGE_ERROR, - _("Unable to copy file descriptor: %s\n%s"), file, g_strerror (errno)); - return FALSE; - } - - /* this does an lseek so we don't have to */ - stream = camel_stream_fs_new_with_fd (camelfd); - if (camel_data_wrapper_write_to_stream (CAMEL_DATA_WRAPPER (message), stream) == -1 - || camel_stream_close (CAMEL_STREAM (stream)) == -1) { - e_notice (composer, GTK_MESSAGE_ERROR, - _("Error autosaving message: %s\n %s"), file, strerror(errno)); - - success = FALSE; - } else { - CORBA_Environment ev; - CORBA_exception_init (&ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "saved", &ev); - CORBA_exception_free (&ev); - e_msg_composer_unset_changed (composer); - e_msg_composer_set_autosaved (composer); - } - - camel_object_unref (stream); - - camel_object_unref (message); - - return success; -} - -static EMsgComposer * -autosave_load_draft (const char *filename) -{ - CamelStream *stream; - CamelMimeMessage *msg; - EMsgComposer *composer; - - g_return_val_if_fail (filename != NULL, NULL); - - g_warning ("autosave load filename = \"%s\"", filename); - - stream = camel_stream_fs_new_with_name (filename, O_RDONLY, 0); - - if (stream == NULL) - return NULL; - - msg = camel_mime_message_new (); - camel_data_wrapper_construct_from_stream (CAMEL_DATA_WRAPPER (msg), stream); - unlink (filename); - - composer = e_msg_composer_new_with_message (msg); - if (composer) { - autosave_save_draft (composer); - - g_signal_connect (GTK_OBJECT (composer), "send", - G_CALLBACK (em_utils_composer_send_cb), NULL); - - g_signal_connect (GTK_OBJECT (composer), "save-draft", - G_CALLBACK (em_utils_composer_save_draft_cb), NULL); - - gtk_widget_show (GTK_WIDGET (composer)); - } - - camel_object_unref (stream); - return composer; -} - -static gboolean -autosave_is_owned (AutosaveManager *am, const char *file) -{ - return g_hash_table_lookup (am->table, file) != NULL; -} - -static void -autosave_manager_query_load_orphans (AutosaveManager *am, GtkWindow *parent) -{ - DIR *dir; - struct dirent *d; - GSList *match = NULL; - gint len = strlen (AUTOSAVE_SEED); - gint load = FALSE; - - dir = opendir (g_get_home_dir()); - if (!dir) { - return; - } - - while ((d = readdir (dir))) { - if ((!strncmp (d->d_name, AUTOSAVE_SEED, len - 6)) - && (strlen (d->d_name) == len) - && (!autosave_is_owned (am, d->d_name))) { - char *filename = g_strdup_printf ("%s/%s", g_get_home_dir(), d->d_name); - struct stat st; - - /* - * check if the file has any length, It is a valid case if it doesn't - * so we simply don't ask then. - */ - if (stat (filename, &st) == -1 || st.st_size == 0) { - unlink (filename); - g_free (filename); - continue; - } - match = g_slist_prepend (match, filename); - } - } - - closedir (dir); - - if (match != NULL) { - GtkWidget *dialog; - - dialog = gtk_message_dialog_new (parent, - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT, - GTK_MESSAGE_QUESTION, GTK_BUTTONS_YES_NO, - _("Ximian Evolution has found unsaved files from a previous session.\n" - "Would you like to try to recover them?")); - gtk_dialog_set_default_response (GTK_DIALOG (dialog), GTK_RESPONSE_YES); - load = gtk_dialog_run (GTK_DIALOG (dialog)) == GTK_RESPONSE_YES; - gtk_widget_destroy (dialog); - } - - while (match != NULL) { - GSList *next = match->next; - char *filename = match->data; - EMsgComposer *composer; - - if (load) { - composer = autosave_load_draft (filename); - } else { - unlink (filename); - } - - g_free (filename); - g_slist_free_1 (match); - match = next; - } -} - -static void -autosave_run_foreach_cb (gpointer key, gpointer value, gpointer data) -{ - EMsgComposer *composer = E_MSG_COMPOSER (value); - - if (composer->enable_autosave) - autosave_save_draft (composer); -} - -static gint -autosave_run (gpointer data) -{ - AutosaveManager *am = data; - - g_hash_table_foreach (am->table, (GHFunc)autosave_run_foreach_cb, am); - - autosave_manager_stop (am); - autosave_manager_start (am); - - return FALSE; -} - -static gboolean -autosave_init_file (EMsgComposer *composer) -{ - if (composer->autosave_file == NULL) { - composer->autosave_file = g_strdup_printf ("%s/%s", g_get_home_dir(), AUTOSAVE_SEED); - composer->autosave_fd = mkstemp (composer->autosave_file); - return TRUE; - } - return FALSE; -} - -static void -autosave_manager_start (AutosaveManager *am) -{ - if (am->id == 0) - am->id = gtk_timeout_add (AUTOSAVE_INTERVAL, autosave_run, am); -} - -static void -autosave_manager_stop (AutosaveManager *am) -{ - if (am->id) { - gtk_timeout_remove (am->id); - am->id = 0; - } -} - -static AutosaveManager * -autosave_manager_new () -{ - AutosaveManager *am; - - am = g_new (AutosaveManager, 1); - am->table = g_hash_table_new (g_str_hash, g_str_equal); - am->id = 0; - am->ask = TRUE; - - return am; -} - -static void -autosave_manager_register (AutosaveManager *am, EMsgComposer *composer) -{ - char *key; - - g_return_if_fail (composer != NULL); - - if (autosave_init_file (composer)) { - key = g_path_get_basename (composer->autosave_file); - g_hash_table_insert (am->table, key, composer); - if (am->ask) { - /* keep recursion out of our bedrooms. */ - am->ask = FALSE; - autosave_manager_query_load_orphans (am, (GtkWindow *)composer); - am->ask = TRUE; - } - } - autosave_manager_start (am); -} - -static void -autosave_manager_unregister (AutosaveManager *am, EMsgComposer *composer) -{ - char *key, *oldkey; - void *olddata; - - if (!composer->autosave_file) - return; - - key = g_path_get_basename(composer->autosave_file); - if (g_hash_table_lookup_extended(am->table, key, (void **)&oldkey, &olddata)) { - g_hash_table_remove(am->table, oldkey); - g_free(oldkey); - g_free(key); - } - - /* only remove the file if we can successfully save it */ - /* FIXME this test could probably be more efficient */ - if (autosave_save_draft (composer)) { - unlink (composer->autosave_file); - } - close (composer->autosave_fd); - g_free (composer->autosave_file); - composer->autosave_file = NULL; - - if (g_hash_table_size (am->table) == 0) - autosave_manager_stop (am); -} - -static void -menu_file_save_draft_cb (BonoboUIComponent *uic, void *data, const char *path) -{ - g_signal_emit (data, signals[SAVE_DRAFT], 0, FALSE); - e_msg_composer_unset_changed (E_MSG_COMPOSER (data)); - e_msg_composer_unset_autosaved (E_MSG_COMPOSER (data)); -} - -/* Exit dialog. (Displays a "Save composition to 'Drafts' before exiting?" warning before actually exiting.) */ - -static void -do_exit (EMsgComposer *composer) -{ - const char *subject; - GtkWidget *dialog; - int button; - - if (!e_msg_composer_is_dirty (composer) && !e_msg_composer_is_autosaved (composer)) { - gtk_widget_destroy (GTK_WIDGET (composer)); - return; - } - - gdk_window_raise (GTK_WIDGET (composer)->window); - - subject = e_msg_composer_hdrs_get_subject (E_MSG_COMPOSER_HDRS (composer->hdrs)); - - dialog = gtk_message_dialog_new (GTK_WINDOW (composer), - GTK_DIALOG_MODAL | GTK_DIALOG_DESTROY_WITH_PARENT, - GTK_MESSAGE_ERROR, GTK_BUTTONS_NONE, - _("The message \"%s\" has not been sent.\n\n" - "Do you wish to save your changes?"), - subject); - - gtk_dialog_add_buttons (GTK_DIALOG (dialog), - _("_Discard Changes"), GTK_RESPONSE_NO, - GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, - GTK_STOCK_SAVE, GTK_RESPONSE_YES, - NULL); - gtk_window_set_title (GTK_WINDOW (dialog), _("Warning: Modified Message")); - gtk_dialog_set_default_response (GTK_DIALOG (dialog), GTK_RESPONSE_YES); - button = gtk_dialog_run (GTK_DIALOG (dialog)); - gtk_widget_destroy (dialog); - - switch (button) { - case GTK_RESPONSE_YES: - /* Save */ - g_signal_emit (GTK_OBJECT (composer), signals[SAVE_DRAFT], 0, TRUE); - e_msg_composer_unset_changed (composer); - e_msg_composer_unset_autosaved (composer); - break; - case GTK_RESPONSE_NO: - /* Don't save */ - gtk_widget_destroy (GTK_WIDGET (composer)); - break; - case GTK_RESPONSE_CANCEL: - break; - } -} - -/* Menu callbacks. */ - -static void -menu_file_open_cb (BonoboUIComponent *uic, - void *data, - const char *path) -{ - EMsgComposer *composer; - char *file_name; - - composer = E_MSG_COMPOSER (data); - - file_name = e_msg_composer_select_file (composer, _("Open file")); - if (file_name == NULL) - return; - - load (composer, file_name); - - g_free (file_name); -} - -static void -menu_file_save_cb (BonoboUIComponent *uic, - void *data, - const char *path) -{ - EMsgComposer *composer; - CORBA_char *file_name; - CORBA_Environment ev; - - composer = E_MSG_COMPOSER (data); - - CORBA_exception_init (&ev); - - file_name = Bonobo_PersistFile_getCurrentFile (composer->persist_file_interface, &ev); - - if (ev._major != CORBA_NO_EXCEPTION) { - save (composer, NULL); - } else { - save (composer, file_name); - CORBA_free (file_name); - } - CORBA_exception_free (&ev); -} - -static void -menu_file_save_as_cb (BonoboUIComponent *uic, - void *data, - const char *path) -{ - EMsgComposer *composer; - - composer = E_MSG_COMPOSER (data); - - save (composer, NULL); -} - -static void -menu_file_send_cb (BonoboUIComponent *uic, - void *data, - const char *path) -{ - g_signal_emit (GTK_OBJECT (data), signals[SEND], 0); -} - -static void -menu_file_close_cb (BonoboUIComponent *uic, - void *data, - const char *path) -{ - EMsgComposer *composer; - - composer = E_MSG_COMPOSER (data); - do_exit (composer); -} - -static void -menu_file_add_attachment_cb (BonoboUIComponent *uic, - void *data, - const char *path) -{ - EMsgComposer *composer; - - composer = E_MSG_COMPOSER (data); - - e_msg_composer_attachment_bar_attach - (E_MSG_COMPOSER_ATTACHMENT_BAR (composer->attachment_bar), - NULL); -} - -static void -menu_edit_cut_cb (BonoboUIComponent *uic, void *data, const char *path) -{ - EMsgComposer *composer = data; - - g_return_if_fail (composer->focused_entry != NULL); - - if (GTK_IS_ENTRY (composer->focused_entry)) { - gtk_editable_cut_clipboard (GTK_EDITABLE (composer->focused_entry)); - } else { - /* happy happy joy joy, an EEntry. */ - g_assert_not_reached (); - } -} - -static void -menu_edit_copy_cb (BonoboUIComponent *uic, void *data, const char *path) -{ - EMsgComposer *composer = data; - - g_return_if_fail (composer->focused_entry != NULL); - - if (GTK_IS_ENTRY (composer->focused_entry)) { - gtk_editable_copy_clipboard (GTK_EDITABLE (composer->focused_entry)); - } else { - /* happy happy joy joy, an EEntry. */ - g_assert_not_reached (); - } -} - -static void -menu_edit_paste_cb (BonoboUIComponent *uic, void *data, const char *path) -{ - EMsgComposer *composer = data; - - g_return_if_fail (composer->focused_entry != NULL); - - if (GTK_IS_ENTRY (composer->focused_entry)) { - gtk_editable_paste_clipboard (GTK_EDITABLE (composer->focused_entry)); - } else { - /* happy happy joy joy, an EEntry. */ - g_assert_not_reached (); - } -} - -static void -menu_edit_select_all_cb (BonoboUIComponent *uic, void *data, const char *path) -{ - EMsgComposer *composer = data; - - g_return_if_fail (composer->focused_entry != NULL); - - if (GTK_IS_ENTRY (composer->focused_entry)) { - gtk_editable_set_position (GTK_EDITABLE (composer->focused_entry), -1); - gtk_editable_select_region (GTK_EDITABLE (composer->focused_entry), 0, -1); - } else { - /* happy happy joy joy, an EEntry. */ - g_assert_not_reached (); - } -} - -static void -menu_edit_delete_all_cb (BonoboUIComponent *uic, void *data, const char *path) -{ - CORBA_Environment ev; - EMsgComposer *composer; - - composer = E_MSG_COMPOSER (data); - CORBA_exception_init (&ev); - - GNOME_GtkHTML_Editor_Engine_undoBegin (composer->editor_engine, "Delete all but signature", "Undelete all", &ev); - GNOME_GtkHTML_Editor_Engine_freeze (composer->editor_engine, &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "disable-selection", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "text-default-color", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "bold-off", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "italic-off", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "underline-off", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "strikeout-off", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "select-all", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "delete", &ev); - GNOME_GtkHTML_Editor_Engine_setParagraphData (composer->editor_engine, "signature", "0", &ev); - GNOME_GtkHTML_Editor_Engine_setParagraphData (composer->editor_engine, "orig", "0", &ev); - e_msg_composer_show_sig_file (composer); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "style-normal", &ev); - GNOME_GtkHTML_Editor_Engine_thaw (composer->editor_engine, &ev); - GNOME_GtkHTML_Editor_Engine_undoEnd (composer->editor_engine, &ev); - - CORBA_exception_free (&ev); - /* printf ("delete all\n"); */ -} - -static void -menu_view_attachments_activate_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer user_data) - -{ - gboolean new_state; - - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - new_state = atoi (state); - - e_msg_composer_show_attachments (E_MSG_COMPOSER (user_data), new_state); -} - -static void -menu_format_html_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer user_data) - -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - e_msg_composer_set_send_html (E_MSG_COMPOSER (user_data), atoi (state)); -} - -static void -menu_security_pgp_sign_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer composer) - -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - e_msg_composer_set_pgp_sign (E_MSG_COMPOSER (composer), atoi (state)); -} - -static void -menu_security_pgp_encrypt_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer composer) - -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - e_msg_composer_set_pgp_encrypt (E_MSG_COMPOSER (composer), atoi (state)); -} - -static void -menu_security_smime_sign_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer composer) - -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - e_msg_composer_set_smime_sign (E_MSG_COMPOSER (composer), atoi (state)); -} - -static void -menu_security_smime_encrypt_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer composer) - -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - e_msg_composer_set_smime_encrypt (E_MSG_COMPOSER (composer), atoi (state)); -} - - -static void -menu_view_from_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer user_data) -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - e_msg_composer_set_view_from (E_MSG_COMPOSER (user_data), atoi (state)); -} - -static void -menu_view_replyto_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer user_data) -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - e_msg_composer_set_view_replyto (E_MSG_COMPOSER (user_data), atoi (state)); -} - -static void -menu_view_cc_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer user_data) -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - e_msg_composer_set_view_cc (E_MSG_COMPOSER (user_data), atoi (state)); -} - -static void -menu_view_bcc_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer user_data) -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - e_msg_composer_set_view_bcc (E_MSG_COMPOSER (user_data), atoi (state)); -} - -static void -menu_changed_charset_cb (BonoboUIComponent *component, - const char *path, - Bonobo_UIComponent_EventType type, - const char *state, - gpointer user_data) -{ - if (type != Bonobo_UIComponent_STATE_CHANGED) - return; - - if (atoi (state)) { - /* Charset menu names are "Charset-%s" where %s is the charset name */ - g_free (E_MSG_COMPOSER (user_data)->charset); - E_MSG_COMPOSER (user_data)->charset = g_strdup (path + strlen ("Charset-")); - } -} - - -static BonoboUIVerb verbs [] = { - - BONOBO_UI_VERB ("FileOpen", menu_file_open_cb), - BONOBO_UI_VERB ("FileSave", menu_file_save_cb), - BONOBO_UI_VERB ("FileSaveAs", menu_file_save_as_cb), - BONOBO_UI_VERB ("FileSaveDraft", menu_file_save_draft_cb), - BONOBO_UI_VERB ("FileClose", menu_file_close_cb), - - BONOBO_UI_VERB ("FileAttach", menu_file_add_attachment_cb), - - BONOBO_UI_VERB ("FileSend", menu_file_send_cb), - - BONOBO_UI_VERB ("DeleteAll", menu_edit_delete_all_cb), - - BONOBO_UI_VERB_END -}; - -static EPixmap pixcache [] = { - E_PIXMAP ("/Toolbar/FileAttach", "buttons/add-attachment.png"), - E_PIXMAP ("/Toolbar/FileSend", "buttons/send-24.png"), - -/* E_PIXMAP ("/menu/Insert/FileAttach", "buttons/add-attachment.png"), */ - E_PIXMAP ("/commands/FileSend", "send-16.png"), - E_PIXMAP ("/commands/FileSave", "save-16.png"), - E_PIXMAP ("/commands/FileSaveAs", "save-as-16.png"), - - E_PIXMAP_END -}; - -static void sig_select_item (EMsgComposer *composer); - -static void -signature_cb (GtkWidget *w, EMsgComposer *composer) -{ - MailConfigSignature *old_sig; - gboolean old_auto; - int idx = g_list_index (GTK_MENU_SHELL (w)->children, gtk_menu_get_active (GTK_MENU (w))); - int len = g_list_length (GTK_MENU_SHELL (w)->children); - - /* printf ("signature_cb: %d\n", idx); */ - - old_sig = composer->signature; - old_auto = composer->auto_signature; - - if (idx < len) { - if (idx == 0) { /* none */ - composer->signature = NULL; - composer->auto_signature = FALSE; - } else if (idx == 1) { /* auto */ - composer->signature = NULL; - composer->auto_signature = TRUE; - } else { - composer->signature = g_slist_nth_data (mail_config_get_signature_list (), idx - 2); - composer->auto_signature = FALSE; - } - if (old_sig != composer->signature || old_auto != composer->auto_signature) - e_msg_composer_show_sig_file (composer); - } - /* printf ("signature_cb end\n"); */ -} - -static void setup_signatures_menu (EMsgComposer *composer); - -static void -sig_event_client (MailConfigSigEvent event, MailConfigSignature *sig, EMsgComposer *composer) -{ - switch (event) { - case MAIL_CONFIG_SIG_EVENT_DELETED: - if (sig == composer->signature) { - composer->signature = NULL; - composer->auto_signature = TRUE; - e_msg_composer_show_sig_file (composer); - } - setup_signatures_menu (composer); - break; - case MAIL_CONFIG_SIG_EVENT_ADDED: - case MAIL_CONFIG_SIG_EVENT_NAME_CHANGED: - setup_signatures_menu (composer); - default: - ; - } -} - -static void -prepare_signatures_menu (EMsgComposer *composer) -{ - GtkWidget *hbox; - GtkWidget *label; - - hbox = e_msg_composer_hdrs_get_from_hbox (E_MSG_COMPOSER_HDRS (composer->hdrs)); - - label = gtk_label_new (_("Signature:")); - gtk_widget_show (label); - - composer->sig_omenu = gtk_option_menu_new (); - gtk_widget_show (composer->sig_omenu); - - gtk_box_pack_end_defaults (GTK_BOX (hbox), composer->sig_omenu); - gtk_box_pack_end (GTK_BOX (hbox), label, FALSE, TRUE, 0); -} - -static void -sig_select_item (EMsgComposer *composer) -{ - int idx; - - if (composer->auto_signature) { - idx = 1; - } else if (composer->signature == NULL) { - idx = 0; - } else { - idx = composer->signature->id + 2; - } - - gtk_option_menu_set_history (GTK_OPTION_MENU (composer->sig_omenu), idx); -} - -static void -setup_signatures_menu (EMsgComposer *composer) -{ - GtkWidget *menu; - GtkWidget *mi; - GSList *node; - -#define ADD(x) \ - mi = (x ? gtk_menu_item_new_with_label (x) : gtk_menu_item_new ()); \ - gtk_widget_show (mi); \ - gtk_menu_shell_append(GTK_MENU_SHELL(menu), mi); - - menu = gtk_menu_new (); - ADD (_("None")); - ADD (_("Autogenerated")); - - node = mail_config_get_signature_list (); - while (node != NULL) { - ADD (((MailConfigSignature *) node->data)->name); - node = node->next; - } -#undef ADD - - gtk_widget_show (menu); - gtk_option_menu_set_menu (GTK_OPTION_MENU (composer->sig_omenu), menu); - sig_select_item (composer); - - g_signal_connect (menu, "selection-done", (GCallback)signature_cb, composer); -} - -static void -setup_ui (EMsgComposer *composer) -{ - BonoboUIContainer *container; - const char *default_charset; - gboolean hide_smime; - - container = bonobo_window_get_ui_container (BONOBO_WINDOW (composer)); - - composer->uic = bonobo_ui_component_new_default (); - /* FIXME: handle bonobo exceptions */ - bonobo_ui_component_set_container (composer->uic, bonobo_object_corba_objref (BONOBO_OBJECT (container)), NULL); - - bonobo_ui_component_add_verb_list_with_data (composer->uic, verbs, composer); - - bonobo_ui_component_freeze (composer->uic, NULL); - - bonobo_ui_util_set_ui (composer->uic, PREFIX, - EVOLUTION_UIDIR "/evolution-message-composer.xml", - "evolution-message-composer", NULL); - - e_pixmaps_update (composer->uic, pixcache); - - /* Populate the Charset Encoding menu and default it to whatever the user - chose as his default charset in the mailer */ - default_charset = composer_get_default_charset_setting (); - e_charset_picker_bonobo_ui_populate (composer->uic, "/menu/Edit/EncodingPlaceholder", - default_charset, - menu_changed_charset_cb, - composer); - - /* Format -> HTML */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/FormatHtml", - "state", composer->send_html ? "1" : "0", NULL); - bonobo_ui_component_add_listener ( - composer->uic, "FormatHtml", - menu_format_html_cb, composer); - - /* View/From */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/ViewFrom", - "state", composer->view_from ? "1" : "0", NULL); - bonobo_ui_component_add_listener ( - composer->uic, "ViewFrom", - menu_view_from_cb, composer); - - /* View/ReplyTo */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/ViewReplyTo", - "state", composer->view_replyto ? "1" : "0", NULL); - bonobo_ui_component_add_listener ( - composer->uic, "ViewReplyTo", - menu_view_replyto_cb, composer); - - /* View/CC */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/ViewCC", - "state", composer->view_cc ? "1" : "0", NULL); - bonobo_ui_component_add_listener ( - composer->uic, "ViewCC", - menu_view_cc_cb, composer); - - /* View/BCC */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/ViewBCC", - "state", composer->view_bcc ? "1" : "0", NULL); - bonobo_ui_component_add_listener ( - composer->uic, "ViewBCC", - menu_view_bcc_cb, composer); - - /* Security -> PGP Sign */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/SecurityPGPSign", - "state", composer->pgp_sign ? "1" : "0", NULL); - - bonobo_ui_component_add_listener ( - composer->uic, "SecurityPGPSign", - menu_security_pgp_sign_cb, composer); - - /* Security -> PGP Encrypt */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/SecurityPGPEncrypt", - "state", composer->pgp_encrypt ? "1" : "0", NULL); - - bonobo_ui_component_add_listener ( - composer->uic, "SecurityPGPEncrypt", - menu_security_pgp_encrypt_cb, composer); - -#if defined(HAVE_NSS) && defined(SMIME_SUPPORTED) - hide_smime = FALSE; -#else - hide_smime = TRUE; -#endif - - /* Security -> S/MIME Sign */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/SecuritySMimeSign", - "state", composer->smime_sign ? "1" : "0", NULL); - bonobo_ui_component_set_prop ( - composer->uic, "/commands/SecuritySMimeSign", - "hidden", hide_smime ? "1" : "0", NULL); - - bonobo_ui_component_add_listener ( - composer->uic, "SecuritySMimeSign", - menu_security_smime_sign_cb, composer); - - /* Security -> S/MIME Encrypt */ - bonobo_ui_component_set_prop ( - composer->uic, "/commands/SecuritySMimeEncrypt", - "state", composer->smime_encrypt ? "1" : "0", NULL); - bonobo_ui_component_set_prop ( - composer->uic, "/commands/SecuritySMimeEncrypt", - "hidden", hide_smime ? "1" : "0", NULL); - - bonobo_ui_component_add_listener ( - composer->uic, "SecuritySMimeEncrypt", - menu_security_smime_encrypt_cb, composer); - - /* View -> Attachments */ - bonobo_ui_component_add_listener ( - composer->uic, "ViewAttach", - menu_view_attachments_activate_cb, composer); - - mail_config_signature_register_client ((MailConfigSignatureClient) sig_event_client, composer); - - bonobo_ui_component_thaw (composer->uic, NULL); - - /* Create the UIComponent for the non-control entries */ - - composer->entry_uic = bonobo_ui_component_new_default (); -} - - -/* Miscellaneous callbacks. */ - -static void -attachment_bar_changed_cb (EMsgComposerAttachmentBar *bar, - void *data) -{ - EMsgComposer *composer; - gboolean show = FALSE; - - composer = E_MSG_COMPOSER (data); - - if (e_msg_composer_attachment_bar_get_num_attachments (bar) > 0) - show = TRUE; - - e_msg_composer_show_attachments (composer, show); - - /* Mark the composer as changed so it prompts about unsaved - changes on close */ - e_msg_composer_set_changed (composer); -} - -static void -subject_changed_cb (EMsgComposerHdrs *hdrs, - gchar *subject, - void *data) -{ - EMsgComposer *composer; - - composer = E_MSG_COMPOSER (data); - - gtk_window_set_title (GTK_WINDOW (composer), subject[0] ? subject : _("Compose a message")); -} - -static void -hdrs_changed_cb (EMsgComposerHdrs *hdrs, - void *data) -{ - EMsgComposer *composer; - - composer = E_MSG_COMPOSER (data); - - /* Mark the composer as changed so it prompts about unsaved changes on close */ - e_msg_composer_set_changed (composer); -} - -enum { - UPDATE_AUTO_CC, - UPDATE_AUTO_BCC, -}; - -static void -update_auto_recipients (EMsgComposerHdrs *hdrs, int mode, const char *auto_addrs) -{ - EABDestination *dest, **destv = NULL; - CamelInternetAddress *iaddr; - GList *list, *tail, *node; - int i, n = 0; - - tail = list = NULL; - - if (auto_addrs) { - iaddr = camel_internet_address_new (); - if (camel_address_decode (CAMEL_ADDRESS (iaddr), auto_addrs) != -1) { - for (i = 0; i < camel_address_length (CAMEL_ADDRESS (iaddr)); i++) { - const char *name, *addr; - - if (!camel_internet_address_get (iaddr, i, &name, &addr)) - continue; - - dest = eab_destination_new (); - eab_destination_set_auto_recipient (dest, TRUE); - - if (name) - eab_destination_set_name (dest, name); - - if (addr) - eab_destination_set_email (dest, addr); - - node = g_list_alloc (); - node->data = dest; - node->next = NULL; - - if (tail) { - node->prev = tail; - tail->next = node; - } else { - node->prev = NULL; - list = node; - } - - tail = node; - n++; - } - } - - camel_object_unref (iaddr); - } - - switch (mode) { - case UPDATE_AUTO_CC: - destv = e_msg_composer_hdrs_get_cc (hdrs); - break; - case UPDATE_AUTO_BCC: - destv = e_msg_composer_hdrs_get_bcc (hdrs); - break; - default: - g_assert_not_reached (); - } - - if (destv) { - for (i = 0; destv[i]; i++) { - if (!eab_destination_is_auto_recipient (destv[i])) { - node = g_list_alloc (); - node->data = eab_destination_copy (destv[i]); - node->next = NULL; - - if (tail) { - node->prev = tail; - tail->next = node; - } else { - node->prev = NULL; - list = node; - } - - tail = node; - n++; - } - } - - eab_destination_freev (destv); - } - - destv = eab_destination_list_to_vector_sized (list, n); - g_list_free (list); - - switch (mode) { - case UPDATE_AUTO_CC: - e_msg_composer_hdrs_set_cc (hdrs, destv); - break; - case UPDATE_AUTO_BCC: - e_msg_composer_hdrs_set_bcc (hdrs, destv); - break; - default: - g_assert_not_reached (); - } - - eab_destination_freev (destv); -} - -static void -from_changed_cb (EMsgComposerHdrs *hdrs, void *data) -{ - EMsgComposer *composer; - - composer = E_MSG_COMPOSER (data); - - if (hdrs->account) { - EAccount *account = hdrs->account; - - e_msg_composer_set_pgp_sign (composer, - account->pgp_always_sign && - (!account->pgp_no_imip_sign || !composer->mime_type || - strncasecmp (composer->mime_type, "text/calendar", 13) != 0)); - e_msg_composer_set_smime_sign (composer, account->smime_sign_default); - e_msg_composer_set_smime_encrypt (composer, account->smime_encrypt_default); - update_auto_recipients (hdrs, UPDATE_AUTO_CC, account->always_cc ? account->cc_addrs : NULL); - update_auto_recipients (hdrs, UPDATE_AUTO_BCC, account->always_bcc ? account->bcc_addrs : NULL); - } else { - update_auto_recipients (hdrs, UPDATE_AUTO_CC, NULL); - update_auto_recipients (hdrs, UPDATE_AUTO_BCC, NULL); - } - - set_editor_signature (composer); - e_msg_composer_show_sig_file (composer); -} - - -/* GObject methods. */ - -static void -composer_finalise (GObject *object) -{ - EMsgComposer *composer; - - composer = E_MSG_COMPOSER (object); - - if (composer->extra_hdr_names) { - int i; - - for (i = 0; i < composer->extra_hdr_names->len; i++) { - g_free (composer->extra_hdr_names->pdata[i]); - g_free (composer->extra_hdr_values->pdata[i]); - } - g_ptr_array_free (composer->extra_hdr_names, TRUE); - g_ptr_array_free (composer->extra_hdr_values, TRUE); - } - - e_msg_composer_clear_inlined_table (composer); - g_hash_table_destroy (composer->inline_images); - g_hash_table_destroy (composer->inline_images_by_url); - - g_free (composer->charset); - g_free (composer->mime_type); - g_free (composer->mime_body); - - if (composer->redirect) - camel_object_unref (composer->redirect); - - if (G_OBJECT_CLASS (parent_class)->finalize != NULL) - (* G_OBJECT_CLASS (parent_class)->finalize) (object); -} - -static void -composer_dispose(GObject *object) -{ - /* When destroy() is called, the contents of the window - * (including the remote editor control) will already have - * been destroyed, so we have to do this here. - */ - autosave_manager_unregister (am, E_MSG_COMPOSER (object)); - if (G_OBJECT_CLASS (parent_class)->dispose != NULL) - (* G_OBJECT_CLASS (parent_class)->dispose) (object); -} - -/* GtkObject methods */ -static void -destroy (GtkObject *object) -{ - EMsgComposer *composer; - CORBA_Environment ev; - - composer = E_MSG_COMPOSER (object); - - CORBA_exception_init (&ev); - - if (composer->uic) { - bonobo_object_unref (BONOBO_OBJECT (composer->uic)); - composer->uic = NULL; - } - - if (composer->entry_uic) { - bonobo_object_unref (BONOBO_OBJECT (composer->entry_uic)); - composer->entry_uic = NULL; - } - - /* FIXME? I assume the Bonobo widget will get destroyed - normally? */ - if (composer->address_dialog != NULL) { - gtk_widget_destroy (composer->address_dialog); - composer->address_dialog = NULL; - } - if (composer->hdrs != NULL) { - gtk_widget_destroy (composer->hdrs); - composer->hdrs = NULL; - } - - if (composer->notify_id) { - GConfClient *gconf = gconf_client_get_default (); - gconf_client_notify_remove (gconf, composer->notify_id); - composer->notify_id = 0; - g_object_unref (gconf); - } - - if (composer->persist_stream_interface != CORBA_OBJECT_NIL) { - Bonobo_Unknown_unref (composer->persist_stream_interface, &ev); - CORBA_Object_release (composer->persist_stream_interface, &ev); - composer->persist_stream_interface = CORBA_OBJECT_NIL; - } - - if (composer->persist_file_interface != CORBA_OBJECT_NIL) { - Bonobo_Unknown_unref (composer->persist_file_interface, &ev); - CORBA_Object_release (composer->persist_file_interface, &ev); - composer->persist_file_interface = CORBA_OBJECT_NIL; - } - - if (composer->editor_engine != CORBA_OBJECT_NIL) { - Bonobo_Unknown_unref (composer->editor_engine, &ev); - CORBA_Object_release (composer->editor_engine, &ev); - composer->editor_engine = CORBA_OBJECT_NIL; - } - - CORBA_exception_free (&ev); - - if (composer->editor_listener) { - bonobo_object_unref (composer->editor_listener); - composer->editor_listener = NULL; - } - - mail_config_signature_unregister_client ((MailConfigSignatureClient) sig_event_client, composer); - - if (GTK_OBJECT_CLASS (parent_class)->destroy != NULL) - (* GTK_OBJECT_CLASS (parent_class)->destroy) (object); -} - - -/* GtkWidget methods. */ - -static int -delete_event (GtkWidget *widget, - GdkEventAny *event) -{ - do_exit (E_MSG_COMPOSER (widget)); - - return TRUE; -} - -static void -message_rfc822_dnd (EMsgComposer *composer, CamelStream *stream) -{ - CamelMimeParser *mp; - - mp = camel_mime_parser_new (); - camel_mime_parser_scan_from (mp, TRUE); - camel_mime_parser_init_with_stream (mp, stream); - - while (camel_mime_parser_step (mp, 0, 0) == CAMEL_MIME_PARSER_STATE_FROM) { - CamelMimeMessage *message; - CamelMimePart *part; - - message = camel_mime_message_new (); - if (camel_mime_part_construct_from_parser (CAMEL_MIME_PART (message), mp) == -1) { - camel_object_unref (message); - break; - } - - part = camel_mime_part_new (); - camel_mime_part_set_disposition (part, "inline"); - camel_medium_set_content_object (CAMEL_MEDIUM (part), - CAMEL_DATA_WRAPPER (message)); - camel_mime_part_set_content_type (part, "message/rfc822"); - e_msg_composer_attachment_bar_attach_mime_part (E_MSG_COMPOSER_ATTACHMENT_BAR (composer->attachment_bar), - part); - camel_object_unref (message); - camel_object_unref (part); - - /* skip over the FROM_END state */ - camel_mime_parser_step (mp, 0, 0); - } - - camel_object_unref (mp); -} - -static void -drag_data_received (EMsgComposer *composer, GdkDragContext *context, - int x, int y, GtkSelectionData *selection, - guint info, guint time) -{ - char *tmp, *str, **urls; - CamelMimePart *mime_part; - CamelStream *stream; - CamelURL *url; - int i; - - switch (info) { - case DND_TYPE_MESSAGE_RFC822: - d(printf ("dropping a message/rfc822\n")); - /* write the message(s) out to a CamelStream so we can use it */ - stream = camel_stream_mem_new (); - camel_stream_write (stream, selection->data, selection->length); - camel_stream_reset (stream); - - message_rfc822_dnd (composer, stream); - camel_object_unref (stream); - break; - case DND_TYPE_TEXT_URI_LIST: - case DND_TYPE_NETSCAPE_URL: - d(printf ("dropping a text/uri-list\n")); - tmp = g_strndup (selection->data, selection->length); - urls = g_strsplit (tmp, "\n", 0); - g_free (tmp); - - for (i = 0; urls[i] != NULL; i++) { - str = g_strstrip (urls[i]); - - if (!strncasecmp (str, "mailto:", 7)) { - handle_mailto (composer, str); - g_free (str); - } else { - url = camel_url_new (str, NULL); - g_free (str); - - if (url == NULL) - continue; - - if (!strcasecmp (url->protocol, "file")) - e_msg_composer_attachment_bar_attach - (E_MSG_COMPOSER_ATTACHMENT_BAR (composer->attachment_bar), - url->path); - - camel_url_free (url); - } - } - - g_free (urls); - break; - case DND_TYPE_TEXT_VCARD: - d(printf ("dropping a text/x-vcard\n")); - mime_part = camel_mime_part_new (); - camel_mime_part_set_content (mime_part, selection->data, - selection->length, "text/x-vcard"); - camel_mime_part_set_disposition (mime_part, "inline"); - - e_msg_composer_attachment_bar_attach_mime_part - (E_MSG_COMPOSER_ATTACHMENT_BAR (composer->attachment_bar), - mime_part); - - camel_object_unref (mime_part); - default: - d(printf ("dropping an unknown\n")); - break; - } -} - -static void -class_init (EMsgComposerClass *klass) -{ - GtkObjectClass *object_class; - GtkWidgetClass *widget_class; - GObjectClass *gobject_class; - - gobject_class = G_OBJECT_CLASS(klass); - object_class = GTK_OBJECT_CLASS (klass); - widget_class = GTK_WIDGET_CLASS (klass); - - gobject_class->finalize = composer_finalise; - gobject_class->dispose = composer_dispose; - object_class->destroy = destroy; - widget_class->delete_event = delete_event; - - parent_class = g_type_class_ref(bonobo_window_get_type ()); - - signals[SEND] = - g_signal_new ("send", - E_TYPE_MSG_COMPOSER, - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (EMsgComposerClass, send), - NULL, NULL, - g_cclosure_marshal_VOID__VOID, - G_TYPE_NONE, 0); - - signals[SAVE_DRAFT] = - g_signal_new ("save-draft", - E_TYPE_MSG_COMPOSER, - G_SIGNAL_RUN_LAST, - G_STRUCT_OFFSET (EMsgComposerClass, save_draft), - NULL, NULL, - g_cclosure_marshal_VOID__BOOLEAN, - G_TYPE_NONE, - 1, G_TYPE_BOOLEAN); -} - -static void -init (EMsgComposer *composer) -{ - composer->uic = NULL; - - composer->hdrs = NULL; - composer->extra_hdr_names = g_ptr_array_new (); - composer->extra_hdr_values = g_ptr_array_new (); - - composer->focused_entry = NULL; - - composer->editor = NULL; - - composer->address_dialog = NULL; - - composer->attachment_bar = NULL; - composer->attachment_scrolled_window = NULL; - - composer->persist_file_interface = CORBA_OBJECT_NIL; - composer->persist_stream_interface = CORBA_OBJECT_NIL; - - composer->editor_engine = CORBA_OBJECT_NIL; - composer->inline_images = g_hash_table_new (g_str_hash, g_str_equal); - composer->inline_images_by_url = g_hash_table_new (g_str_hash, g_str_equal); - composer->current_images = NULL; - - composer->attachment_bar_visible = FALSE; - composer->send_html = FALSE; - composer->pgp_sign = FALSE; - composer->pgp_encrypt = FALSE; - composer->smime_sign = FALSE; - composer->smime_encrypt = FALSE; - - composer->has_changed = FALSE; - composer->autosaved = FALSE; - - composer->redirect = FALSE; - - composer->charset = NULL; - - composer->enable_autosave = TRUE; - composer->autosave_file = NULL; - composer->autosave_fd = -1; -} - - -GtkType -e_msg_composer_get_type (void) -{ - static GType type = 0; - - if (type == 0) { - static const GTypeInfo info = { - sizeof (EMsgComposerClass), - NULL, NULL, - (GClassInitFunc) class_init, - NULL, NULL, - sizeof (EMsgComposer), - 0, - (GInstanceInitFunc) init, - }; - - type = g_type_register_static (bonobo_window_get_type (), "EMsgComposer", &info, 0); - } - - return type; -} - -static void -e_msg_composer_load_config (EMsgComposer *composer) -{ - GConfClient *gconf; - - gconf = gconf_client_get_default (); - - composer->view_from = gconf_client_get_bool ( - gconf, "/apps/evolution/mail/composer/view/From", NULL); - composer->view_replyto = gconf_client_get_bool ( - gconf, "/apps/evolution/mail/composer/view/ReplyTo", NULL); - composer->view_cc = gconf_client_get_bool ( - gconf, "/apps/evolution/mail/composer/view/Cc", NULL); - composer->view_bcc = gconf_client_get_bool ( - gconf, "/apps/evolution/mail/composer/view/Bcc", NULL); - composer->view_subject = gconf_client_get_bool ( - gconf, "/apps/evolution/mail/composer/view/Subject", NULL); - - g_object_unref (gconf); -} - -static int -e_msg_composer_get_visible_flags (EMsgComposer *composer) -{ - int flags = 0; - - if (composer->view_from) - flags |= E_MSG_COMPOSER_VISIBLE_FROM; - if (composer->view_replyto) - flags |= E_MSG_COMPOSER_VISIBLE_REPLYTO; - if (composer->view_cc) - flags |= E_MSG_COMPOSER_VISIBLE_CC; - if (composer->view_bcc) - flags |= E_MSG_COMPOSER_VISIBLE_BCC; - if (composer->view_subject) - flags |= E_MSG_COMPOSER_VISIBLE_SUBJECT; - - /* - * Until we have a GUI way, lets make sure that - * even if the user screws up, we will do the right - * thing (screws up == edit the config file manually - * and screw up). - */ - flags |= E_MSG_COMPOSER_VISIBLE_SUBJECT; - return flags; -} - - -static void -map_default_cb (EMsgComposer *composer, gpointer user_data) -{ - GtkWidget *widget; - BonoboControlFrame *cf; - Bonobo_PropertyBag pb = CORBA_OBJECT_NIL; - CORBA_Environment ev; - const char *subject; - char *text; - - /* If the 'To:' field is empty, focus it (This is ridiculously complicated) */ - - widget = e_msg_composer_hdrs_get_to_entry (E_MSG_COMPOSER_HDRS (composer->hdrs)); - cf = bonobo_widget_get_control_frame (BONOBO_WIDGET (widget)); - pb = bonobo_control_frame_get_control_property_bag (cf, NULL); - text = bonobo_pbclient_get_string (pb, "text", NULL); - bonobo_object_release_unref (pb, NULL); - - if (!text || text[0] == '\0') { - bonobo_control_frame_control_activate (cf); - - g_free (text); - return; - } - g_free (text); - - /* If not, check the subject field */ - - subject = e_msg_composer_hdrs_get_subject (E_MSG_COMPOSER_HDRS (composer->hdrs)); - - if (!subject || subject[0] == '\0') { - widget = e_msg_composer_hdrs_get_subject_entry (E_MSG_COMPOSER_HDRS (composer->hdrs)); - gtk_widget_grab_focus (widget); - return; - } - - /* Jump to the editor as a last resort. */ - - CORBA_exception_init (&ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "grab-focus", &ev); - CORBA_exception_free (&ev); -} - -static void -msg_composer_destroy_notify (void *data) -{ - EMsgComposer *composer = E_MSG_COMPOSER (data); - - all_composers = g_slist_remove (all_composers, composer); -} - -static int -composer_key_pressed (GtkWidget *widget, GdkEventKey *event, gpointer user_data) -{ - if (event->keyval == GDK_Escape) { - do_exit (E_MSG_COMPOSER (widget)); - - g_signal_stop_emission_by_name (widget, "key-press-event"); - return TRUE; /* Handled. */ - } - - return FALSE; /* Not handled. */ -} - -/* Verbs for non-control entries */ -static BonoboUIVerb entry_verbs [] = { - BONOBO_UI_VERB ("EditCut", menu_edit_cut_cb), - BONOBO_UI_VERB ("EditCopy", menu_edit_copy_cb), - BONOBO_UI_VERB ("EditPaste", menu_edit_paste_cb), - BONOBO_UI_VERB ("EditSelectAll", menu_edit_select_all_cb), - BONOBO_UI_VERB_END -}; - -/* All this snot is so that Cut/Copy/Paste work. */ -static gboolean -composer_entry_focus_in_event_cb (GtkWidget *widget, GdkEventFocus *event, gpointer user_data) -{ - EMsgComposer *composer = user_data; - BonoboUIContainer *container; - - composer->focused_entry = widget; - - container = bonobo_window_get_ui_container (BONOBO_WINDOW (composer)); - bonobo_ui_component_set_container (composer->entry_uic, bonobo_object_corba_objref (BONOBO_OBJECT (container)), NULL); - - bonobo_ui_component_add_verb_list_with_data (composer->entry_uic, entry_verbs, composer); - - bonobo_ui_component_freeze (composer->entry_uic, NULL); - - bonobo_ui_util_set_ui (composer->entry_uic, PREFIX, - EVOLUTION_UIDIR "/evolution-composer-entries.xml", - "evolution-composer-entries", NULL); - - bonobo_ui_component_thaw (composer->entry_uic, NULL); - - return FALSE; -} - -static gboolean -composer_entry_focus_out_event_cb (GtkWidget *widget, GdkEventFocus *event, gpointer user_data) -{ - EMsgComposer *composer = user_data; - - g_assert (composer->focused_entry == widget); - composer->focused_entry = NULL; - - bonobo_ui_component_unset_container (composer->entry_uic, NULL); - - return FALSE; -} - -static void -setup_cut_copy_paste (EMsgComposer *composer) -{ - EMsgComposerHdrs *hdrs; - GtkWidget *entry; - - hdrs = (EMsgComposerHdrs *) composer->hdrs; - - entry = e_msg_composer_hdrs_get_subject_entry (hdrs); - g_signal_connect (entry, "focus_in_event", G_CALLBACK (composer_entry_focus_in_event_cb), composer); - g_signal_connect (entry, "focus_out_event", G_CALLBACK (composer_entry_focus_out_event_cb), composer); - - entry = e_msg_composer_hdrs_get_reply_to_entry (hdrs); - g_signal_connect (entry, "focus_in_event", G_CALLBACK (composer_entry_focus_in_event_cb), composer); - g_signal_connect (entry, "focus_out_event", G_CALLBACK (composer_entry_focus_out_event_cb), composer); -} - -static void -composer_settings_update (GConfClient *gconf, guint cnxn_id, GConfEntry *entry, gpointer data) -{ - gboolean bool; - EMsgComposer *composer = data; - - bool = gconf_client_get_bool (gconf, "/apps/evolution/mail/composer/magic_smileys", NULL); - bonobo_widget_set_property (BONOBO_WIDGET (composer->editor), - "MagicSmileys", TC_CORBA_boolean, bool, - NULL); - - bool = gconf_client_get_bool (gconf, "/apps/evolution/mail/composer/magic_links", NULL); - bonobo_widget_set_property (BONOBO_WIDGET (composer->editor), - "MagicLinks", TC_CORBA_boolean, bool, - NULL); - - bool = gconf_client_get_bool (gconf, "/apps/evolution/mail/composer/inline_spelling", NULL); - bonobo_widget_set_property (BONOBO_WIDGET (composer->editor), - "InlineSpelling", TC_CORBA_boolean, bool, - NULL); -} - -static EMsgComposer * -create_composer (int visible_mask) -{ - EMsgComposer *composer; - GtkWidget *vbox; - Bonobo_Unknown editor_server; - CORBA_Environment ev; - GConfClient *gconf; - int vis; - BonoboControlFrame *control_frame; - - composer = g_object_new (E_TYPE_MSG_COMPOSER, "win_name", _("Compose a message"), NULL); - gtk_window_set_title ((GtkWindow *) composer, _("Compose a message")); - - all_composers = g_slist_prepend (all_composers, composer); - - g_signal_connect (composer, "key-press-event", - G_CALLBACK (composer_key_pressed), - NULL); - g_signal_connect (composer, "destroy", - G_CALLBACK (msg_composer_destroy_notify), - NULL); - - gtk_window_set_default_size (GTK_WINDOW (composer), - DEFAULT_WIDTH, DEFAULT_HEIGHT); - gnome_window_icon_set_from_file (GTK_WINDOW (composer), EVOLUTION_IMAGESDIR - "/compose-message.png"); - - /* DND support */ - gtk_drag_dest_set (GTK_WIDGET (composer), GTK_DEST_DEFAULT_ALL, - drop_types, num_drop_types, GDK_ACTION_COPY); - g_signal_connect (composer, "drag_data_received", - G_CALLBACK (drag_data_received), NULL); - e_msg_composer_load_config (composer); - - setup_ui (composer); - - vbox = gtk_vbox_new (FALSE, 0); - - vis = e_msg_composer_get_visible_flags (composer); - composer->hdrs = e_msg_composer_hdrs_new (composer->uic, visible_mask, vis); - if (!composer->hdrs) { - e_activation_failure_dialog (GTK_WINDOW (composer), - _("Could not create composer window:\n" - "Unable to activate address selector control."), - SELECT_NAMES_OAFIID, - "IDL:Bonobo/Control:1.0"); - gtk_object_destroy (GTK_OBJECT (composer)); - return NULL; - } - - gtk_container_set_border_width (GTK_CONTAINER (vbox), 6); - gtk_box_set_spacing (GTK_BOX (vbox), 6); - gtk_box_pack_start (GTK_BOX (vbox), composer->hdrs, FALSE, FALSE, 0); - g_signal_connect (composer->hdrs, "subject_changed", - G_CALLBACK (subject_changed_cb), composer); - g_signal_connect (composer->hdrs, "hdrs_changed", - G_CALLBACK (hdrs_changed_cb), composer); - g_signal_connect (composer->hdrs, "from_changed", - G_CALLBACK (from_changed_cb), composer); - gtk_widget_show (composer->hdrs); - - prepare_signatures_menu (composer); - setup_signatures_menu (composer); - - from_changed_cb(composer->hdrs, composer); - - /* Editor component. */ - composer->editor = bonobo_widget_new_control ( - GNOME_GTKHTML_EDITOR_CONTROL_ID, - bonobo_ui_component_get_container (composer->uic)); - if (!composer->editor) { - e_activation_failure_dialog (GTK_WINDOW (composer), - _("Could not create composer window:\n" - "Unable to activate HTML editor component.\n" - "Please make sure you have the correct version\n" - "of gtkhtml and libgtkhtml installed.\n"), - GNOME_GTKHTML_EDITOR_CONTROL_ID, - "IDL:Bonobo/Control:1.0"); - gtk_object_destroy (GTK_OBJECT (composer)); - return NULL; - } - - control_frame = bonobo_widget_get_control_frame (BONOBO_WIDGET (composer->editor)); - bonobo_control_frame_set_autoactivate (control_frame, TRUE); - - /* let the editor know which mode we are in */ - bonobo_widget_set_property (BONOBO_WIDGET (composer->editor), - "FormatHTML", TC_CORBA_boolean, composer->send_html, - NULL); - - gconf = gconf_client_get_default (); - composer_settings_update (gconf, 0, NULL, composer); - gconf_client_add_dir (gconf, "/apps/evolution/mail/composer", GCONF_CLIENT_PRELOAD_ONELEVEL, NULL); - composer->notify_id = gconf_client_notify_add (gconf, "/apps/evolution/mail/composer", - composer_settings_update, composer, NULL, NULL); - g_object_unref (gconf); - - editor_server = bonobo_widget_get_objref (BONOBO_WIDGET (composer->editor)); - - /* FIXME: handle exceptions */ - CORBA_exception_init (&ev); - composer->persist_file_interface - = Bonobo_Unknown_queryInterface (editor_server, "IDL:Bonobo/PersistFile:1.0", &ev); - composer->persist_stream_interface - = Bonobo_Unknown_queryInterface (editor_server, "IDL:Bonobo/PersistStream:1.0", &ev); - CORBA_exception_free (&ev); - - gtk_box_pack_start (GTK_BOX (vbox), composer->editor, TRUE, TRUE, 0); - - /* Attachment editor, wrapped into an EScrollFrame. We don't - show it for now. */ - - composer->attachment_scrolled_window = gtk_scrolled_window_new (NULL, NULL); - gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (composer->attachment_scrolled_window), - GTK_SHADOW_IN); - gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (composer->attachment_scrolled_window), - GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC); - - composer->attachment_bar = e_msg_composer_attachment_bar_new (NULL); - GTK_WIDGET_SET_FLAGS (composer->attachment_bar, GTK_CAN_FOCUS); - gtk_container_add (GTK_CONTAINER (composer->attachment_scrolled_window), - composer->attachment_bar); - gtk_box_pack_start (GTK_BOX (vbox), - composer->attachment_scrolled_window, - FALSE, FALSE, GNOME_PAD_SMALL); - - g_signal_connect (composer->attachment_bar, "changed", - G_CALLBACK (attachment_bar_changed_cb), composer); - - bonobo_window_set_contents (BONOBO_WINDOW (composer), vbox); - gtk_widget_show (vbox); - - /* If we show this widget earlier, we lose network transparency. i.e. the - component appears on the machine evo is running on, ignoring any DISPLAY - variable. */ - gtk_widget_show (composer->editor); - - e_msg_composer_show_attachments (composer, FALSE); - - prepare_engine (composer); - if (composer->editor_engine == CORBA_OBJECT_NIL) { - e_activation_failure_dialog (GTK_WINDOW (composer), - _("Could not create composer window:\n" - "Unable to activate HTML editor component."), - GNOME_GTKHTML_EDITOR_CONTROL_ID, - "IDL:GNOME/GtkHTML/Editor/Engine:1.0"); - gtk_object_destroy (GTK_OBJECT (composer)); - return NULL; - } - - setup_cut_copy_paste (composer); - - g_signal_connect (composer, "map", (GCallback) map_default_cb, NULL); - - if (am == NULL) - am = autosave_manager_new (); - - autosave_manager_register (am, composer); - - return composer; -} - -static void -set_editor_signature (EMsgComposer *composer) -{ - EAccountIdentity *id; - GSList *signatures; - - /* printf ("set_editor_signature\n"); */ - id = E_MSG_COMPOSER_HDRS (composer->hdrs)->account->id; - - signatures = mail_config_get_signature_list (); - - composer->signature = g_slist_nth_data (signatures, id->def_signature); - composer->auto_signature = id->auto_signature; - - /* printf ("auto: %d\n", id->auto_signature); */ - - sig_select_item (composer); - - /* printf ("set_editor_signature end\n"); */ -} - - -/** - * e_msg_composer_new: - * - * Create a new message composer widget. - * - * Return value: A pointer to the newly created widget - **/ -EMsgComposer * -e_msg_composer_new (void) -{ - gboolean send_html; - GConfClient *gconf; - EMsgComposer *new; - - gconf = gconf_client_get_default (); - send_html = gconf_client_get_bool (gconf, "/apps/evolution/mail/composer/send_html", NULL); - g_object_unref (gconf); - - new = create_composer (E_MSG_COMPOSER_VISIBLE_MASK_MAIL); - if (new) { - e_msg_composer_set_send_html (new, send_html); - set_editor_text (new, ""); - set_editor_signature (new); - } - - return new; -} - -/** - * e_msg_composer_new_post: - * - * Create a new message composer widget. - * - * Return value: A pointer to the newly created widget - **/ -EMsgComposer * -e_msg_composer_new_post (void) -{ - gboolean send_html; - GConfClient *gconf; - EMsgComposer *new; - - gconf = gconf_client_get_default (); - send_html = gconf_client_get_bool (gconf, "/apps/evolution/mail/composer/send_html", NULL); - g_object_unref (gconf); - - new = create_composer (E_MSG_COMPOSER_VISIBLE_MASK_POST); - if (new) { - e_msg_composer_set_send_html (new, send_html); - set_editor_text (new, ""); - set_editor_signature (new); - } - - return new; -} - - -static gboolean -is_special_header (const char *hdr_name) -{ - /* Note: a header is a "special header" if it has any meaning: - 1. it's not a X-* header or - 2. it's an X-Evolution* header - */ - if (strncasecmp (hdr_name, "X-", 2)) - return TRUE; - - if (!strncasecmp (hdr_name, "X-Evolution", 11)) - return TRUE; - - /* we can keep all other X-* headers */ - - return FALSE; -} - -static void -e_msg_composer_set_pending_body (EMsgComposer *composer, char *text) -{ - char *old; - - old = g_object_get_data ((GObject *) composer, "body:text"); - g_free (old); - g_object_set_data ((GObject *) composer, "body:text", text); -} - -static void -e_msg_composer_flush_pending_body (EMsgComposer *composer, gboolean apply) -{ - char *body; - - body = g_object_get_data ((GObject *) composer, "body:text"); - if (body) { - if (apply) - set_editor_text (composer, body); - - g_object_set_data ((GObject *) composer, "body:text", NULL); - g_free (body); - } -} - -static void -add_attachments_handle_mime_part (EMsgComposer *composer, CamelMimePart *mime_part, - gboolean just_inlines, gboolean related, int depth) -{ - CamelContentType *content_type; - CamelDataWrapper *wrapper; - - content_type = camel_mime_part_get_content_type (mime_part); - wrapper = camel_medium_get_content_object (CAMEL_MEDIUM (mime_part)); - - if (CAMEL_IS_MULTIPART (wrapper)) { - /* another layer of multipartness... */ - add_attachments_from_multipart (composer, (CamelMultipart *) wrapper, just_inlines, depth + 1); - } else if (just_inlines) { - if (camel_mime_part_get_content_id (mime_part) || - camel_mime_part_get_content_location (mime_part)) - e_msg_composer_add_inline_image_from_mime_part (composer, mime_part); - } else if (CAMEL_IS_MIME_MESSAGE (wrapper)) { - /* do nothing */ - } else if (related && camel_content_type_is (content_type, "image", "*")) { - e_msg_composer_add_inline_image_from_mime_part (composer, mime_part); - } else { - if (camel_content_type_is (content_type, "text", "*")) { - /* do nothing */ - } else { - e_msg_composer_attach (composer, mime_part); - } - } -} - -static void -add_attachments_from_multipart (EMsgComposer *composer, CamelMultipart *multipart, - gboolean just_inlines, int depth) -{ - /* find appropriate message attachments to add to the composer */ - CamelMimePart *mime_part; - gboolean related; - int i, nparts; - - related = camel_content_type_is (CAMEL_DATA_WRAPPER (multipart)->mime_type, "multipart", "related"); - - if (CAMEL_IS_MULTIPART_SIGNED (multipart)) { - mime_part = camel_multipart_get_part (multipart, CAMEL_MULTIPART_SIGNED_CONTENT); - add_attachments_handle_mime_part (composer, mime_part, just_inlines, related, depth); - } else if (CAMEL_IS_MULTIPART_ENCRYPTED (multipart)) { - /* what should we do in this case? */ - } else { - nparts = camel_multipart_get_number (multipart); - - for (i = 0; i < nparts; i++) { - mime_part = camel_multipart_get_part (multipart, i); - add_attachments_handle_mime_part (composer, mime_part, just_inlines, related, depth); - } - } -} - - -/** - * e_msg_composer_add_message_attachments: - * @composer: the composer to add the attachments to. - * @message: the source message to copy the attachments from. - * @just_inlines: whether to attach all attachments or just add - * inline images. - * - * Walk through all the mime parts in @message and add them to the composer - * specified in @composer. - */ -void -e_msg_composer_add_message_attachments (EMsgComposer *composer, CamelMimeMessage *message, - gboolean just_inlines) -{ - CamelDataWrapper *wrapper; - - wrapper = camel_medium_get_content_object (CAMEL_MEDIUM (message)); - if (!CAMEL_IS_MULTIPART (wrapper)) - return; - - /* there must be attachments... */ - add_attachments_from_multipart (composer, (CamelMultipart *) wrapper, just_inlines, 0); -} - - -static void -handle_multipart_signed (EMsgComposer *composer, CamelMultipart *multipart, int depth) -{ - CamelContentType *content_type; - CamelDataWrapper *content; - CamelMimePart *mime_part; - - /* FIXME: make sure this isn't an s/mime signed part?? */ - e_msg_composer_set_pgp_sign (composer, TRUE); - - mime_part = camel_multipart_get_part (multipart, CAMEL_MULTIPART_SIGNED_CONTENT); - content_type = camel_mime_part_get_content_type (mime_part); - - content = camel_medium_get_content_object (CAMEL_MEDIUM (mime_part)); - - if (CAMEL_IS_MULTIPART (content)) { - multipart = CAMEL_MULTIPART (content); - - /* Note: depth is preserved here because we're not - counting multipart/signed as a multipart, instead - we want to treat the content part as our mime part - here. */ - - if (CAMEL_IS_MULTIPART_SIGNED (content)) { - /* handle the signed content and configure the composer to sign outgoing messages */ - handle_multipart_signed (composer, multipart, depth); - } else if (CAMEL_IS_MULTIPART_ENCRYPTED (content)) { - /* decrypt the encrypted content and configure the composer to encrypt outgoing messages */ - handle_multipart_encrypted (composer, multipart, depth); - } else if (camel_content_type_is (content_type, "multipart", "alternative")) { - /* this contains the text/plain and text/html versions of the message body */ - handle_multipart_alternative (composer, multipart, depth); - } else { - /* there must be attachments... */ - handle_multipart (composer, multipart, depth); - } - } else if (camel_content_type_is (content_type, "text", "*")) { - e_msg_composer_set_pending_body (composer, em_utils_part_to_html (mime_part)); - } else { - e_msg_composer_attach (composer, mime_part); - } -} - -static void -handle_multipart_encrypted (EMsgComposer *composer, CamelMultipart *multipart, int depth) -{ - CamelMultipartEncrypted *mpe = (CamelMultipartEncrypted *) multipart; - CamelContentType *content_type; - CamelCipherContext *cipher; - CamelDataWrapper *content; - CamelMimePart *mime_part; - CamelException ex; - - /* FIXME: make sure this is a PGP/MIME encrypted part?? */ - e_msg_composer_set_pgp_encrypt (composer, TRUE); - - camel_exception_init (&ex); - cipher = mail_crypto_get_pgp_cipher_context (NULL); - mime_part = camel_multipart_encrypted_decrypt (mpe, cipher, &ex); - camel_object_unref (cipher); - camel_exception_clear (&ex); - - if (!mime_part) - return; - - content_type = camel_mime_part_get_content_type (mime_part); - - content = camel_medium_get_content_object (CAMEL_MEDIUM (mime_part)); - - if (CAMEL_IS_MULTIPART (content)) { - multipart = CAMEL_MULTIPART (content); - - /* Note: depth is preserved here because we're not - counting multipart/encrypted as a multipart, instead - we want to treat the content part as our mime part - here. */ - - if (CAMEL_IS_MULTIPART_SIGNED (content)) { - /* handle the signed content and configure the composer to sign outgoing messages */ - handle_multipart_signed (composer, multipart, depth); - } else if (CAMEL_IS_MULTIPART_ENCRYPTED (content)) { - /* decrypt the encrypted content and configure the composer to encrypt outgoing messages */ - handle_multipart_encrypted (composer, multipart, depth); - } else if (camel_content_type_is (content_type, "multipart", "alternative")) { - /* this contains the text/plain and text/html versions of the message body */ - handle_multipart_alternative (composer, multipart, depth); - } else { - /* there must be attachments... */ - handle_multipart (composer, multipart, depth); - } - } else if (camel_content_type_is (content_type, "text", "*")) { - e_msg_composer_set_pending_body (composer, em_utils_part_to_html (mime_part)); - } else { - e_msg_composer_attach (composer, mime_part); - } - - camel_object_unref (mime_part); -} - -static void -handle_multipart_alternative (EMsgComposer *composer, CamelMultipart *multipart, int depth) -{ - /* Find the text/html part and set the composer body to it's contents */ - CamelMimePart *text_part = NULL; - int i, nparts; - - nparts = camel_multipart_get_number (multipart); - - for (i = 0; i < nparts; i++) { - CamelContentType *content_type; - CamelDataWrapper *content; - CamelMimePart *mime_part; - - mime_part = camel_multipart_get_part (multipart, i); - content_type = camel_mime_part_get_content_type (mime_part); - content = camel_medium_get_content_object (CAMEL_MEDIUM (mime_part)); - - if (CAMEL_IS_MULTIPART (content)) { - CamelMultipart *mp; - - mp = CAMEL_MULTIPART (content); - - if (CAMEL_IS_MULTIPART_SIGNED (content)) { - /* handle the signed content and configure the composer to sign outgoing messages */ - handle_multipart_signed (composer, mp, depth + 1); - } else if (CAMEL_IS_MULTIPART_ENCRYPTED (content)) { - /* decrypt the encrypted content and configure the composer to encrypt outgoing messages */ - handle_multipart_encrypted (composer, mp, depth + 1); - } else { - /* depth doesn't matter so long as we don't pass 0 */ - handle_multipart (composer, mp, depth + 1); - } - } else if (camel_content_type_is (content_type, "text", "html")) { - /* text/html is preferable, so once we find it we're done... */ - text_part = mime_part; - break; - } else if (camel_content_type_is (content_type, "text", "*")) { - /* anyt text part not text/html is second rate so the first - text part we find isn't necessarily the one we'll use. */ - if (!text_part) - text_part = mime_part; - } else { - e_msg_composer_attach (composer, mime_part); - } - } - - if (text_part) - e_msg_composer_set_pending_body(composer, em_utils_part_to_html(text_part)); -} - -static void -handle_multipart (EMsgComposer *composer, CamelMultipart *multipart, int depth) -{ - int i, nparts; - - nparts = camel_multipart_get_number (multipart); - - for (i = 0; i < nparts; i++) { - CamelContentType *content_type; - CamelDataWrapper *content; - CamelMimePart *mime_part; - - mime_part = camel_multipart_get_part (multipart, i); - content_type = camel_mime_part_get_content_type (mime_part); - content = camel_medium_get_content_object (CAMEL_MEDIUM (mime_part)); - - if (CAMEL_IS_MULTIPART (content)) { - CamelMultipart *mp; - - mp = CAMEL_MULTIPART (content); - - if (CAMEL_IS_MULTIPART_SIGNED (content)) { - /* handle the signed content and configure the composer to sign outgoing messages */ - handle_multipart_signed (composer, mp, depth + 1); - } else if (CAMEL_IS_MULTIPART_ENCRYPTED (content)) { - /* decrypt the encrypted content and configure the composer to encrypt outgoing messages */ - handle_multipart_encrypted (composer, mp, depth + 1); - } else if (camel_content_type_is (content_type, "multipart", "alternative")) { - handle_multipart_alternative (composer, mp, depth + 1); - } else { - /* depth doesn't matter so long as we don't pass 0 */ - handle_multipart (composer, mp, depth + 1); - } - } else if (depth == 0 && i == 0) { - /* Since the first part is not multipart/alternative, then this must be the body */ - e_msg_composer_set_pending_body(composer, em_utils_part_to_html(mime_part)); - } else if (camel_mime_part_get_content_id (mime_part) || - camel_mime_part_get_content_location (mime_part)) { - /* special in-line attachment */ - e_msg_composer_add_inline_image_from_mime_part (composer, mime_part); - } else { - /* normal attachment */ - e_msg_composer_attach (composer, mime_part); - } - } -} - -static void -set_signature_gui (EMsgComposer *composer) -{ - CORBA_Environment ev; - - composer->auto_signature = FALSE; - composer->signature = NULL; - - CORBA_exception_init (&ev); - if (GNOME_GtkHTML_Editor_Engine_searchByData (composer->editor_engine, 1, "ClueFlow", "signature", "1", &ev)) { - gchar *str = NULL; - - str = GNOME_GtkHTML_Editor_Engine_getParagraphData (composer->editor_engine, "signature_name", &ev); - if (ev._major == CORBA_NO_EXCEPTION && str) { - if (!strncmp (str, "name:", 5)) { - GSList *list = NULL; - char *decoded_signature_name = decode_signature_name (str + 5); - - list = mail_config_get_signature_list (); - if (list && decoded_signature_name) - for (; list; list = list->next) { - if (!strcmp (decoded_signature_name, - ((MailConfigSignature *) list->data)->name)) - break; - } - if (list && decoded_signature_name) - composer->signature = (MailConfigSignature *) list->data; - else - composer->auto_signature = TRUE; - g_free (decoded_signature_name); - } else if (!strcmp (str, "auto")) { - composer->auto_signature = TRUE; - } - } - sig_select_item (composer); - } - CORBA_exception_free (&ev); -} - - -static void -auto_recip_free (gpointer key, gpointer value, gpointer user_data) -{ - g_free (key); -} - -/** - * e_msg_composer_new_with_message: - * @message: The message to use as the source - * - * Create a new message composer widget. - * - * Note: Designed to work only for messages constructed using Evolution. - * - * Return value: A pointer to the newly created widget - **/ -EMsgComposer * -e_msg_composer_new_with_message (CamelMimeMessage *message) -{ - const CamelInternetAddress *to, *cc, *bcc; - GList *To = NULL, *Cc = NULL, *Bcc = NULL; - const char *format, *subject, *postto; - EABDestination **Tov, **Ccv, **Bccv; - GHashTable *auto_cc, *auto_bcc; - CamelContentType *content_type; - struct _camel_header_raw *headers; - CamelDataWrapper *content; - EAccount *account = NULL; - char *account_name; - EMsgComposer *new; - XEvolution *xev; - int len, i; - - postto = camel_medium_get_header (CAMEL_MEDIUM (message), "X-Evolution-PostTo"); - - new = create_composer (postto ? E_MSG_COMPOSER_VISIBLE_MASK_POST : E_MSG_COMPOSER_VISIBLE_MASK_MAIL); - if (!new) - return NULL; - - if (postto) - e_msg_composer_hdrs_set_post_to (E_MSG_COMPOSER_HDRS (new->hdrs), postto); - - /* Restore the Account preference */ - account_name = (char *) camel_medium_get_header (CAMEL_MEDIUM (message), "X-Evolution-Account"); - if (account_name) { - account_name = g_strdup (account_name); - g_strstrip (account_name); - - account = mail_config_get_account_by_name (account_name); - } - - if (postto == NULL) { - auto_cc = g_hash_table_new (camel_strcase_hash, camel_strcase_equal); - auto_bcc = g_hash_table_new (camel_strcase_hash, camel_strcase_equal); - - if (account) { - CamelInternetAddress *iaddr; - - /* hash our auto-recipients for this account */ - if (account->always_cc) { - iaddr = camel_internet_address_new (); - if (camel_address_decode (CAMEL_ADDRESS (iaddr), account->cc_addrs) != -1) { - for (i = 0; i < camel_address_length (CAMEL_ADDRESS (iaddr)); i++) { - const char *name, *addr; - - if (!camel_internet_address_get (iaddr, i, &name, &addr)) - continue; - - g_hash_table_insert (auto_cc, g_strdup (addr), GINT_TO_POINTER (TRUE)); - } - } - camel_object_unref (iaddr); - } - - if (account->always_bcc) { - iaddr = camel_internet_address_new (); - if (camel_address_decode (CAMEL_ADDRESS (iaddr), account->bcc_addrs) != -1) { - for (i = 0; i < camel_address_length (CAMEL_ADDRESS (iaddr)); i++) { - const char *name, *addr; - - if (!camel_internet_address_get (iaddr, i, &name, &addr)) - continue; - - g_hash_table_insert (auto_bcc, g_strdup (addr), GINT_TO_POINTER (TRUE)); - } - } - camel_object_unref (iaddr); - } - } - - to = camel_mime_message_get_recipients (message, CAMEL_RECIPIENT_TYPE_TO); - cc = camel_mime_message_get_recipients (message, CAMEL_RECIPIENT_TYPE_CC); - bcc = camel_mime_message_get_recipients (message, CAMEL_RECIPIENT_TYPE_BCC); - - len = CAMEL_ADDRESS (to)->addresses->len; - for (i = 0; i < len; i++) { - const char *name, *addr; - - if (camel_internet_address_get (to, i, &name, &addr)) { - EABDestination *dest = eab_destination_new (); - eab_destination_set_name (dest, name); - eab_destination_set_email (dest, addr); - To = g_list_append (To, dest); - } - } - Tov = eab_destination_list_to_vector (To); - g_list_free (To); - - len = CAMEL_ADDRESS (cc)->addresses->len; - for (i = 0; i < len; i++) { - const char *name, *addr; - - if (camel_internet_address_get (cc, i, &name, &addr)) { - EABDestination *dest = eab_destination_new (); - eab_destination_set_name (dest, name); - eab_destination_set_email (dest, addr); - - if (g_hash_table_lookup (auto_cc, addr)) - eab_destination_set_auto_recipient (dest, TRUE); - - Cc = g_list_append (Cc, dest); - } - } - - Ccv = eab_destination_list_to_vector (Cc); - g_hash_table_foreach (auto_cc, auto_recip_free, NULL); - g_hash_table_destroy (auto_cc); - g_list_free (Cc); - - len = CAMEL_ADDRESS (bcc)->addresses->len; - for (i = 0; i < len; i++) { - const char *name, *addr; - - if (camel_internet_address_get (bcc, i, &name, &addr)) { - EABDestination *dest = eab_destination_new (); - eab_destination_set_name (dest, name); - eab_destination_set_email (dest, addr); - - if (g_hash_table_lookup (auto_bcc, addr)) - eab_destination_set_auto_recipient (dest, TRUE); - - Bcc = g_list_append (Bcc, dest); - } - } - - Bccv = eab_destination_list_to_vector (Bcc); - g_hash_table_foreach (auto_bcc, auto_recip_free, NULL); - g_hash_table_destroy (auto_bcc); - g_list_free (Bcc); - } else { - Tov = NULL; - Ccv = NULL; - Bccv = NULL; - } - - subject = camel_mime_message_get_subject (message); - - e_msg_composer_set_headers (new, account_name, Tov, Ccv, Bccv, subject); - - g_free (account_name); - - eab_destination_freev (Tov); - eab_destination_freev (Ccv); - eab_destination_freev (Bccv); - - /* Restore the format editing preference */ - format = camel_medium_get_header (CAMEL_MEDIUM (message), "X-Evolution-Format"); - if (format) { - while (*format && isspace ((unsigned) *format)) - format++; - - if (!strcasecmp (format, "text/html")) - e_msg_composer_set_send_html (new, TRUE); - else - e_msg_composer_set_send_html (new, FALSE); - } - - /* Remove any other X-Evolution-* headers that may have been set */ - xev = mail_tool_remove_xevolution_headers (message); - mail_tool_destroy_xevolution (xev); - - /* set extra headers */ - headers = CAMEL_MIME_PART (message)->headers; - while (headers) { - if (!is_special_header (headers->name) || - !strcasecmp (headers->name, "References") || - !strcasecmp (headers->name, "In-Reply-To")) { - g_ptr_array_add (new->extra_hdr_names, g_strdup (headers->name)); - g_ptr_array_add (new->extra_hdr_values, g_strdup (headers->value)); - } - - headers = headers->next; - } - - /* Restore the attachments and body text */ - content = camel_medium_get_content_object (CAMEL_MEDIUM (message)); - if (CAMEL_IS_MULTIPART (content)) { - CamelMultipart *multipart; - - multipart = CAMEL_MULTIPART (content); - content_type = camel_mime_part_get_content_type (CAMEL_MIME_PART (message)); - - if (CAMEL_IS_MULTIPART_SIGNED (content)) { - /* handle the signed content and configure the composer to sign outgoing messages */ - handle_multipart_signed (new, multipart, 0); - } else if (CAMEL_IS_MULTIPART_ENCRYPTED (content)) { - /* decrypt the encrypted content and configure the composer to encrypt outgoing messages */ - handle_multipart_encrypted (new, multipart, 0); - } else if (camel_content_type_is (content_type, "multipart", "alternative")) { - /* this contains the text/plain and text/html versions of the message body */ - handle_multipart_alternative (new, multipart, 0); - } else { - /* there must be attachments... */ - handle_multipart (new, multipart, 0); - } - } else { - e_msg_composer_set_pending_body(new, em_utils_part_to_html((CamelMimePart *)message)); - } - - /* We wait until now to set the body text because we need to ensure that - * the attachment bar has all the attachments, before we request them. - */ - e_msg_composer_flush_pending_body (new, TRUE); - - set_signature_gui (new); - - return new; -} - -static void -disable_editor (EMsgComposer *composer) -{ - gtk_widget_set_sensitive (composer->editor, FALSE); - gtk_widget_set_sensitive (composer->attachment_bar, FALSE); - - bonobo_ui_component_set_prop (composer->uic, "/menu/Edit", "sensitive", "0", NULL); - bonobo_ui_component_set_prop (composer->uic, "/menu/Format", "sensitive", "0", NULL); - bonobo_ui_component_set_prop (composer->uic, "/menu/Insert", "sensitive", "0", NULL); -} - -/** - * e_msg_composer_new_redirect: - * @message: The message to use as the source - * - * Create a new message composer widget. - * - * Return value: A pointer to the newly created widget - **/ -EMsgComposer * -e_msg_composer_new_redirect (CamelMimeMessage *message, const char *resent_from) -{ - EMsgComposer *composer; - const char *subject; - - g_return_val_if_fail (CAMEL_IS_MIME_MESSAGE (message), NULL); - - composer = e_msg_composer_new_with_message (message); - subject = camel_mime_message_get_subject (message); - - composer->redirect = message; - camel_object_ref (message); - - e_msg_composer_set_headers (composer, resent_from, NULL, NULL, NULL, subject); - - disable_editor (composer); - - return composer; -} - - -static GList * -add_recipients (GList *list, const char *recips, gboolean decode) -{ - CamelInternetAddress *cia; - const char *name, *addr; - int num, i; - - cia = camel_internet_address_new (); - if (decode) - num = camel_address_decode (CAMEL_ADDRESS (cia), recips); - else - num = camel_address_unformat (CAMEL_ADDRESS (cia), recips); - - for (i = 0; i < num; i++) { - if (camel_internet_address_get (cia, i, &name, &addr)) { - EABDestination *dest = eab_destination_new (); - eab_destination_set_name (dest, name); - eab_destination_set_email (dest, addr); - - list = g_list_append (list, dest); - } - } - - return list; -} - -static void -handle_mailto (EMsgComposer *composer, const char *mailto) -{ - EMsgComposerHdrs *hdrs; - GList *to = NULL, *cc = NULL, *bcc = NULL; - EABDestination **tov, **ccv, **bccv; - char *subject = NULL, *body = NULL; - char *header, *content, *buf; - size_t nread, nwritten; - const char *p; - int len, clen; - CamelURL *url; - - buf = g_strdup (mailto); - - /* Parse recipients (everything after ':' until '?' or eos). */ - p = buf + 7; - len = strcspn (p, "?"); - if (len) { - content = g_strndup (p, len); - camel_url_decode (content); - to = add_recipients (to, content, FALSE); - g_free (content); - } - - p += len; - if (*p == '?') { - p++; - - while (*p) { - len = strcspn (p, "=&"); - - /* If it's malformed, give up. */ - if (p[len] != '=') - break; - - header = (char *) p; - header[len] = '\0'; - p += len + 1; - - clen = strcspn (p, "&"); - - content = g_strndup (p, clen); - camel_url_decode (content); - - if (!strcasecmp (header, "to")) { - to = add_recipients (to, content, FALSE); - } else if (!strcasecmp (header, "cc")) { - cc = add_recipients (cc, content, FALSE); - } else if (!strcasecmp (header, "bcc")) { - bcc = add_recipients (bcc, content, FALSE); - } else if (!strcasecmp (header, "subject")) { - g_free (subject); - if (g_utf8_validate (content, -1, NULL)) { - subject = content; - content = NULL; - } else { - subject = g_locale_to_utf8 (content, clen, &nread, - &nwritten, NULL); - if (subject) { - subject = g_realloc (subject, nwritten + 1); - subject[nwritten] = '\0'; - } - } - } else if (!strcasecmp (header, "body")) { - g_free (body); - if (g_utf8_validate (content, -1, NULL)) { - body = content; - content = NULL; - } else { - body = g_locale_to_utf8 (content, clen, &nread, - &nwritten, NULL); - if (body) { - body = g_realloc (body, nwritten + 1); - body[nwritten] = '\0'; - } - } - } else if (!strcasecmp (header, "attach")) { - /* Change file url to absolute path */ - if (!strncasecmp (content, "file:", 5)) { - url = camel_url_new (content, NULL); - e_msg_composer_attachment_bar_attach (E_MSG_COMPOSER_ATTACHMENT_BAR (composer->attachment_bar), - url->path); - camel_url_free (url); - } else { - e_msg_composer_attachment_bar_attach (E_MSG_COMPOSER_ATTACHMENT_BAR (composer->attachment_bar), - content); - } - } else if (!strcasecmp (header, "from")) { - /* Ignore */ - } else if (!strcasecmp (header, "reply-to")) { - /* ignore */ - } else { - /* add an arbitrary header? */ - e_msg_composer_add_header (composer, header, content); - } - - g_free (content); - - p += clen; - if (*p == '&') { - p++; - if (!strcmp (p, "amp;")) - p += 4; - } - } - } - - g_free (buf); - - tov = eab_destination_list_to_vector (to); - ccv = eab_destination_list_to_vector (cc); - bccv = eab_destination_list_to_vector (bcc); - - g_list_free (to); - g_list_free (cc); - g_list_free (bcc); - - hdrs = E_MSG_COMPOSER_HDRS (composer->hdrs); - - e_msg_composer_hdrs_set_to (hdrs, tov); - e_msg_composer_hdrs_set_cc (hdrs, ccv); - e_msg_composer_hdrs_set_bcc (hdrs, bccv); - - eab_destination_freev (tov); - eab_destination_freev (ccv); - eab_destination_freev (bccv); - - if (subject) { - e_msg_composer_hdrs_set_subject (hdrs, subject); - g_free (subject); - } - - if (body) { - char *htmlbody; - - htmlbody = camel_text_to_html (body, CAMEL_MIME_FILTER_TOHTML_PRE, 0); - set_editor_text (composer, htmlbody); - g_free (htmlbody); - } -} - -/** - * e_msg_composer_new_from_url: - * @url: a mailto URL - * - * Create a new message composer widget, and fill in fields as - * defined by the provided URL. - **/ -EMsgComposer * -e_msg_composer_new_from_url (const char *url) -{ - EMsgComposer *composer; - - g_return_val_if_fail (strncasecmp (url, "mailto:", 7) == 0, NULL); - - composer = e_msg_composer_new (); - if (!composer) - return NULL; - - handle_mailto (composer, url); - - return composer; -} - - -/** - * e_msg_composer_show_attachments: - * @composer: A message composer widget - * @show: A boolean specifying whether the attachment bar should be shown or - * not - * - * If @show is %FALSE, hide the attachment bar. Otherwise, show it. - **/ -void -e_msg_composer_show_attachments (EMsgComposer *composer, - gboolean show) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - show_attachments (composer, show); -} - - -/** - * e_msg_composer_set_headers: - * @composer: a composer object - * @from: the name of the account the user will send from, - * or %NULL for the default account - * @to: the values for the "To" header - * @cc: the values for the "Cc" header - * @bcc: the values for the "Bcc" header - * @subject: the value for the "Subject" header - * - * Sets the headers in the composer to the given values. - **/ -void -e_msg_composer_set_headers (EMsgComposer *composer, - const char *from, - EABDestination **to, - EABDestination **cc, - EABDestination **bcc, - const char *subject) -{ - EMsgComposerHdrs *hdrs; - - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - hdrs = E_MSG_COMPOSER_HDRS (composer->hdrs); - - e_msg_composer_hdrs_set_to (hdrs, to); - e_msg_composer_hdrs_set_cc (hdrs, cc); - e_msg_composer_hdrs_set_bcc (hdrs, bcc); - e_msg_composer_hdrs_set_subject (hdrs, subject); - e_msg_composer_hdrs_set_from_account (hdrs, from); -} - - -/** - * e_msg_composer_set_body_text: - * @composer: a composer object - * @text: the HTML text to initialize the editor with - * - * Loads the given HTML text into the editor. - **/ -void -e_msg_composer_set_body_text (EMsgComposer *composer, const char *text) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - set_editor_text (composer, text); - - /* set editor text unfortunately kills the signature so we - have to re-show it */ - e_msg_composer_show_sig_file (composer); -} - - -/** - * e_msg_composer_set_body: - * @composer: a composer object - * @body: the data to initialize the composer with - * @mime_type: the MIME type of data - * - * Loads the given data into the composer as the message body. - * This function should only be used by the CORBA composer factory. - **/ -void -e_msg_composer_set_body (EMsgComposer *composer, const char *body, - const char *mime_type) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - set_editor_text (composer, _("<b>(The composer contains a non-text " - "message body, which cannot be " - "edited.)<b>")); - e_msg_composer_set_send_html (composer, FALSE); - disable_editor (composer); - - g_free (composer->mime_body); - composer->mime_body = g_strdup (body); - g_free (composer->mime_type); - composer->mime_type = g_strdup (mime_type); - - if (g_ascii_strncasecmp (composer->mime_type, "text/calendar", 13) == 0) { - EMsgComposerHdrs *hdrs = E_MSG_COMPOSER_HDRS (composer->hdrs); - if (hdrs->account && hdrs->account->pgp_no_imip_sign) - e_msg_composer_set_pgp_sign (composer, FALSE); - } -} - - -/** - * e_msg_composer_add_header: - * @composer: a composer object - * @name: the header name - * @value: the header value - * - * Adds a header with @name and @value to the message. This header - * may not be displayed by the composer, but will be included in - * the message it outputs. - **/ -void -e_msg_composer_add_header (EMsgComposer *composer, const char *name, - const char *value) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - g_return_if_fail (name != NULL); - g_return_if_fail (value != NULL); - - g_ptr_array_add (composer->extra_hdr_names, g_strdup (name)); - g_ptr_array_add (composer->extra_hdr_values, g_strdup (value)); -} - - -/** - * e_msg_composer_attach: - * @composer: a composer object - * @attachment: the CamelMimePart to attach - * - * Attaches @attachment to the message being composed in the composer. - **/ -void -e_msg_composer_attach (EMsgComposer *composer, CamelMimePart *attachment) -{ - EMsgComposerAttachmentBar *bar; - - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - g_return_if_fail (CAMEL_IS_MIME_PART (attachment)); - - bar = E_MSG_COMPOSER_ATTACHMENT_BAR (composer->attachment_bar); - e_msg_composer_attachment_bar_attach_mime_part (bar, attachment); -} - - -/** - * e_msg_composer_add_inline_image_from_file: - * @composer: a composer object - * @file_name: the name of the file containing the image - * - * This reads in the image in @file_name and adds it to @composer - * as an inline image, to be wrapped in a multipart/related. - * - * Return value: the newly-created CamelMimePart (which must be reffed - * if the caller wants to keep its own reference), or %NULL on error. - **/ -CamelMimePart * -e_msg_composer_add_inline_image_from_file (EMsgComposer *composer, - const char *file_name) -{ - char *mime_type, *cid, *url, *name; - CamelStream *stream; - CamelDataWrapper *wrapper; - CamelMimePart *part; - struct stat statbuf; - - /* check for regular file */ - if (stat (file_name, &statbuf) < 0 || !S_ISREG (statbuf.st_mode)) - return NULL; - - stream = camel_stream_fs_new_with_name (file_name, O_RDONLY, 0); - if (!stream) - return NULL; - - wrapper = camel_data_wrapper_new (); - camel_data_wrapper_construct_from_stream (wrapper, stream); - camel_object_unref (CAMEL_OBJECT (stream)); - - mime_type = e_msg_composer_guess_mime_type (file_name); - camel_data_wrapper_set_mime_type (wrapper, mime_type ? mime_type : "application/octet-stream"); - g_free (mime_type); - - part = camel_mime_part_new (); - camel_medium_set_content_object (CAMEL_MEDIUM (part), wrapper); - camel_object_unref (wrapper); - - cid = camel_header_msgid_generate (); - camel_mime_part_set_content_id (part, cid); - name = g_path_get_basename(file_name); - camel_mime_part_set_filename (part, name); - g_free(name); - camel_mime_part_set_encoding (part, CAMEL_TRANSFER_ENCODING_BASE64); - - url = g_strdup_printf ("file:%s", file_name); - g_hash_table_insert (composer->inline_images_by_url, url, part); - - url = g_strdup_printf ("cid:%s", cid); - g_hash_table_insert (composer->inline_images, url, part); - g_free (cid); - - return part; -} - - -/** - * e_msg_composer_add_inline_image_from_mime_part: - * @composer: a composer object - * @part: a CamelMimePart containing image data - * - * This adds the mime part @part to @composer as an inline image, to - * be wrapped in a multipart/related. - **/ -void -e_msg_composer_add_inline_image_from_mime_part (EMsgComposer *composer, - CamelMimePart *part) -{ - char *url; - const char *location, *cid; - - cid = camel_mime_part_get_content_id (part); - if (!cid) { - camel_mime_part_set_content_id (part, NULL); - cid = camel_mime_part_get_content_id (part); - } - - url = g_strdup_printf ("cid:%s", cid); - g_hash_table_insert (composer->inline_images, url, part); - camel_object_ref (part); - - location = camel_mime_part_get_content_location (part); - if (location) { - g_hash_table_insert (composer->inline_images_by_url, - g_strdup (location), part); - } -} - - -/** - * e_msg_composer_get_message: - * @composer: A message composer widget - * - * Retrieve the message edited by the user as a CamelMimeMessage. The - * CamelMimeMessage object is created on the fly; subsequent calls to this - * function will always create new objects from scratch. - * - * Return value: A pointer to the new CamelMimeMessage object - **/ -CamelMimeMessage * -e_msg_composer_get_message (EMsgComposer *composer, gboolean save_html_object_data) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), NULL); - - return build_message (composer, save_html_object_data); -} - - -CamelMimeMessage * -e_msg_composer_get_message_draft (EMsgComposer *composer) -{ - CamelMimeMessage *msg; - EAccount *account; - gboolean old_send_html; - gboolean old_pgp_sign; - gboolean old_pgp_encrypt; - gboolean old_smime_sign; - gboolean old_smime_encrypt; - - /* always save drafts as HTML to preserve formatting */ - old_send_html = composer->send_html; - composer->send_html = TRUE; - old_pgp_sign = composer->pgp_sign; - composer->pgp_sign = FALSE; - old_pgp_encrypt = composer->pgp_encrypt; - composer->pgp_encrypt = FALSE; - old_smime_sign = composer->smime_sign; - composer->smime_sign = FALSE; - old_smime_encrypt = composer->smime_encrypt; - composer->smime_encrypt = FALSE; - - msg = e_msg_composer_get_message (composer, TRUE); - - composer->send_html = old_send_html; - composer->pgp_sign = old_pgp_sign; - composer->pgp_encrypt = old_pgp_encrypt; - composer->smime_sign = old_smime_sign; - composer->smime_encrypt = old_smime_encrypt; - - /* Attach account info to the draft. */ - account = e_msg_composer_get_preferred_account (composer); - if (account && account->name) - camel_medium_set_header (CAMEL_MEDIUM (msg), "X-Evolution-Account", account->name); - - /* build_message() set this to text/html since we set composer->send_html to - TRUE before calling e_msg_composer_get_message() */ - if (!composer->send_html) - camel_medium_set_header (CAMEL_MEDIUM (msg), "X-Evolution-Format", "text/plain"); - - return msg; -} - - -static void -delete_old_signature (EMsgComposer *composer) -{ - CORBA_Environment ev; - - /* printf ("delete_old_signature\n"); */ - CORBA_exception_init (&ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "cursor-bod", &ev); - if (GNOME_GtkHTML_Editor_Engine_searchByData (composer->editor_engine, 1, "ClueFlow", "signature", "1", &ev)) { - /* printf ("found\n"); */ - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "select-paragraph", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "delete", &ev); - /* selection-move-right doesn't succeed means that we are already on the end of document */ - /* if (!rv) - break; */ - GNOME_GtkHTML_Editor_Engine_setParagraphData (composer->editor_engine, "signature", "0", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "delete-back", &ev); - } - CORBA_exception_free (&ev); -} - - -/** - * e_msg_composer_show_sig: - * @composer: A message composer widget - * - * Set a signature - **/ -void -e_msg_composer_show_sig_file (EMsgComposer *composer) -{ - CORBA_Environment ev; - char *html; - - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - /* printf ("e_msg_composer_show_sig_file\n"); */ - /* printf ("set sig '%s' '%s'\n", sig_file, composer->sig_file); */ - - composer->in_signature_insert = TRUE; - CORBA_exception_init (&ev); - GNOME_GtkHTML_Editor_Engine_freeze (composer->editor_engine, &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "cursor-position-save", &ev); - GNOME_GtkHTML_Editor_Engine_undoBegin (composer->editor_engine, "Set signature", "Reset signature", &ev); - - delete_old_signature (composer); - html = get_signature_html (composer); - if (html) { - if (!GNOME_GtkHTML_Editor_Engine_isParagraphEmpty (composer->editor_engine, &ev)) - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "insert-paragraph", &ev); - if (!GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "cursor-backward", &ev)) - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "insert-paragraph", &ev); - else - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "cursor-forward", &ev); - /* printf ("insert %s\n", html); */ - GNOME_GtkHTML_Editor_Engine_setParagraphData (composer->editor_engine, "orig", "0", &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "indent-zero", &ev); - GNOME_GtkHTML_Editor_Engine_insertHTML (composer->editor_engine, html, &ev); - g_free (html); - } - - GNOME_GtkHTML_Editor_Engine_undoEnd (composer->editor_engine, &ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "cursor-position-restore", &ev); - GNOME_GtkHTML_Editor_Engine_thaw (composer->editor_engine, &ev); - CORBA_exception_free (&ev); - composer->in_signature_insert = FALSE; - - /* printf ("e_msg_composer_show_sig_file end\n"); */ -} - - -/** - * e_msg_composer_set_send_html: - * @composer: A message composer widget - * @send_html: Whether the composer should have the "Send HTML" flag set - * - * Set the status of the "Send HTML" toggle item. The user can override it. - **/ -void -e_msg_composer_set_send_html (EMsgComposer *composer, - gboolean send_html) -{ - CORBA_Environment ev; - - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - if (composer->send_html && send_html) - return; - - if (!composer->send_html && !send_html) - return; - - composer->send_html = send_html; - - CORBA_exception_init (&ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "block-redraw", &ev); - CORBA_exception_free (&ev); - - bonobo_ui_component_set_prop (composer->uic, "/commands/FormatHtml", - "state", composer->send_html ? "1" : "0", NULL); - - /* let the editor know which mode we are in */ - bonobo_widget_set_property (BONOBO_WIDGET (composer->editor), - "FormatHTML", TC_CORBA_boolean, - composer->send_html, NULL); - - CORBA_exception_init (&ev); - GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "unblock-redraw", &ev); - CORBA_exception_free (&ev); -} - - -/** - * e_msg_composer_get_send_html: - * @composer: A message composer widget - * - * Get the status of the "Send HTML mail" flag. - * - * Return value: The status of the "Send HTML mail" flag. - **/ -gboolean -e_msg_composer_get_send_html (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->send_html; -} - - -/** - * e_msg_composer_get_preferred_account: - * @composer: composer - * - * Returns the user-specified account (from field). - */ -EAccount * -e_msg_composer_get_preferred_account (EMsgComposer *composer) -{ - EMsgComposerHdrs *hdrs; - - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), NULL); - - hdrs = E_MSG_COMPOSER_HDRS (composer->hdrs); - - return hdrs->account; -} - - -/** - * e_msg_composer_set_pgp_sign: - * @composer: A message composer widget - * @send_html: Whether the composer should have the "PGP Sign" flag set - * - * Set the status of the "PGP Sign" toggle item. The user can override it. - **/ -void -e_msg_composer_set_pgp_sign (EMsgComposer *composer, gboolean pgp_sign) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - if (composer->pgp_sign && pgp_sign) - return; - if (!composer->pgp_sign && !pgp_sign) - return; - - composer->pgp_sign = pgp_sign; - - bonobo_ui_component_set_prop (composer->uic, "/commands/SecurityPGPSign", - "state", composer->pgp_sign ? "1" : "0", NULL); -} - - -/** - * e_msg_composer_get_pgp_sign: - * @composer: A message composer widget - * - * Get the status of the "PGP Sign" flag. - * - * Return value: The status of the "PGP Sign" flag. - **/ -gboolean -e_msg_composer_get_pgp_sign (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->pgp_sign; -} - - -/** - * e_msg_composer_set_pgp_encrypt: - * @composer: A message composer widget - * @send_html: Whether the composer should have the "PGP Encrypt" flag set - * - * Set the status of the "PGP Encrypt" toggle item. The user can override it. - **/ -void -e_msg_composer_set_pgp_encrypt (EMsgComposer *composer, gboolean pgp_encrypt) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - if (composer->pgp_encrypt && pgp_encrypt) - return; - if (!composer->pgp_encrypt && !pgp_encrypt) - return; - - composer->pgp_encrypt = pgp_encrypt; - - bonobo_ui_component_set_prop (composer->uic, "/commands/SecurityPGPEncrypt", - "state", composer->pgp_encrypt ? "1" : "0", NULL); -} - - -/** - * e_msg_composer_get_pgp_encrypt: - * @composer: A message composer widget - * - * Get the status of the "PGP Encrypt" flag. - * - * Return value: The status of the "PGP Encrypt" flag. - **/ -gboolean -e_msg_composer_get_pgp_encrypt (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->pgp_encrypt; -} - - -/** - * e_msg_composer_set_smime_sign: - * @composer: A message composer widget - * @send_html: Whether the composer should have the "S/MIME Sign" flag set - * - * Set the status of the "S/MIME Sign" toggle item. The user can override it. - **/ -void -e_msg_composer_set_smime_sign (EMsgComposer *composer, gboolean smime_sign) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - if (composer->smime_sign && smime_sign) - return; - if (!composer->smime_sign && !smime_sign) - return; - - composer->smime_sign = smime_sign; - - bonobo_ui_component_set_prop (composer->uic, "/commands/SecuritySMimeSign", - "state", composer->smime_sign ? "1" : "0", NULL); -} - - -/** - * e_msg_composer_get_smime_sign: - * @composer: A message composer widget - * - * Get the status of the "S/MIME Sign" flag. - * - * Return value: The status of the "S/MIME Sign" flag. - **/ -gboolean -e_msg_composer_get_smime_sign (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->smime_sign; -} - - -/** - * e_msg_composer_set_smime_encrypt: - * @composer: A message composer widget - * @send_html: Whether the composer should have the "S/MIME Encrypt" flag set - * - * Set the status of the "S/MIME Encrypt" toggle item. The user can override it. - **/ -void -e_msg_composer_set_smime_encrypt (EMsgComposer *composer, gboolean smime_encrypt) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - if (composer->smime_encrypt && smime_encrypt) - return; - if (!composer->smime_encrypt && !smime_encrypt) - return; - - composer->smime_encrypt = smime_encrypt; - - bonobo_ui_component_set_prop (composer->uic, "/commands/SecuritySMimeEncrypt", - "state", composer->smime_encrypt ? "1" : "0", NULL); -} - - -/** - * e_msg_composer_get_smime_encrypt: - * @composer: A message composer widget - * - * Get the status of the "S/MIME Encrypt" flag. - * - * Return value: The status of the "S/MIME Encrypt" flag. - **/ -gboolean -e_msg_composer_get_smime_encrypt (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->smime_encrypt; -} - - -/** - * e_msg_composer_get_view_from: - * @composer: A message composer widget - * - * Get the status of the "View From header" flag. - * - * Return value: The status of the "View From header" flag. - **/ -gboolean -e_msg_composer_get_view_from (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->view_from; -} - - -/** - * e_msg_composer_set_view_from: - * @composer: A message composer widget - * @state: whether to show or hide the From selector - * - * Controls the state of the From selector - */ -void -e_msg_composer_set_view_from (EMsgComposer *composer, gboolean view_from) -{ - GConfClient *gconf; - - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - if ((composer->view_from && view_from) || - (!composer->view_from && !view_from)) - return; - - composer->view_from = view_from; - bonobo_ui_component_set_prop (composer->uic, "/commands/ViewFrom", - "state", composer->view_from ? "1" : "0", NULL); - - gconf = gconf_client_get_default (); - gconf_client_set_bool (gconf, "/apps/evolution/mail/composer/view/From", view_from, NULL); - g_object_unref (gconf); - - e_msg_composer_hdrs_set_visible (E_MSG_COMPOSER_HDRS (composer->hdrs), - e_msg_composer_get_visible_flags (composer)); -} - - -/** - * e_msg_composer_get_view_replyto: - * @composer: A message composer widget - * - * Get the status of the "View Reply-To header" flag. - * - * Return value: The status of the "View Reply-To header" flag. - **/ -gboolean -e_msg_composer_get_view_replyto (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->view_replyto; -} - - -/** - * e_msg_composer_set_view_replyto: - * @composer: A message composer widget - * @state: whether to show or hide the Reply-To selector - * - * Controls the state of the Reply-To selector - */ -void -e_msg_composer_set_view_replyto (EMsgComposer *composer, gboolean view_replyto) -{ - GConfClient *gconf; - - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - if ((composer->view_replyto && view_replyto) || - (!composer->view_replyto && !view_replyto)) - return; - - composer->view_replyto = view_replyto; - bonobo_ui_component_set_prop (composer->uic, "/commands/ViewReplyTo", - "state", composer->view_replyto ? "1" : "0", NULL); - - gconf = gconf_client_get_default (); - gconf_client_set_bool (gconf, "/apps/evolution/mail/composer/view/ReplyTo", view_replyto, NULL); - g_object_unref (gconf); - - e_msg_composer_hdrs_set_visible (E_MSG_COMPOSER_HDRS (composer->hdrs), - e_msg_composer_get_visible_flags (composer)); -} - - -/** - * e_msg_composer_get_view_cc: - * @composer: A message composer widget - * - * Get the status of the "View CC header" flag. - * - * Return value: The status of the "View CC header" flag. - **/ -gboolean -e_msg_composer_get_view_cc (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->view_cc; -} - - -/** - * e_msg_composer_set_view_cc: - * @composer: A message composer widget - * @state: whether to show or hide the cc view - * - * Controls the state of the CC display - */ -void -e_msg_composer_set_view_cc (EMsgComposer *composer, gboolean view_cc) -{ - GConfClient *gconf; - - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - if ((composer->view_cc && view_cc) || - (!composer->view_cc && !view_cc)) - return; - - composer->view_cc = view_cc; - bonobo_ui_component_set_prop (composer->uic, "/commands/ViewCC", - "state", composer->view_cc ? "1" : "0", NULL); - - gconf = gconf_client_get_default (); - gconf_client_set_bool (gconf, "/apps/evolution/mail/composer/view/Cc", view_cc, NULL); - g_object_unref (gconf); - - e_msg_composer_hdrs_set_visible (E_MSG_COMPOSER_HDRS (composer->hdrs), - e_msg_composer_get_visible_flags (composer)); -} - - -/** - * e_msg_composer_get_view_bcc: - * @composer: A message composer widget - * - * Get the status of the "View BCC header" flag. - * - * Return value: The status of the "View BCC header" flag. - **/ -gboolean -e_msg_composer_get_view_bcc (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->view_bcc; -} - - -/** - * e_msg_composer_set_view_bcc: - * @composer: A message composer widget - * @state: whether to show or hide the bcc view - * - * Controls the state of the BCC display - */ -void -e_msg_composer_set_view_bcc (EMsgComposer *composer, gboolean view_bcc) -{ - GConfClient *gconf; - - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - if ((composer->view_bcc && view_bcc) || - (!composer->view_bcc && !view_bcc)) - return; - - composer->view_bcc = view_bcc; - bonobo_ui_component_set_prop (composer->uic, "/commands/ViewBCC", - "state", composer->view_bcc ? "1" : "0", NULL); - - gconf = gconf_client_get_default (); - gconf_client_set_bool (gconf, "/apps/evolution/mail/composer/view/Bcc", view_bcc, NULL); - g_object_unref (gconf); - - e_msg_composer_hdrs_set_visible (E_MSG_COMPOSER_HDRS (composer->hdrs), - e_msg_composer_get_visible_flags (composer)); -} - - -EABDestination ** -e_msg_composer_get_recipients (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), NULL); - - return composer->hdrs ? e_msg_composer_hdrs_get_recipients (E_MSG_COMPOSER_HDRS (composer->hdrs)) : NULL; -} - -EABDestination ** -e_msg_composer_get_to (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), NULL); - - return composer->hdrs ? e_msg_composer_hdrs_get_to (E_MSG_COMPOSER_HDRS (composer->hdrs)) : NULL; -} - -EABDestination ** -e_msg_composer_get_cc (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), NULL); - - return composer->hdrs ? e_msg_composer_hdrs_get_cc (E_MSG_COMPOSER_HDRS (composer->hdrs)) : NULL; -} - -EABDestination ** -e_msg_composer_get_bcc (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), NULL); - - return composer->hdrs ? e_msg_composer_hdrs_get_bcc (E_MSG_COMPOSER_HDRS (composer->hdrs)) : NULL; -} - -const char * -e_msg_composer_get_subject (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), NULL); - - return composer->hdrs ? e_msg_composer_hdrs_get_subject (E_MSG_COMPOSER_HDRS (composer->hdrs)) : NULL; -} - - -/** - * e_msg_composer_guess_mime_type: - * @file_name: filename - * - * Returns the guessed mime type of the file given by #file_name. - **/ -char * -e_msg_composer_guess_mime_type (const char *file_name) -{ - GnomeVFSFileInfo *info; - GnomeVFSResult result; - - info = gnome_vfs_file_info_new (); - result = gnome_vfs_get_file_info (file_name, info, - GNOME_VFS_FILE_INFO_GET_MIME_TYPE | - GNOME_VFS_FILE_INFO_FOLLOW_LINKS); - if (result == GNOME_VFS_OK) { - char *type; - - type = g_strdup (gnome_vfs_file_info_get_mime_type (info)); - gnome_vfs_file_info_unref (info); - return type; - } else { - gnome_vfs_file_info_unref (info); - return NULL; - } -} - - -/** - * e_msg_composer_set_changed: - * @composer: An EMsgComposer object. - * - * Mark the composer as changed, so before the composer gets destroyed - * the user will be prompted about unsaved changes. - **/ -void -e_msg_composer_set_changed (EMsgComposer *composer) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - composer->has_changed = TRUE; -} - - -/** - * e_msg_composer_unset_changed: - * @composer: An EMsgComposer object. - * - * Mark the composer as unchanged, so no prompt about unsaved changes - * will appear before destroying the composer. - **/ -void -e_msg_composer_unset_changed (EMsgComposer *composer) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - composer->has_changed = FALSE; -} - -gboolean -e_msg_composer_is_dirty (EMsgComposer *composer) -{ - CORBA_Environment ev; - gboolean rv; - - CORBA_exception_init (&ev); - rv = composer->has_changed - || (GNOME_GtkHTML_Editor_Engine_hasUndo (composer->editor_engine, &ev) && - !GNOME_GtkHTML_Editor_Engine_runCommand (composer->editor_engine, "is-saved", &ev)); - CORBA_exception_free (&ev); - - return rv; -} - -/** - * e_msg_composer_set_autosaved: - * @composer: An EMsgComposer object. - * - * Mark the composer as autosaved, so before the composer gets destroyed - * the user will be prompted about unsaved changes. - **/ -void -e_msg_composer_set_autosaved (EMsgComposer *composer) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - composer->autosaved = TRUE; -} - - -/** - * e_msg_composer_unset_autosaved: - * @composer: An EMsgComposer object. - * - * Mark the composer as unautosaved, so no prompt about unsaved changes - * will appear before destroying the composer. - **/ -void -e_msg_composer_unset_autosaved (EMsgComposer *composer) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - composer->autosaved = FALSE; -} - -gboolean -e_msg_composer_is_autosaved (EMsgComposer *composer) -{ - g_return_val_if_fail (E_IS_MSG_COMPOSER (composer), FALSE); - - return composer->autosaved; -} - -void -e_msg_composer_set_enable_autosave (EMsgComposer *composer, gboolean enabled) -{ - g_return_if_fail (E_IS_MSG_COMPOSER (composer)); - - composer->enable_autosave = enabled; -} - -static char * -next_word (const char *s, const char **sr) -{ - if (!s || !*s) - return NULL; - else { - const char *begin; - gunichar uc; - gboolean cited; - - do { - begin = s; - cited = FALSE; - uc = g_utf8_get_char (s); - if (uc == 0) - return NULL; - s = g_utf8_next_char (s); - } while (!html_selection_spell_word (uc, &cited) && !cited && s); - - /* we are at beginning of word */ - if (s && *s) { - gboolean cited_end; - - cited_end = FALSE; - uc = g_utf8_get_char (s); - - /* go to end of word */ - while (html_selection_spell_word (uc, &cited_end) || (!cited && cited_end)) { - cited_end = FALSE; - s = g_utf8_next_char (s); - uc = g_utf8_get_char (s); - if (uc == 0) - break; - } - *sr = s; - return s ? g_strndup (begin, s - begin) : g_strdup (begin); - } else - return NULL; - } -} - - -void -e_msg_composer_ignore (EMsgComposer *composer, const char *str) -{ - CORBA_Environment ev; - char *word; - - if (!str) - return; - - CORBA_exception_init (&ev); - while ((word = next_word (str, &str))) { - /* printf ("ignore word %s\n", word); */ - GNOME_GtkHTML_Editor_Engine_ignoreWord (composer->editor_engine, word, &ev); - g_free (word); - } - CORBA_exception_free (&ev); -} - - -void -e_msg_composer_drop_editor_undo (EMsgComposer *composer) -{ - CORBA_Environment ev; - - CORBA_exception_init (&ev); - GNOME_GtkHTML_Editor_Engine_dropUndo (composer->editor_engine, &ev); - CORBA_exception_free (&ev); -} - - -gboolean -e_msg_composer_request_close_all (void) -{ - GSList *p, *pnext; - - for (p = all_composers; p != NULL; p = pnext) { - pnext = p->next; - do_exit (E_MSG_COMPOSER (p->data)); - } - - if (all_composers == NULL) - return TRUE; - else - return FALSE; -} - -void -e_msg_composer_check_autosave(GtkWindow *parent) -{ - if (am == NULL) - am = autosave_manager_new(); - - if (am->ask) { - am->ask = FALSE; - autosave_manager_query_load_orphans (am, parent); - am->ask = TRUE; - } -} diff --git a/composer/e-msg-composer.h b/composer/e-msg-composer.h deleted file mode 100644 index dcc308cac0..0000000000 --- a/composer/e-msg-composer.h +++ /dev/null @@ -1,226 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* e-msg-composer.h - * - * Copyright (C) 1999, 2000 Ximian, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * published by the Free Software Foundation; either version 2 of the - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this program; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - * - * Author: Ettore Perazzoli - */ - - -#ifndef ___E_MSG_COMPOSER_H__ -#define ___E_MSG_COMPOSER_H__ - -typedef struct _EMsgComposer EMsgComposer; -typedef struct _EMsgComposerClass EMsgComposerClass; - -#include <bonobo/bonobo-window.h> -#include <bonobo/bonobo-ui-component.h> - -#include "e-msg-composer-attachment-bar.h" -#include "e-msg-composer-hdrs.h" -#include "Editor.h" - -#include <mail/mail-config.h> - -#ifdef __cplusplus -extern "C" { -#pragma } -#endif /* __cplusplus */ - - -#define E_TYPE_MSG_COMPOSER (e_msg_composer_get_type ()) -#define E_MSG_COMPOSER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), E_TYPE_MSG_COMPOSER, EMsgComposer)) -#define E_MSG_COMPOSER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), E_TYPE_MSG_COMPOSER, EMsgComposerClass)) -#define E_IS_MSG_COMPOSER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), E_TYPE_MSG_COMPOSER)) -#define E_IS_MSG_COMPOSER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((obj), E_TYPE_MSG_COMPOSER)) - - - -struct _EMsgComposer { - BonoboWindow parent; - - /* Main UIComponent */ - BonoboUIComponent *uic; - - /* UIComponent for the non-control GtkEntries */ - BonoboUIComponent *entry_uic; - - GtkWidget *hdrs; - GPtrArray *extra_hdr_names, *extra_hdr_values; - - GtkWidget *focused_entry; - - GtkWidget *editor; - - GtkWidget *attachment_bar; - GtkWidget *attachment_scrolled_window; - - GtkWidget *address_dialog; - - Bonobo_PersistFile persist_file_interface; - Bonobo_PersistStream persist_stream_interface; - GNOME_GtkHTML_Editor_Engine editor_engine; - BonoboObject *editor_listener; - GHashTable *inline_images, *inline_images_by_url; - GList *current_images; - - char *mime_type, *mime_body, *charset; - - char *autosave_file; - int autosave_fd; - guint32 enable_autosave : 1; - - guint32 attachment_bar_visible : 1; - guint32 send_html : 1; - guint32 is_alternative : 1; - guint32 pgp_sign : 1; - guint32 pgp_encrypt : 1; - guint32 smime_sign : 1; - guint32 smime_encrypt : 1; - guint32 view_from : 1; - guint32 view_replyto : 1; - guint32 view_bcc : 1; - guint32 view_cc : 1; - guint32 view_subject : 1; - guint32 has_changed : 1; - guint32 autosaved : 1; - - guint32 mode_post : 1; - - guint32 in_signature_insert : 1; - guint32 auto_signature : 1; - - MailConfigSignature *signature; - GtkWidget *sig_omenu; - - CamelMimeMessage *redirect; - - guint notify_id; -}; - -struct _EMsgComposerClass { - BonoboWindowClass parent_class; - - void (* send) (EMsgComposer *composer); - void (* save_draft) (EMsgComposer *composer, int quit); -}; - - -GtkType e_msg_composer_get_type (void); - -EMsgComposer *e_msg_composer_new (void); -EMsgComposer *e_msg_composer_new_post (void); - -EMsgComposer *e_msg_composer_new_with_message (CamelMimeMessage *msg); -EMsgComposer *e_msg_composer_new_from_url (const char *url); -EMsgComposer *e_msg_composer_new_redirect (CamelMimeMessage *message, - const char *resent_from); - -void e_msg_composer_show_attachments (EMsgComposer *composer, - gboolean show); -void e_msg_composer_set_headers (EMsgComposer *composer, - const char *from, - EABDestination **to, - EABDestination **cc, - EABDestination **bcc, - const char *subject); -void e_msg_composer_set_body_text (EMsgComposer *composer, - const char *text); -void e_msg_composer_set_body (EMsgComposer *composer, - const char *body, - const char *mime_type); -void e_msg_composer_add_header (EMsgComposer *composer, - const char *name, - const char *value); -void e_msg_composer_attach (EMsgComposer *composer, - CamelMimePart *attachment); -CamelMimePart *e_msg_composer_add_inline_image_from_file (EMsgComposer *composer, - const char *filename); -void e_msg_composer_add_inline_image_from_mime_part (EMsgComposer *composer, - CamelMimePart *part); -CamelMimeMessage *e_msg_composer_get_message (EMsgComposer *composer, - gboolean save_html_object_data); -CamelMimeMessage *e_msg_composer_get_message_draft (EMsgComposer *composer); -void e_msg_composer_show_sig_file (EMsgComposer *composer); -gboolean e_msg_composer_get_send_html (EMsgComposer *composer); -void e_msg_composer_set_send_html (EMsgComposer *composer, - gboolean send_html); - -gboolean e_msg_composer_get_view_from (EMsgComposer *composer); -void e_msg_composer_set_view_from (EMsgComposer *composer, - gboolean view_from); -gboolean e_msg_composer_get_view_replyto (EMsgComposer *composer); -void e_msg_composer_set_view_replyto (EMsgComposer *composer, - gboolean view_replyto); -gboolean e_msg_composer_get_view_cc (EMsgComposer *composer); -void e_msg_composer_set_view_cc (EMsgComposer *composer, - gboolean view_cc); -gboolean e_msg_composer_get_view_bcc (EMsgComposer *composer); -void e_msg_composer_set_view_bcc (EMsgComposer *composer, - gboolean view_bcc); - -EABDestination **e_msg_composer_get_recipients (EMsgComposer *composer); -EABDestination **e_msg_composer_get_to (EMsgComposer *composer); -EABDestination **e_msg_composer_get_cc (EMsgComposer *composer); -EABDestination **e_msg_composer_get_bcc (EMsgComposer *composer); -const char *e_msg_composer_get_subject (EMsgComposer *composer); - -EAccount *e_msg_composer_get_preferred_account (EMsgComposer *composer); -void e_msg_composer_clear_inlined_table (EMsgComposer *composer); -char *e_msg_composer_guess_mime_type (const char *file_name); -void e_msg_composer_set_changed (EMsgComposer *composer); -void e_msg_composer_unset_changed (EMsgComposer *composer); -gboolean e_msg_composer_is_dirty (EMsgComposer *composer); -void e_msg_composer_set_autosaved (EMsgComposer *composer); -void e_msg_composer_unset_autosaved (EMsgComposer *composer); -gboolean e_msg_composer_is_autosaved (EMsgComposer *composer); -void e_msg_composer_set_enable_autosave (EMsgComposer *composer, - gboolean enabled); - -/* PGP */ -void e_msg_composer_set_pgp_sign (EMsgComposer *composer, - gboolean pgp_sign); -gboolean e_msg_composer_get_pgp_sign (EMsgComposer *composer); -void e_msg_composer_set_pgp_encrypt (EMsgComposer *composer, - gboolean pgp_encrypt); -gboolean e_msg_composer_get_pgp_encrypt (EMsgComposer *composer); - -/* S/MIME */ -void e_msg_composer_set_smime_sign (EMsgComposer *composer, - gboolean smime_sign); -gboolean e_msg_composer_get_smime_sign (EMsgComposer *composer); -void e_msg_composer_set_smime_encrypt (EMsgComposer *composer, - gboolean smime_encrypt); -gboolean e_msg_composer_get_smime_encrypt (EMsgComposer *composer); -char *e_msg_composer_get_sig_file_content (const char *sigfile, - gboolean in_html); -void e_msg_composer_add_message_attachments (EMsgComposer *composer, - CamelMimeMessage *message, - gboolean just_inlines); -void e_msg_composer_ignore (EMsgComposer *composer, - const char *str); -void e_msg_composer_drop_editor_undo (EMsgComposer *composer); - -gboolean e_msg_composer_request_close_all (void); -void e_msg_composer_check_autosave (GtkWindow *parent); - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif /* ___E_MSG_COMPOSER_H__ */ diff --git a/composer/evolution-composer.c b/composer/evolution-composer.c deleted file mode 100644 index 31da13c342..0000000000 --- a/composer/evolution-composer.c +++ /dev/null @@ -1,397 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* evolution-composer.c - * - * Copyright (C) 2000 Ximian, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * published by the Free Software Foundation; either version 2 of the - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this program; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - * - * Author: Dan Winship <danw@ximian.com> - */ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <string.h> -#include <gtk/gtksignal.h> -#include <bonobo/bonobo-item-handler.h> -#include <bonobo/bonobo-generic-factory.h> -#include <gal/util/e-util.h> -#include <gal/widgets/e-gui-utils.h> -#include <camel/camel.h> -#include "evolution-composer.h" -#include "mail/mail-config.h" - -#define PARENT_TYPE BONOBO_OBJECT_TYPE -static BonoboObjectClass *parent_class = NULL; - -struct _EvolutionComposerPrivate { - int send_id; - int save_draft_id; - - void (*send_cb) (EMsgComposer *, gpointer); - void (*save_draft_cb) (EMsgComposer *, int, gpointer); -}; - -/* CORBA interface implementation. */ -static EABDestination ** -corba_recipientlist_to_destv (const GNOME_Evolution_Composer_RecipientList *cl) -{ - GNOME_Evolution_Composer_Recipient *recip; - EABDestination **destv; - int i; - - if (cl->_length == 0) - return NULL; - - destv = g_new (EABDestination *, cl->_length+1); - - for (i = 0; i < cl->_length; ++i) { - recip = &(cl->_buffer[i]); - - destv[i] = eab_destination_new (); - - if (*recip->name) - eab_destination_set_name (destv[i], recip->name); - eab_destination_set_email (destv[i], recip->address); - - } - destv[cl->_length] = NULL; - - return destv; -} - -static void -impl_Composer_set_headers (PortableServer_Servant servant, - const CORBA_char *from, - const GNOME_Evolution_Composer_RecipientList *to, - const GNOME_Evolution_Composer_RecipientList *cc, - const GNOME_Evolution_Composer_RecipientList *bcc, - const CORBA_char *subject, - CORBA_Environment *ev) -{ - BonoboObject *bonobo_object; - EvolutionComposer *composer; - EABDestination **tov, **ccv, **bccv; - EAccountList *accounts; - EAccount *account; - EIterator *iter; - int found = 0; - - bonobo_object = bonobo_object_from_servant (servant); - composer = EVOLUTION_COMPOSER (bonobo_object); - - account = mail_config_get_account_by_name (from); - if (!account) { - accounts = mail_config_get_accounts (); - iter = e_list_get_iterator ((EList *) accounts); - while (e_iterator_is_valid (iter)) { - account = (EAccount *) e_iterator_get (iter); - - if (!strcasecmp (account->id->address, from)) { - found = TRUE; - break; - } - - e_iterator_next (iter); - } - - g_object_unref (iter); - - if (!found) - account = mail_config_get_default_account (); - } - - tov = corba_recipientlist_to_destv (to); - ccv = corba_recipientlist_to_destv (cc); - bccv = corba_recipientlist_to_destv (bcc); - - e_msg_composer_set_headers (composer->composer, account->name, - tov, ccv, bccv, subject); - - eab_destination_freev (tov); - eab_destination_freev (ccv); - eab_destination_freev (bccv); -} - -static void -impl_Composer_set_multipart_type (PortableServer_Servant servant, - GNOME_Evolution_Composer_MultipartType type, - CORBA_Environment *ev) -{ - BonoboObject *bonobo_object; - EvolutionComposer *composer; - - bonobo_object = bonobo_object_from_servant (servant); - composer = EVOLUTION_COMPOSER (bonobo_object); - - if (type == GNOME_Evolution_Composer_ALTERNATIVE) { - composer->composer->is_alternative = TRUE; - composer->composer->send_html = FALSE; - } -} - -static void -impl_Composer_set_body (PortableServer_Servant servant, - const CORBA_char *body, - const CORBA_char *mime_type, - CORBA_Environment *ev) -{ - BonoboObject *bonobo_object; - EvolutionComposer *composer; - - bonobo_object = bonobo_object_from_servant (servant); - composer = EVOLUTION_COMPOSER (bonobo_object); - - if (!strcasecmp (mime_type, "text/plain")) { - char *htmlbody = camel_text_to_html (body, CAMEL_MIME_FILTER_TOHTML_PRE, 0); - - e_msg_composer_set_body_text (composer->composer, htmlbody); - g_free (htmlbody); - } else if (!strcasecmp (mime_type, "text/html")) - e_msg_composer_set_body_text (composer->composer, body); - else - e_msg_composer_set_body (composer->composer, body, mime_type); -} - -static void -impl_Composer_attach_MIME (PortableServer_Servant servant, - const CORBA_char *data, - CORBA_Environment *ev) -{ - BonoboObject *bonobo_object; - EvolutionComposer *composer; - CamelMimePart *attachment; - CamelStream *mem_stream; - int status; - - bonobo_object = bonobo_object_from_servant (servant); - composer = EVOLUTION_COMPOSER (bonobo_object); - - mem_stream = camel_stream_mem_new_with_buffer (data, strlen (data)); - attachment = camel_mime_part_new (); - status = camel_data_wrapper_construct_from_stream ( - CAMEL_DATA_WRAPPER (attachment), mem_stream); - camel_object_unref (mem_stream); - - if (status == -1) { - CORBA_exception_set (ev, CORBA_USER_EXCEPTION, - ex_GNOME_Evolution_Composer_CouldNotParse, - NULL); - return; - } - - e_msg_composer_attach (composer->composer, attachment); - camel_object_unref (CAMEL_OBJECT (attachment)); -} - -static void -impl_Composer_attach_data (PortableServer_Servant servant, - const CORBA_char *content_type, - const CORBA_char *filename, - const CORBA_char *description, - const CORBA_boolean show_inline, - const GNOME_Evolution_Composer_AttachmentData *data, - CORBA_Environment *ev) -{ - BonoboObject *bonobo_object; - EvolutionComposer *composer; - CamelMimePart *attachment; - - bonobo_object = bonobo_object_from_servant (servant); - composer = EVOLUTION_COMPOSER (bonobo_object); - - attachment = camel_mime_part_new (); - camel_mime_part_set_content (attachment, data->_buffer, data->_length, - content_type); - - if (*filename) - camel_mime_part_set_filename (attachment, filename); - if (*description) - camel_mime_part_set_description (attachment, description); - camel_mime_part_set_disposition (attachment, show_inline ? - "inline" : "attachment"); - - e_msg_composer_attach (composer->composer, attachment); - camel_object_unref (attachment); -} - -static void -impl_Composer_show (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - BonoboObject *bonobo_object; - EvolutionComposer *composer; - - bonobo_object = bonobo_object_from_servant (servant); - composer = EVOLUTION_COMPOSER (bonobo_object); - - gtk_widget_show (GTK_WIDGET (composer->composer)); -} - -static void -impl_Composer_send (PortableServer_Servant servant, - CORBA_Environment *ev) -{ - BonoboObject *bonobo_object; - EvolutionComposer *composer; - - bonobo_object = bonobo_object_from_servant (servant); - composer = EVOLUTION_COMPOSER (bonobo_object); - - composer->priv->send_cb (composer->composer, NULL); -} - -POA_GNOME_Evolution_Composer__epv * -evolution_composer_get_epv (void) -{ - POA_GNOME_Evolution_Composer__epv *epv; - - epv = g_new0 (POA_GNOME_Evolution_Composer__epv, 1); - epv->setHeaders = impl_Composer_set_headers; - epv->setMultipartType = impl_Composer_set_multipart_type; - epv->setBody = impl_Composer_set_body; - epv->attachMIME = impl_Composer_attach_MIME; - epv->attachData = impl_Composer_attach_data; - epv->show = impl_Composer_show; - epv->send = impl_Composer_send; - - return epv; -} - - -/* GObject stuff */ - -static void -finalise (GObject *object) -{ - EvolutionComposer *composer = EVOLUTION_COMPOSER (object); - struct _EvolutionComposerPrivate *p = composer->priv; - - g_signal_handler_disconnect(composer->composer, p->send_id); - g_signal_handler_disconnect(composer->composer, p->save_draft_id); - g_free(p); - - if (composer->composer) { - g_object_unref(composer->composer); - composer->composer = NULL; - } - - G_OBJECT_CLASS (parent_class)->finalize (object); -} - -static void -evolution_composer_class_init (EvolutionComposerClass *klass) -{ - GObjectClass *object_class; - POA_GNOME_Evolution_Composer__epv *epv; - - object_class = G_OBJECT_CLASS (klass); - object_class->finalize = finalise; - - parent_class = g_type_class_ref(bonobo_object_get_type ()); - - epv = &klass->epv; - - epv->setHeaders = impl_Composer_set_headers; - epv->setMultipartType = impl_Composer_set_multipart_type; - epv->setBody = impl_Composer_set_body; - epv->attachMIME = impl_Composer_attach_MIME; - epv->attachData = impl_Composer_attach_data; - epv->show = impl_Composer_show; - epv->send = impl_Composer_send; -} - -static void -evolution_composer_init (EvolutionComposer *composer) -{ - EAccount *account; - - account = mail_config_get_default_account (); - composer->composer = e_msg_composer_new (); - composer->priv = g_malloc0(sizeof(*composer->priv)); -} - -#if 0 -static Bonobo_ItemContainer_ObjectNames * -enum_objects (BonoboItemHandler *handler, gpointer data, CORBA_Environment *ev) -{ -} -#endif - -static Bonobo_Unknown -get_object (BonoboItemHandler *h, const char *item_name, gboolean only_if_exists, - gpointer data, CORBA_Environment *ev) -{ - EvolutionComposer *composer = data; - GSList *options, *l; - - options = bonobo_item_option_parse (item_name); - for (l = options; l; l = l->next){ - BonoboItemOption *option = l->data; - - if (strcmp (option->key, "visible") == 0){ - gboolean show = 1; - - if (option->value) - show = atoi (option->value); - - if (show) - gtk_widget_show (GTK_WIDGET (composer->composer)); - else - gtk_widget_hide (GTK_WIDGET (composer->composer)); - } - } - return bonobo_object_dup_ref ( - BONOBO_OBJECT (composer)->corba_objref, ev); -} - -void -evolution_composer_construct (EvolutionComposer *composer, - GNOME_Evolution_Composer corba_object) -{ - BonoboObject *item_handler; - - g_return_if_fail (composer != NULL); - g_return_if_fail (EVOLUTION_IS_COMPOSER (composer)); - g_return_if_fail (corba_object != CORBA_OBJECT_NIL); - - /*bonobo_object_construct (BONOBO_OBJECT (composer), corba_object);*/ - - item_handler = BONOBO_OBJECT ( - bonobo_item_handler_new (NULL, get_object, composer)); - bonobo_object_add_interface (BONOBO_OBJECT (composer), BONOBO_OBJECT (item_handler)); -} - -EvolutionComposer * -evolution_composer_new (void (*send) (EMsgComposer *, gpointer), - void (*save_draft) (EMsgComposer *, int, gpointer)) -{ - EvolutionComposer *new; - struct _EvolutionComposerPrivate *p; - - new = g_object_new(EVOLUTION_TYPE_COMPOSER, NULL); - evolution_composer_construct (new, bonobo_object_corba_objref((BonoboObject *)new)); - p = new->priv; - p->send_cb = send; - p->save_draft_cb = save_draft; - p->send_id = g_signal_connect (new->composer, "send", G_CALLBACK (send), NULL); - p->save_draft_id = g_signal_connect (new->composer, "save-draft", G_CALLBACK (save_draft), NULL); - - return new; -} - -BONOBO_TYPE_FUNC_FULL(EvolutionComposer, GNOME_Evolution_Composer, BONOBO_TYPE_OBJECT, evolution_composer) diff --git a/composer/evolution-composer.h b/composer/evolution-composer.h deleted file mode 100644 index 8928801583..0000000000 --- a/composer/evolution-composer.h +++ /dev/null @@ -1,75 +0,0 @@ -/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */ -/* evolution-composer.h - * - * Copyright (C) 2000 Ximian, Inc. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of version 2 of the GNU General Public - * published by the Free Software Foundation; either version 2 of the - * License as published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public - * License along with this program; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place - Suite 330, - * Boston, MA 02111-1307, USA. - * - * Author: Dan Winship - */ - -#ifndef __EVOLUTION_COMPOSER_H__ -#define __EVOLUTION_COMPOSER_H__ - -#include <bonobo/bonobo-object.h> - -#include "Composer.h" -#include "e-msg-composer.h" - -#ifdef __cplusplus -extern "C" { -#pragma } -#endif /* __cplusplus */ - -#define EVOLUTION_TYPE_COMPOSER (evolution_composer_get_type ()) -#define EVOLUTION_COMPOSER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), EVOLUTION_TYPE_COMPOSER, EvolutionComposer)) -#define EVOLUTION_COMPOSER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), EVOLUTION_TYPE_COMPOSER, EvolutionComposerClass)) -#define EVOLUTION_IS_COMPOSER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), EVOLUTION_TYPE_COMPOSER)) -#define EVOLUTION_IS_COMPOSER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((obj), EVOLUTION_TYPE_COMPOSER)) - -typedef struct _EvolutionComposer EvolutionComposer; -typedef struct _EvolutionComposerClass EvolutionComposerClass; - -struct _EvolutionComposer { - BonoboObject parent; - - struct _EvolutionComposerPrivate *priv; - - EMsgComposer *composer; -}; - -struct _EvolutionComposerClass { - BonoboObjectClass parent_class; - - POA_GNOME_Evolution_Composer__epv epv; -}; - -POA_GNOME_Evolution_Composer__epv *evolution_composer_get_epv (void); - -GtkType evolution_composer_get_type (void); -void evolution_composer_construct (EvolutionComposer *, - GNOME_Evolution_Composer); -EvolutionComposer *evolution_composer_new (void (*send_cb) (EMsgComposer *, gpointer), - void (*save_draft_cb) (EMsgComposer *, int, gpointer)); - -void evolution_composer_factory_init (void (*send) (EMsgComposer *, gpointer), - void (*save_draft) (EMsgComposer *, int, gpointer)); - -#ifdef __cplusplus -} -#endif /* __cplusplus */ - -#endif /* __EVOLUTION_COMPOSER_H__ */ diff --git a/composer/listener.c b/composer/listener.c deleted file mode 100644 index 0d0dc2f652..0000000000 --- a/composer/listener.c +++ /dev/null @@ -1,275 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* This file is part of gnome-spell bonobo component - - Copyright (C) 2000 Ximian, Inc. - Authors: Radek Doulik <rodo@ximian.com> - - This program is free software; you can redistribute it and/or - modify it under the terms of version 2 of the GNU General Public - License as published by the Free Software Foundation. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public - License along with this program; if not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ - -#ifdef HAVE_CONFIG_H -#include <config.h> -#endif - -#include <string.h> -#include <bonobo/bonobo-arg.h> -#include <bonobo/bonobo-object.h> -#include <bonobo/bonobo-stream-client.h> - -#include "listener.h" - -static BonoboObjectClass *listener_parent_class; -static POA_GNOME_GtkHTML_Editor_Listener__vepv listener_vepv; - -inline static EditorListener * -listener_from_servant (PortableServer_Servant servant) -{ - return EDITOR_LISTENER (bonobo_object_from_servant (servant)); -} - -static CORBA_any * -get_any_null () -{ - CORBA_any *rv; - - rv = CORBA_any__alloc (); - rv->_type = TC_null; - - return rv; -} - -static gchar * -resolve_image_url (EditorListener *l, gchar *url) -{ - CamelMimePart *part; - const char *cid; - - part = g_hash_table_lookup (l->composer->inline_images_by_url, url); - if (!part && !strncmp (url, "file:", 5)) { - part = e_msg_composer_add_inline_image_from_file (l->composer, - url + 5); - } - if (!part && !strncmp (url, "cid:", 4)) { - part = g_hash_table_lookup (l->composer->inline_images, url); - } - if (!part) - return NULL; - - l->composer->current_images = g_list_prepend (l->composer->current_images, part); - - cid = camel_mime_part_get_content_id (part); - if (!cid) - return NULL; - - return g_strconcat ("cid:", cid, NULL); -} - -static void -reply_indent (EditorListener *l, CORBA_Environment * ev) -{ - if (!GNOME_GtkHTML_Editor_Engine_isParagraphEmpty (l->composer->editor_engine, ev)) { - if (GNOME_GtkHTML_Editor_Engine_isPreviousParagraphEmpty (l->composer->editor_engine, ev)) - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "cursor-backward", ev); - else { - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "text-default-color", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "italic-off", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "insert-paragraph", ev); - return; - } - } - - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "style-normal", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "indent-zero", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "text-default-color", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "italic-off", ev); -} - -static void -clear_signature (GNOME_GtkHTML_Editor_Engine e, CORBA_Environment * ev) -{ - if (GNOME_GtkHTML_Editor_Engine_isParagraphEmpty (e, ev)) - GNOME_GtkHTML_Editor_Engine_setParagraphData (e, "signature", "0", ev); - else if (GNOME_GtkHTML_Editor_Engine_isPreviousParagraphEmpty (e, ev) - && GNOME_GtkHTML_Editor_Engine_runCommand (e, "cursor-backward", ev)) { - GNOME_GtkHTML_Editor_Engine_setParagraphData (e, "signature", "0", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (e, "cursor-forward", ev); - } - GNOME_GtkHTML_Editor_Engine_runCommand (e, "text-default-color", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (e, "italic-off", ev); -} - -static void -insert_paragraph_before (EditorListener *l, CORBA_Environment * ev) -{ - if (!l->composer->in_signature_insert) { - CORBA_char *orig, *signature; - gboolean changed = FALSE; - /* FIXME check for insert-paragraph command */ - - orig = GNOME_GtkHTML_Editor_Engine_getParagraphData (l->composer->editor_engine, "orig", ev); - if (ev->_major == CORBA_NO_EXCEPTION) { - if (orig && *orig == '1') { - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "text-default-color", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "italic-off", ev); - changed = TRUE; - } - CORBA_free (orig); - } - if (!changed) { - signature = GNOME_GtkHTML_Editor_Engine_getParagraphData (l->composer->editor_engine, "signature", ev); - if (ev->_major == CORBA_NO_EXCEPTION) { - if (signature && *signature == '1') { - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "text-default-color", - ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "italic-off", ev); - } - CORBA_free (signature); - } - } - } -} - -static void -insert_paragraph_after (EditorListener *l, CORBA_Environment * ev) -{ - if (!l->composer->in_signature_insert) { - CORBA_char *orig, *signature; - /* FIXME check for insert-paragraph command */ - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "text-default-color", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "italic-off", ev); - - orig = GNOME_GtkHTML_Editor_Engine_getParagraphData (l->composer->editor_engine, "orig", ev); - if (ev->_major == CORBA_NO_EXCEPTION) { - if (orig && *orig == '1') - reply_indent (l, ev); - GNOME_GtkHTML_Editor_Engine_setParagraphData (l->composer->editor_engine, "orig", "0", ev); - CORBA_free (orig); - } - signature = GNOME_GtkHTML_Editor_Engine_getParagraphData (l->composer->editor_engine, "signature", ev); - if (ev->_major == CORBA_NO_EXCEPTION) { - if (signature && *signature == '1') - clear_signature (l->composer->editor_engine, ev); - CORBA_free (signature); - } - } -} - -static CORBA_any * -impl_event (PortableServer_Servant _servant, - const CORBA_char * name, const CORBA_any * arg, - CORBA_Environment * ev) -{ - EditorListener *l = listener_from_servant (_servant); - CORBA_any *rv = NULL; - gchar *command; - - if (!strcmp (name, "command_before")) { - command = BONOBO_ARG_GET_STRING (arg); - if (!strcmp (command, "insert-paragraph")) { - insert_paragraph_before (l, ev); - } - } else if (!strcmp (name, "command_after")) { - command = BONOBO_ARG_GET_STRING (arg); - if (!strcmp (command, "insert-paragraph")) { - insert_paragraph_after (l, ev); - } - } else if (!strcmp (name, "image_url")) { - gchar *url; - - if ((url = resolve_image_url (l, BONOBO_ARG_GET_STRING (arg)))) { - rv = bonobo_arg_new (BONOBO_ARG_STRING); - BONOBO_ARG_SET_STRING (rv, url); - /* printf ("new url: %s\n", url); */ - g_free (url); - } - } else if (!strcmp (name, "delete")) { - CORBA_char *orig; - - if (GNOME_GtkHTML_Editor_Engine_isParagraphEmpty (l->composer->editor_engine, ev)) { - orig = GNOME_GtkHTML_Editor_Engine_getParagraphData (l->composer->editor_engine, "orig", ev); - if (ev->_major == CORBA_NO_EXCEPTION) { - if (orig && *orig == '1') { - GNOME_GtkHTML_Editor_Engine_setParagraphData (l->composer->editor_engine, "orig", "0", ev); - - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "indent-zero", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "style-normal", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "text-default-color", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "italic-off", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "insert-paragraph", ev); - GNOME_GtkHTML_Editor_Engine_runCommand (l->composer->editor_engine, "delete-back", ev); - } - CORBA_free (orig); - } - } - } else if (!strcmp (name, "url_requested")) { - GNOME_GtkHTML_Editor_URLRequestEvent *e; - CamelMimePart *part; - GByteArray *ba; - CamelStream *cstream; - CamelDataWrapper *wrapper; - - e = (GNOME_GtkHTML_Editor_URLRequestEvent *)arg->_value; - - if (!e->url || e->stream == CORBA_OBJECT_NIL) - return get_any_null (); - - part = g_hash_table_lookup (l->composer->inline_images_by_url, e->url); - if (!part) - part = g_hash_table_lookup (l->composer->inline_images, e->url); - if (!part) - return get_any_null (); - - /* Write the data to a CamelStreamMem... */ - ba = g_byte_array_new (); - cstream = camel_stream_mem_new_with_byte_array (ba); - wrapper = camel_medium_get_content_object (CAMEL_MEDIUM (part)); - camel_data_wrapper_decode_to_stream (wrapper, cstream); - - bonobo_stream_client_write (e->stream, ba->data, ba->len, ev); - - camel_object_unref (cstream); - } - - return rv ? rv : get_any_null (); -} - -static void -listener_class_init (EditorListenerClass *klass) -{ - POA_GNOME_GtkHTML_Editor_Listener__epv *epv; - - listener_parent_class = g_type_class_ref(bonobo_object_get_type ()); - - epv = &klass->epv; - epv->event = impl_event; -} - -static void -listener_init(EditorListener *object) -{ -} - -BONOBO_TYPE_FUNC_FULL(EditorListener, GNOME_GtkHTML_Editor_Listener, BONOBO_TYPE_OBJECT, listener); - -EditorListener * -listener_new (EMsgComposer *composer) -{ - EditorListener *listener; - - listener = g_object_new (EDITOR_LISTENER_TYPE, NULL); - listener->composer = composer; - - return listener; -} diff --git a/composer/listener.h b/composer/listener.h deleted file mode 100644 index d238583453..0000000000 --- a/composer/listener.h +++ /dev/null @@ -1,51 +0,0 @@ -/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */ -/* This file is part of gnome-spell bonobo component - - Copyright (C) 2000 Ximian, Inc. - Authors: Radek Doulik <rodo@ximian.com> - - This program is free software; you can redistribute it and/or - modify it under the terms of version 2 of the GNU General Public - License as published by the Free Software Foundation. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU General Public - License along with this program; if not, write to the - Free Software Foundation, Inc., 59 Temple Place - Suite 330, - Boston, MA 02111-1307, USA. -*/ - -#ifndef LISTENER_H_ -#define LISTENER_H_ - -#include <bonobo/bonobo-object.h> -#include "Editor.h" -#include "e-msg-composer.h" - -#define EDITOR_LISTENER_TYPE (listener_get_type ()) -#define EDITOR_LISTENER(o) (G_TYPE_CHECK_INSTANCE_CAST ((o), EDITOR_LISTENER_TYPE, EditorListener)) -#define EDITOR_LISTENER_CLASS(k) (G_TYPE_CHECK_CLASS_CAST ((k), EDITOR_LISTENER_TYPE, EditorListenerClass)) -#define IS_EDITOR_LISTENER(o) (G_TYPE_CHECK_INSTANCE_TYPE ((o), EDITOR_LISTENER_TYPE)) -#define IS_EDITOR_LISTENER_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE ((k), EDITOR_LISTENER_TYPE)) - -typedef struct { - BonoboObject parent; - EMsgComposer *composer; -} EditorListener; - -typedef struct { - BonoboObjectClass parent_class; - - POA_GNOME_GtkHTML_Editor_Listener__epv epv; -} EditorListenerClass; - -GtkType listener_get_type (void); -EditorListener *listener_construct (EditorListener *listener, - GNOME_GtkHTML_Editor_Listener corba_listener); -EditorListener *listener_new (EMsgComposer *composer); - -#endif /* LISTENER_H_ */ |