Commit 8cdc248c9769e50477679725f3d2c1d2af108a8b

Authored by Perry Werneck
1 parent a41df4d9
Exists in master and in 1 other branch develop

Refactoring "paste from file" method.

src/dialogs/load.c 0 → 100644
... ... @@ -0,0 +1,333 @@
  1 +/*
  2 + * "Software pw3270, desenvolvido com base nos códigos fontes do WC3270 e X3270
  3 + * (Paul Mattes Paul.Mattes@usa.net), de emulação de terminal 3270 para acesso a
  4 + * aplicativos mainframe. Registro no INPI sob o nome G3270.
  5 + *
  6 + * Copyright (C) <2008> <Banco do Brasil S.A.>
  7 + *
  8 + * Este programa é software livre. Você pode redistribuí-lo e/ou modificá-lo sob
  9 + * os termos da GPL v.2 - Licença Pública Geral GNU, conforme publicado pela
  10 + * Free Software Foundation.
  11 + *
  12 + * Este programa é distribuído na expectativa de ser útil, mas SEM QUALQUER
  13 + * GARANTIA; sem mesmo a garantia implícita de COMERCIALIZAÇÃO ou de ADEQUAÇÃO
  14 + * A QUALQUER PROPÓSITO EM PARTICULAR. Consulte a Licença Pública Geral GNU para
  15 + * obter mais detalhes.
  16 + *
  17 + * Você deve ter recebido uma cópia da Licença Pública Geral GNU junto com este
  18 + * programa; se não, escreva para a Free Software Foundation, Inc., 51 Franklin
  19 + * St, Fifth Floor, Boston, MA 02110-1301 USA
  20 + *
  21 + * Este programa está nomeado como - e possui - linhas de código.
  22 + *
  23 + * Contatos:
  24 + *
  25 + * perry.werneck@gmail.com (Alexandre Perry de Souza Werneck)
  26 + * erico.mendonca@gmail.com (Erico Mascarenhas Mendonça)
  27 + *
  28 + */
  29 +
  30 +
  31 + #include "private.h"
  32 + #include <internals.h>
  33 + #include <lib3270.h>
  34 + #include <lib3270/selection.h>
  35 + #include <clipboard.h>
  36 + #include <limits.h>
  37 + #include <v3270/dialogs.h>
  38 +
  39 +/*--[ Widget definition ]----------------------------------------------------------------------------*/
  40 +
  41 + typedef struct _V3270LoadDialog
  42 + {
  43 + GtkDialog parent;
  44 +
  45 + GtkWidget * terminal;
  46 + GtkWidget * filename;
  47 + GtkWidget * charset;
  48 +
  49 + } V3270LoadDialog;
  50 +
  51 + typedef struct _V3270LoadDialogClass
  52 + {
  53 + GtkDialogClass parent_class;
  54 + int dummy;
  55 +
  56 + } V3270LoadDialogClass;
  57 +
  58 + #define GTK_TYPE_V3270LoadDialog (V3270LoadDialog_get_type ())
  59 + #define V3270_LOAD_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTK_TYPE_V3270LoadDialog, V3270LoadDialog))
  60 + #define V3270LoadDialog_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GTK_TYPE_V3270Loadialog, V3270LoadDialogClass))
  61 + #define IS_V3270LoadDialog(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTK_TYPE_V3270LoadDialog))
  62 + #define IS_V3270LoadDialog_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTK_TYPE_V3270LoadDialog))
  63 + #define V3270LoadDialog_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GTK_TYPE_V3270LoadDialog, V3270LoadDialogClass))
  64 +
  65 + G_DEFINE_TYPE(V3270LoadDialog, V3270LoadDialog, GTK_TYPE_DIALOG);
  66 +
  67 +/*--[ Implement ]------------------------------------------------------------------------------------*/
  68 +
  69 + static void V3270LoadDialog_class_init(V3270LoadDialogClass G_GNUC_UNUSED(*klass))
  70 + {
  71 +
  72 + debug("%s",__FUNCTION__);
  73 +
  74 + }
  75 +
  76 + static void cancel_operation(GtkButton G_GNUC_UNUSED(*button), GtkDialog *dialog)
  77 + {
  78 + gtk_dialog_response(dialog,GTK_RESPONSE_CANCEL);
  79 + }
  80 +
  81 + static void apply_operation(GtkButton G_GNUC_UNUSED(*button), GtkDialog *dialog)
  82 + {
  83 + gtk_dialog_response(dialog,GTK_RESPONSE_APPLY);
  84 + }
  85 +
  86 +#ifdef WIN32
  87 +static void icon_press(GtkEntry G_GNUC_UNUSED(*entry), G_GNUC_UNUSED GtkEntryIconPosition icon_pos, G_GNUC_UNUSED GdkEvent *event, V3270LoadDialog *widget)
  88 +{
  89 + g_autofree gchar *filename =
  90 + v3270_select_file(
  91 + GTK_WIDGET(widget),
  92 + _( "Select file"),
  93 + _("Open"),
  94 + GTK_FILE_CHOOSER_ACTION_OPEN,
  95 + gtk_entry_get_text(GTK_ENTRY(widget->filename)),
  96 + N_("All files"), "*.*",
  97 + NULL
  98 + );
  99 +
  100 + if(filename && *filename) {
  101 + gtk_entry_set_text(GTK_ENTRY(widget->filename),filename);
  102 + }
  103 +
  104 +}
  105 +#else
  106 +static void icon_press(GtkEntry *entry, G_GNUC_UNUSED GtkEntryIconPosition icon_pos, G_GNUC_UNUSED GdkEvent *event, V3270LoadDialog *widget)
  107 +{
  108 + GtkWidget * dialog =
  109 + gtk_file_chooser_dialog_new(
  110 + _( "Select file"),
  111 + GTK_WINDOW(widget),
  112 + GTK_FILE_CHOOSER_ACTION_OPEN,
  113 + _("Cancel"), GTK_RESPONSE_CANCEL,
  114 + _("Open"), GTK_RESPONSE_ACCEPT,
  115 + NULL );
  116 +
  117 +
  118 + gtk_window_set_deletable(GTK_WINDOW(dialog),FALSE);
  119 + g_signal_connect(G_OBJECT(dialog),"close",G_CALLBACK(v3270_dialog_close),NULL);
  120 +
  121 + const gchar *filename = gtk_entry_get_text(entry);
  122 +
  123 + if(filename && *filename)
  124 + gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(dialog),filename);
  125 +
  126 + if(gtk_dialog_run(GTK_DIALOG(dialog)) == GTK_RESPONSE_ACCEPT)
  127 + gtk_entry_set_text(entry,gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(dialog)));
  128 +
  129 + gtk_widget_destroy(dialog);
  130 +
  131 + }
  132 +#endif // _WIN32
  133 +
  134 + static void V3270LoadDialog_init(V3270LoadDialog *dialog)
  135 + {
  136 + // 0--------1---------------------2-------3--------------------4
  137 + // 0 - Filename xxxxxxxxx.xxxxxxxxx.xxxxxxxxx.xxxxxxxxx.xxxxxxxxx. x
  138 + // 1 - Charset xxxxxxxxx.xxxxxxxxx. Format: xxxxxxxxx.xxxxxxxxx.
  139 +
  140 +
  141 + gtk_window_set_deletable(GTK_WINDOW(dialog),FALSE);
  142 +
  143 + // Setup visual elements
  144 + // https://developer.gnome.org/hig/stable/visual-layout.html.en
  145 + GtkWidget *widget;
  146 + GtkWidget *button;
  147 +
  148 + GtkBox * box = GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog)));
  149 + gtk_window_set_resizable(GTK_WINDOW(dialog),FALSE);
  150 + gtk_container_set_border_width(GTK_CONTAINER(box),18);
  151 +
  152 + GtkGrid * grid = GTK_GRID(gtk_grid_new());
  153 + gtk_grid_set_row_spacing(GTK_GRID(grid),6);
  154 + gtk_grid_set_column_spacing(GTK_GRID(grid),12);
  155 + gtk_box_pack_start(box,GTK_WIDGET(grid),TRUE,TRUE,2);
  156 +
  157 + // Filename entry
  158 + {
  159 + dialog->filename = gtk_entry_new();
  160 + gtk_widget_set_hexpand(GTK_WIDGET(dialog->filename),TRUE);
  161 +
  162 + widget = gtk_label_new_with_mnemonic(_("_Filename"));
  163 + gtk_widget_set_halign(widget,GTK_ALIGN_END);
  164 + gtk_widget_set_valign(widget,GTK_ALIGN_CENTER);
  165 + gtk_grid_attach(grid,widget,0,0,1,1);
  166 + gtk_label_set_mnemonic_widget(GTK_LABEL(widget),dialog->filename);
  167 +
  168 + gtk_entry_set_icon_from_icon_name(GTK_ENTRY(dialog->filename),GTK_ENTRY_ICON_SECONDARY,"document-open");
  169 + gtk_entry_set_icon_activatable(GTK_ENTRY(dialog->filename),GTK_ENTRY_ICON_SECONDARY,TRUE);
  170 + gtk_entry_set_icon_tooltip_text(GTK_ENTRY(dialog->filename),GTK_ENTRY_ICON_SECONDARY,_("Select file"));
  171 + g_signal_connect(G_OBJECT(dialog->filename),"icon-press",G_CALLBACK(icon_press),dialog);
  172 +
  173 + gtk_entry_set_width_chars(GTK_ENTRY(dialog->filename),60);
  174 + gtk_entry_set_max_length(GTK_ENTRY(dialog->filename),PATH_MAX);
  175 + gtk_grid_attach(grid,GTK_WIDGET(dialog->filename),1,0,3,1);
  176 + }
  177 +
  178 + // Charset drop-down
  179 + {
  180 + widget = gtk_label_new_with_mnemonic (_("C_haracter Coding"));
  181 + gtk_widget_set_halign(widget,GTK_ALIGN_END);
  182 + gtk_widget_set_valign(widget,GTK_ALIGN_CENTER);
  183 + gtk_grid_attach(grid,widget,0,1,1,1);
  184 +
  185 + dialog->charset = v3270_charset_combo_box_new();
  186 + gtk_grid_attach(grid,dialog->charset,1,1,1,1);
  187 +
  188 + }
  189 +
  190 +
  191 + // Buttons
  192 + // https://developer.gnome.org/icon-naming-spec/
  193 +#ifdef _WIN32
  194 + widget = NULL;
  195 +#elif GTK_CHECK_VERSION(3,14,0)
  196 + widget = gtk_dialog_get_header_bar(GTK_DIALOG(dialog));
  197 +#else
  198 + widget = NULL;
  199 +#endif // GTK(3,14,0)
  200 +
  201 + if(widget)
  202 + {
  203 + // Have header bar
  204 + button = gtk_button_new_with_mnemonic(_("_Cancel"));
  205 + gtk_widget_set_tooltip_markup(button,_("Click to cancel operation"));
  206 + gtk_header_bar_pack_start(GTK_HEADER_BAR(widget),button);
  207 + g_signal_connect(G_OBJECT(button),"clicked",G_CALLBACK(cancel_operation),dialog);
  208 +
  209 + button = gtk_button_new_with_mnemonic(_("_Load"));
  210 + gtk_widget_set_tooltip_markup(button,_("Click to load file"));
  211 + gtk_header_bar_pack_end(GTK_HEADER_BAR(widget),button);
  212 + g_signal_connect(G_OBJECT(button),"clicked",G_CALLBACK(apply_operation),dialog);
  213 + }
  214 + else
  215 + {
  216 + gtk_box_set_spacing(
  217 + GTK_BOX(gtk_dialog_get_content_area(GTK_DIALOG(dialog))),
  218 + 18
  219 + );
  220 +
  221 + gtk_dialog_add_buttons(
  222 + GTK_DIALOG (dialog),
  223 + _("_Cancel"), GTK_RESPONSE_CANCEL,
  224 + _("_Load"), GTK_RESPONSE_APPLY,
  225 + NULL
  226 + );
  227 + }
  228 +
  229 + }
  230 +
  231 + GtkWidget * v3270_load_dialog_new(GtkWidget *widget, const gchar *filename)
  232 + {
  233 + g_return_val_if_fail(GTK_IS_V3270(widget),NULL);
  234 +
  235 + gboolean use_header;
  236 + g_object_get(gtk_settings_get_default(), "gtk-dialogs-use-header", &use_header, NULL);
  237 +
  238 + // Create dialog
  239 + V3270LoadDialog * dialog = V3270_LOAD_DIALOG(
  240 + g_object_new(
  241 + GTK_TYPE_V3270LoadDialog,
  242 + "use-header-bar", (use_header ? 1 : 0),
  243 + NULL)
  244 + );
  245 +
  246 + dialog->terminal = widget;
  247 +
  248 + gtk_window_set_title(GTK_WINDOW(dialog),_("Paste from file"));
  249 +
  250 + if(filename)
  251 + gtk_entry_set_text(GTK_ENTRY(dialog->filename),filename);
  252 +
  253 + gtk_window_set_transient_for(GTK_WINDOW(dialog), GTK_WINDOW(gtk_widget_get_toplevel(widget)));
  254 + gtk_window_set_modal(GTK_WINDOW(dialog), TRUE);
  255 + gtk_window_set_destroy_with_parent(GTK_WINDOW(dialog), TRUE);
  256 +
  257 + return GTK_WIDGET(dialog);
  258 + }
  259 +
  260 + void v3270_load_dialog_apply(GtkWidget *widget, GError **error)
  261 + {
  262 + V3270LoadDialog * dialog = V3270_LOAD_DIALOG(widget);
  263 +
  264 + debug("%s error=%p",__FUNCTION__,*error);
  265 +
  266 + if(!v3270_is_connected(dialog->terminal))
  267 + {
  268 + *error = g_error_new(g_quark_from_static_string(PACKAGE_NAME),ENOTCONN,"%s",strerror(ENOTCONN));
  269 + return;
  270 + }
  271 +
  272 + // Load file
  273 + g_autofree gchar * contents = NULL;
  274 + g_file_get_contents(
  275 + gtk_entry_get_text(GTK_ENTRY(dialog->filename)),
  276 + &contents,
  277 + NULL,
  278 + error
  279 + );
  280 +
  281 + // Got contents, check for charset conversion.
  282 + g_autofree gchar * converted =
  283 + v3270_convert_to_3270_charset(
  284 + dialog->terminal,
  285 + contents,
  286 + gtk_combo_box_get_active_id(GTK_COMBO_BOX(dialog->charset)),
  287 + error
  288 + );
  289 +
  290 + if(*error)
  291 + return;
  292 +
  293 + gboolean next = lib3270_paste(
  294 + v3270_get_session(dialog->terminal),
  295 + (unsigned char *) converted
  296 + ) ? TRUE : FALSE;
  297 +
  298 + debug("next=%s",next ? "YES" : "NO");
  299 +
  300 + g_signal_emit(
  301 + dialog->terminal,
  302 + v3270_widget_signal[V3270_SIGNAL_PASTENEXT],
  303 + 0,
  304 + next
  305 + );
  306 +
  307 + }
  308 +
  309 + void v3270_load_dialog_run(GtkWidget *widget)
  310 + {
  311 + debug("%s",__FUNCTION__);
  312 + if(gtk_dialog_run(GTK_DIALOG(widget)) == GTK_RESPONSE_APPLY)
  313 + {
  314 + GError * error = NULL;
  315 + v3270_load_dialog_apply(widget,&error);
  316 +
  317 + if(error)
  318 + {
  319 + v3270_popup_gerror(
  320 + widget,
  321 + error,
  322 + NULL,
  323 + _("Can't open %s"),gtk_entry_get_text(GTK_ENTRY(V3270_LOAD_DIALOG(widget)->filename))
  324 + );
  325 + g_error_free(error);
  326 + }
  327 +
  328 + }
  329 + debug("%s",__FUNCTION__);
  330 +
  331 + }
  332 +
  333 +
