2 * Copyright 2008 Department of Mathematical Sciences, New Mexico State University
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * DEPARTMENT OF MATHEMATICAL SCIENCES OR NEW MEXICO STATE UNIVERSITY BE
18 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
19 * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
20 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 #include <freetype/freetype.h>
26 #include "grayswatch.h"
28 static GtkWidget *pref_dialog;
29 static GtkWidget *pref_unicode;
30 static GtkWidget *pref_adobe;
31 static GtkWidget *pref_cursor_font;
32 static GtkWidget *pref_apply;
34 static GtkWidget *pref_fsel_dialog;
35 static gboolean pref_fsel_unicode;
37 static GtkWidget *pref_color;
38 static GtkWidget *pref_color_dialog;
39 static GtkWidget *pref_color_win[16];
41 static gbdfed_options_t tmp_opts;
44 pref_toggle(GtkWidget *w, gpointer data)
49 which = GPOINTER_TO_INT(data);
51 val = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(w));
54 case 0: tmp_opts.backups = val; break;
55 case 1: tmp_opts.font_opts.correct_metrics = val; break;
56 case 2: tmp_opts.font_opts.pad_cells = val; break;
57 case 3: tmp_opts.font_opts.keep_unencoded = val; break;
58 case 4: tmp_opts.font_opts.keep_comments = val; break;
61 tmp_opts.font_opts.otf_flags &= ~FT_LOAD_NO_HINTING;
63 tmp_opts.font_opts.otf_flags |= FT_LOAD_NO_HINTING;
65 case 6: tmp_opts.sbit = val; break;
67 tmp_opts.show_cap_height = val;
70 tmp_opts.show_x_height = val;
74 * Toggle the Really Exit dialog.
76 tmp_opts.really_exit = val;
79 tmp_opts.pixel_size = (unsigned int)
80 gtk_combo_box_get_active(GTK_COMBO_BOX(w)) + 2;
85 * Enable the Apply button.
87 gtk_widget_set_sensitive(pref_apply, TRUE);
91 pref_eol(GtkWidget *w, gpointer data)
93 tmp_opts.font_opts.eol = gtk_combo_box_get_active(GTK_COMBO_BOX(w)) + 1;
96 * Enable the Apply button.
98 gtk_widget_set_sensitive(pref_apply, TRUE);
102 pref_make_general_page()
104 GtkWidget *table, *button, *hbox, *tmp, *omenu, *frame, *vbox;
106 vbox = gtk_vbox_new(FALSE, 10);
109 * Create the load/save option selection.
111 frame = gtk_frame_new("Load/Save");
112 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
114 table = gtk_table_new(2, 3, FALSE);
116 button = gtk_check_button_new_with_label("Make Backups");
117 if (tmp_opts.backups)
118 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
119 (void) g_signal_connect(G_OBJECT(button), "toggled",
120 G_CALLBACK(pref_toggle),
122 gtk_table_attach(GTK_TABLE(table), button, 0, 1, 0, 1,
123 GTK_FILL|GTK_EXPAND, GTK_FILL, 5, 5);
125 button = gtk_check_button_new_with_label("Correct Metrics");
126 if (tmp_opts.font_opts.correct_metrics)
127 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
128 (void) g_signal_connect(G_OBJECT(button), "toggled",
129 G_CALLBACK(pref_toggle),
131 gtk_table_attach(GTK_TABLE(table), button, 1, 2, 0, 1,
132 GTK_FILL|GTK_EXPAND, GTK_FILL, 5, 5);
134 button = gtk_check_button_new_with_label("Pad Character Cells");
135 if (tmp_opts.font_opts.pad_cells)
136 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
137 (void) g_signal_connect(G_OBJECT(button), "toggled",
138 G_CALLBACK(pref_toggle),
140 gtk_table_attach(GTK_TABLE(table), button, 2, 3, 0, 1,
141 GTK_FILL|GTK_EXPAND, GTK_FILL, 5, 5);
143 button = gtk_check_button_new_with_label("Keep Unencoded Glyphs");
144 if (tmp_opts.font_opts.keep_unencoded)
145 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
146 (void) g_signal_connect(G_OBJECT(button), "toggled",
147 G_CALLBACK(pref_toggle),
149 gtk_table_attach(GTK_TABLE(table), button, 0, 1, 1, 2,
150 GTK_FILL|GTK_EXPAND, GTK_FILL, 5, 5);
152 button = gtk_check_button_new_with_label("Keep Comments");
153 if (tmp_opts.font_opts.keep_comments)
154 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
155 (void) g_signal_connect(G_OBJECT(button), "toggled",
156 G_CALLBACK(pref_toggle),
158 gtk_table_attach(GTK_TABLE(table), button, 1, 2, 1, 2,
159 GTK_FILL|GTK_EXPAND, GTK_FILL, 5, 5);
161 hbox = gtk_hbox_new(FALSE, 0);
162 tmp = gtk_label_new("EOL:");
163 gtk_box_pack_start(GTK_BOX(hbox), tmp, FALSE, FALSE, 0);
165 omenu = gtk_combo_box_new_text();
166 gtk_combo_box_append_text(GTK_COMBO_BOX(omenu), "Unix [LF]");
167 gtk_combo_box_append_text(GTK_COMBO_BOX(omenu), "WIN/DOS [CRLF]");
168 gtk_combo_box_append_text(GTK_COMBO_BOX(omenu), "MAC [CR]");
169 gtk_combo_box_set_active(GTK_COMBO_BOX(omenu), tmp_opts.font_opts.eol - 1);
170 (void) g_signal_connect(G_OBJECT(omenu), "changed",
171 G_CALLBACK(pref_eol), 0);
173 gtk_box_pack_start(GTK_BOX(hbox), omenu, TRUE, TRUE, 0);
175 gtk_table_attach(GTK_TABLE(table), hbox, 2, 3, 1, 2,
176 GTK_FILL|GTK_EXPAND, GTK_FILL, 5, 5);
178 gtk_container_add(GTK_CONTAINER(frame), table);
180 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
182 frame = gtk_frame_new("OpenType");
183 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
185 button = gtk_check_button_new_with_label("Hint Glyphs");
186 if (!(tmp_opts.font_opts.otf_flags & FT_LOAD_NO_HINTING))
187 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
189 (void) g_signal_connect(G_OBJECT(button), "toggled",
190 G_CALLBACK(pref_toggle),
194 * No Freetype support means no point in being able to toggle this
197 gtk_widget_set_sensitive(button, FALSE);
199 gtk_container_add(GTK_CONTAINER(frame), button);
201 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
203 frame = gtk_frame_new("SBIT");
204 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
206 button = gtk_check_button_new_with_label("Generate SBIT Metrics File");
208 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
209 (void) g_signal_connect(G_OBJECT(button), "toggled",
210 G_CALLBACK(pref_toggle),
212 gtk_container_add(GTK_CONTAINER(frame), button);
214 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
220 pref_change_size(GtkWidget *w, gpointer data)
222 gint v, which = GPOINTER_TO_INT(data);
224 v = (gint) gtk_spin_button_get_value(GTK_SPIN_BUTTON(w));
227 case 0: tmp_opts.font_opts.point_size = (int) v; break;
228 case 1: tmp_opts.font_opts.resolution_x = (int) v; break;
229 case 2: tmp_opts.font_opts.resolution_y = (int) v; break;
233 * Enable the apply button.
235 gtk_widget_set_sensitive(pref_apply, TRUE);
239 * Synchronize the vertical resolution with the horizontal resolution.
242 pref_sync_res(GtkWidget *w, GdkEventFocus *ev, gpointer data)
247 b = GTK_SPIN_BUTTON(data);
248 v = (gfloat) gtk_spin_button_get_value(b);
250 if (v != (gfloat) gtk_spin_button_get_value(GTK_SPIN_BUTTON(w))) {
251 gtk_spin_button_set_value(GTK_SPIN_BUTTON(w), v);
254 * Enable the apply button.
256 gtk_widget_set_sensitive(pref_apply, TRUE);
261 pref_set_spacing(GtkWidget *w, gpointer data)
263 tmp_opts.font_opts.font_spacing = GPOINTER_TO_INT(data);
266 * Enable the apply button.
268 gtk_widget_set_sensitive(pref_apply, TRUE);
272 pref_set_cursor_font(GtkWidget *w, gpointer data)
274 tmp_opts.font_opts.cursor_font =
275 gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(w));
278 * Enable the apply button.
280 gtk_widget_set_sensitive(pref_apply, TRUE);
284 pref_color_response(GtkDialog *d, gint response, gpointer data)
288 if (response == GTK_RESPONSE_REJECT) {
290 * Replace the colors with those found in the original
293 memcpy(&tmp_opts.colors, &options.colors,
294 sizeof(unsigned short) * 20);
296 if (tmp_opts.font_opts.bits_per_pixel == 2) {
297 for (i = 0; i < 4; i++)
298 grayswatch_set_gray(GRAYSWATCH(pref_color_win[i]),
301 for (i = 0; i < 16; i++)
302 grayswatch_set_gray(GRAYSWATCH(pref_color_win[i]),
303 tmp_opts.colors[i + 4]);
305 } else if (response == GTK_RESPONSE_CLOSE)
306 gtk_widget_hide(GTK_WIDGET(data));
310 pref_color_update_color(GtkWidget *w, gint color, gpointer data)
312 gint which = GPOINTER_TO_INT(data);
314 if (tmp_opts.font_opts.bits_per_pixel == 2)
315 tmp_opts.colors[which] = color;
316 else if (tmp_opts.font_opts.bits_per_pixel == 4)
317 tmp_opts.colors[which + 4] = color;
320 * Make sure the Apply button is enabled.
322 gtk_widget_set_sensitive(pref_apply, TRUE);
326 pref_select_colors(GtkWidget *w, gpointer data)
331 if (pref_color_dialog == 0) {
333 pref_color_dialog = gtk_dialog_new();
334 (void) g_signal_connect(G_OBJECT(pref_color_dialog), "delete_event",
335 G_CALLBACK(gtk_widget_hide), 0);
336 (void) g_signal_connect(G_OBJECT(pref_color_dialog), "response",
337 G_CALLBACK(pref_color_response),
338 (gpointer) pref_color_dialog);
339 gtk_window_set_resizable(GTK_WINDOW(pref_color_dialog), TRUE);
341 hbox = gtk_hbox_new(FALSE, 0);
343 for (i = 0; i < 16; i++) {
344 pref_color_win[i] = grayswatch_new(tmp_opts.colors[i + 4]);
345 g_signal_connect(G_OBJECT(pref_color_win[i]), "value-changed",
346 G_CALLBACK(pref_color_update_color),
348 gtk_widget_set_size_request(pref_color_win[i], 50, 75);
349 gtk_box_pack_start(GTK_BOX(hbox), pref_color_win[i],
353 gtk_container_add(GTK_CONTAINER(GTK_DIALOG(pref_color_dialog)->vbox),
359 gtk_dialog_add_buttons(GTK_DIALOG(pref_color_dialog),
360 GTK_STOCK_REVERT_TO_SAVED,
363 GTK_RESPONSE_CLOSE, NULL);
365 gtk_dialog_set_default_response(GTK_DIALOG(pref_color_dialog),
368 gtk_widget_show_all(pref_color_dialog);
372 * If selecting colors for 2 bits-per-pixel, hide all but the first 4.
373 * Set the first 4 colors depending on the bits-per-pixel value.
375 for (i = 0; i < 16; i++) {
377 * We don't want setting the gray values to trigger the signal.
378 * That causes the Apply button to be made sensitive.
380 grayswatch_block_signal(GRAYSWATCH(pref_color_win[i]), TRUE);
381 if (tmp_opts.font_opts.bits_per_pixel == 2 && i >= 4)
382 gtk_widget_hide(pref_color_win[i]);
385 if (tmp_opts.font_opts.bits_per_pixel == 2)
386 grayswatch_set_gray(GRAYSWATCH(pref_color_win[i]),
389 grayswatch_set_gray(GRAYSWATCH(pref_color_win[i]),
390 tmp_opts.colors[i + 4]);
392 gtk_widget_show(pref_color_win[i]);
394 grayswatch_block_signal(GRAYSWATCH(pref_color_win[i]), FALSE);
398 * Center the dialog and show it.
400 guiutil_show_dialog_centered(pref_color_dialog, pref_dialog);
404 pref_set_bpp(GtkWidget *w, gpointer data)
408 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(w)) == FALSE)
411 tmp_opts.font_opts.bits_per_pixel = GPOINTER_TO_INT(data);
412 on = (tmp_opts.font_opts.bits_per_pixel == 1 ||
413 tmp_opts.font_opts.bits_per_pixel == 8) ? FALSE : TRUE;
415 if (pref_color_dialog != 0 && GTK_WIDGET_VISIBLE(pref_color_dialog)) {
416 if (tmp_opts.font_opts.bits_per_pixel == 1 ||
417 tmp_opts.font_opts.bits_per_pixel == 8)
418 gtk_widget_hide(pref_color_dialog);
420 pref_select_colors(w, data);
423 gtk_widget_set_sensitive(pref_color, on);
426 * Enable the apply button.
428 gtk_widget_set_sensitive(pref_apply, TRUE);
432 pref_make_newfont_page()
434 GtkWidget *label, *table, *button, *hbox, *vbox, *frame, *tmp;
437 vbox = gtk_vbox_new(FALSE, 10);
440 * Create the font size selection.
442 frame = gtk_frame_new("Font Size");
443 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
445 table = gtk_table_new(3, 2, FALSE);
447 label = gtk_label_new("Point Size:");
448 gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
449 gtk_table_attach(GTK_TABLE(table), label, 0, 1, 0, 1,
450 GTK_FILL, GTK_FILL, 5, 0);
452 label = gtk_label_new("Horizontal Resolution:");
453 gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
454 gtk_table_attach(GTK_TABLE(table), label, 0, 1, 1, 2,
455 GTK_FILL, GTK_FILL, 5, 5);
457 label = gtk_label_new("Vertical Resolution:");
458 gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
459 gtk_table_attach(GTK_TABLE(table), label, 0, 1, 2, 3,
460 GTK_FILL, GTK_FILL, 5, 5);
463 * Make the spinboxes for the point size and resolutions.
465 adj = (GtkAdjustment *) gtk_adjustment_new(0.0, 4.0, 256.0, 1.0, 2.0, 0.0);
466 button = gtk_spin_button_new(adj, 1.0, 0);
467 gtk_spin_button_set_numeric(GTK_SPIN_BUTTON(button), TRUE);
468 gtk_spin_button_set_value(GTK_SPIN_BUTTON(button),
469 (gfloat) tmp_opts.font_opts.point_size);
470 gtk_widget_set_size_request(button, 100, -1);
471 (void) g_signal_connect(G_OBJECT(button), "changed",
472 G_CALLBACK(pref_change_size),
474 gtk_table_attach(GTK_TABLE(table), button, 1, 2, 0, 1,
475 GTK_FILL, GTK_FILL, 5, 5);
477 adj = (GtkAdjustment *) gtk_adjustment_new(0.0, 20.0, 1200.0,
479 tmp = button = gtk_spin_button_new(adj, 1.0, 0);
480 gtk_spin_button_set_numeric(GTK_SPIN_BUTTON(button), TRUE);
481 gtk_spin_button_set_value(GTK_SPIN_BUTTON(button),
482 (gfloat) tmp_opts.font_opts.resolution_x);
483 gtk_widget_set_size_request(button, 100, -1);
484 (void) g_signal_connect(G_OBJECT(button), "changed",
485 G_CALLBACK(pref_change_size),
487 gtk_table_attach(GTK_TABLE(table), button, 1, 2, 1, 2,
488 GTK_FILL, GTK_FILL, 5, 5);
490 adj = (GtkAdjustment *) gtk_adjustment_new(0.0, 20.0, 1200.0,
492 button = gtk_spin_button_new(adj, 1.0, 0);
493 gtk_spin_button_set_numeric(GTK_SPIN_BUTTON(button), TRUE);
494 gtk_spin_button_set_value(GTK_SPIN_BUTTON(button),
495 (gfloat) tmp_opts.font_opts.resolution_y);
496 gtk_widget_set_size_request(button, 100, -1);
497 (void) g_signal_connect(G_OBJECT(button), "changed",
498 G_CALLBACK(pref_change_size),
500 (void) g_signal_connect(G_OBJECT(button), "focus-in-event",
501 G_CALLBACK(pref_sync_res), (gpointer) tmp);
502 gtk_table_attach(GTK_TABLE(table), button, 1, 2, 2, 3,
503 GTK_FILL, GTK_FILL, 5, 5);
505 gtk_container_add(GTK_CONTAINER(frame), table);
507 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
510 * Create the spacing selection.
512 frame = gtk_frame_new("Spacing");
513 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
515 hbox = gtk_hbox_new(FALSE, 0);
517 button = gtk_radio_button_new_with_label(0, "Proportional");
518 if (tmp_opts.font_opts.font_spacing == BDF_PROPORTIONAL)
519 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
521 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), FALSE);
522 (void) g_signal_connect(G_OBJECT(button), "toggled",
523 G_CALLBACK(pref_set_spacing),
524 GINT_TO_POINTER(BDF_PROPORTIONAL));
525 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 5);
528 gtk_radio_button_new_with_label_from_widget(GTK_RADIO_BUTTON(button),
530 if (tmp_opts.font_opts.font_spacing == BDF_MONOWIDTH)
531 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
533 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), FALSE);
534 (void) g_signal_connect(G_OBJECT(button), "toggled",
535 G_CALLBACK(pref_set_spacing),
536 GINT_TO_POINTER(BDF_MONOWIDTH));
537 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 5);
540 gtk_radio_button_new_with_label_from_widget(GTK_RADIO_BUTTON(button),
542 if (tmp_opts.font_opts.font_spacing == BDF_CHARCELL)
543 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
545 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), FALSE);
546 (void) g_signal_connect(G_OBJECT(button), "toggled",
547 G_CALLBACK(pref_set_spacing),
548 GINT_TO_POINTER(BDF_CHARCELL));
549 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0);
551 gtk_container_add(GTK_CONTAINER(frame), hbox);
553 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
556 * Create the bits-per-pixel selection.
558 frame = gtk_frame_new("Bits Per Pixel");
559 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
561 hbox = gtk_hbox_new(FALSE, 0);
563 button = gtk_radio_button_new_with_label(0, "1 bpp");
564 if (tmp_opts.font_opts.bits_per_pixel == 1)
565 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
567 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), FALSE);
568 (void) g_signal_connect(G_OBJECT(button), "toggled",
569 G_CALLBACK(pref_set_bpp),
571 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 5);
574 gtk_radio_button_new_with_label_from_widget(GTK_RADIO_BUTTON(button),
576 if (tmp_opts.font_opts.bits_per_pixel == 2)
577 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
579 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), FALSE);
580 (void) g_signal_connect(G_OBJECT(button), "toggled",
581 G_CALLBACK(pref_set_bpp),
583 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 5);
586 gtk_radio_button_new_with_label_from_widget(GTK_RADIO_BUTTON(button),
588 if (tmp_opts.font_opts.bits_per_pixel == 4)
589 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
591 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), FALSE);
592 (void) g_signal_connect(G_OBJECT(button), "toggled",
593 G_CALLBACK(pref_set_bpp),
595 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 5);
598 gtk_radio_button_new_with_label_from_widget(GTK_RADIO_BUTTON(button),
600 if (tmp_opts.font_opts.bits_per_pixel == 8)
601 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
603 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), FALSE);
604 (void) g_signal_connect(G_OBJECT(button), "toggled",
605 G_CALLBACK(pref_set_bpp),
607 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 5);
609 pref_color = gtk_button_new_with_label("Select Colors");
610 (void) g_signal_connect(G_OBJECT(pref_color), "clicked",
611 G_CALLBACK(pref_select_colors), 0);
612 if (tmp_opts.font_opts.bits_per_pixel == 1)
613 gtk_widget_set_sensitive(pref_color, FALSE);
615 gtk_box_pack_start(GTK_BOX(hbox), pref_color, FALSE, FALSE, 0);
617 gtk_container_add(GTK_CONTAINER(frame), hbox);
619 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
621 frame = gtk_frame_new("Cursor Fonts");
622 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
624 pref_cursor_font = gtk_check_button_new_with_label("Cursor Font");
625 if (tmp_opts.font_opts.cursor_font)
626 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(pref_cursor_font),
628 (void) g_signal_connect(G_OBJECT(pref_cursor_font), "toggled",
629 G_CALLBACK(pref_set_cursor_font), 0);
630 gtk_container_add(GTK_CONTAINER(frame), pref_cursor_font);
631 gtk_widget_set_sensitive(pref_cursor_font, FALSE);
633 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
639 pref_fgrid_mode(GtkWidget *w, gpointer data)
641 tmp_opts.overwrite_mode =
642 gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(w));
645 * Enable the Apply button.
647 gtk_widget_set_sensitive(pref_apply, TRUE);
651 pref_set_filename(GtkWidget *w, gpointer data)
656 fname = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(w));
658 if (pref_fsel_unicode)
659 gtk_entry_set_text(GTK_ENTRY(pref_unicode), fname);
661 gtk_entry_set_text(GTK_ENTRY(pref_adobe), fname);
664 * Enable the Apply button.
666 gtk_widget_set_sensitive(pref_apply, TRUE);
675 handle_filename_response(GtkDialog *d, gint response, gpointer data)
678 case GTK_RESPONSE_ACCEPT:
679 pref_set_filename(GTK_WIDGET(d), data);
681 case GTK_RESPONSE_CANCEL:
682 gtk_widget_hide(GTK_WIDGET(d));
688 pref_show_fsel_dialog(GtkWidget *w, gpointer data)
690 pref_fsel_unicode = GPOINTER_TO_INT(data);
692 if (pref_fsel_dialog == 0) {
693 pref_fsel_dialog = gtk_file_chooser_dialog_new("Glyph Name",
694 GTK_WINDOW(pref_dialog),
695 GTK_FILE_CHOOSER_ACTION_OPEN,
701 (void) g_signal_connect(G_OBJECT(pref_fsel_dialog), "delete_event",
702 G_CALLBACK(gtk_widget_hide), 0);
704 (void) g_signal_connect(G_OBJECT(pref_fsel_dialog), "response",
705 G_CALLBACK(handle_filename_response),
710 * Set the title of the dialog.
712 if (pref_fsel_unicode)
713 strcpy(buffer1, "Unicode Character Database Selection");
715 strcpy(buffer1, "Adobe Glyph Name File Selection");
717 gtk_window_set_title(GTK_WINDOW(pref_fsel_dialog), buffer1);
719 guiutil_show_dialog_centered(pref_fsel_dialog, pref_dialog);
721 gtk_window_set_modal(GTK_WINDOW(pref_fsel_dialog), TRUE);
725 pref_make_edit_page()
728 GtkWidget *vbox, *hbox, *frame, *button, *label, *omenu;
729 GtkWidget *tmp, *table;
731 vbox = gtk_vbox_new(FALSE, 10);
733 frame = gtk_frame_new("Font Grid Selection Paste");
734 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
736 hbox = gtk_hbox_new(FALSE, 5);
738 button = gtk_radio_button_new_with_label(0, "Overwrites");
739 if (tmp_opts.overwrite_mode)
740 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
742 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), FALSE);
743 (void) g_signal_connect(G_OBJECT(button), "toggled",
744 G_CALLBACK(pref_fgrid_mode), 0);
745 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0);
748 gtk_radio_button_new_with_label_from_widget(GTK_RADIO_BUTTON(button),
750 if (tmp_opts.overwrite_mode)
751 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), FALSE);
753 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
754 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 0);
756 gtk_container_add(GTK_CONTAINER(frame), hbox);
758 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
760 frame = gtk_frame_new("Glyph Editors");
761 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
763 hbox = gtk_hbox_new(FALSE, 5);
765 button = gtk_check_button_new_with_label("Show Cap Height");
766 if (tmp_opts.show_cap_height)
767 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
768 (void) g_signal_connect(G_OBJECT(button), "toggled",
769 G_CALLBACK(pref_toggle),
771 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 5);
773 button = gtk_check_button_new_with_label("Show X Height");
774 if (tmp_opts.show_cap_height)
775 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
776 (void) g_signal_connect(G_OBJECT(button), "toggled",
777 G_CALLBACK(pref_toggle),
779 gtk_box_pack_start(GTK_BOX(hbox), button, FALSE, FALSE, 5);
781 label = gtk_label_new("Pixel Size:");
782 gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
783 gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
785 omenu = gtk_combo_box_new_text();
786 for (i = 2; i < 21; i++) {
787 sprintf(buffer1, "%dx%d", i, i);
788 gtk_combo_box_append_text(GTK_COMBO_BOX(omenu), buffer1);
790 gtk_combo_box_set_active(GTK_COMBO_BOX(omenu), tmp_opts.pixel_size - 2);
791 g_signal_connect(G_OBJECT(omenu), "changed",
792 G_CALLBACK(pref_toggle), GINT_TO_POINTER(10));
794 gtk_box_pack_start(GTK_BOX(hbox), omenu, TRUE, TRUE, 0);
796 gtk_container_add(GTK_CONTAINER(frame), hbox);
798 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
800 frame = gtk_frame_new("Glyph Name Lists");
801 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
803 table = gtk_table_new(2, 3, FALSE);
805 label = gtk_label_new("Unicode Character Database:");
806 gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
807 gtk_table_attach(GTK_TABLE(table), label, 0, 1, 0, 1,
808 GTK_FILL, GTK_FILL, 5, 5);
810 label = gtk_label_new("Adobe Glyph List:");
811 gtk_misc_set_alignment(GTK_MISC(label), 1.0, 0.5);
812 gtk_table_attach(GTK_TABLE(table), label, 0, 1, 1, 2,
813 GTK_FILL, GTK_FILL, 5, 5);
818 tmp = pref_unicode = gtk_entry_new();
819 gtk_widget_set_size_request(tmp, 250, -1);
820 if (tmp_opts.unicode_name_file)
821 gtk_entry_set_text(GTK_ENTRY(pref_unicode), tmp_opts.unicode_name_file);
822 gtk_table_attach(GTK_TABLE(table), tmp, 1, 2, 0, 1,
823 GTK_FILL|GTK_EXPAND, GTK_FILL, 0, 5);
825 tmp = pref_adobe = gtk_entry_new();
826 gtk_widget_set_size_request(tmp, 250, -1);
827 if (tmp_opts.adobe_name_file)
828 gtk_entry_set_text(GTK_ENTRY(pref_adobe), tmp_opts.adobe_name_file);
829 gtk_table_attach(GTK_TABLE(table), tmp, 1, 2, 1, 2,
830 GTK_FILL|GTK_EXPAND, GTK_FILL, 0, 5);
833 * Add the browse buttons.
835 button = gtk_button_new_with_label("Browse");
836 (void) g_signal_connect(G_OBJECT(button), "clicked",
837 G_CALLBACK(pref_show_fsel_dialog),
838 GINT_TO_POINTER(TRUE));
839 gtk_table_attach(GTK_TABLE(table), button, 2, 3, 0, 1,
841 button = gtk_button_new_with_label("Browse");
842 (void) g_signal_connect(G_OBJECT(button), "clicked",
843 G_CALLBACK(pref_show_fsel_dialog),
844 GINT_TO_POINTER(FALSE));
845 gtk_table_attach(GTK_TABLE(table), button, 2, 3, 1, 2,
848 gtk_container_add(GTK_CONTAINER(frame), table);
850 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
856 pref_make_other_page()
858 GtkWidget *frame, *button, *vbox;
860 frame = gtk_frame_new("Dialogs");
861 gtk_frame_set_shadow_type(GTK_FRAME(frame), GTK_SHADOW_ETCHED_IN);
863 vbox = gtk_vbox_new(FALSE, 0);
865 button = gtk_check_button_new_with_label("Show \"Really Exit\" Dialog");
866 if (tmp_opts.really_exit)
867 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(button), TRUE);
868 (void) g_signal_connect(G_OBJECT(button), "toggled",
869 G_CALLBACK(pref_toggle),
870 GUINT_TO_POINTER(9));
871 gtk_container_add(GTK_CONTAINER(frame), button);
872 gtk_box_pack_start(GTK_BOX(vbox), frame, FALSE, FALSE, 0);
878 pref_apply_changes(void)
883 * Take care of setting the file names for the glyph name lists.
885 fname = (gchar *) gtk_entry_get_text(GTK_ENTRY(pref_unicode));
886 if (fname != 0 && fname[0] != 0)
887 tmp_opts.unicode_name_file = g_strdup(fname);
889 fname = (gchar *) gtk_entry_get_text(GTK_ENTRY(pref_adobe));
890 if (fname != 0 && fname[0] != 0)
891 tmp_opts.adobe_name_file = g_strdup(fname);
894 * If the name files are different, delete the old name files first.
896 if (options.unicode_name_file != 0 &&
897 options.unicode_name_file != tmp_opts.unicode_name_file)
898 g_free(options.unicode_name_file);
899 if (options.adobe_name_file != 0 &&
900 options.adobe_name_file != tmp_opts.adobe_name_file)
901 g_free(options.adobe_name_file);
904 * Copy the updated options over.
906 (void) memcpy((char *) &options, (char *) &tmp_opts,
907 sizeof(gbdfed_options_t));
910 * Set the glyph edit options.
912 guigedit_show_cap_height(tmp_opts.show_cap_height);
913 guigedit_show_x_height(tmp_opts.show_x_height);
914 guigedit_set_pixel_size(tmp_opts.pixel_size);
917 * Disable the apply button.
919 gtk_widget_set_sensitive(pref_apply, FALSE);
930 * If any changes were made, do an update before saving.
932 if (GTK_WIDGET_SENSITIVE(pref_apply))
933 pref_apply_changes();
935 if ((home = getenv("HOME")) == 0) {
936 guiutil_error_message(editors[0].shell,
937 "Save Preferences: Unable to locate home directory.");
941 sprintf(buffer1, "%s/.gbdfedrc", home);
942 if ((out = fopen(buffer1, "w")) == 0) {
943 sprintf(buffer2, "Save Preferences: Unable to write to %s.", buffer1);
944 guiutil_error_message(editors[0].shell, buffer2);
949 * First, write the gbdfed options.
951 fprintf(out, "#########################\n");
952 fprintf(out, "#\n# gbdfed options.\n#\n");
953 fprintf(out, "#########################\n\n");
955 if (options.no_blanks)
956 fprintf(out, "skip_blank_pages true\n\n");
958 fprintf(out, "skip_blank_pages false\n\n");
960 if (options.really_exit)
961 fprintf(out, "really_exit true\n\n");
963 fprintf(out, "really_exit false\n\n");
964 if (options.overwrite_mode)
965 fprintf(out, "grid_overwrite_mode true\n\n");
967 fprintf(out, "grid_overwrite_mode false\n\n");
969 if (options.accelerator != 0)
970 fprintf(out, "close_accelerator %s\n\n",
971 options.accelerator);
972 if (options.accelerator_text != 0)
973 fprintf(out, "close_accelerator_text %s\n\n",
974 options.accelerator_text);
976 if (options.unicode_name_file != 0)
977 fprintf(out, "name_file %s\n\n", options.unicode_name_file);
979 if (options.adobe_name_file != 0)
980 fprintf(out, "adobe_name_file %s\n\n",
981 options.adobe_name_file);
983 fprintf(out, "pixel_size %d\n\n", options.pixel_size);
985 if (options.show_cap_height)
986 fprintf(out, "show_cap_height true\n\n");
988 fprintf(out, "show_cap_height false\n\n");
990 if (options.show_x_height)
991 fprintf(out, "show_x_height true\n\n");
993 fprintf(out, "show_x_height false\n\n");
996 fprintf(out, "generate_sbit_metrics true\n\n");
998 fprintf(out, "generate_sbit_metrics false\n\n");
1001 * Save the grayscales.
1003 fprintf(out, "#\n# Grayscale values. Must be between 0 and 255.\n#\n");
1004 fprintf(out, "2bpp_grays ");
1005 for (i = 0; i < 4; i++) {
1006 fprintf(out, "%d", options.colors[i]);
1010 fprintf(out, "\n4bpp_grays ");
1011 for (i = 4; i < 20; i++) {
1012 fprintf(out, "%d", options.colors[i]);
1016 fprintf(out, "\n\n");
1022 fprintf(out, "#\n# Color values for 2 bits per pixel.\n#\n");
1023 for (i = 0; i < 4; i++) {
1025 * Do this to avoid writing negative values.
1027 c = options.colors[i];
1028 fprintf(out, "color%d %d\n", i, c);
1031 fprintf(out, "\n#\n# Color values for 4 bits per pixel.\n#\n");
1032 for (i = 4; i < 20; i++) {
1034 * Do this to avoid writing negative values.
1036 c = options.colors[i];
1037 fprintf(out, "color%d %d\n", i, c);
1043 * The save the BDF specific options.
1045 fprintf(out, "#########################\n");
1046 fprintf(out, "#\n# BDF font options.\n#\n");
1047 fprintf(out, "#########################\n\n");
1048 bdf_save_options(out, &options.font_opts);
1053 pref_response(GtkDialog *d, gint response, gpointer data)
1055 if (response == GTK_RESPONSE_APPLY)
1056 pref_apply_changes();
1057 else if (response == GTK_RESPONSE_OK)
1061 * Make sure the color chooser dialog is hidden if it
1064 if (pref_color_dialog != 0 && GTK_WIDGET_VISIBLE(pref_color_dialog))
1065 gtk_widget_hide(pref_color_dialog);
1067 gtk_widget_hide(GTK_WIDGET(d));
1072 guiedit_show_preferences(GtkWidget *w, gpointer data)
1074 GtkWidget *dvbox, *nb, *button, *table, *label;
1076 if (pref_dialog == 0) {
1078 * Initialize the temporary options.
1080 (void) memcpy((char *) &tmp_opts, (char *) &options,
1081 sizeof(gbdfed_options_t));
1083 pref_dialog = gtk_dialog_new();
1084 (void) g_signal_connect(G_OBJECT(pref_dialog), "delete_event",
1085 G_CALLBACK(gtk_widget_hide), 0);
1087 sprintf(buffer1, "%s Preferences", g_get_prgname());
1088 gtk_window_set_title(GTK_WINDOW(pref_dialog), buffer1);
1090 dvbox = GTK_DIALOG(pref_dialog)->vbox;
1093 * Create the notebook that will contain the Preference tabs.
1095 nb = gtk_notebook_new();
1098 * Create the General Options page.
1100 label = gtk_label_new("General Options");
1101 table = pref_make_general_page();
1102 gtk_notebook_append_page(GTK_NOTEBOOK(nb), table, label);
1105 * Create the New Font Options page.
1107 label = gtk_label_new("New Font Options");
1108 table = pref_make_newfont_page();
1109 gtk_notebook_append_page(GTK_NOTEBOOK(nb), table, label);
1112 * Create the Editing Options page.
1114 label = gtk_label_new("Editing Options");
1115 table = pref_make_edit_page();
1116 gtk_notebook_append_page(GTK_NOTEBOOK(nb), table, label);
1119 * Create the Other Options page.
1121 label = gtk_label_new("Other Options");
1122 table = pref_make_other_page();
1123 gtk_notebook_append_page(GTK_NOTEBOOK(nb), table, label);
1126 * Finally, add the notebook to the dialog's vbox.
1128 gtk_container_add(GTK_CONTAINER(dvbox), nb);
1131 * Add the buttons at the bottom.
1133 pref_apply = gtk_dialog_add_button(GTK_DIALOG(pref_dialog),
1135 GTK_RESPONSE_APPLY);
1136 gtk_widget_set_sensitive(pref_apply, FALSE);
1138 button = gtk_dialog_add_button(GTK_DIALOG(pref_dialog),
1142 button = gtk_dialog_add_button(GTK_DIALOG(pref_dialog),
1144 GTK_RESPONSE_CLOSE);
1145 gtk_dialog_set_default_response(GTK_DIALOG(pref_dialog),
1146 GTK_RESPONSE_CLOSE);
1148 g_signal_connect(G_OBJECT(pref_dialog), "response",
1149 G_CALLBACK(pref_response), 0);
1151 gtk_widget_show_all(dvbox);
1154 guiutil_show_dialog_centered(pref_dialog, editors[0].shell);
1158 guiedit_preference_cleanup()
1161 * Does nothing at the moment.