diff options
author | Matthew Barnes <mbarnes@src.gnome.org> | 2008-11-24 13:14:44 +0800 |
---|---|---|
committer | Matthew Barnes <mbarnes@src.gnome.org> | 2008-11-24 13:14:44 +0800 |
commit | 4f4615a46d5ba518c1e6a0c2412b1edf1e268d99 (patch) | |
tree | 828acaa7b76aa12a490a3238b0ec4a7086b8be16 /mail | |
parent | 076b7c45131482b87d18963d34d035435491ee8d (diff) | |
download | gsoc2013-evolution-4f4615a46d5ba518c1e6a0c2412b1edf1e268d99.tar gsoc2013-evolution-4f4615a46d5ba518c1e6a0c2412b1edf1e268d99.tar.gz gsoc2013-evolution-4f4615a46d5ba518c1e6a0c2412b1edf1e268d99.tar.bz2 gsoc2013-evolution-4f4615a46d5ba518c1e6a0c2412b1edf1e268d99.tar.lz gsoc2013-evolution-4f4615a46d5ba518c1e6a0c2412b1edf1e268d99.tar.xz gsoc2013-evolution-4f4615a46d5ba518c1e6a0c2412b1edf1e268d99.tar.zst gsoc2013-evolution-4f4615a46d5ba518c1e6a0c2412b1edf1e268d99.zip |
Merge revisions 36737:36810 from trunk.
svn path=/branches/kill-bonobo/; revision=36811
Diffstat (limited to 'mail')
-rw-r--r-- | mail/ChangeLog | 64 | ||||
-rw-r--r-- | mail/em-composer-prefs.c | 56 | ||||
-rw-r--r-- | mail/em-folder-view.c | 4 | ||||
-rw-r--r-- | mail/em-format-html.c | 27 | ||||
-rw-r--r-- | mail/evolution-mail.schemas.in | 18 | ||||
-rw-r--r-- | mail/filtertypes.xml | 104 | ||||
-rw-r--r-- | mail/mail-config.c | 75 | ||||
-rw-r--r-- | mail/mail-config.glade | 19 | ||||
-rw-r--r-- | mail/mail-vfolder.c | 5 | ||||
-rw-r--r-- | mail/vfoldertypes.xml | 83 |
10 files changed, 370 insertions, 85 deletions
diff --git a/mail/ChangeLog b/mail/ChangeLog index 76ed190ad0..2f615c2a1c 100644 --- a/mail/ChangeLog +++ b/mail/ChangeLog @@ -1,3 +1,67 @@ +2008-11-23 Matthew Barnes <mbarnes@redhat.com> + + ** Fixes part of bug #552850 + + * evolution-mail.schemas.in: + Prefer the term "side bar" over "folder tree". + +2008-11-19 Srinivasa Ragavan <sragavan@novell.com> + + ** Fix for bug #555276 + + * mail/mail-vfolder.c: Don't load vfolder as subfolder. + +2008-11-13 Bharath Acharya <abharath@novell.com> + + * em-folder-view.c: (emfv_setting_notify): + * em-format-html.c: (efh_format_headers): Do not display the default + headers when all the headers are disabled in Mail preferences. + +2008-11-12 Milan Crha <mcrha@redhat.com> + + ** Part of fix for bug #524377 + + * mail-config.glade: + * evolution-mail.schemas.in: + * em-composer-prefs.c: (em_composer_prefs_construct): + * mail-config.c: (gconf_outlook_filenames_changed), (mail_config_init): + Declare, be able to change and listen to changes on new key, + '/apps/evolution/mail/composer/outlook_filenames' to encode file names + header in camel based on the RFC 2047, instead of the correct RFC 2231. + +2008-11-07 Matthew Barnes <mbarnes@redhat.com> + + ** Fix for bug #552583 + + * mail-config.c: (mail_config_get_account_by_source_url): + Instead of preserving the authmech attribute in the two URLs + being compared, strip the attributes out of both URLs and just do + a simple string comparison. We're just trying to match a URL to + an account here. The authentication method shouldn't be relevant. + +2008-11-07 Bharath Acharya <abharath@novell.com> + + ** Fix for BNC bug #437226 + + * em-format-html.c (efh_format_headers): Regression caused by r35319. + Check for the condition only after the while loop. + +2008-11-05 Matthew Barnes <mbarnes@redhat.com> + + ** Fixes part of bug #559371 + + * em-composer-prefs.c (spell_language_save), (spell_setup): + Simplify the logic by using e_load_spell_languages() and + e_save_spell_languages(). + +2008-11-04 Milan Crha <mcrha@redhat.com> + + ** Fix for bug #386036 + + * vfoldertypes.xml: + * filtertypes.xml: Added new option "Sender or Recipients" which + filters on From/To/Cc/Bcc headers. + 2008-11-02 Matthew Barnes <mbarnes@redhat.com> ** Fixes part of bug #559042 diff --git a/mail/em-composer-prefs.c b/mail/em-composer-prefs.c index 75a6781759..0b19cc24bf 100644 --- a/mail/em-composer-prefs.c +++ b/mail/em-composer-prefs.c @@ -584,46 +584,41 @@ spell_language_toggled_cb (GtkCellRendererToggle *renderer, static void spell_language_save (EMComposerPrefs *prefs) { - GSList *list = NULL; - GConfClient *client; + GList *spell_languages = NULL; GtkTreeModel *model; GtkTreeIter iter; - const gchar *key; gboolean valid; model = prefs->language_model; - /* Build a list of active languages. */ + /* Build a list of active spell languages. */ valid = gtk_tree_model_get_iter_first (model, &iter); while (valid) { const GtkhtmlSpellLanguage *language; - const gchar *code; gboolean active; gtk_tree_model_get ( model, &iter, 0, &active, 2, &language, -1); - code = gtkhtml_spell_language_get_code (language); if (active) - list = g_slist_prepend (list, (gpointer) code); + spell_languages = g_list_prepend ( + spell_languages, (gpointer) language); valid = gtk_tree_model_iter_next (model, &iter); } - list = g_slist_reverse (list); + spell_languages = g_list_reverse (spell_languages); /* Update the GConf value. */ - client = mail_config_get_gconf_client (); - key = "/apps/evolution/mail/composer/spell_languages"; - gconf_client_set_list (client, key, GCONF_VALUE_STRING, list, NULL); + e_save_spell_languages (spell_languages); - g_slist_free (list); + g_list_free (spell_languages); } static void spell_setup (EMComposerPrefs *prefs) { const GList *available_languages; - GSList *active_languages, *iter; + GList *active_languages; GConfClient *client; GtkListStore *store; GdkColor color; @@ -634,27 +629,7 @@ spell_setup (EMComposerPrefs *prefs) store = GTK_LIST_STORE (prefs->language_model); available_languages = gtkhtml_spell_language_get_available (); - /* Retrieve a list of language codes from GConf. */ - key = "/apps/evolution/mail/composer/spell_languages"; - active_languages = gconf_client_get_list ( - client, key, GCONF_VALUE_STRING, NULL); - - /* Convert the list to GtkhtmlSpellLanguages. */ - for (iter = active_languages; iter != NULL; iter = iter->next) { - gchar *code = iter->data; - - iter->data = (gpointer) gtkhtml_spell_language_lookup (code); - g_free (code); - } - - /* Make sure we have _something_ active. */ - if (active_languages == NULL) { - const GtkhtmlSpellLanguage *default_language; - - default_language = gtkhtml_spell_language_lookup (NULL); - active_languages = g_slist_prepend ( - active_languages, (gpointer) default_language); - } + active_languages = e_load_spell_languages (); /* Populate the GtkListStore. */ while (available_languages != NULL) { @@ -665,7 +640,7 @@ spell_setup (EMComposerPrefs *prefs) language = available_languages->data; name = gtkhtml_spell_language_get_name (language); - active = (g_slist_find (active_languages, language) != NULL); + active = (g_list_find (active_languages, language) != NULL); gtk_list_store_append (store, &tree_iter); @@ -676,10 +651,7 @@ spell_setup (EMComposerPrefs *prefs) available_languages = available_languages->next; } - /* Update the GConf list in case we used a default language. */ - spell_language_save (prefs); - - g_slist_free (active_languages); + g_list_free (active_languages); key = "/apps/evolution/mail/composer/spell_color"; string = gconf_client_get_string (client, key, NULL); @@ -945,6 +917,12 @@ em_composer_prefs_construct (EMComposerPrefs *prefs) gtk_widget_set_sensitive (widget, FALSE); gconf_bridge_bind_property (bridge, key, G_OBJECT (widget), "active"); + key = "/apps/evolution/mail/composer/outlook_filenames"; + widget = glade_xml_get_widget (gui, "chkOutlookFilenames"); + if (!gconf_client_key_is_writable (client, key, NULL)) + gtk_widget_set_sensitive (widget, FALSE); + gconf_bridge_bind_property (bridge, key, G_OBJECT (widget), "active"); + key = "/apps/evolution/mail/composer/top_signature"; widget = glade_xml_get_widget (gui, "chkTopSignature"); if (!gconf_client_key_is_writable (client, key, NULL)) diff --git a/mail/em-folder-view.c b/mail/em-folder-view.c index 77c74125d6..6dfe8735d6 100644 --- a/mail/em-folder-view.c +++ b/mail/em-folder-view.c @@ -2901,7 +2901,6 @@ emfv_setting_notify(GConfClient *gconf, guint cnxn_id, GConfEntry *entry, EMFold case EMFV_HEADERS: { GSList *header_config_list, *p; EMFormat *emf = (EMFormat *)emfv->preview; - int added_headers = 0; header_config_list = gconf_client_get_list(gconf, "/apps/evolution/mail/display/headers", GCONF_VALUE_STRING, NULL); em_format_clear_headers((EMFormat *)emfv->preview); @@ -2913,15 +2912,12 @@ emfv_setting_notify(GConfClient *gconf, guint cnxn_id, GConfEntry *entry, EMFold h = em_mailer_prefs_header_from_xml(xml); if (h && h->enabled) { em_format_add_header(emf, h->name, EM_FORMAT_HEADER_BOLD); - added_headers++; } em_mailer_prefs_header_free(h); p = g_slist_next(p); } g_slist_foreach(header_config_list, (GFunc) g_free, NULL); g_slist_free(header_config_list); - if (added_headers == 0) - em_format_default_headers(emf); /* force a redraw */ if (emf->message) em_format_redraw(emf); diff --git a/mail/em-format-html.c b/mail/em-format-html.c index 3ad759bfef..8aed5e814c 100644 --- a/mail/em-format-html.c +++ b/mail/em-format-html.c @@ -1891,22 +1891,23 @@ efh_format_headers(EMFormatHTML *efh, CamelStream *stream, CamelMedium *part) g_free(name); } else if (!g_ascii_strcasecmp (header->name, "X-Evolution-Mail-From-Delegate")) { mail_from_delegate = TRUE; - } else if (header_sender && header_from && mail_from_delegate) { - camel_stream_printf(stream, "<tr><td><table border=1 width=\"100%%\" cellspacing=2 cellpadding=2><tr>"); - if(gtk_widget_get_default_direction () == GTK_TEXT_DIR_RTL) - camel_stream_printf (stream, "<td align=\"right\" width=\"100%%\">"); - else - camel_stream_printf (stream, "<td align=\"left\" width=\"100%%\">"); - /* To translators: This message suggests to the receipients that the sender of the mail is - different from the one listed in From field. - */ - camel_stream_printf(stream, _("This message was sent by <b>%s</b> on behalf of <b>%s</b>"), header_sender, header_from); - camel_stream_printf(stream, "</td></tr></table></td></tr>"); - break; } header = header->next; } + + if (header_sender && header_from && mail_from_delegate) { + camel_stream_printf(stream, "<tr><td><table border=1 width=\"100%%\" cellspacing=2 cellpadding=2><tr>"); + if(gtk_widget_get_default_direction () == GTK_TEXT_DIR_RTL) + camel_stream_printf (stream, "<td align=\"right\" width=\"100%%\">"); + else + camel_stream_printf (stream, "<td align=\"left\" width=\"100%%\">"); + /* To translators: This message suggests to the receipients that the sender of the mail is + different from the one listed in From field. + */ + camel_stream_printf(stream, _("This message was sent by <b>%s</b> on behalf of <b>%s</b>"), header_sender, header_from); + camel_stream_printf(stream, "</td></tr></table></td></tr>"); + } g_free (header_sender); g_free (header_from); @@ -1918,7 +1919,7 @@ efh_format_headers(EMFormatHTML *efh, CamelStream *stream, CamelMedium *part) /* dump selected headers */ h = (EMFormatHeader *)emf->header_list.head; - if (h->next == NULL || emf->mode == EM_FORMAT_ALLHEADERS) { + if (emf->mode == EM_FORMAT_ALLHEADERS) { header = ((CamelMimePart *)part)->headers; while (header) { efh_format_header(emf, stream, part, header, EM_FORMAT_HTML_HEADER_NOCOLUMNS, charset); diff --git a/mail/evolution-mail.schemas.in b/mail/evolution-mail.schemas.in index 5e328b5457..fbebba87cb 100644 --- a/mail/evolution-mail.schemas.in +++ b/mail/evolution-mail.schemas.in @@ -186,6 +186,20 @@ </schema> <schema> + <key>/schemas/apps/evolution/mail/composer/outlook_filenames</key> + <applyto>/apps/evolution/mail/composer/outlook_filenames</applyto> + <owner>evolution-mail</owner> + <type>bool</type> + <default>false</default> + <locale name="C"> + <short>Encode file names in an Outlook/GMail way</short> + <long> + Encode file names in the mail headers same as Outlook or GMail does, to let them understand localized file names sent by Evolution, because they do not follow the RFC 2231, but uses incorrect RFC 2047 standard. + </long> + </locale> + </schema> + + <schema> <key>/schemas/apps/evolution/mail/composer/width</key> <applyto>/apps/evolution/mail/composer/width</applyto> <owner>evolution-mail</owner> @@ -232,9 +246,9 @@ <type>bool</type> <default>false</default> <locale name="C"> - <short>Disable or enable ellipsizing of folder names in folder tree</short> + <short>Disable or enable ellipsizing of folder names in side bar</short> <long> - Whether disable ellipsizing feature of folder names in folder tree. + Whether disable ellipsizing feature of folder names in side bar. </long> </locale> </schema> diff --git a/mail/filtertypes.xml b/mail/filtertypes.xml index 74029112d1..60702f2b08 100644 --- a/mail/filtertypes.xml +++ b/mail/filtertypes.xml @@ -283,7 +283,109 @@ </input> <input type="address" name="recipient"/> </part> - + + <part name="senderto"> + <title>Sender or Recipients</title> + <input type="optionlist" name="recipient-type"> + <option value="contains"> + <title>contains</title> + <code> + (match-all (or (header-contains "From" ${recipient}) + (header-contains "To" ${recipient}) + (header-contains "Cc" ${recipient}) + (header-contains "Bcc" ${recipient}))) + </code> + </option> + <option value="not contains"> + <title>does not contain</title> + <code> + (match-all (not (or + (header-contains "From" ${recipient}) + (header-contains "To" ${recipient}) + (header-contains "Cc" ${recipient}) + (header-contains "Bcc" ${recipient})))) + </code> + </option> + <option value="is"> + <title>is</title> + <code> + (match-all (or (header-matches "From" ${recipient}) + (header-matches "To" ${recipient}) + (header-matches "Cc" ${recipient}) + (header-matches "Bcc" ${recipient}))) + </code> + </option> + <option value="is not"> + <title>is not</title> + <code> + (match-all (not (or + (header-matches "From" ${recipient}) + (header-matches "To" ${recipient}) + (header-matches "Cc" ${recipient}) + (header-matches "Bcc" ${recipient})))) + </code> + </option> + <option value="starts with"> + <title>starts with</title> + <code> + (match-all (or (header-starts-with "From" ${recipient}) + (header-starts-with "To" ${recipient}) + (header-starts-with "Cc" ${recipient}) + (header-starts-with "Bcc" ${recipient}))) + </code> + </option> + <option value="not starts with"> + <title>does not start with</title> + <code> + (match-all (not (or + (header-starts-with "From" ${recipient}) + (header-starts-with "To" ${recipient}) + (header-starts-with "Cc" ${recipient}) + (header-starts-with "Bcc" ${recipient})))) + </code> + </option> + <option value="ends with"> + <title>ends with</title> + <code> + (match-all (or (header-ends-with "From" ${recipient}) + (header-ends-with "To" ${recipient}) + (header-ends-with "Cc" ${recipient}) + (header-ends-with "Bcc" ${recipient}))) + </code> + </option> + <option value="not ends with"> + <title>does not end with</title> + <code> + (match-all (not (or + (header-ends-with "From" ${recipient}) + (header-ends-with "To" ${recipient}) + (header-ends-with "Cc" ${recipient}) + (header-ends-with "Bcc" ${recipient})))) + </code> + </option> + <option value="matches soundex"> + <title>sounds like</title> + <code> + (match-all (or (header-soundex "From" ${recipient}) + (header-soundex "To" ${recipient}) + (header-soundex "Cc" ${recipient}) + (header-soundex "Bcc" ${recipient}))) + </code> + </option> + <option value="not match soundex"> + <title>does not sound like</title> + <code> + (match-all (not (or + (header-soundex "From" ${recipient}) + (header-soundex "To" ${recipient}) + (header-soundex "Cc" ${recipient}) + (header-soundex "Bcc" ${recipient})))) + </code> + </option> + </input> + <input type="address" name="recipient"/> + </part> + <part name="subject"> <title>Subject</title> <input type="optionlist" name="subject-type"> diff --git a/mail/mail-config.c b/mail/mail-config.c index 4ae2b0f885..8993e3b915 100644 --- a/mail/mail-config.c +++ b/mail/mail-config.c @@ -249,6 +249,22 @@ gconf_style_changed (GConfClient *client, guint cnxn_id, } static void +gconf_outlook_filenames_changed (GConfClient *client, guint cnxn_id, + GConfEntry *entry, gpointer user_data) +{ + extern int camel_header_param_encode_filenames_in_rfc_2047; + + g_return_if_fail (client != NULL); + + /* pass option to the camel */ + if (gconf_client_get_bool (client, "/apps/evolution/mail/composer/outlook_filenames", NULL)) { + camel_header_param_encode_filenames_in_rfc_2047 = 1; + } else { + camel_header_param_encode_filenames_in_rfc_2047 = 0; + } +} + +static void gconf_jh_check_changed (GConfClient *client, guint cnxn_id, GConfEntry *entry, gpointer user_data) { @@ -370,6 +386,12 @@ mail_config_init (void) gconf_client_notify_add ( config->gconf, key, func, NULL, NULL, NULL); + key = "/apps/evolution/mail/composer/outlook_filenames"; + func = (GConfClientNotifyFunc) gconf_outlook_filenames_changed; + gconf_outlook_filenames_changed (config->gconf, 0, NULL, NULL); + gconf_client_notify_add ( + config->gconf, key, func, NULL, NULL, NULL); + /* Display Configuration */ gconf_client_add_dir ( @@ -782,48 +804,49 @@ mail_config_get_account_by_uid (const char *uid) EAccount * mail_config_get_account_by_source_url (const char *source_url) { - CamelProvider *provider; - EAccount *account; - CamelURL *source; + EAccount *account = NULL; EIterator *iter; g_return_val_if_fail (source_url != NULL, NULL); - provider = camel_provider_get(source_url, NULL); - if (!provider) - return NULL; - - source = camel_url_new (source_url, NULL); - if (!source) - return NULL; - iter = e_list_get_iterator ((EList *) config->accounts); while (e_iterator_is_valid (iter)) { + CamelURL *url; + gchar *string; + account = (EAccount *) e_iterator_get (iter); - if (account->source && account->source->url && account->source->url[0]) { - CamelURL *url; + e_iterator_next (iter); + + if (account->source == NULL) + continue; - url = camel_url_new (account->source->url, NULL); - if (url && provider->url_equal (url, source)) { - camel_url_free (url); - camel_url_free (source); - g_object_unref (iter); + else if (account->source->url == NULL) + continue; - return account; - } + else if (*account->source->url == '\0') + continue; - if (url) - camel_url_free (url); - } + url = camel_url_new (account->source->url, NULL); + if (url == NULL) + continue; - e_iterator_next (iter); + /* Simplify the account URL for comparison. */ + string = camel_url_to_string (url, CAMEL_URL_HIDE_ALL); + if (string == NULL || strcmp (string, source_url) != 0) + account = NULL; /* not a match */ + + camel_url_free (url); + g_free (string); + + if (account != NULL) { + g_object_unref (iter); + return account; + } } g_object_unref (iter); - camel_url_free (source); - return NULL; } diff --git a/mail/mail-config.glade b/mail/mail-config.glade index 69a9016535..6c3dc7937a 100644 --- a/mail/mail-config.glade +++ b/mail/mail-config.glade @@ -7124,6 +7124,25 @@ For example: "Work" or "Personal"</property> </child> <child> + <widget class="GtkCheckButton" id="chkOutlookFilenames"> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="label" translatable="yes">Encode file names in an Outlook/GMail way</property> + <property name="use_underline">True</property> + <property name="relief">GTK_RELIEF_NORMAL</property> + <property name="focus_on_click">True</property> + <property name="active">False</property> + <property name="inconsistent">False</property> + <property name="draw_indicator">True</property> + </widget> + <packing> + <property name="padding">0</property> + <property name="expand">False</property> + <property name="fill">False</property> + </packing> + </child> + + <child> <widget class="GtkTable" id="tableForwardsReplies"> <property name="visible">True</property> <property name="n_rows">3</property> diff --git a/mail/mail-vfolder.c b/mail/mail-vfolder.c index 3dadf3d37f..4498817afa 100644 --- a/mail/mail-vfolder.c +++ b/mail/mail-vfolder.c @@ -267,6 +267,11 @@ vfolder_adduri_exec (struct _adduri_msg *m) g_warning("Folder '%s' disappeared while I was adding/remove it to/from my vfolder", m->uri); return; } + if (strncmp(m->uri, "vfolder:/", 9) == 0 || + strncmp(m->uri, "email://vfolder@local", 21) == 0) { + printf("Ignoring loading vfolder as a subfolder \n"); + return; + } if (folder == NULL) folder = mail_tool_uri_to_folder (m->uri, 0, &m->base.ex); diff --git a/mail/vfoldertypes.xml b/mail/vfoldertypes.xml index 2ccb552cb5..f7b4b7d8cd 100644 --- a/mail/vfoldertypes.xml +++ b/mail/vfoldertypes.xml @@ -115,6 +115,89 @@ <input type="address" name="recipient"/> </part> + <part name="senderto"> + <title>Sender or Recipients</title> + <input type="optionlist" name="recipient-type"> + <option value="contains"> + <title>contains</title> + <code> + (match-all (or (header-contains "From" ${recipient}) + (header-contains "To" ${recipient}) + (header-contains "Cc" ${recipient}) + (header-contains "Bcc" ${recipient}))) + </code> + </option> + <option value="not contains"> + <title>does not contain</title> + <code> + (match-all (not (or + (header-contains "From" ${recipient}) + (header-contains "To" ${recipient}) + (header-contains "Cc" ${recipient}) + (header-contains "Bcc" ${recipient})))) + </code> + </option> + <option value="is"> + <title>is</title> + <code> + (match-all (or (header-matches "From" ${recipient}) + (header-matches "To" ${recipient}) + (header-matches "Cc" ${recipient}) + (header-matches "Bcc" ${recipient}))) + </code> + </option> + <option value="is not"> + <title>is not</title> + <code> + (match-all (not (or + (header-matches "From" ${recipient}) + (header-matches "To" ${recipient}) + (header-matches "Cc" ${recipient}) + (header-matches "Bcc" ${recipient})))) + </code> + </option> + <option value="starts with"> + <title>starts with</title> + <code> + (match-all (or (header-starts-with "From" ${recipient}) + (header-starts-with "To" ${recipient}) + (header-starts-with "Cc" ${recipient}) + (header-starts-with "Bcc" ${recipient}))) + </code> + </option> + <option value="not starts with"> + <title>does not start with</title> + <code> + (match-all (not (or + (header-starts-with "From" ${recipient}) + (header-starts-with "To" ${recipient}) + (header-starts-with "Cc" ${recipient}) + (header-starts-with "Bcc" ${recipient})))) + </code> + </option> + <option value="ends with"> + <title>ends with</title> + <code> + (match-all (or (header-ends-with "From" ${recipient}) + (header-ends-with "To" ${recipient}) + (header-ends-with "Cc" ${recipient}) + (header-ends-with "Bcc" ${recipient}))) + </code> + </option> + <option value="not ends with"> + <title>does not end with</title> + <code> + (match-all (not (or + (header-ends-with "From" ${recipient}) + (header-ends-with "To" ${recipient}) + (header-ends-with "Cc" ${recipient}) + (header-ends-with "Bcc" ${recipient})))) + </code> + </option> + </input> + <input type="address" name="recipient"/> + </part> + <part name="subject"> <title>Subject</title> <input type="optionlist" name="subject-type"> |