... ...
src/dialogs/popups.c
... ... @@ -100,3 +100,34 @@
100 100  
101 101 }
102 102  
  103 + void v3270_popup_gerror(GtkWidget *widget, GError *error, const gchar *title, const gchar *fmt, ...)
  104 + {
  105 +
  106 + // Format message.
  107 + va_list arg_ptr;
  108 + va_start(arg_ptr, fmt);
  109 + g_autofree gchar *text = g_strdup_vprintf(fmt,arg_ptr);
  110 + va_end(arg_ptr);
  111 +
  112 + GtkWidget *dialog = gtk_message_dialog_new(
  113 + GTK_WINDOW(gtk_widget_get_toplevel(widget)),
  114 + GTK_DIALOG_DESTROY_WITH_PARENT,
  115 + GTK_MESSAGE_ERROR,
  116 + GTK_BUTTONS_OK,
  117 + "%s",text
  118 + );
  119 +
  120 + if(title)
  121 + gtk_window_set_title(GTK_WINDOW(dialog), title);
  122 + else
  123 + gtk_window_set_title(GTK_WINDOW(dialog), (title ? title : _("Operation failed")));
  124 +
  125 + if(error)
  126 + gtk_message_dialog_format_secondary_text(GTK_MESSAGE_DIALOG(dialog),"%s",error->message);
  127 +
  128 + g_signal_connect(dialog,"close",G_CALLBACK(gtk_widget_destroy),NULL);
  129 + g_signal_connect(dialog,"response",G_CALLBACK(gtk_widget_destroy),NULL);
  130 +
  131 + gtk_widget_show_all(dialog);
  132 +
  133 + }
