static void compose_advanced_action_cb (Compose *compose,
ComposeCallAdvancedAction action);
-static gboolean compose_grab_focus_cb (GtkWidget *widget,
+static void compose_grab_focus_cb (GtkWidget *widget,
Compose *compose);
-static gboolean compose_grab_focus_before_cb (GtkWidget *widget,
+static void compose_grab_focus_before_cb(GtkWidget *widget,
Compose *compose);
static void compose_changed_cb (GtkTextBuffer *textbuf,
static void compose_toggle_encrypt_cb (gpointer data,
guint action,
GtkWidget *widget);
-static void compose_set_privacy_system_cb(gpointer data,
- guint action,
- GtkWidget *widget);
+static void compose_set_privacy_system_cb(GtkWidget *widget,
+ gpointer data);
static void compose_update_privacy_system_menu_item(Compose * compose);
static void activate_privacy_system (Compose *compose,
PrefsAccount *account);
static gint compose_defer_auto_save_draft (Compose *compose);
static PrefsAccount *compose_guess_forward_account_from_msginfo (MsgInfo *msginfo);
+static void compose_close (Compose *compose);
+
static GtkItemFactoryEntry compose_popup_entries[] =
{
{N_("/_Add..."), NULL, compose_attach_cb, 0, NULL},
#endif
{N_("/_Options"), NULL, NULL, 0, "<Branch>"},
{N_("/_Options/Privacy System"), NULL, NULL, 0, "<Branch>"},
- {N_("/_Options/Privacy System/None"), NULL, compose_set_privacy_system_cb, 0, "<RadioItem>"},
+ {N_("/_Options/Privacy System/None"), NULL, NULL, 0, "<RadioItem>"},
{N_("/_Options/Si_gn"), NULL, compose_toggle_sign_cb , 0, "<ToggleItem>"},
{N_("/_Options/_Encrypt"), NULL, compose_toggle_encrypt_cb, 0, "<ToggleItem>"},
{N_("/_Options/---"), NULL, NULL, 0, "<Separator>"},
{"text/uri-list", 0, 0}
};
+static gboolean compose_put_existing_to_front(MsgInfo *info)
+{
+ GList *compose_list = compose_get_compose_list();
+ GList *elem = NULL;
+
+ if (compose_list) {
+ for (elem = compose_list; elem != NULL && elem->data != NULL;
+ elem = elem->next) {
+ Compose *c = (Compose*)elem->data;
+
+ if (!c->targetinfo || !c->targetinfo->msgid ||
+ !info->msgid)
+ continue;
+
+ if (!strcmp(c->targetinfo->msgid, info->msgid)) {
+ gtkut_window_popup(c->window);
+ return TRUE;
+ }
+ }
+ }
+ return FALSE;
+}
+
Compose *compose_new(PrefsAccount *account, const gchar *mailto,
GPtrArray *attach_files)
{
if (account->auto_sig)
compose_insert_sig(compose, FALSE);
- if (quote && prefs_common.linewrap_quote)
- compose_wrap_line_all(compose);
-
cursor_pos = quote_fmt_get_cursor_pos();
gtk_text_buffer_get_start_iter(textbuf, &iter);
gtk_text_buffer_get_iter_at_offset(textbuf, &iter, cursor_pos);
gtk_text_buffer_place_cursor(textbuf, &iter);
-
- if (quote && prefs_common.linewrap_quote) {
+
+ if (quote && prefs_common.linewrap_quote)
compose_wrap_line_all(compose);
- gtk_text_view_set_editable(GTK_TEXT_VIEW(compose->text), TRUE);
- }
gtk_widget_grab_focus(compose->text);
g_return_if_fail(msginfo != NULL);
g_return_if_fail(msginfo->folder != NULL);
+ if (compose_put_existing_to_front(msginfo))
+ return;
+
if (msginfo->folder->stype == F_QUEUE || msginfo->folder->stype == F_DRAFT) {
gchar queueheader_buf[BUFFSIZE];
gint id, param;
g_signal_handlers_block_by_func(G_OBJECT(textbuf),
G_CALLBACK(compose_changed_cb),
compose);
+
+ g_signal_handlers_block_by_func(G_OBJECT(textbuf),
+ G_CALLBACK(text_inserted),
+ compose);
if ((fp = procmime_get_first_text_content(msginfo)) == NULL)
g_warning("Can't get text part\n");
while (fgets(buf, sizeof(buf), fp) != NULL) {
strcrchomp(buf);
gtk_text_buffer_insert(textbuf, &iter, buf, -1);
+ gtk_text_buffer_get_iter_at_mark(textbuf, &iter, mark);
}
fclose(fp);
}
compose_attach_parts(compose, msginfo);
+ g_signal_handlers_unblock_by_func(G_OBJECT(textbuf),
+ G_CALLBACK(text_inserted),
+ compose);
g_signal_handlers_unblock_by_func(G_OBJECT(textbuf),
G_CALLBACK(compose_changed_cb),
compose);
FILE *fp;
off_t size;
gint row;
+ gchar *name;
if (!is_file_exist(file)) {
g_warning("File %s doesn't exist\n", file);
if (!g_ascii_strcasecmp(content_type, "message/rfc822")) {
MsgInfo *msginfo;
MsgFlags flags = {0, 0};
- const gchar *name;
- if (procmime_get_encoding_for_file(file) == ENC_7BIT)
+ if (procmime_get_encoding_for_text_file(file) == ENC_7BIT)
ainfo->encoding = ENC_7BIT;
else
ainfo->encoding = ENC_8BIT;
msginfo = procheader_parse_file(file, flags, FALSE, FALSE);
if (msginfo && msginfo->subject)
- name = msginfo->subject;
+ name = g_strdup(msginfo->subject);
else
- name = g_basename(filename ? filename : file);
+ name = g_path_get_basename(filename ? filename : file);
ainfo->name = g_strdup_printf(_("Message: %s"), name);
procmsg_msginfo_free(msginfo);
} else {
if (!g_ascii_strncasecmp(content_type, "text", 4))
- ainfo->encoding =
- procmime_get_encoding_for_file(file);
+ ainfo->encoding = procmime_get_encoding_for_text_file(file);
else
ainfo->encoding = ENC_BASE64;
- ainfo->name = g_strdup
- (g_basename(filename ? filename : file));
+ name = g_path_get_basename(filename ? filename : file);
+ ainfo->name = g_strdup(name);
}
+ g_free(name);
} else {
ainfo->content_type = procmime_get_mime_type(file);
if (!ainfo->content_type) {
g_strdup("application/octet-stream");
ainfo->encoding = ENC_BASE64;
} else if (!g_ascii_strncasecmp(ainfo->content_type, "text", 4))
- ainfo->encoding = procmime_get_encoding_for_file(file);
+ ainfo->encoding =
+ procmime_get_encoding_for_text_file(file);
else
ainfo->encoding = ENC_BASE64;
- ainfo->name = g_strdup(g_basename(filename ? filename : file));
+ name = g_path_get_basename(filename ? filename : file);
+ ainfo->name = g_strdup(name);
+ g_free(name);
}
if (!strcmp(ainfo->content_type, "unknown")) {
#undef WRAP_DEBUG
#ifdef WRAP_DEBUG
/* Darko: used when I debug wrapping */
-void dump_text(GtkTextBuffer textbuf, int pos, int tlen, int breakoncr)
+void dump_text(GtkTextBuffer *textbuf, int pos, int tlen, int breakoncr)
{
gint i, clen;
gchar cbuf[CHAR_BUF_SIZE];
+ GtkTextIter iter, end_iter;
printf("%d [", pos);
gtk_text_buffer_get_iter_at_offset(textbuf, &iter, pos);
gtk_text_buffer_get_iter_at_offset(textbuf, &end_iter, pos + tlen);
for (; gtk_text_iter_forward_char(&iter) &&
- gtk_text_iter_compare(&iter, &end_iter) < 0;)
+ gtk_text_iter_compare(&iter, &end_iter) < 0;) {
GET_CHAR(&iter, cbuf, clen);
if (clen < 0) break;
if (breakoncr && clen == 1 && cbuf[0] == '\n')
gint ch_len;
gboolean is_new_line = TRUE, do_delete = FALSE;
guint i_len = 0;
- gboolean linewrap_quote = TRUE;
+ gboolean linewrap_quote = prefs_common.linewrap_quote;
gboolean set_editable_pos = FALSE;
gint editable_pos = 0;
guint linewrap_len = prefs_common.linewrap_len;
is_new_line = TRUE;
#ifdef WRAP_DEBUG
g_print("after delete l_pos=");
- dump_text(text, line_pos, tlen, 1);
+ dump_text(textbuf, line_pos, tlen, 1);
#endif
/* move beginning of line if we are on LF */
gtk_text_buffer_get_iter_at_offset(textbuf,
#ifdef WRAP_DEBUG
g_print("should wrap cur_pos=%d ", cur_pos);
- dump_text(text, p_pos, tlen, 1);
- dump_text(text, line_pos, tlen, 1);
+ dump_text(textbuf, p_pos, tlen, 1);
+ dump_text(textbuf, line_pos, tlen, 1);
#endif
/* force wrapping if it is one long word but not URL */
if (line_pos - p_pos <= i_len)
gtkut_text_buffer_is_uri_string(textbuf, line_pos, tlen)) {
#ifdef WRAP_DEBUG
g_print("found URL at ");
- dump_text(text, line_pos, tlen, 1);
+ dump_text(textbuf, line_pos, tlen, 1);
#endif
continue;
}
do_delete = FALSE;
#ifdef WRAP_DEBUG
g_print("after CR insert ");
- dump_text(text, line_pos, tlen, 1);
- dump_text(text, cur_pos, tlen, 1);
+ dump_text(textbuf, line_pos, tlen, 1);
+ dump_text(textbuf, cur_pos, tlen, 1);
#endif
/* should we insert quotation ? */
}
#ifdef WRAP_DEBUG
g_print("after quote insert ");
- dump_text(text, line_pos, tlen, 1);
+ dump_text(textbuf, line_pos, tlen, 1);
#endif
}
}
if (prefs_common.send_dialog_mode != SEND_DIALOG_ALWAYS) {
compose->sending = FALSE;
- gtk_widget_destroy(compose->window);
+ compose_close(compose);
/* No more compose access in the normal codepath
* after this point! */
}
folder_item_remove_msg(folder, msgnum);
folder_item_scan(folder);
if (prefs_common.send_dialog_mode == SEND_DIALOG_ALWAYS)
- gtk_widget_destroy(compose->window);
- }
+ compose_close(compose);
+ } else {
+ alertpanel_error(_("The message was queued but could not be "
+ "sent.\nUse \"Send queued messages\" from "
+ "the main window to retry."));
+ if (prefs_common.send_dialog_mode == SEND_DIALOG_ALWAYS) {
+ compose_allow_user_actions (compose, TRUE);
+ compose->sending = FALSE;
+ }
+ return -1;
+ }
return 0;
/* Resent-Message-ID */
if (compose->account->gen_msgid) {
- generate_msgid(compose->account->address, buf, sizeof(buf));
+ generate_msgid(buf, sizeof(buf));
fprintf(fp, "Resent-Message-ID: <%s>\n", buf);
compose->msgid = g_strdup(buf);
}
mimetext->subtype = g_strdup("plain");
g_hash_table_insert(mimetext->typeparameters, g_strdup("charset"),
g_strdup(out_codeset));
+ /* protect trailing spaces when signing message */
+ if (action == COMPOSE_WRITE_FOR_SEND && compose->use_signing &&
+ privacy_system_can_sign(compose->privacy_system))
+ encoding = ENC_QUOTED_PRINTABLE;
if (encoding != ENC_UNKNOWN)
procmime_encode_content(mimetext, encoding);
/* sign message if sending */
if (action == COMPOSE_WRITE_FOR_SEND && compose->use_signing &&
privacy_system_can_sign(compose->privacy_system))
- if (!privacy_sign(compose->privacy_system, mimemsg))
+ if (!privacy_sign(compose->privacy_system, mimemsg, compose->account))
return -1;
procmime_write_mimeinfo(mimemsg, fp);
gchar *encdata;
encdata = privacy_get_encrypt_data(compose->privacy_system, compose->to_list);
- fprintf(fp, "X-Sylpheed-Encrypt-Data:%s\n", encdata);
+ if (encdata != NULL)
+ fprintf(fp, "X-Sylpheed-Encrypt-Data:%s\n",
+ encdata);
g_free(encdata);
}
}
compose_add_headerfield_from_headerlist(compose, header, "Bcc", ", ");
/* Subject */
- str = gtk_entry_get_text(GTK_ENTRY(compose->subject_entry));
+ str = gtk_editable_get_chars(GTK_EDITABLE(compose->subject_entry), 0, -1);
if (*str != '\0' && !IS_IN_CUSTOM_HEADER("Subject")) {
- gchar *tmpstr;
-
- tmpstr = g_strdup(str);
- if (tmpstr == NULL) {
- g_string_free(header, TRUE);
- return NULL;
- }
g_strstrip(str);
if (*str != '\0') {
compose_convert_header(buf, sizeof(buf), str,
strlen("Subject: "), FALSE);
g_string_append_printf(header, "Subject: %s\n", buf);
}
- g_free(tmpstr);
}
+ g_free(str);
/* Message-ID */
if (compose->account->gen_msgid) {
- generate_msgid(compose->account->address, buf, sizeof(buf));
+ generate_msgid(buf, sizeof(buf));
g_string_append_printf(header, "Message-ID: <%s>\n", buf);
compose->msgid = g_strdup(buf);
}
g_free(tmp);
entry_str = gtk_entry_get_text(GTK_ENTRY(headerentry->entry));
- Xstrdup_a(headervalue, entry_str, return -1);
+ Xstrdup_a(headervalue, entry_str, return NULL);
subst_char(headervalue, '\r', ' ');
subst_char(headervalue, '\n', ' ');
string = std_headers;
gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(menuitem), TRUE);
}
-static void compose_set_privacy_system_cb(gpointer data,
- guint action,
- GtkWidget *widget)
+static void compose_set_privacy_system_cb(GtkWidget *widget, gpointer data)
{
Compose *compose = (Compose *) data;
gchar *systemid;
GtkItemFactory *ifactory;
gboolean can_sign = FALSE, can_encrypt = FALSE;
+ g_return_if_fail(GTK_IS_CHECK_MENU_ITEM(widget));
+
+ if (!GTK_CHECK_MENU_ITEM(widget)->active)
+ return;
+
systemid = g_object_get_data(G_OBJECT(widget), "privacy_system");
g_free(compose->privacy_system);
compose->privacy_system = NULL;
can_encrypt = privacy_system_can_encrypt(systemid);
}
+ debug_print("activated privacy system: %s\n", systemid != NULL ? systemid : "None");
+
ifactory = gtk_item_factory_from_widget(compose->menubar);
menu_set_sensitive(ifactory, "/Options/Sign", can_sign);
menu_set_sensitive(ifactory, "/Options/Encrypt", can_encrypt);
void compose_update_privacy_systems_menu(Compose *compose)
{
static gchar *branch_path = "/Options/Privacy System";
+ static gboolean connected = FALSE;
GtkItemFactory *ifactory;
GtkWidget *menuitem;
- gchar *menu_path;
GSList *systems, *cur;
GList *amenu;
- GtkItemFactoryEntry ifentry = {NULL, NULL, NULL, 0, "<Branch>"};
GtkWidget *widget;
+ GtkWidget *system_none;
+ GSList *group;
ifactory = gtk_item_factory_from_widget(compose->menubar);
/* remove old entries */
- ifentry.path = branch_path;
menuitem = gtk_item_factory_get_widget(ifactory, branch_path);
g_return_if_fail(menuitem != NULL);
amenu = alist;
}
- ifentry.accelerator = NULL;
- ifentry.callback_action = 0;
- ifentry.callback = compose_set_privacy_system_cb;
- ifentry.item_type = "/Options/Privacy System/None";
+ system_none = gtk_item_factory_get_widget(ifactory,
+ "/Options/Privacy System/None");
+ if (!connected) {
+ g_signal_connect(G_OBJECT(system_none), "activate",
+ G_CALLBACK(compose_set_privacy_system_cb), compose);
+ connected = TRUE;
+ }
systems = privacy_get_system_ids();
for (cur = systems; cur != NULL; cur = g_slist_next(cur)) {
gchar *systemid = cur->data;
- menu_path = g_strdup_printf("%s/%s", branch_path,
- privacy_system_get_name(systemid));
- ifentry.path = menu_path;
- gtk_item_factory_create_item(ifactory, &ifentry, compose, 1);
- widget = gtk_item_factory_get_widget(ifactory, menu_path);
-
+ group = gtk_radio_menu_item_get_group(GTK_RADIO_MENU_ITEM(system_none));
+ widget = gtk_radio_menu_item_new_with_label(group,
+ privacy_system_get_name(systemid));
g_object_set_data_full(G_OBJECT(widget), "privacy_system",
g_strdup(systemid), g_free);
+ g_signal_connect(G_OBJECT(widget), "activate",
+ G_CALLBACK(compose_set_privacy_system_cb), compose);
+ gtk_menu_append(GTK_MENU(system_none->parent), widget);
+ gtk_widget_show(widget);
g_free(systemid);
- g_free(menu_path);
}
g_slist_free(systems);
}
compose_entry_append(compose, tmpl->bcc, COMPOSE_BCC);
if (replace)
- gtk_text_buffer_set_text(buffer, "\0", 1);
+ gtk_text_buffer_set_text(buffer, "", -1);
mark = gtk_text_buffer_get_insert(buffer);
gtk_text_buffer_get_iter_at_mark(buffer, &iter, mark);
GtkTextView *text = GTK_TEXT_VIEW(compose->text);
GtkTextBuffer *buffer = gtk_text_view_get_buffer(text);
- gtk_text_buffer_set_text(buffer, "\0", 1);
+ gtk_text_buffer_set_text(buffer, "", -1);
compose_insert_file(compose, compose->exteditor_file);
compose_changed_cb(NULL, compose);
gint val;
val = compose_queue_sub(compose, NULL, NULL, TRUE);
- if (!val) gtk_widget_destroy(compose->window);
+ if (!val)
+ compose_close(compose);
}
void compose_draft (gpointer data)
}
fprintf(fp, "X-Sylpheed-Sign:%d\n", compose->use_signing);
fprintf(fp, "X-Sylpheed-Encrypt:%d\n", compose->use_encryption);
- fprintf(fp, "X-Sylpheed-Gnupg-Mode:%s\n", compose->privacy_system);
+ fprintf(fp, "X-Sylpheed-Privacy-System:%s\n", compose->privacy_system);
fprintf(fp, "\n");
if (compose_write_to_file(compose, fp, COMPOSE_WRITE_FOR_STORE) < 0) {
lock = FALSE;
if (action == COMPOSE_QUIT_EDITING)
- gtk_widget_destroy(compose->window);
+ compose_close(compose);
else {
struct stat s;
gchar *path;
for ( tmp = file_list; tmp; tmp = tmp->next) {
gchar *file = (gchar *) tmp->data;
gchar *filedup = g_strdup(file);
- const gchar *shortfile = g_basename(filedup);
+ gchar *shortfile = g_path_get_basename(filedup);
ComposeInsertResult res;
res = compose_insert_file(compose, file);
alertpanel_error(_("File '%s' contained invalid characters\n"
"for the current encoding, insertion may be incorrect."), shortfile);
}
+ g_free(shortfile);
g_free(filedup);
g_free(file);
}
}
}
- gtk_widget_destroy(compose->window);
+ compose_close(compose);
}
static void compose_address_cb(gpointer data, guint action, GtkWidget *widget)
static gchar *cliptext = NULL;
-static gboolean compose_grab_focus_before_cb(GtkWidget *widget, Compose *compose)
+static void compose_grab_focus_before_cb(GtkWidget *widget, Compose *compose)
{
gchar *str = NULL;
GtkClipboard *clip = gtk_clipboard_get(gdk_atom_intern("PRIMARY", FALSE));
- if (cliptext)
+ if (cliptext) {
g_free(cliptext);
+ cliptext = NULL;
+ }
+
if (gtk_clipboard_wait_is_text_available(clip))
cliptext = gtk_clipboard_wait_for_text(clip);
-
- return FALSE;
}
-static gboolean compose_grab_focus_cb(GtkWidget *widget, Compose *compose)
+static void compose_grab_focus_cb(GtkWidget *widget, Compose *compose)
{
gchar *str = NULL;
GtkClipboard *clip = gtk_clipboard_get(gdk_atom_intern("PRIMARY", FALSE));
if (GTK_IS_EDITABLE(widget) || GTK_IS_TEXT_VIEW(widget))
compose->focused_editable = widget;
-
- return TRUE;
}
static void compose_changed_cb(GtkTextBuffer *textbuf, Compose *compose)
static void activate_privacy_system(Compose *compose, PrefsAccount *account)
{
- /* TODO
- if (account->default_gnupg_mode)
- compose->gnupg_mode = GNUPG_MODE_INLINE;
- else
- compose->gnupg_mode = GNUPG_MODE_DETACH;
- */
+ g_free(compose->privacy_system);
+ compose->privacy_system = g_strdup(account->default_privacy_system);
compose_update_privacy_system_menu_item(compose);
}
} else
gtk_text_buffer_insert(buffer, iter, text, len);
- if (prefs_common.autowrap)
+ if (compose->autowrap)
compose_wrap_line_all_full(compose, TRUE);
g_signal_handlers_unblock_by_func(G_OBJECT(buffer),
return account;
}
+static void compose_close(Compose *compose)
+{
+ gint x, y;
+
+ g_return_if_fail(compose);
+ gtkut_widget_get_uposition(compose->window, &x, &y);
+ prefs_common.compose_x = x;
+ prefs_common.compose_y = y;
+ gtk_widget_destroy(compose->window);
+}
+
/**
* Add entry field for each address in list.
* \param compose E-Mail composition object.