#include "alertpanel.h"
#include "manage_window.h"
#include "folder.h"
+#include "folder_item_prefs.h"
#include "addr_compl.h"
#include "quote_fmt.h"
#include "undo.h"
#define MAX_REFERENCES_LEN 999
static GList *compose_list = NULL;
+static GSList *extra_headers = NULL;
static Compose *compose_generic_new (PrefsAccount *account,
const gchar *to,
static void compose_attach_update_label(Compose *compose);
static void compose_set_folder_prefs(Compose *compose, FolderItem *folder,
gboolean respect_default_to);
+static void compose_subject_entry_activated(GtkWidget *widget, gpointer data);
static GtkActionEntry compose_popup_entries[] =
{
GdkColormap *cmap;
gboolean success[8];
int i;
-#endif
GdkColor color[8];
+#endif
buffer = gtk_text_view_get_buffer(text);
compose->no_wrap_tag = gtk_text_buffer_create_tag(buffer, "no_wrap", NULL);
compose->no_join_tag = gtk_text_buffer_create_tag(buffer, "no_join", NULL);
+#if !GTK_CHECK_VERSION(2, 24, 0)
color[0] = quote_color1;
color[1] = quote_color2;
color[2] = quote_color3;
color[5] = quote_bgcolor3;
color[6] = signature_color;
color[7] = uri_color;
-#if !GTK_CHECK_VERSION(2, 24, 0)
+
cmap = gdk_drawable_get_colormap(gtk_widget_get_window(compose->window));
gdk_colormap_alloc_colors(cmap, color, 8, FALSE, TRUE, success);
for (i = 0; i < 8; i++) {
if (success[i] == FALSE) {
- GtkStyle *style;
-
g_warning("Compose: color allocation failed.\n");
- style = gtk_widget_get_style(GTK_WIDGET(text));
quote_color1 = quote_color2 = quote_color3 =
quote_bgcolor1 = quote_bgcolor2 = quote_bgcolor3 =
signature_color = uri_color = black;
const gchar *body_fmt = NULL;
MsgInfo *full_msginfo;
- if (prefs_common.fw_quotefmt && *prefs_common.fw_quotefmt)
- body_fmt = gettext(prefs_common.fw_quotefmt);
- else
- body_fmt = "";
-
full_msginfo = procmsg_msginfo_get_full_info(msginfo);
if (!full_msginfo)
full_msginfo = procmsg_msginfo_copy(msginfo);
}
if (fp != NULL) {
- gboolean prev_autowrap = compose->autowrap;
- GtkTextBuffer *buffer = textbuf;
+ gboolean prev_autowrap;
+ GtkTextBuffer *buffer;
BLOCK_WRAP();
while (fgets(buf, sizeof(buf), fp) != NULL) {
strcrchomp(buf);
gchar *tmp = g_strdup(begin);
gchar *o_tmp = tmp;
tmp[cur-begin]='\0';
- cur++;
- begin = cur;
while (*tmp == ' ' || *tmp == '\t')
tmp++;
compose_add_header_entry(compose, header, tmp, pref_type);
ref_id_list = g_slist_remove
(ref_id_list, ref_id_list->next->data);
} else {
- slist_free_strings(ref_id_list);
- g_slist_free(ref_id_list);
+ slist_free_strings_full(ref_id_list);
return NULL;
}
} else
g_string_append_printf(new_ref, "<%s>", (gchar *)cur->data);
}
- slist_free_strings(ref_id_list);
- g_slist_free(ref_id_list);
+ slist_free_strings_full(ref_id_list);
new_ref_str = new_ref->str;
g_string_free(new_ref, FALSE);
g_free(addr);
}
- slist_free_strings(cc_list);
- g_slist_free(cc_list);
+ slist_free_strings_full(cc_list);
}
g_free(ac_email);
gboolean badtxt = FALSE;
struct stat file_stat;
int ret;
+ GString *file_contents = NULL;
cm_return_val_if_fail(file != NULL, COMPOSE_INSERT_NO_FILE);
cur_encoding = conv_get_locale_charset_str_no_utf8();
+ file_contents = g_string_new("");
while (fgets(buf, sizeof(buf), fp) != NULL) {
gchar *str;
if (str[len] == '\r') str[len] = '\n';
}
- gtk_text_buffer_insert(buffer, &iter, str, -1);
+ file_contents = g_string_append(file_contents, str);
g_free(str);
}
+ gtk_text_buffer_insert(buffer, &iter, file_contents->str, -1);
+ g_string_free(file_contents, TRUE);
+
+ compose_changed_cb(NULL, compose);
g_signal_handlers_unblock_by_func(G_OBJECT(buffer),
G_CALLBACK(text_inserted),
compose);
static void compose_select_account(Compose *compose, PrefsAccount *account,
gboolean init)
{
- gchar *from = NULL, *header;
+ gchar *from = NULL, *header = NULL;
ComposeHeaderEntry *header_entry;
+#if GTK_CHECK_VERSION(2, 24, 0)
+ GtkTreeIter iter;
+#endif
cm_return_if_fail(account != NULL);
}
header_entry = (ComposeHeaderEntry *) compose->header_list->data;
+#if !GTK_CHECK_VERSION(2, 24, 0)
header = gtk_combo_box_get_active_text(GTK_COMBO_BOX(header_entry->combo));
+#else
+ if (gtk_combo_box_get_active_iter(GTK_COMBO_BOX(header_entry->combo), &iter))
+ gtk_tree_model_get(gtk_combo_box_get_model(GTK_COMBO_BOX(
+ header_entry->combo)), &iter, COMBOBOX_TEXT, &header, -1);
+#endif
if (header && !strlen(gtk_entry_get_text(GTK_ENTRY(header_entry->entry)))) {
if (account->protocol == A_NNTP) {
gchar **strptr;
/* free to and newsgroup list */
- slist_free_strings(compose->to_list);
- g_slist_free(compose->to_list);
+ slist_free_strings_full(compose->to_list);
compose->to_list = NULL;
- slist_free_strings(compose->newsgroup_list);
- g_slist_free(compose->newsgroup_list);
+ slist_free_strings_full(compose->newsgroup_list);
compose->newsgroup_list = NULL;
/* search header entries for to and newsgroup entries */
FILE *fp;
GSList *cur;
gint num;
- static gboolean lock = FALSE;
PrefsAccount *mailac = NULL, *newsac = NULL;
gboolean err = FALSE;
debug_print("queueing message...\n");
cm_return_val_if_fail(compose->account != NULL, -1);
- lock = TRUE;
-
if (compose_check_entries(compose, check_subject) == FALSE) {
- lock = FALSE;
if (compose->batch) {
gtk_widget_show_all(compose->window);
}
if (!compose->to_list && !compose->newsgroup_list) {
g_warning("can't get recipient list.");
- lock = FALSE;
return -1;
}
else if (cur_account && cur_account->protocol != A_NNTP)
mailac = cur_account;
else if (!(mailac = compose_current_mail_account())) {
- lock = FALSE;
alertpanel_error(_("No account for sending mails available!"));
return -1;
}
if (compose->account->protocol == A_NNTP)
newsac = compose->account;
else {
- lock = FALSE;
alertpanel_error(_("Selected account isn't NNTP: Posting is impossible."));
return -1;
}
if ((fp = g_fopen(tmp, "wb")) == NULL) {
FILE_OP_ERROR(tmp, "fopen");
g_free(tmp);
- lock = FALSE;
return -2;
}
if (compose->use_encryption) {
gchar *encdata;
if (!compose_warn_encryption(compose)) {
- lock = FALSE;
fclose(fp);
claws_unlink(tmp);
g_free(tmp);
err |= (fprintf(fp, "X-Claws-Encrypt:%d\n", compose->use_encryption) < 0);
/* and if encdata was null, it means there's been a problem in
* key selection */
- lock = FALSE;
+ if (err == TRUE)
+ g_warning("failed to write queue message");
fclose(fp);
claws_unlink(tmp);
g_free(tmp);
if (compose->redirect_filename != NULL) {
if (compose_redirect_write_to_file(compose, fp) < 0) {
- lock = FALSE;
fclose(fp);
claws_unlink(tmp);
g_free(tmp);
} else {
gint result = 0;
if ((result = compose_write_to_file(compose, fp, COMPOSE_WRITE_FOR_SEND, TRUE)) < 0) {
- lock = FALSE;
fclose(fp);
claws_unlink(tmp);
g_free(tmp);
fclose(fp);
claws_unlink(tmp);
g_free(tmp);
- lock = FALSE;
return -2;
}
if (fclose(fp) == EOF) {
FILE_OP_ERROR(tmp, "fclose");
claws_unlink(tmp);
g_free(tmp);
- lock = FALSE;
return -2;
}
g_warning("can't find queue folder\n");
claws_unlink(tmp);
g_free(tmp);
- lock = FALSE;
return -1;
}
folder_item_scan(queue);
g_warning("can't queue the message\n");
claws_unlink(tmp);
g_free(tmp);
- lock = FALSE;
return -1;
}
!g_ascii_strcasecmp(mimepart->subtype, "rfc822")) {
mimepart->disposition = DISPOSITIONTYPE_INLINE;
} else if (mimepart->type == MIMETYPE_TEXT) {
- if (!ainfo->name && compose->mode == COMPOSE_FORWARD_INLINE) {
+ if (!ainfo->name && g_ascii_strcasecmp(mimepart->subtype, "plain")) {
/* Text parts with no name come from multipart/alternative
* forwards. Make sure the recipient won't look at the
* original HTML part by mistake. */
gtk_widget_show(menuitem);
}
+void compose_add_extra_header(gchar *header, GtkListStore *model)
+{
+ GtkTreeIter iter;
+ if (strcmp(header, "")) {
+ COMBOBOX_ADD(model, header, COMPOSE_TO);
+ }
+}
+
+void compose_add_extra_header_entries(GtkListStore *model)
+{
+ FILE *exh;
+ gchar *exhrc;
+ gchar buf[BUFFSIZE];
+ gint lastc;
+
+ if (extra_headers == NULL) {
+ exhrc = g_strconcat(get_rc_dir(), G_DIR_SEPARATOR_S, "extraheaderrc", NULL);
+ if ((exh = g_fopen(exhrc, "rb")) == NULL) {
+ debug_print("extra headers file not found\n");
+ goto extra_headers_done;
+ }
+ while (fgets(buf, BUFFSIZE, exh) != NULL) {
+ lastc = strlen(buf) - 1; /* remove trailing control chars */
+ while (lastc >= 0 && buf[lastc] != ':')
+ buf[lastc--] = '\0';
+ if (lastc > 0 && buf[0] != '#' && buf[lastc] == ':') {
+ buf[lastc] = '\0'; /* remove trailing : for comparison */
+ if (custom_header_is_allowed(buf)) {
+ buf[lastc] = ':';
+ extra_headers = g_slist_prepend(extra_headers, g_strdup(buf));
+ }
+ else
+ g_message("disallowed extra header line: %s\n", buf);
+ }
+ else {
+ if (buf[0] != '#')
+ g_message("invalid extra header line: %s\n", buf);
+ }
+ }
+ fclose(exh);
+extra_headers_done:
+ g_free(exhrc);
+ extra_headers = g_slist_prepend(extra_headers, g_strdup("")); /* end of list */
+ extra_headers = g_slist_reverse(extra_headers);
+ }
+ g_slist_foreach(extra_headers, (GFunc)compose_add_extra_header, (gpointer)model);
+}
+
static void compose_create_header_entry(Compose *compose)
{
gchar *headers[] = {"To:", "Cc:", "Bcc:", "Newsgroups:", "Reply-To:", "Followup-To:", NULL};
headerentry = g_new0(ComposeHeaderEntry, 1);
- /* Combo box */
+ /* Combo box model */
model = gtk_list_store_new(3, G_TYPE_STRING, G_TYPE_INT, G_TYPE_BOOLEAN);
+#if !GTK_CHECK_VERSION(2, 24, 0)
combo = gtk_combo_box_entry_new_with_model(GTK_TREE_MODEL(model), 0);
+#endif
COMBOBOX_ADD(model, prefs_common_translated_header_name("To:"),
COMPOSE_TO);
COMBOBOX_ADD(model, prefs_common_translated_header_name("Cc:"),
COMPOSE_REPLYTO);
COMBOBOX_ADD(model, prefs_common_translated_header_name("Followup-To:"),
COMPOSE_FOLLOWUPTO);
+ compose_add_extra_header_entries(model);
+ /* Combo box */
+#if GTK_CHECK_VERSION(2, 24, 0)
+ combo = gtk_combo_box_new_with_model_and_entry(GTK_TREE_MODEL(model));
+ GtkCellRenderer *cell = gtk_cell_renderer_text_new();
+ gtk_cell_renderer_set_alignment(cell, 0.0, 0.5);
+ gtk_cell_layout_pack_start(GTK_CELL_LAYOUT(combo), cell, TRUE);
+ gtk_combo_box_set_entry_text_column(combo, 0);
+#endif
gtk_combo_box_set_active(GTK_COMBO_BOX(combo), 0);
g_signal_connect(G_OBJECT(gtk_bin_get_child(GTK_BIN(combo))), "grab_focus",
G_CALLBACK(compose_grab_focus_cb), compose);
g_signal_connect(G_OBJECT(savemsg_checkbtn), "toggled",
G_CALLBACK(compose_savemsg_checkbtn_cb), compose);
+#if !GTK_CHECK_VERSION(2, 24, 0)
savemsg_combo = gtk_combo_box_entry_new_text();
+#else
+ savemsg_combo = gtk_combo_box_text_new_with_entry();
+#endif
compose->savemsg_checkbtn = savemsg_checkbtn;
compose->savemsg_combo = savemsg_combo;
gtk_widget_show(savemsg_combo);
G_CALLBACK(compose_savemsg_select_cb),
compose);
- rowcount++;
-
return table;
}
UndoMain *undostruct;
- gchar *titles[N_ATTACH_COLS];
GtkWidget *popupmenu;
GtkWidget *tmpl_menu;
GtkActionGroup *action_group = NULL;
debug_print("Creating compose window...\n");
compose = g_new0(Compose, 1);
- titles[COL_MIMETYPE] = _("MIME type");
- titles[COL_SIZE] = _("Size");
- titles[COL_NAME] = _("Name");
- titles[COL_CHARSET] = _("Charset");
-
compose->batch = batch;
compose->account = account;
compose->folder = folder;
- compose->mutex = g_mutex_new();
+ compose->mutex = cm_mutex_new();
compose->set_cursor_pos = -1;
#if !(GTK_CHECK_VERSION(2,12,0))
G_CALLBACK(compose_popup_menu), compose);
#endif
g_signal_connect(G_OBJECT(subject_entry), "changed",
- G_CALLBACK(compose_changed_cb), compose);
+ G_CALLBACK(compose_changed_cb), compose);
+ g_signal_connect(G_OBJECT(subject_entry), "activate",
+ G_CALLBACK(compose_subject_entry_activated), compose);
/* drag and drop */
gtk_drag_dest_set(text, GTK_DEST_DEFAULT_ALL, compose_mime_types,
* however this may change. */
address_completion_end(compose->window);
- slist_free_strings(compose->to_list);
- g_slist_free(compose->to_list);
- slist_free_strings(compose->newsgroup_list);
- g_slist_free(compose->newsgroup_list);
- slist_free_strings(compose->header_list);
- g_slist_free(compose->header_list);
+ slist_free_strings_full(compose->to_list);
+ slist_free_strings_full(compose->newsgroup_list);
+ slist_free_strings_full(compose->header_list);
+
+ slist_free_strings_full(extra_headers);
+ extra_headers = NULL;
compose->header_list = compose->newsgroup_list = compose->to_list = NULL;
gtk_widget_destroy(compose->window);
toolbar_destroy(compose->toolbar);
g_free(compose->toolbar);
- g_mutex_free(compose->mutex);
+ cm_mutex_free(compose->mutex);
g_free(compose);
}
gtk_table_attach(GTK_TABLE(table), label, 0, 1, 0, (0 + 1),
GTK_FILL, 0, 0, 0);
gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
+#if !GTK_CHECK_VERSION(2, 24, 0)
mimetype_entry = gtk_combo_box_entry_new_text();
+#else
+ mimetype_entry = gtk_combo_box_text_new_with_entry();
+#endif
gtk_table_attach(GTK_TABLE(table), mimetype_entry, 1, 2, 0, (0 + 1),
GTK_EXPAND|GTK_SHRINK|GTK_FILL, 0, 0, 0);
for (mime_type_list = strlist; mime_type_list != NULL;
mime_type_list = mime_type_list->next) {
+#if !GTK_CHECK_VERSION(2, 24, 0)
gtk_combo_box_append_text(GTK_COMBO_BOX(mimetype_entry), mime_type_list->data);
+#else
+ gtk_combo_box_text_append_text(GTK_COMBO_BOX_TEXT(mimetype_entry), mime_type_list->data);
+#endif
g_free(mime_type_list->data);
}
g_list_free(strlist);
GSList *list, *saved_list = NULL;
HeaderEntryState *state;
GtkRcStyle *style = NULL;
+#if !GTK_CHECK_VERSION(3, 0, 0)
static GdkColor yellow;
static gboolean color_set = FALSE;
+#else
+ static GdkColor yellow = { (guint32)0, (guint32)0xf5, (guint32)0xf6, (guint32)0xbe };
+#endif
/* Get ID of active account in the combo box */
menu = gtk_combo_box_get_model(optmenu);
GTK_EDITABLE(hentry->entry), 0, -1);
state->type = hentry->type;
+#if !GTK_CHECK_VERSION(3, 0, 0)
if (!color_set) {
gdk_color_parse("#f5f6be", &yellow);
color_set = gdk_colormap_alloc_color(
gdk_colormap_get_system(),
&yellow, FALSE, TRUE);
}
+#endif
style = gtk_widget_get_modifier_style(hentry->entry);
state->entry_marked = gdk_color_equal(&yellow,
tmpl = g_object_get_data(G_OBJECT(widget), "template");
cm_return_if_fail(tmpl != NULL);
- msg = g_strdup_printf(_("Do you want to apply the template '%s' ?"),
+ msg = g_strdup_printf(_("Do you want to apply the template '%s'?"),
tmpl->name);
val = alertpanel(_("Apply template"), msg,
_("_Replace"), _("_Insert"), GTK_STOCK_CANCEL);
GtkTextBuffer *buffer;
GtkTextMark *mark;
GtkTextIter ins;
- gint count;
cm_return_if_fail(GTK_IS_TEXT_VIEW(text));
buffer = gtk_text_view_get_buffer(GTK_TEXT_VIEW(text));
mark = gtk_text_buffer_get_insert(buffer);
gtk_text_buffer_get_iter_at_mark(buffer, &ins, mark);
- count = gtk_text_iter_inside_word (&ins) ? 2 : 1;
if (gtk_text_iter_backward_word_starts(&ins, 1))
gtk_text_buffer_place_cursor(buffer, &ins);
}
}
#endif
+static void compose_subject_entry_activated(GtkWidget *widget, gpointer data)
+{
+ Compose *compose = (Compose *)data;
+
+ cm_return_if_fail(compose != NULL);
+
+ gtk_widget_grab_focus(compose->text);
+}
+
/*
* End of Source.
*/