... ...
src/dialogs/print/print.c
... ... @@ -30,6 +30,7 @@
30 30 #include "private.h"
31 31 #include <sys/param.h>
32 32 #include <lib3270/selection.h>
  33 + #include <v3270/dialogs.h>
33 34 #include <clipboard.h>
34 35  
35 36 G_DEFINE_TYPE(V3270PrintOperation, V3270PrintOperation, GTK_TYPE_PRINT_OPERATION);
... ... @@ -45,25 +46,16 @@
45 46  
46 47 if(result == GTK_PRINT_OPERATION_RESULT_ERROR)
47 48 {
48   - GError * err = NULL;
  49 + GError * err = NULL;
49 50  
50 51 gtk_print_operation_get_error(prt,&err);
51 52  
52   - GtkWidget *dialog = gtk_message_dialog_new_with_markup(
53   - GTK_WINDOW(gtk_widget_get_toplevel(GTK_WIDGET(operation->widget))),
54   - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
55   - GTK_MESSAGE_ERROR,GTK_BUTTONS_CLOSE,
56   - "%s",_( "Print operation failed" )
57   - );
58   -
59   - g_warning("%s",err->message);
60   -
61   - gtk_window_set_title(GTK_WINDOW(dialog),_("Error"));
62   -
63   - gtk_message_dialog_format_secondary_markup(GTK_MESSAGE_DIALOG(dialog),"%s",err->message);
64   -
65   - gtk_dialog_run(GTK_DIALOG(dialog));
66   - gtk_widget_destroy(dialog);
  53 + v3270_popup_gerror(
  54 + GTK_WIDGET(operation->widget),
  55 + err,
  56 + NULL,
  57 + "%s",_( "Print operation failed" )
  58 + );
67 59  
68 60 g_error_free(err);
69 61  
... ...
src/dialogs/save/convenience.c
... ... @@ -72,7 +72,6 @@
72 72 return errno = ENOTCONN;
73 73 }
74 74  
75   - lib3270_trace_event(v3270_get_session(widget),"save action activated (type=%d)",(int) mode);
76 75 int rc = lib3270_save(v3270_get_session(widget),mode,filename);
77 76  
78 77 if(!rc)
... ...
src/dialogs/save/private.h
... ... @@ -27,14 +27,27 @@
27 27 *
28 28 */
29 29  
  30 + #include <config.h>
  31 + #define ENABLE_NLS
  32 +
  33 + #ifndef GETTEXT_PACKAGE
  34 + #define GETTEXT_PACKAGE PACKAGE_NAME
  35 + #endif
  36 +
  37 + #include <libintl.h>
  38 + #include <glib/gi18n.h>
  39 + #include <gtk/gtk.h>
  40 + #include <lib3270.h>
30 41 #include <v3270.h>
31   - #include <save.h>
  42 + #include <v3270/dialogs.h>
32 43 #include <v3270/print.h>
33 44 #include <lib3270/log.h>
34 45 #include <lib3270/trace.h>
35 46  
36 47 /*--[ Widget definition ]----------------------------------------------------------------------------*/
37 48  
  49 + G_BEGIN_DECLS
  50 +
38 51 struct _V3270SaveDialog
39 52 {
40 53 GtkDialog parent;
... ... @@ -54,7 +67,19 @@
54 67  
55 68 };
56 69  
57   -/*--[ Prototypes ]-----------------------------------------------------------------------------------*/
  70 +/*--[ Save Dialog Widget ]---------------------------------------------------------------------------*/
  71 +
  72 + #define GTK_TYPE_V3270SaveDialog (V3270SaveDialog_get_type ())
  73 + #define V3270_SAVE_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTK_TYPE_V3270SaveDialog, V3270SaveDialog))
  74 + #define V3270SaveDialog_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GTK_TYPE_V3270SaveDialog, V3270SaveDialogClass))
  75 + #define IS_V3270SaveDialog(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTK_TYPE_V3270SaveDialog))
  76 + #define IS_V3270SaveDialog_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTK_TYPE_V3270SaveDialog))
  77 + #define V3270SaveDialog_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GTK_TYPE_V3270SaveDialog, V3270SaveDialogClass))
  78 +
  79 + typedef struct _V3270SaveDialog V3270SaveDialog;
  80 + typedef struct _V3270SaveDialogClass V3270SaveDialogClass;
  81 +
  82 + G_END_DECLS
58 83  
59 84  
60 85  
... ...
src/dialogs/save/save.c
... ... @@ -447,21 +447,14 @@ static void icon_press(GtkEntry *entry, G_GNUC_UNUSED GtkEntryIconPosition icon_
447 447  
448 448 if(error)
449 449 {
450   - GtkWidget *popup = gtk_message_dialog_new_with_markup(
451   - GTK_WINDOW(gtk_widget_get_toplevel(widget)),
452   - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
453   - GTK_MESSAGE_ERROR,GTK_BUTTONS_CLOSE,
454   - _("Can't save %s"),gtk_entry_get_text(GTK_ENTRY(V3270_SAVE_DIALOG(widget)->filename))
  450 + v3270_popup_gerror(
  451 + widget,
  452 + error,
  453 + NULL,
  454 + _("Can't save %s"),gtk_entry_get_text(GTK_ENTRY(V3270_SAVE_DIALOG(widget)->filename))
455 455 );
456 456  
457   - gtk_window_set_title(GTK_WINDOW(popup),_("Operation has failed"));
458   -
459   - gtk_message_dialog_format_secondary_markup(GTK_MESSAGE_DIALOG(popup),"%s",error->message);
460 457 g_error_free(error);
461   -
462   - gtk_dialog_run(GTK_DIALOG(popup));
463   - gtk_widget_destroy(popup);
464   -
465 458 }
466 459  
467 460 }
... ...
src/dialogs/transfer.c
... ... @@ -39,6 +39,7 @@
39 39  
40 40 #include <v3270.h>
41 41 #include <v3270/filetransfer.h>
  42 + #include <v3270/dialogs.h>
42 43  
43 44 /*--[ Implement ]------------------------------------------------------------------------------------*/
44 45  
... ... @@ -89,21 +90,15 @@ static void save_activity_clicked(GtkWidget *button, GObject *activity)
89 90  
90 91 if(!g_file_set_contents(filename,text,-1,&error)) {
91 92  
92   - GtkWidget *popup = gtk_message_dialog_new_with_markup(
93   - GTK_WINDOW(gtk_widget_get_toplevel(button)),
94   - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
95   - GTK_MESSAGE_ERROR,GTK_BUTTONS_CLOSE,
96   - _("Can't save %s"),filename
  93 + v3270_popup_gerror(
  94 + button,
  95 + error,
  96 + NULL,
  97 + _("Can't save %s"),filename
97 98 );
98 99  
99   - gtk_window_set_title(GTK_WINDOW(popup),_("Operation has failed"));
100   -
101   - gtk_message_dialog_format_secondary_markup(GTK_MESSAGE_DIALOG(popup),"%s",error->message);
102 100 g_error_free(error);
103 101  
104   - gtk_dialog_run(GTK_DIALOG(popup));
105   - gtk_widget_destroy(popup);
106   -
107 102 }
108 103  
109 104 }
... ...
src/filetransfer/activitylist.c
... ... @@ -28,6 +28,7 @@
28 28 */
29 29  
30 30 #include <internals.h>
  31 + #include <v3270/dialogs.h>
31 32 #include "private.h"
32 33 #include "marshal.h"
33 34  
... ... @@ -430,21 +431,15 @@
430 431  
431 432 if(!g_file_set_contents(list->filename,text,-1,&error)) {
432 433  
433   - GtkWidget *popup = gtk_message_dialog_new_with_markup(
434   - GTK_WINDOW(gtk_widget_get_toplevel(widget)),
435   - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
436   - GTK_MESSAGE_ERROR,GTK_BUTTONS_CLOSE,
437   - _("Can't save %s"),list->filename
  434 + v3270_popup_gerror(
  435 + widget,
  436 + error,
  437 + NULL,
  438 + _("Can't save %s"),list->filename
438 439 );
439 440  
440   - gtk_window_set_title(GTK_WINDOW(popup),_("Operation has failed"));
441   -
442   - gtk_message_dialog_format_secondary_markup(GTK_MESSAGE_DIALOG(popup),"%s",error->message);
443 441 g_error_free(error);
444 442  
445   - gtk_dialog_run(GTK_DIALOG(popup));
446   - gtk_widget_destroy(popup);
447   -
448 443 }
449 444  
450 445  
... ...
src/filetransfer/load.c
... ... @@ -32,6 +32,7 @@
32 32  
33 33 #include <ctype.h>
34 34 #include <stdlib.h>
  35 + #include <v3270/dialogs.h>
35 36  
36 37  
37 38 /*--[ Statics ]--------------------------------------------------------------------------------------*/
... ... @@ -263,23 +264,15 @@ LIB3270_EXPORT void v3270ft_load(GtkWidget *widget,const gchar *filename) {
263 264  
264 265 if(error) {
265 266  
266   - GtkWidget *popup = gtk_message_dialog_new_with_markup(
267   - GTK_WINDOW(widget),
268   - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
269   - GTK_MESSAGE_ERROR,GTK_BUTTONS_CLOSE,
270   - _("Can't load %s"),filename);
271   -
272   - gtk_window_set_title(GTK_WINDOW(popup),_("Operation has failed"));
273   -
274   - if(error->message && *error->message) {
275   - gtk_message_dialog_format_secondary_markup(GTK_MESSAGE_DIALOG(popup),"%s",error->message);
276   - }
  267 + v3270_popup_gerror(
  268 + widget,
  269 + error,
  270 + NULL,
  271 + _("Can't load %s"),filename
  272 + );
277 273  
278 274 g_error_free(error);
279 275  
280   - gtk_dialog_run(GTK_DIALOG(popup));
281   - gtk_widget_destroy(popup);
282   -
283 276 }
284 277  
285 278 }
... ...
src/filetransfer/save.c
... ... @@ -109,20 +109,15 @@ static const gchar * getNameByFlag(LIB3270_FT_OPTION opt, LIB3270_FT_OPTION mask
109 109  
110 110 if(!g_file_set_contents(filename,text,-1,&error)) {
111 111  
112   - GtkWidget *popup = gtk_message_dialog_new_with_markup(
113   - GTK_WINDOW(widget),
114   - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
115   - GTK_MESSAGE_ERROR,GTK_BUTTONS_CLOSE,
116   - _("Can't save %s"),filename);
  112 + v3270_popup_gerror(
  113 + widget,
  114 + error,
  115 + NULL,
  116 + _("Can't save %s"),filename
  117 + );
117 118  
118   - gtk_window_set_title(GTK_WINDOW(popup),_("Operation has failed"));
119   -
120   - gtk_message_dialog_format_secondary_markup(GTK_MESSAGE_DIALOG(popup),"%s",error->message);
121 119 g_error_free(error);
122 120  
123   - gtk_dialog_run(GTK_DIALOG(popup));
124   - gtk_widget_destroy(popup);
125   -
126 121 }
127 122  
128 123 g_free(text);
... ...
src/include/internals.h
... ... @@ -107,6 +107,8 @@
107 107  
108 108 G_GNUC_INTERNAL void v3270_dialog_close(GtkDialog *dialog, gpointer user_data);
109 109  
  110 + G_GNUC_INTERNAL gchar * v3270_convert_to_3270_charset(GtkWidget *widget, const gchar *text, const gchar *encoding, GError **error);
  111 +
110 112  
111 113 /*--[ Internal Widgets & Tools ]---------------------------------------------------------------------*/
112 114  
... ...
src/include/save.h
... ... @@ -31,37 +31,6 @@
31 31  
32 32 #define V3270SAVE_H_INCLUDED 1
33 33  
34   - #include <config.h>
35   - #define ENABLE_NLS
36 34  
37   - #ifndef GETTEXT_PACKAGE
38   - #define GETTEXT_PACKAGE PACKAGE_NAME
39   - #endif
40   -
41   - #include <libintl.h>
42   - #include <glib/gi18n.h>
43   - #include <gtk/gtk.h>
44   - #include <lib3270.h>
45   -
46   - G_BEGIN_DECLS
47   -
48   -/*--[ Progress widget ]------------------------------------------------------------------------------*/
49   -
50   - #define GTK_TYPE_V3270SaveDialog (V3270SaveDialog_get_type ())
51   - #define V3270_SAVE_DIALOG(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTK_TYPE_V3270SaveDialog, V3270SaveDialog))
52   - #define V3270SaveDialog_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GTK_TYPE_V3270SaveDialog, V3270SaveDialogClass))
53   - #define IS_V3270SaveDialog(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTK_TYPE_V3270SaveDialog))
54   - #define IS_V3270SaveDialog_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTK_TYPE_V3270SaveDialog))
55   - #define V3270SaveDialog_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GTK_TYPE_V3270SaveDialog, V3270SaveDialogClass))
56   -
57   - typedef struct _V3270SaveDialog V3270SaveDialog;
58   - typedef struct _V3270SaveDialogClass V3270SaveDialogClass;
59   -
60   -/*--[ Prototipes ]-----------------------------------------------------------------------------------*/
61   -
62   - GtkWidget * v3270_save_dialog_new(GtkWidget *widget, LIB3270_CONTENT_OPTION mode, const gchar *filename);
63   - void v3270_save_dialog_run(GtkWidget *widget);
64   -
65   - G_END_DECLS
66 35  
67 36 #endif // V3270SAVE_H_INCLUDED
... ...
src/include/v3270.h
... ... @@ -210,6 +210,7 @@
210 210  
211 211 LIB3270_EXPORT void v3270_paste(GtkWidget *widget);
212 212 LIB3270_EXPORT void v3270_paste_text(GtkWidget *widget);
  213 + LIB3270_EXPORT void v3270_paste_from_file(GtkWidget *widget);
213 214 LIB3270_EXPORT void v3270_input_text(GtkWidget *widget, const gchar *text, const gchar *encoding);
214 215  
215 216 // Colors
... ...
src/include/v3270/dialogs.h
... ... @@ -39,6 +39,15 @@
39 39 LIB3270_EXPORT GtkWidget * v3270_dialog_new(GtkWidget *widget, const gchar *title, const gchar *apply);
40 40 LIB3270_EXPORT void v3270_error_popup(GtkWidget *widget, const gchar *title, const gchar *summary, const gchar *body);
41 41  
  42 + LIB3270_EXPORT GtkWidget * v3270_save_dialog_new(GtkWidget *widget, LIB3270_CONTENT_OPTION mode, const gchar *filename);
  43 + LIB3270_EXPORT void v3270_save_dialog_run(GtkWidget *widget);
  44 +
  45 + LIB3270_EXPORT GtkWidget * v3270_load_dialog_new(GtkWidget *widget, const gchar *filename);
  46 + LIB3270_EXPORT void v3270_load_dialog_run(GtkWidget *widget);
  47 +
  48 + LIB3270_EXPORT void v3270_popup_gerror(GtkWidget *widget, GError *error, const gchar *title, const gchar *fmt, ...) G_GNUC_PRINTF(4,5);
  49 +
  50 +
42 51 G_END_DECLS
43 52  
44 53 #endif // V3270_DIALOGS_H_INCLUDED
... ...
src/selection/text.c
... ... @@ -29,6 +29,7 @@
29 29  
30 30 #include <clipboard.h>
31 31 #include <lib3270/selection.h>
  32 + #include <v3270/dialogs.h>
32 33  
33 34 /*--[ Implement ]------------------------------------------------------------------------------------*/
34 35  
... ... @@ -71,48 +72,50 @@ gchar * v3270_get_copy_as_text(v3270 * terminal, const gchar *encoding)
71 72 return v3270_get_selection_as_text(terminal, terminal->selection.blocks, encoding, FALSE);
72 73 }
73 74  
74   -LIB3270_EXPORT void v3270_input_text(GtkWidget *widget, const gchar *text, const gchar *encoding)
  75 +gchar * v3270_convert_to_3270_charset(GtkWidget *widget, const gchar *text, const gchar *encoding, GError **error)
75 76 {
76   - gchar * buffer = NULL;
77   - H3270 * session = v3270_get_session(widget);
78   - const gchar * charset = lib3270_get_display_charset(session);
79   - gboolean next;
  77 + if(*error || !text)
  78 + return NULL;
80 79  
81   - if(!text)
82   - return;
83   - else if(g_ascii_strcasecmp(encoding,charset))
84   - buffer = g_convert(text, -1, charset, encoding, NULL, NULL, NULL);
85   - else
86   - buffer = g_strdup(text);
87   -
88   - if(!buffer)
89   - {
90   - /* Conversion failed, update special chars and try again */
91   - size_t f;
92   -
93   - static const struct _xlat
94   - {
95   - const gchar *from;
96   - const gchar *to;
97   - } xlat[] =
98   - {
99   - { "–", "-" },
100   - { "→", "->" },
101   - { "←", "<-" },
102   - { "©", "(c)" },
103   - { "↔", "<->" },
104   - { "™", "(TM)" },
105   - { "®", "(R)" },
106   - { "“", "\"" },
107   - { "”", "\"" },
108   - { "…", "..." },
109   - { "•", "*" },
110   - { "․", "." },
111   - { "·", "*" },
112   -
113   - };
114   -
115   - gchar *string = g_strdup(text);
  80 + const gchar * charset = lib3270_get_display_charset(v3270_get_session(widget));
  81 + if(!encoding || (g_ascii_strcasecmp(encoding,charset) == 0))
  82 + {
  83 + // No conversion needed.
  84 + return g_strdup(text);
  85 + }
  86 +
  87 + gchar *converted = g_convert(text, -1, charset, encoding, NULL, NULL, NULL);
  88 + if(converted)
  89 + return converted;
  90 +
  91 + // Conversion failed, update UTF-8 special chars and try again
  92 + if(!g_ascii_strcasecmp(encoding,"UTF-8"))
  93 + {
  94 + size_t f;
  95 +
  96 + static const struct _xlat
  97 + {
  98 + const gchar *from;
  99 + const gchar *to;
  100 + } xlat[] =
  101 + {
  102 + { "–", "-" },
  103 + { "→", "->" },
  104 + { "←", "<-" },
  105 + { "©", "(c)" },
  106 + { "↔", "<->" },
  107 + { "™", "(TM)" },
  108 + { "®", "(R)" },
  109 + { "“", "\"" },
  110 + { "”", "\"" },
  111 + { "…", "..." },
  112 + { "•", "*" },
  113 + { "․", "." },
  114 + { "·", "*" },
  115 +
  116 + };
  117 +
  118 + g_autofree gchar *string = g_strdup(text);
116 119  
117 120 // FIXME (perry#1#): Is there any better way for a "sed" here?
118 121 for(f=0;f<G_N_ELEMENTS(xlat);f++)
... ... @@ -129,52 +132,55 @@ LIB3270_EXPORT void v3270_input_text(GtkWidget *widget, const gchar *text, const
129 132 }
130 133 }
131 134  
132   - buffer = g_convert(string, -1, charset, encoding, NULL, NULL, NULL);
  135 + converted = g_convert(string, -1, charset, encoding, NULL, NULL, NULL);
  136 +
  137 + if(converted)
  138 + return converted;
  139 +
  140 + }
133 141  
134   - if(!buffer)
  142 + /*
  143 + // Still failing, convert line by line
  144 + {
  145 + size_t f;
  146 + gchar **ln = g_strsplit(text,"\n",-1);
  147 +
  148 + for(f=0;ln[f];f++)
135 149 {
136   - // Still failing, convert line by line
137   - gchar **ln = g_strsplit(string,"\n",-1);
  150 + GError *error = NULL;
  151 + gchar *str = g_convert(ln[f], -1, charset, encoding, NULL, NULL, error);
138 152  
139   - for(f=0;ln[f];f++)
  153 + if(!str)
140 154 {
141   - GError *error = NULL;
142   - gchar *str = g_convert(ln[f], -1, charset, encoding, NULL, NULL, &error);
143   -
144   - if(!str)
145   - {
146   - GtkWidget *dialog = gtk_message_dialog_new( GTK_WINDOW( gtk_widget_get_toplevel(widget)),
147   - GTK_DIALOG_DESTROY_WITH_PARENT,
148   - GTK_MESSAGE_ERROR,
149   - GTK_BUTTONS_OK,
150   - _( "Can't convert line %lu from %s to %s" ),(unsigned long) (f+1), encoding, charset);
151   -
152   - gtk_window_set_title(GTK_WINDOW(dialog), _( "Charset error" ) );
153   -
154   - if(error)
155   - {
156   - gtk_message_dialog_format_secondary_text(GTK_MESSAGE_DIALOG(dialog),"%s\n%s",error->message, ln[f]);
157   - g_error_free(error);
158   - error = NULL;
159   - }
160   -
161   - gtk_dialog_run(GTK_DIALOG (dialog));
162   - gtk_widget_destroy(dialog);
163   -
164   - break;
165   - }
166   - else
167   - {
168   - g_free(str);
169   - }
170   -
  155 + g_strfreev(ln);
  156 + return NULL;
171 157 }
172   - g_strfreev(ln);
  158 +
  159 + g_free(str);
173 160  
174 161 }
  162 + g_strfreev(ln);
  163 +
  164 + }
  165 + */
  166 +
  167 + // Can't convert, use fallbacks
  168 + return g_convert_with_fallback(
  169 + text,
  170 + -1,
  171 + charset,
  172 + encoding,
  173 + " ",
  174 + NULL,
  175 + NULL,
  176 + error
  177 + );
  178 +}
175 179  
176   - g_free(string);
177   - }
  180 +LIB3270_EXPORT void v3270_input_text(GtkWidget *widget, const gchar *text, const gchar *encoding)
  181 +{
  182 + GError * error = NULL;
  183 + g_autofree gchar * buffer = v3270_convert_to_3270_charset(widget,text,encoding,&error);
178 184  
179 185 if(buffer)
180 186 {
... ... @@ -187,17 +193,27 @@ LIB3270_EXPORT void v3270_input_text(GtkWidget *widget, const gchar *text, const
187 193 *ptr = ' ';
188 194 }
189 195 }
190   - else
  196 +
  197 + if(error)
191 198 {
192 199 g_signal_emit(widget,v3270_widget_signal[V3270_SIGNAL_PASTENEXT], 0, FALSE);
  200 + v3270_popup_gerror(widget,error,NULL,"%s",_("Can't paste text"));
  201 + g_error_free(error);
193 202 return;
194 203 }
195 204  
196   - next = lib3270_paste(session,(unsigned char *) buffer) ? TRUE : FALSE;
197   -
198   - g_free(buffer);
199   -
200   - g_signal_emit(widget,v3270_widget_signal[V3270_SIGNAL_PASTENEXT], 0, next);
  205 + // Do paste.
  206 + gboolean next = lib3270_paste(
  207 + v3270_get_session(widget),
  208 + (unsigned char *) buffer
  209 + ) ? TRUE : FALSE;
  210 +
  211 + g_signal_emit(
  212 + v3270_get_session(widget),
  213 + v3270_widget_signal[V3270_SIGNAL_PASTENEXT],
  214 + 0,
  215 + next
  216 + );
201 217  
202 218 }
203 219  
... ...
src/terminal/callbacks.c
... ... @@ -35,7 +35,7 @@
35 35  
36 36 #include <terminal.h>
37 37 #include <internals.h>
38   - #include <save.h>
  38 + #include <v3270/dialogs.h>
39 39  
40 40 #include <gtk/gtk.h>
41 41 #include <libintl.h>
... ... @@ -337,7 +337,7 @@ static int save(H3270 *session, LIB3270_CONTENT_OPTION mode, const char *filenam
337 337 GtkWidget * widget = GTK_WIDGET(lib3270_get_user_data(session));
338 338  
339 339 if(!GTK_IS_V3270(widget))
340   - return EINVAL;
  340 + return errno = EINVAL;
341 341  
342 342 GtkWidget *dialog = v3270_save_dialog_new(widget,mode,filename);
343 343 gtk_widget_show_all(dialog);
... ... @@ -347,6 +347,21 @@ static int save(H3270 *session, LIB3270_CONTENT_OPTION mode, const char *filenam
347 347 return 0;
348 348 }
349 349  
  350 +static int load(H3270 *session, const char *filename)
  351 +{
  352 + GtkWidget * widget = GTK_WIDGET(lib3270_get_user_data(session));
  353 +
  354 + if(!GTK_IS_V3270(widget))
  355 + return errno = EINVAL;
  356 +
  357 + GtkWidget *dialog = v3270_load_dialog_new(widget,filename);
  358 + gtk_widget_show_all(dialog);
  359 + v3270_load_dialog_run(dialog);
  360 + gtk_widget_destroy(dialog);
  361 +
  362 + return 0;
  363 +}
  364 +
350 365 static void popup_handler(H3270 *session, LIB3270_NOTIFY type, const char *title, const char *msg, const char *fmt, va_list args)
351 366 {
352 367 GtkWidget *terminal = (GtkWidget *) lib3270_get_user_data(session);
... ... @@ -493,6 +508,7 @@ static void popup_handler(H3270 *session, LIB3270_NOTIFY type, const char *title
493 508 cbk->update_ssl = update_ssl;
494 509 cbk->print = print;
495 510 cbk->save = save;
  511 + cbk->load = load;
496 512 cbk->popup_ssl_error = popup_ssl_error;
497 513  
498 514 }
... ...
src/terminal/charset.c
... ... @@ -32,6 +32,7 @@
32 32 #include <lib3270/charset.h>
33 33 #include <lib3270/log.h>
34 34 #include <lib3270/X11keysym.h>
  35 + #include <v3270/dialogs.h>
35 36  
36 37 #define ERROR_DOMAIN g_quark_from_static_string(PACKAGE_NAME)
37 38  
... ... @@ -454,27 +455,17 @@
454 455  
455 456 if(error)
456 457 {
457   - GtkWidget * dialog;
458   - gchar * name = g_path_get_basename(path);
  458 + g_autofree gchar * name = g_path_get_basename(path);
459 459  
460   - dialog = gtk_message_dialog_new( NULL,
461   - GTK_DIALOG_DESTROY_WITH_PARENT,
462   - GTK_MESSAGE_WARNING,
463   - GTK_BUTTONS_OK,
464   - _( "Can't parse %s" ), name);
465   -
466   - g_free(name);
467   -
468   - gtk_window_set_title(GTK_WINDOW(dialog), _( "Remap Failed" ) );
469   -
470   - if(error->message)
471   - gtk_message_dialog_format_secondary_text(GTK_MESSAGE_DIALOG(dialog), "%s", error->message);
  460 + v3270_popup_gerror(
  461 + widget,
  462 + error,
  463 + _( "Remap Failed" ),
  464 + _( "Can't parse %s" ), name
  465 + );
472 466  
473 467 g_error_free(error);
474 468  
475   - gtk_dialog_run(GTK_DIALOG (dialog));
476   - gtk_widget_destroy(dialog);
477   -
478 469 } else {
479 470  
480 471 H3270 * hSession = v3270_get_session(widget);
... ...
src/testprogram/toolbar.c
... ... @@ -59,11 +59,16 @@
59 59 lib3270_disconnect(v3270_get_session(terminal));
60 60 }
61 61  
62   -static void save_all_clicked(GtkButton G_GNUC_UNUSED(*button), GtkWidget *terminal)
  62 + static void save_all_clicked(GtkButton G_GNUC_UNUSED(*button), GtkWidget *terminal)
63 63 {
64 64 lib3270_save_all(v3270_get_session(terminal),NULL);
65 65 }
66 66  
  67 + static void load_clicked(GtkButton G_GNUC_UNUSED(*button), GtkWidget *terminal)
  68 + {
  69 + lib3270_load(v3270_get_session(terminal),NULL);
  70 + }
  71 +
67 72 static void ft_clicked(GtkButton *button, GtkWidget *terminal)
68 73 {
69 74 v3270_error_popup(terminal,"title","summary","body");
... ... @@ -176,25 +181,28 @@ static void save_all_clicked(GtkButton G_GNUC_UNUSED(*button), GtkWidget *termin
176 181  
177 182 // https://specifications.freedesktop.org/icon-naming-spec/icon-naming-spec-latest.html
178 183 static const struct _buttons {
179   - const gchar * icon;
  184 + const gchar * icon; // https://specifications.freedesktop.org/icon-naming-spec/latest/ar01s04.html
180 185 GCallback callback;
181 186 const gchar * tooltip;
182 187 } buttons[] = {
183   - { "gtk-connect", G_CALLBACK(connect_clicked), "Connect to host" },
184   - { "gtk-disconnect", G_CALLBACK(disconnect_clicked), "Disconnect from host" },
185   - { "gtk-select-color", G_CALLBACK(color_clicked), "Edit or change color scheme" },
186   - { "gtk-home", G_CALLBACK(host_clicked), "Configure host" },
187   - { "gtk-print", G_CALLBACK(print_clicked), "Print screen contents" },
188   - { "gtk-harddisk", G_CALLBACK(ft_clicked), "Open file transfer dialog" },
189   - { "gtk-copy", G_CALLBACK(copy_clicked), "Copy data" },
190   - { "gtk-paste", G_CALLBACK(paste_clicked), "Paste data" },
191   - { "gtk-save", G_CALLBACK(save_all_clicked), "Save screen" }
  188 + { "gtk-connect", G_CALLBACK(connect_clicked), "Connect to host" },
  189 + { "gtk-disconnect", G_CALLBACK(disconnect_clicked), "Disconnect from host" },
  190 + { "gtk-select-color", G_CALLBACK(color_clicked), "Edit or change color scheme" },
  191 + { "network-server", G_CALLBACK(host_clicked), "Configure host" },
  192 + { "gtk-print", G_CALLBACK(print_clicked), "Print screen contents" },
  193 + { "gtk-harddisk", G_CALLBACK(ft_clicked), "Open file transfer dialog" },
  194 + { "gtk-copy", G_CALLBACK(copy_clicked), "Copy data" },
  195 + { "gtk-paste", G_CALLBACK(paste_clicked), "Paste data" },
  196 + { "document-save", G_CALLBACK(save_all_clicked), "Save screen" },
  197 + { "document-open", G_CALLBACK(load_clicked), "Paste file" },
  198 +
192 199 };
193 200  
194 201 GtkWidget * toolbar = gtk_toolbar_new();
195 202 for(f = 0; f < G_N_ELEMENTS(buttons); f++)
196 203 {
197   - GtkWidget * button = GTK_WIDGET(gtk_tool_button_new_from_stock(buttons[f].icon));
  204 + GtkWidget * button = gtk_tool_button_new(gtk_image_new_from_icon_name(buttons[f].icon,GTK_ICON_SIZE_SMALL_TOOLBAR),"-");
  205 +
198 206 gtk_widget_set_tooltip_markup(button,buttons[f].tooltip);
199 207 g_signal_connect(G_OBJECT(button),"clicked",buttons[f].callback,terminal);
200 208 gtk_toolbar_insert(GTK_TOOLBAR(toolbar),GTK_TOOL_ITEM(button),-1);
... ...
src/trace/trace.c
... ... @@ -50,6 +50,7 @@
50 50 #include <lib3270/trace.h>
51 51 #include <lib3270/properties.h>
52 52 #include <v3270/trace.h>
  53 + #include <v3270/dialogs.h>
53 54 #include <internals.h>
54 55  
55 56 #if defined( HAVE_SYSLOG )
... ... @@ -443,23 +444,14 @@
443 444  
444 445 if(error)
445 446 {
446   - GtkWidget *popup =
447   - gtk_message_dialog_new_with_markup(
448   - GTK_WINDOW(gtk_widget_get_toplevel(widget)),
449   - GTK_DIALOG_MODAL|GTK_DIALOG_DESTROY_WITH_PARENT,
450   - GTK_MESSAGE_ERROR,
451   - GTK_BUTTONS_CLOSE,
452   - _( "Can't save %s" ),
453   - filename
454   - );
455   -
456   - gtk_window_set_title(GTK_WINDOW(popup),_("Can't save file"));
457   -
458   - gtk_message_dialog_format_secondary_markup(GTK_MESSAGE_DIALOG(popup),"%s",error->message);
459   - g_error_free(error);
  447 + v3270_popup_gerror(
  448 + widget,
  449 + error,
  450 + NULL,
  451 + _( "Can't save %s" ), filename
  452 + );
460 453  
461   - gtk_dialog_run(GTK_DIALOG(popup));
462   - gtk_widget_destroy(popup);
  454 + g_error_free(error);
463 455  
464 456 }
465 457  
... ...
v3270.cbp
... ... @@ -60,6 +60,9 @@
60 60 <Unit filename="src/dialogs/linux/select.c">
61 61 <Option compilerVar="CC" />
62 62 </Unit>
  63 + <Unit filename="src/dialogs/pastefile.c">
  64 + <Option compilerVar="CC" />
  65 + </Unit>
63 66 <Unit filename="src/dialogs/popups.c">
64 67 <Option compilerVar="CC" />
65 68 </Unit>
... ...