]> Pileus Git - ~andy/gtk/blob - gtk/gtkfontsel.c
GtkFontSelection: move public members to private structure
[~andy/gtk] / gtk / gtkfontsel.c
1 /* GTK - The GIMP Toolkit
2  * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
3  *
4  * Massively updated for Pango by Owen Taylor, May 2000
5  * GtkFontSelection widget for Gtk+, by Damon Chaplin, May 1998.
6  * Based on the GnomeFontSelector widget, by Elliot Lee, but major changes.
7  * The GnomeFontSelector was derived from app/text_tool.c in the GIMP.
8  *
9  * This library is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public
11  * License as published by the Free Software Foundation; either
12  * version 2 of the License, or (at your option) any later version.
13  *
14  * This library is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with this library; if not, write to the
21  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
22  * Boston, MA 02111-1307, USA.
23  */
24
25 /*
26  * Modified by the GTK+ Team and others 1997-2000.  See the AUTHORS
27  * file for a list of people on the GTK+ Team.  See the ChangeLog
28  * files for a list of changes.  These files are distributed with
29  * GTK+ at ftp://ftp.gtk.org/pub/gtk/. 
30  */
31
32 #include "config.h"
33 #include <stdlib.h>
34 #include <glib/gprintf.h>
35 #include <string.h>
36
37 #include <atk/atk.h>
38
39 #include "gdk/gdk.h"
40 #include "gdk/gdkkeysyms.h"
41
42 #include "gtkfontsel.h"
43
44 #include "gtkbutton.h"
45 #include "gtkcellrenderertext.h"
46 #include "gtkentry.h"
47 #include "gtkframe.h"
48 #include "gtkhbbox.h"
49 #include "gtkhbox.h"
50 #include "gtklabel.h"
51 #include "gtkliststore.h"
52 #include "gtkrc.h"
53 #include "gtkstock.h"
54 #include "gtktable.h"
55 #include "gtktreeselection.h"
56 #include "gtktreeview.h"
57 #include "gtkvbox.h"
58 #include "gtkscrolledwindow.h"
59 #include "gtkintl.h"
60 #include "gtkaccessible.h"
61 #include "gtkprivate.h"
62 #include "gtkbuildable.h"
63
64 struct _GtkFontSelectionPriv
65 {
66   GtkWidget *font_entry;        /* Used _get_family_entry() for consistency, -mr */
67   GtkWidget *font_style_entry;  /* Used _get_face_entry() for consistency, -mr */
68
69   GtkWidget *size_entry;
70   GtkWidget *preview_entry;
71
72   GtkWidget *family_list;
73   GtkWidget *face_list;
74   GtkWidget *size_list;
75
76   PangoFontFamily *family;      /* Current family */
77   PangoFontFace *face;          /* Current face */
78
79   gint size;
80 };
81
82
83 struct _GtkFontSelectionDialogPriv
84 {
85   GtkWidget *fontsel;
86
87   GtkWidget *ok_button;
88   GtkWidget *apply_button;
89   GtkWidget *cancel_button;
90 };
91
92
93 /* We don't enable the font and style entries because they don't add
94  * much in terms of visible effect and have a weird effect on keynav.
95  * the Windows font selector has entries similarly positioned but they
96  * act in conjunction with the associated lists to form a single focus
97  * location.
98  */
99 #undef INCLUDE_FONT_ENTRIES
100
101 /* This is the default text shown in the preview entry, though the user
102    can set it. Remember that some fonts only have capital letters. */
103 #define PREVIEW_TEXT N_("abcdefghijk ABCDEFGHIJK")
104
105 #define DEFAULT_FONT_NAME "Sans 10"
106
107 /* This is the initial and maximum height of the preview entry (it expands
108    when large font sizes are selected). Initial height is also the minimum. */
109 #define INITIAL_PREVIEW_HEIGHT 44
110 #define MAX_PREVIEW_HEIGHT 300
111
112 /* These are the sizes of the font, style & size lists. */
113 #define FONT_LIST_HEIGHT        136
114 #define FONT_LIST_WIDTH         190
115 #define FONT_STYLE_LIST_WIDTH   170
116 #define FONT_SIZE_LIST_WIDTH    60
117
118 /* These are what we use as the standard font sizes, for the size list.
119  */
120 static const guint16 font_sizes[] = {
121   6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 20, 22, 24, 26, 28,
122   32, 36, 40, 48, 56, 64, 72
123 };
124
125 enum {
126    PROP_0,
127    PROP_FONT_NAME,
128    PROP_PREVIEW_TEXT
129 };
130
131
132 enum {
133   FAMILY_COLUMN,
134   FAMILY_NAME_COLUMN
135 };
136
137 enum {
138   FACE_COLUMN,
139   FACE_NAME_COLUMN
140 };
141
142 enum {
143   SIZE_COLUMN
144 };
145
146 static void    gtk_font_selection_set_property       (GObject         *object,
147                                                       guint            prop_id,
148                                                       const GValue    *value,
149                                                       GParamSpec      *pspec);
150 static void    gtk_font_selection_get_property       (GObject         *object,
151                                                       guint            prop_id,
152                                                       GValue          *value,
153                                                       GParamSpec      *pspec);
154 static void    gtk_font_selection_finalize           (GObject         *object);
155 static void    gtk_font_selection_screen_changed     (GtkWidget       *widget,
156                                                       GdkScreen       *previous_screen);
157 static void    gtk_font_selection_style_set          (GtkWidget      *widget,
158                                                       GtkStyle       *prev_style);
159
160 /* These are the callbacks & related functions. */
161 static void     gtk_font_selection_select_font           (GtkTreeSelection *selection,
162                                                           gpointer          data);
163 static void     gtk_font_selection_show_available_fonts  (GtkFontSelection *fs);
164
165 static void     gtk_font_selection_show_available_styles (GtkFontSelection *fs);
166 static void     gtk_font_selection_select_best_style     (GtkFontSelection *fs,
167                                                           gboolean          use_first);
168 static void     gtk_font_selection_select_style          (GtkTreeSelection *selection,
169                                                           gpointer          data);
170
171 static void     gtk_font_selection_select_best_size      (GtkFontSelection *fs);
172 static void     gtk_font_selection_show_available_sizes  (GtkFontSelection *fs,
173                                                           gboolean          first_time);
174 static void     gtk_font_selection_size_activate         (GtkWidget        *w,
175                                                           gpointer          data);
176 static gboolean gtk_font_selection_size_focus_out        (GtkWidget        *w,
177                                                           GdkEventFocus    *event,
178                                                           gpointer          data);
179 static void     gtk_font_selection_select_size           (GtkTreeSelection *selection,
180                                                           gpointer          data);
181
182 static void     gtk_font_selection_scroll_on_map         (GtkWidget        *w,
183                                                           gpointer          data);
184
185 static void     gtk_font_selection_preview_changed       (GtkWidget        *entry,
186                                                           GtkFontSelection *fontsel);
187 static void     gtk_font_selection_scroll_to_selection   (GtkFontSelection *fontsel);
188
189
190 /* Misc. utility functions. */
191 static void    gtk_font_selection_load_font          (GtkFontSelection *fs);
192 static void    gtk_font_selection_update_preview     (GtkFontSelection *fs);
193
194 static PangoFontDescription *gtk_font_selection_get_font_description (GtkFontSelection *fontsel);
195 static gboolean gtk_font_selection_select_font_desc  (GtkFontSelection      *fontsel,
196                                                       PangoFontDescription  *new_desc,
197                                                       PangoFontFamily      **pfamily,
198                                                       PangoFontFace        **pface);
199 static void     gtk_font_selection_reload_fonts          (GtkFontSelection *fontsel);
200 static void     gtk_font_selection_ref_family            (GtkFontSelection *fontsel,
201                                                           PangoFontFamily  *family);
202 static void     gtk_font_selection_ref_face              (GtkFontSelection *fontsel,
203                                                           PangoFontFace    *face);
204
205 G_DEFINE_TYPE (GtkFontSelection, gtk_font_selection, GTK_TYPE_VBOX)
206
207 static void
208 gtk_font_selection_class_init (GtkFontSelectionClass *klass)
209 {
210   GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
211   GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (klass);
212
213   gobject_class->finalize = gtk_font_selection_finalize;
214   gobject_class->set_property = gtk_font_selection_set_property;
215   gobject_class->get_property = gtk_font_selection_get_property;
216
217   widget_class->screen_changed = gtk_font_selection_screen_changed;
218   widget_class->style_set = gtk_font_selection_style_set;
219    
220   g_object_class_install_property (gobject_class,
221                                    PROP_FONT_NAME,
222                                    g_param_spec_string ("font-name",
223                                                         P_("Font name"),
224                                                         P_("The string that represents this font"),
225                                                         DEFAULT_FONT_NAME,
226                                                         GTK_PARAM_READWRITE));
227   g_object_class_install_property (gobject_class,
228                                    PROP_PREVIEW_TEXT,
229                                    g_param_spec_string ("preview-text",
230                                                         P_("Preview text"),
231                                                         P_("The text to display in order to demonstrate the selected font"),
232                                                         _(PREVIEW_TEXT),
233                                                         GTK_PARAM_READWRITE));
234
235   g_type_class_add_private (klass, sizeof (GtkFontSelectionPriv));
236 }
237
238 static void 
239 gtk_font_selection_set_property (GObject         *object,
240                                  guint            prop_id,
241                                  const GValue    *value,
242                                  GParamSpec      *pspec)
243 {
244   GtkFontSelection *fontsel;
245
246   fontsel = GTK_FONT_SELECTION (object);
247
248   switch (prop_id)
249     {
250     case PROP_FONT_NAME:
251       gtk_font_selection_set_font_name (fontsel, g_value_get_string (value));
252       break;
253     case PROP_PREVIEW_TEXT:
254       gtk_font_selection_set_preview_text (fontsel, g_value_get_string (value));
255       break;
256     default:
257       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
258       break;
259     }
260 }
261
262 static void gtk_font_selection_get_property (GObject         *object,
263                                              guint            prop_id,
264                                              GValue          *value,
265                                              GParamSpec      *pspec)
266 {
267   GtkFontSelection *fontsel;
268
269   fontsel = GTK_FONT_SELECTION (object);
270
271   switch (prop_id)
272     {
273     case PROP_FONT_NAME:
274       g_value_take_string (value, gtk_font_selection_get_font_name (fontsel));
275       break;
276     case PROP_PREVIEW_TEXT:
277       g_value_set_string (value, gtk_font_selection_get_preview_text (fontsel));
278       break;
279     default:
280       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
281       break;
282     }
283 }
284
285 /* Handles key press events on the lists, so that we can trap Enter to
286  * activate the default button on our own.
287  */
288 static gboolean
289 list_row_activated (GtkWidget *widget)
290 {
291   GtkWindow *window;
292   
293   window = GTK_WINDOW (gtk_widget_get_toplevel (GTK_WIDGET (widget)));
294   if (!gtk_widget_is_toplevel (GTK_WIDGET (window)))
295     window = NULL;
296   
297   if (window
298       && widget != window->default_widget
299       && !(widget == window->focus_widget &&
300            (!window->default_widget || !gtk_widget_get_sensitive (window->default_widget))))
301     {
302       gtk_window_activate_default (window);
303     }
304   
305   return TRUE;
306 }
307
308 static void
309 gtk_font_selection_init (GtkFontSelection *fontsel)
310 {
311   GtkFontSelectionPriv *priv;
312   GtkWidget *scrolled_win;
313   GtkWidget *text_box;
314   GtkWidget *table, *label;
315   GtkWidget *font_label, *style_label;
316   GtkWidget *vbox;
317   GtkListStore *model;
318   GtkTreeViewColumn *column;
319   GList *focus_chain = NULL;
320   AtkObject *atk_obj;
321
322   fontsel->priv = G_TYPE_INSTANCE_GET_PRIVATE (fontsel,
323                                                GTK_TYPE_FONT_SELECTION,
324                                                GtkFontSelectionPriv);
325   priv = fontsel->priv;
326
327   gtk_widget_push_composite_child ();
328
329   gtk_box_set_spacing (GTK_BOX (fontsel), 12);
330   priv->size = 12 * PANGO_SCALE;
331   
332   /* Create the table of font, style & size. */
333   table = gtk_table_new (3, 3, FALSE);
334   gtk_widget_show (table);
335   gtk_table_set_row_spacings (GTK_TABLE (table), 6);
336   gtk_table_set_col_spacings (GTK_TABLE (table), 12);
337   gtk_box_pack_start (GTK_BOX (fontsel), table, TRUE, TRUE, 0);
338
339 #ifdef INCLUDE_FONT_ENTRIES
340   priv->font_entry = gtk_entry_new ();
341   gtk_editable_set_editable (GTK_EDITABLE (priv->font_entry), FALSE);
342   gtk_widget_set_size_request (priv->font_entry, 20, -1);
343   gtk_widget_show (priv->font_entry);
344   gtk_table_attach (GTK_TABLE (table), priv->font_entry, 0, 1, 1, 2,
345                     GTK_FILL, 0, 0, 0);
346   
347   priv->font_style_entry = gtk_entry_new ();
348   gtk_editable_set_editable (GTK_EDITABLE (priv->font_style_entry), FALSE);
349   gtk_widget_set_size_request (priv->font_style_entry, 20, -1);
350   gtk_widget_show (priv->font_style_entry);
351   gtk_table_attach (GTK_TABLE (table), priv->font_style_entry, 1, 2, 1, 2,
352                     GTK_FILL, 0, 0, 0);
353 #endif /* INCLUDE_FONT_ENTRIES */
354   
355   priv->size_entry = gtk_entry_new ();
356   gtk_widget_set_size_request (priv->size_entry, 20, -1);
357   gtk_widget_show (priv->size_entry);
358   gtk_table_attach (GTK_TABLE (table), priv->size_entry, 2, 3, 1, 2,
359                     GTK_FILL, 0, 0, 0);
360   g_signal_connect (priv->size_entry, "activate",
361                     G_CALLBACK (gtk_font_selection_size_activate),
362                     fontsel);
363   g_signal_connect_after (priv->size_entry, "focus-out-event",
364                           G_CALLBACK (gtk_font_selection_size_focus_out),
365                           fontsel);
366   
367   font_label = gtk_label_new_with_mnemonic (_("_Family:"));
368   gtk_misc_set_alignment (GTK_MISC (font_label), 0.0, 0.5);
369   gtk_widget_show (font_label);
370   gtk_table_attach (GTK_TABLE (table), font_label, 0, 1, 0, 1,
371                     GTK_FILL, 0, 0, 0);  
372
373   style_label = gtk_label_new_with_mnemonic (_("_Style:"));
374   gtk_misc_set_alignment (GTK_MISC (style_label), 0.0, 0.5);
375   gtk_widget_show (style_label);
376   gtk_table_attach (GTK_TABLE (table), style_label, 1, 2, 0, 1,
377                     GTK_FILL, 0, 0, 0);
378   
379   label = gtk_label_new_with_mnemonic (_("Si_ze:"));
380   gtk_label_set_mnemonic_widget (GTK_LABEL (label),
381                                  priv->size_entry);
382   gtk_misc_set_alignment (GTK_MISC (label), 0.0, 0.5);
383   gtk_widget_show (label);
384   gtk_table_attach (GTK_TABLE (table), label, 2, 3, 0, 1,
385                     GTK_FILL, 0, 0, 0);
386   
387   
388   /* Create the lists  */
389
390   model = gtk_list_store_new (2,
391                               G_TYPE_OBJECT,  /* FAMILY_COLUMN */
392                               G_TYPE_STRING); /* FAMILY_NAME_COLUMN */
393   priv->family_list = gtk_tree_view_new_with_model (GTK_TREE_MODEL (model));
394   g_object_unref (model);
395
396   g_signal_connect (priv->family_list, "row-activated",
397                     G_CALLBACK (list_row_activated), fontsel);
398
399   column = gtk_tree_view_column_new_with_attributes ("Family",
400                                                      gtk_cell_renderer_text_new (),
401                                                      "text", FAMILY_NAME_COLUMN,
402                                                      NULL);
403   gtk_tree_view_column_set_sizing (column, GTK_TREE_VIEW_COLUMN_AUTOSIZE);
404   gtk_tree_view_append_column (GTK_TREE_VIEW (priv->family_list), column);
405
406   gtk_tree_view_set_headers_visible (GTK_TREE_VIEW (priv->family_list), FALSE);
407   gtk_tree_selection_set_mode (gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->family_list)),
408                                GTK_SELECTION_BROWSE);
409   
410   gtk_label_set_mnemonic_widget (GTK_LABEL (font_label), priv->family_list);
411
412   scrolled_win = gtk_scrolled_window_new (NULL, NULL);
413   gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (scrolled_win), GTK_SHADOW_IN);
414   gtk_widget_set_size_request (scrolled_win,
415                                FONT_LIST_WIDTH, FONT_LIST_HEIGHT);
416   gtk_container_add (GTK_CONTAINER (scrolled_win), priv->family_list);
417   gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolled_win),
418                                   GTK_POLICY_AUTOMATIC, GTK_POLICY_ALWAYS);
419   gtk_widget_show (priv->family_list);
420   gtk_widget_show (scrolled_win);
421
422   gtk_table_attach (GTK_TABLE (table), scrolled_win, 0, 1, 1, 3,
423                     GTK_EXPAND | GTK_FILL,
424                     GTK_EXPAND | GTK_FILL, 0, 0);
425   focus_chain = g_list_append (focus_chain, scrolled_win);
426   
427   model = gtk_list_store_new (2,
428                               G_TYPE_OBJECT,  /* FACE_COLUMN */
429                               G_TYPE_STRING); /* FACE_NAME_COLUMN */
430   priv->face_list = gtk_tree_view_new_with_model (GTK_TREE_MODEL (model));
431   g_object_unref (model);
432   g_signal_connect (priv->face_list, "row-activated",
433                     G_CALLBACK (list_row_activated), fontsel);
434
435   gtk_label_set_mnemonic_widget (GTK_LABEL (style_label), priv->face_list);
436
437   column = gtk_tree_view_column_new_with_attributes ("Face",
438                                                      gtk_cell_renderer_text_new (),
439                                                      "text", FACE_NAME_COLUMN,
440                                                      NULL);
441   gtk_tree_view_column_set_sizing (column, GTK_TREE_VIEW_COLUMN_AUTOSIZE);
442   gtk_tree_view_append_column (GTK_TREE_VIEW (priv->face_list), column);
443
444   gtk_tree_view_set_headers_visible (GTK_TREE_VIEW (priv->face_list), FALSE);
445   gtk_tree_selection_set_mode (gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->face_list)),
446                                GTK_SELECTION_BROWSE);
447   
448   scrolled_win = gtk_scrolled_window_new (NULL, NULL);
449   gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (scrolled_win), GTK_SHADOW_IN);
450   gtk_widget_set_size_request (scrolled_win,
451                                FONT_STYLE_LIST_WIDTH, FONT_LIST_HEIGHT);
452   gtk_container_add (GTK_CONTAINER (scrolled_win), priv->face_list);
453   gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolled_win),
454                                   GTK_POLICY_AUTOMATIC, GTK_POLICY_ALWAYS);
455   gtk_widget_show (priv->face_list);
456   gtk_widget_show (scrolled_win);
457   gtk_table_attach (GTK_TABLE (table), scrolled_win, 1, 2, 1, 3,
458                     GTK_EXPAND | GTK_FILL,
459                     GTK_EXPAND | GTK_FILL, 0, 0);
460   focus_chain = g_list_append (focus_chain, scrolled_win);
461   
462   focus_chain = g_list_append (focus_chain, priv->size_entry);
463
464   model = gtk_list_store_new (1, G_TYPE_INT);
465   priv->size_list = gtk_tree_view_new_with_model (GTK_TREE_MODEL (model));
466   g_object_unref (model);
467   g_signal_connect (priv->size_list, "row-activated",
468                     G_CALLBACK (list_row_activated), fontsel);
469
470   column = gtk_tree_view_column_new_with_attributes ("Size",
471                                                      gtk_cell_renderer_text_new (),
472                                                      "text", SIZE_COLUMN,
473                                                      NULL);
474   gtk_tree_view_column_set_sizing (column, GTK_TREE_VIEW_COLUMN_AUTOSIZE);
475   gtk_tree_view_append_column (GTK_TREE_VIEW (priv->size_list), column);
476
477   gtk_tree_view_set_headers_visible (GTK_TREE_VIEW (priv->size_list), FALSE);
478   gtk_tree_selection_set_mode (gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->size_list)),
479                                GTK_SELECTION_BROWSE);
480   
481   scrolled_win = gtk_scrolled_window_new (NULL, NULL);
482   gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (scrolled_win), GTK_SHADOW_IN);
483   gtk_container_add (GTK_CONTAINER (scrolled_win), priv->size_list);
484   gtk_widget_set_size_request (scrolled_win, -1, FONT_LIST_HEIGHT);
485   gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolled_win),
486                                   GTK_POLICY_NEVER, GTK_POLICY_ALWAYS);
487   gtk_widget_show (priv->size_list);
488   gtk_widget_show (scrolled_win);
489   gtk_table_attach (GTK_TABLE (table), scrolled_win, 2, 3, 2, 3,
490                     GTK_FILL, GTK_EXPAND | GTK_FILL, 0, 0);
491   focus_chain = g_list_append (focus_chain, scrolled_win);
492
493   gtk_container_set_focus_chain (GTK_CONTAINER (table), focus_chain);
494   g_list_free (focus_chain);
495   
496   /* Insert the fonts. */
497   g_signal_connect (gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->family_list)), "changed",
498                     G_CALLBACK (gtk_font_selection_select_font), fontsel);
499
500   g_signal_connect_after (priv->family_list, "map",
501                           G_CALLBACK (gtk_font_selection_scroll_on_map),
502                           fontsel);
503   
504   g_signal_connect (gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->face_list)), "changed",
505                     G_CALLBACK (gtk_font_selection_select_style), fontsel);
506
507   g_signal_connect (gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->size_list)), "changed",
508                     G_CALLBACK (gtk_font_selection_select_size), fontsel);
509   atk_obj = gtk_widget_get_accessible (priv->size_list);
510   if (GTK_IS_ACCESSIBLE (atk_obj))
511     {
512       /* Accessibility support is enabled.
513        * Make the label ATK_RELATON_LABEL_FOR for the size list as well.
514        */
515       AtkObject *atk_label;
516       AtkRelationSet *relation_set;
517       AtkRelation *relation;
518       AtkObject *obj_array[1];
519
520       atk_label = gtk_widget_get_accessible (label);
521       relation_set = atk_object_ref_relation_set (atk_obj);
522       relation = atk_relation_set_get_relation_by_type (relation_set, ATK_RELATION_LABELLED_BY);
523       if (relation)
524         {
525           atk_relation_add_target (relation, atk_label);
526         }
527       else 
528         {
529           obj_array[0] = atk_label;
530           relation = atk_relation_new (obj_array, 1, ATK_RELATION_LABELLED_BY);
531           atk_relation_set_add (relation_set, relation);
532         }
533       g_object_unref (relation_set);
534
535       relation_set = atk_object_ref_relation_set (atk_label);
536       relation = atk_relation_set_get_relation_by_type (relation_set, ATK_RELATION_LABEL_FOR);
537       if (relation)
538         {
539           atk_relation_add_target (relation, atk_obj);
540         }
541       else 
542         {
543           obj_array[0] = atk_obj;
544           relation = atk_relation_new (obj_array, 1, ATK_RELATION_LABEL_FOR);
545           atk_relation_set_add (relation_set, relation);
546         }
547       g_object_unref (relation_set);
548     }    
549       
550
551   vbox = gtk_vbox_new (FALSE, 6);
552   gtk_widget_show (vbox);
553   gtk_box_pack_start (GTK_BOX (fontsel), vbox, FALSE, TRUE, 0);
554   
555   /* create the text entry widget */
556   label = gtk_label_new_with_mnemonic (_("_Preview:"));
557   gtk_misc_set_alignment (GTK_MISC (label), 0.0, 0.5);
558   gtk_widget_show (label);
559   gtk_box_pack_start (GTK_BOX (vbox), label, FALSE, TRUE, 0);
560   
561   text_box = gtk_hbox_new (FALSE, 0);
562   gtk_widget_show (text_box);
563   gtk_box_pack_start (GTK_BOX (vbox), text_box, FALSE, TRUE, 0);
564   
565   priv->preview_entry = gtk_entry_new ();
566   gtk_label_set_mnemonic_widget (GTK_LABEL (label), priv->preview_entry);
567   gtk_entry_set_text (GTK_ENTRY (priv->preview_entry), _(PREVIEW_TEXT));
568   
569   gtk_widget_show (priv->preview_entry);
570   g_signal_connect (priv->preview_entry, "changed",
571                     G_CALLBACK (gtk_font_selection_preview_changed), fontsel);
572   gtk_widget_set_size_request (priv->preview_entry,
573                                -1, INITIAL_PREVIEW_HEIGHT);
574   gtk_box_pack_start (GTK_BOX (text_box), priv->preview_entry,
575                       TRUE, TRUE, 0);
576   gtk_widget_pop_composite_child();
577 }
578
579 /**
580  * gtk_font_selection_new:
581  *
582  * Creates a new #GtkFontSelection.
583  *
584  * Return value: a n ew #GtkFontSelection
585  */
586 GtkWidget *
587 gtk_font_selection_new (void)
588 {
589   GtkFontSelection *fontsel;
590   
591   fontsel = g_object_new (GTK_TYPE_FONT_SELECTION, NULL);
592   
593   return GTK_WIDGET (fontsel);
594 }
595
596 static void
597 gtk_font_selection_finalize (GObject *object)
598 {
599   GtkFontSelection *fontsel = GTK_FONT_SELECTION (object);
600
601   gtk_font_selection_ref_family (fontsel, NULL);
602   gtk_font_selection_ref_face (fontsel, NULL);
603
604   G_OBJECT_CLASS (gtk_font_selection_parent_class)->finalize (object);
605 }
606
607 static void
608 gtk_font_selection_ref_family (GtkFontSelection *fontsel,
609                                PangoFontFamily  *family)
610 {
611   GtkFontSelectionPriv *priv = fontsel->priv;
612
613   if (family)
614     family = g_object_ref (family);
615   if (priv->family)
616     g_object_unref (priv->family);
617   priv->family = family;
618 }
619
620 static void gtk_font_selection_ref_face (GtkFontSelection *fontsel,
621                                          PangoFontFace    *face)
622 {
623   GtkFontSelectionPriv *priv = fontsel->priv;
624
625   if (face)
626     face = g_object_ref (face);
627   if (priv->face)
628     g_object_unref (priv->face);
629   priv->face = face;
630 }
631
632 static void
633 gtk_font_selection_reload_fonts (GtkFontSelection *fontsel)
634 {
635   if (gtk_widget_has_screen (GTK_WIDGET (fontsel)))
636     {
637       PangoFontDescription *desc;
638       desc = gtk_font_selection_get_font_description (fontsel);
639
640       gtk_font_selection_show_available_fonts (fontsel);
641       gtk_font_selection_show_available_sizes (fontsel, TRUE);
642       gtk_font_selection_show_available_styles (fontsel);
643
644       gtk_font_selection_select_font_desc (fontsel, desc, NULL, NULL);
645       gtk_font_selection_scroll_to_selection (fontsel);
646
647       pango_font_description_free (desc);
648     }
649 }
650
651 static void
652 gtk_font_selection_screen_changed (GtkWidget *widget,
653                                    GdkScreen *previous_screen)
654 {
655   gtk_font_selection_reload_fonts (GTK_FONT_SELECTION (widget));
656 }
657
658 static void
659 gtk_font_selection_style_set (GtkWidget *widget,
660                               GtkStyle  *prev_style)
661 {
662   /* Maybe fonts where installed or removed... */
663   gtk_font_selection_reload_fonts (GTK_FONT_SELECTION (widget));
664 }
665
666 static void
667 gtk_font_selection_preview_changed (GtkWidget        *entry,
668                                     GtkFontSelection *fontsel)
669 {
670   g_object_notify (G_OBJECT (fontsel), "preview-text");
671 }
672
673 static void
674 scroll_to_selection (GtkTreeView *tree_view)
675 {
676   GtkTreeSelection *selection = gtk_tree_view_get_selection (tree_view);
677   GtkTreeModel *model;
678   GtkTreeIter iter;
679
680   if (gtk_tree_selection_get_selected (selection, &model, &iter))
681     {
682       GtkTreePath *path = gtk_tree_model_get_path (model, &iter);
683       gtk_tree_view_scroll_to_cell (tree_view, path, NULL, TRUE, 0.5, 0.5);
684       gtk_tree_path_free (path);
685     }
686 }
687
688 static void
689 set_cursor_to_iter (GtkTreeView *view,
690                     GtkTreeIter *iter)
691 {
692   GtkTreeModel *model = gtk_tree_view_get_model (view);
693   GtkTreePath *path = gtk_tree_model_get_path (model, iter);
694   
695   gtk_tree_view_set_cursor (view, path, NULL, FALSE);
696
697   gtk_tree_path_free (path);
698 }
699
700 static void
701 gtk_font_selection_scroll_to_selection (GtkFontSelection *fontsel)
702 {
703   GtkFontSelectionPriv *priv = fontsel->priv;
704
705   /* Try to scroll the font family list to the selected item */
706   scroll_to_selection (GTK_TREE_VIEW (priv->family_list));
707
708   /* Try to scroll the font family list to the selected item */
709   scroll_to_selection (GTK_TREE_VIEW (priv->face_list));
710
711   /* Try to scroll the font family list to the selected item */
712   scroll_to_selection (GTK_TREE_VIEW (priv->size_list));
713 /* This is called when the list is mapped. Here we scroll to the current
714    font if necessary. */
715 }
716
717 static void
718 gtk_font_selection_scroll_on_map (GtkWidget             *widget,
719                                   gpointer               data)
720 {
721   gtk_font_selection_scroll_to_selection (GTK_FONT_SELECTION (data));
722 }
723
724 /* This is called when a family is selected in the list. */
725 static void
726 gtk_font_selection_select_font (GtkTreeSelection *selection,
727                                 gpointer          data)
728 {
729   GtkFontSelection *fontsel;
730   GtkFontSelectionPriv *priv;
731   GtkTreeModel *model;
732   GtkTreeIter iter;
733 #ifdef INCLUDE_FONT_ENTRIES
734   const gchar *family_name;
735 #endif
736
737   fontsel = GTK_FONT_SELECTION (data);
738   priv = fontsel->priv;
739
740   if (gtk_tree_selection_get_selected (selection, &model, &iter))
741     {
742       PangoFontFamily *family;
743
744       gtk_tree_model_get (model, &iter, FAMILY_COLUMN, &family, -1);
745       if (priv->family != family)
746         {
747           gtk_font_selection_ref_family (fontsel, family);
748
749 #ifdef INCLUDE_FONT_ENTRIES
750           family_name = pango_font_family_get_name (priv->family);
751           gtk_entry_set_text (GTK_ENTRY (priv->font_entry), family_name);
752 #endif
753
754           gtk_font_selection_show_available_styles (fontsel);
755           gtk_font_selection_select_best_style (fontsel, TRUE);
756         }
757
758       g_object_unref (family);
759     }
760 }
761
762 static int
763 cmp_families (const void *a, const void *b)
764 {
765   const char *a_name = pango_font_family_get_name (*(PangoFontFamily **)a);
766   const char *b_name = pango_font_family_get_name (*(PangoFontFamily **)b);
767   
768   return g_utf8_collate (a_name, b_name);
769 }
770
771 static void
772 gtk_font_selection_show_available_fonts (GtkFontSelection *fontsel)
773 {
774   GtkFontSelectionPriv *priv = fontsel->priv;
775   GtkListStore *model;
776   PangoFontFamily **families;
777   PangoFontFamily *match_family = NULL;
778   gint n_families, i;
779   GtkTreeIter match_row;
780
781   model = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (priv->family_list)));
782
783   pango_context_list_families (gtk_widget_get_pango_context (GTK_WIDGET (fontsel)),
784                                &families, &n_families);
785   qsort (families, n_families, sizeof (PangoFontFamily *), cmp_families);
786
787   gtk_list_store_clear (model);
788
789   for (i=0; i<n_families; i++)
790     {
791       const gchar *name = pango_font_family_get_name (families[i]);
792       GtkTreeIter iter;
793
794       gtk_list_store_append (model, &iter);
795       gtk_list_store_set (model, &iter,
796                           FAMILY_COLUMN, families[i],
797                           FAMILY_NAME_COLUMN, name,
798                           -1);
799       
800       if (i == 0 || !g_ascii_strcasecmp (name, "sans"))
801         {
802           match_family = families[i];
803           match_row = iter;
804         }
805     }
806
807   gtk_font_selection_ref_family (fontsel, match_family);
808   if (match_family)
809     {
810       set_cursor_to_iter (GTK_TREE_VIEW (priv->family_list), &match_row);
811 #ifdef INCLUDE_FONT_ENTRIES
812       gtk_entry_set_text (GTK_ENTRY (priv->font_entry), 
813                           pango_font_family_get_name (match_family));
814 #endif /* INCLUDE_FONT_ENTRIES */
815     }
816
817   g_free (families);
818 }
819
820 static int
821 compare_font_descriptions (const PangoFontDescription *a, const PangoFontDescription *b)
822 {
823   int val = strcmp (pango_font_description_get_family (a), pango_font_description_get_family (b));
824   if (val != 0)
825     return val;
826
827   if (pango_font_description_get_weight (a) != pango_font_description_get_weight (b))
828     return pango_font_description_get_weight (a) - pango_font_description_get_weight (b);
829
830   if (pango_font_description_get_style (a) != pango_font_description_get_style (b))
831     return pango_font_description_get_style (a) - pango_font_description_get_style (b);
832   
833   if (pango_font_description_get_stretch (a) != pango_font_description_get_stretch (b))
834     return pango_font_description_get_stretch (a) - pango_font_description_get_stretch (b);
835
836   if (pango_font_description_get_variant (a) != pango_font_description_get_variant (b))
837     return pango_font_description_get_variant (a) - pango_font_description_get_variant (b);
838
839   return 0;
840 }
841
842 static int
843 faces_sort_func (const void *a, const void *b)
844 {
845   PangoFontDescription *desc_a = pango_font_face_describe (*(PangoFontFace **)a);
846   PangoFontDescription *desc_b = pango_font_face_describe (*(PangoFontFace **)b);
847   
848   int ord = compare_font_descriptions (desc_a, desc_b);
849
850   pango_font_description_free (desc_a);
851   pango_font_description_free (desc_b);
852
853   return ord;
854 }
855
856 static gboolean
857 font_description_style_equal (const PangoFontDescription *a,
858                               const PangoFontDescription *b)
859 {
860   return (pango_font_description_get_weight (a) == pango_font_description_get_weight (b) &&
861           pango_font_description_get_style (a) == pango_font_description_get_style (b) &&
862           pango_font_description_get_stretch (a) == pango_font_description_get_stretch (b) &&
863           pango_font_description_get_variant (a) == pango_font_description_get_variant (b));
864 }
865
866 /* This fills the font style list with all the possible style combinations
867    for the current font family. */
868 static void
869 gtk_font_selection_show_available_styles (GtkFontSelection *fontsel)
870 {
871   GtkFontSelectionPriv *priv = fontsel->priv;
872   gint n_faces, i;
873   PangoFontFace **faces;
874   PangoFontDescription *old_desc;
875   GtkListStore *model;
876   GtkTreeIter match_row;
877   PangoFontFace *match_face = NULL;
878
879   model = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (priv->face_list)));
880
881   if (priv->face)
882     old_desc = pango_font_face_describe (priv->face);
883   else
884     old_desc= NULL;
885
886   pango_font_family_list_faces (priv->family, &faces, &n_faces);
887   qsort (faces, n_faces, sizeof (PangoFontFace *), faces_sort_func);
888
889   gtk_list_store_clear (model);
890
891   for (i=0; i < n_faces; i++)
892     {
893       GtkTreeIter iter;
894       const gchar *str = pango_font_face_get_face_name (faces[i]);
895
896       gtk_list_store_append (model, &iter);
897       gtk_list_store_set (model, &iter,
898                           FACE_COLUMN, faces[i],
899                           FACE_NAME_COLUMN, str,
900                           -1);
901
902       if (i == 0)
903         {
904           match_row = iter;
905           match_face = faces[i];
906         }
907       else if (old_desc)
908         {
909           PangoFontDescription *tmp_desc = pango_font_face_describe (faces[i]);
910           
911           if (font_description_style_equal (tmp_desc, old_desc))
912             {
913               match_row = iter;
914               match_face = faces[i];
915             }
916       
917           pango_font_description_free (tmp_desc);
918         }
919     }
920
921   if (old_desc)
922     pango_font_description_free (old_desc);
923
924   gtk_font_selection_ref_face (fontsel, match_face);
925   if (match_face)
926     {
927 #ifdef INCLUDE_FONT_ENTRIES
928       const gchar *str = pango_font_face_get_face_name (priv->face);
929
930       gtk_entry_set_text (GTK_ENTRY (priv->font_style_entry), str);
931 #endif
932       set_cursor_to_iter (GTK_TREE_VIEW (priv->face_list), &match_row);
933     }
934
935   g_free (faces);
936 }
937
938 /* This selects a style when the user selects a font. It just uses the first
939    available style at present. I was thinking of trying to maintain the
940    selected style, e.g. bold italic, when the user selects different fonts.
941    However, the interface is so easy to use now I'm not sure it's worth it.
942    Note: This will load a font. */
943 static void
944 gtk_font_selection_select_best_style (GtkFontSelection *fontsel,
945                                       gboolean          use_first)
946 {
947   GtkFontSelectionPriv *priv = fontsel->priv;
948   GtkTreeIter iter;
949   GtkTreeModel *model;
950
951   model = gtk_tree_view_get_model (GTK_TREE_VIEW (priv->face_list));
952
953   if (gtk_tree_model_get_iter_first (model, &iter))
954     {
955       set_cursor_to_iter (GTK_TREE_VIEW (priv->face_list), &iter);
956       scroll_to_selection (GTK_TREE_VIEW (priv->face_list));
957     }
958
959   gtk_font_selection_show_available_sizes (fontsel, FALSE);
960   gtk_font_selection_select_best_size (fontsel);
961 }
962
963
964 /* This is called when a style is selected in the list. */
965 static void
966 gtk_font_selection_select_style (GtkTreeSelection *selection,
967                                  gpointer          data)
968 {
969   GtkFontSelection *fontsel = GTK_FONT_SELECTION (data);
970   GtkTreeModel *model;
971   GtkTreeIter iter;
972
973   if (gtk_tree_selection_get_selected (selection, &model, &iter))
974     {
975       PangoFontFace *face;
976       
977       gtk_tree_model_get (model, &iter, FACE_COLUMN, &face, -1);
978       gtk_font_selection_ref_face (fontsel, face);
979       g_object_unref (face);
980     }
981
982   gtk_font_selection_show_available_sizes (fontsel, FALSE);
983   gtk_font_selection_select_best_size (fontsel);
984 }
985
986 static void
987 gtk_font_selection_show_available_sizes (GtkFontSelection *fontsel,
988                                          gboolean          first_time)
989 {
990   GtkFontSelectionPriv *priv = fontsel->priv;
991   gint i;
992   GtkListStore *model;
993   gchar buffer[128];
994   gchar *p;
995
996   model = GTK_LIST_STORE (gtk_tree_view_get_model (GTK_TREE_VIEW (priv->size_list)));
997
998   /* Insert the standard font sizes */
999   if (first_time)
1000     {
1001       gtk_list_store_clear (model);
1002
1003       for (i = 0; i < G_N_ELEMENTS (font_sizes); i++)
1004         {
1005           GtkTreeIter iter;
1006
1007           gtk_list_store_append (model, &iter);
1008           gtk_list_store_set (model, &iter, SIZE_COLUMN, font_sizes[i], -1);
1009
1010           if (font_sizes[i] * PANGO_SCALE == priv->size)
1011             set_cursor_to_iter (GTK_TREE_VIEW (priv->size_list), &iter);
1012         }
1013     }
1014   else
1015     {
1016       GtkTreeIter iter;
1017       gboolean found = FALSE;
1018
1019       gtk_tree_model_get_iter_first (GTK_TREE_MODEL (model), &iter);
1020       for (i = 0; i < G_N_ELEMENTS (font_sizes) && !found; i++)
1021         {
1022           if (font_sizes[i] * PANGO_SCALE == priv->size)
1023             {
1024               set_cursor_to_iter (GTK_TREE_VIEW (priv->size_list), &iter);
1025               found = TRUE;
1026             }
1027
1028           gtk_tree_model_iter_next (GTK_TREE_MODEL (model), &iter);
1029         }
1030
1031       if (!found)
1032         {
1033           GtkTreeSelection *selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->size_list));
1034           gtk_tree_selection_unselect_all (selection);
1035         }
1036     }
1037
1038   /* Set the entry to the new size, rounding to 1 digit,
1039    * trimming of trailing 0's and a trailing period
1040    */
1041   g_snprintf (buffer, sizeof (buffer), "%.1f", priv->size / (1.0 * PANGO_SCALE));
1042   if (strchr (buffer, '.'))
1043     {
1044       p = buffer + strlen (buffer) - 1;
1045       while (*p == '0')
1046         p--;
1047       if (*p == '.')
1048         p--;
1049       p[1] = '\0';
1050     }
1051
1052   /* Compare, to avoid moving the cursor unecessarily */
1053   if (strcmp (gtk_entry_get_text (GTK_ENTRY (priv->size_entry)), buffer) != 0)
1054     gtk_entry_set_text (GTK_ENTRY (priv->size_entry), buffer);
1055 }
1056
1057 static void
1058 gtk_font_selection_select_best_size (GtkFontSelection *fontsel)
1059 {
1060   gtk_font_selection_load_font (fontsel);  
1061 }
1062
1063 static void
1064 gtk_font_selection_set_size (GtkFontSelection *fontsel,
1065                              gint              new_size)
1066 {
1067   GtkFontSelectionPriv *priv = fontsel->priv;
1068
1069   if (priv->size != new_size)
1070     {
1071       priv->size = new_size;
1072
1073       gtk_font_selection_show_available_sizes (fontsel, FALSE);      
1074       gtk_font_selection_load_font (fontsel);
1075     }
1076 }
1077
1078 /* If the user hits return in the font size entry, we change to the new font
1079    size. */
1080 static void
1081 gtk_font_selection_size_activate (GtkWidget   *w,
1082                                   gpointer     data)
1083 {
1084   GtkFontSelection *fontsel = GTK_FONT_SELECTION (data);
1085   GtkFontSelectionPriv *priv = fontsel->priv;
1086   gint new_size;
1087   const gchar *text;
1088
1089   text = gtk_entry_get_text (GTK_ENTRY (priv->size_entry));
1090   new_size = MAX (0.1, atof (text) * PANGO_SCALE + 0.5);
1091
1092   if (priv->size != new_size)
1093     gtk_font_selection_set_size (fontsel, new_size);
1094   else 
1095     list_row_activated (w);
1096 }
1097
1098 static gboolean
1099 gtk_font_selection_size_focus_out (GtkWidget     *w,
1100                                    GdkEventFocus *event,
1101                                    gpointer       data)
1102 {
1103   GtkFontSelection *fontsel = GTK_FONT_SELECTION (data);
1104   GtkFontSelectionPriv *priv = fontsel->priv;
1105   gint new_size;
1106   const gchar *text;
1107
1108   text = gtk_entry_get_text (GTK_ENTRY (priv->size_entry));
1109   new_size = MAX (0.1, atof (text) * PANGO_SCALE + 0.5);
1110
1111   gtk_font_selection_set_size (fontsel, new_size);
1112
1113   return TRUE;
1114 }
1115
1116 /* This is called when a size is selected in the list. */
1117 static void
1118 gtk_font_selection_select_size (GtkTreeSelection *selection,
1119                                 gpointer          data)
1120 {
1121   GtkFontSelection *fontsel = GTK_FONT_SELECTION (data);
1122   GtkTreeModel *model;
1123   GtkTreeIter iter;
1124   gint new_size;
1125
1126   if (gtk_tree_selection_get_selected (selection, &model, &iter))
1127     {
1128       gtk_tree_model_get (model, &iter, SIZE_COLUMN, &new_size, -1);
1129       gtk_font_selection_set_size (fontsel, new_size * PANGO_SCALE);
1130     }
1131 }
1132
1133 static void
1134 gtk_font_selection_load_font (GtkFontSelection *fontsel)
1135 {
1136   gtk_font_selection_update_preview (fontsel);
1137 }
1138
1139 static PangoFontDescription *
1140 gtk_font_selection_get_font_description (GtkFontSelection *fontsel)
1141 {
1142   GtkFontSelectionPriv *priv = fontsel->priv;
1143   PangoFontDescription *font_desc;
1144
1145   if (priv->face)
1146     {
1147       font_desc = pango_font_face_describe (priv->face);
1148       pango_font_description_set_size (font_desc, priv->size);
1149     }
1150   else
1151     font_desc = pango_font_description_from_string (DEFAULT_FONT_NAME);
1152
1153   return font_desc;
1154 }
1155
1156 /* This sets the font in the preview entry to the selected font, and tries to
1157    make sure that the preview entry is a reasonable size, i.e. so that the
1158    text can be seen with a bit of space to spare. But it tries to avoid
1159    resizing the entry every time the font changes.
1160    This also used to shrink the preview if the font size was decreased, but
1161    that made it awkward if the user wanted to resize the window themself. */
1162 static void
1163 gtk_font_selection_update_preview (GtkFontSelection *fontsel)
1164 {
1165   GtkFontSelectionPriv *priv = fontsel->priv;
1166   GtkRcStyle *rc_style;
1167   gint new_height;
1168   GtkRequisition old_requisition;
1169   GtkWidget *preview_entry = priv->preview_entry;
1170   const gchar *text;
1171
1172   gtk_widget_get_child_requisition (preview_entry, &old_requisition);
1173   
1174   rc_style = gtk_rc_style_new ();
1175   rc_style->font_desc = gtk_font_selection_get_font_description (fontsel);
1176   
1177   gtk_widget_modify_style (preview_entry, rc_style);
1178   g_object_unref (rc_style);
1179
1180   gtk_widget_size_request (preview_entry, NULL);
1181   
1182   /* We don't ever want to be over MAX_PREVIEW_HEIGHT pixels high. */
1183   new_height = CLAMP (preview_entry->requisition.height, INITIAL_PREVIEW_HEIGHT, MAX_PREVIEW_HEIGHT);
1184
1185   if (new_height > old_requisition.height || new_height < old_requisition.height - 30)
1186     gtk_widget_set_size_request (preview_entry, -1, new_height);
1187   
1188   /* This sets the preview text, if it hasn't been set already. */
1189   text = gtk_entry_get_text (GTK_ENTRY (preview_entry));
1190   if (strlen (text) == 0)
1191     gtk_entry_set_text (GTK_ENTRY (preview_entry), _(PREVIEW_TEXT));
1192   gtk_editable_set_position (GTK_EDITABLE (preview_entry), 0);
1193 }
1194
1195
1196 /*****************************************************************************
1197  * These functions are the main public interface for getting/setting the font.
1198  *****************************************************************************/
1199
1200 /**
1201  * gtk_font_selection_get_family_list:
1202  * @fontsel: a #GtkFontSelection
1203  *
1204  * This returns the #GtkTreeView that lists font families, for
1205  * example, 'Sans', 'Serif', etc.
1206  * 
1207  * Return value: A #GtkWidget that is part of @fontsel
1208  *
1209  * Since: 2.14
1210  */
1211 GtkWidget *
1212 gtk_font_selection_get_family_list (GtkFontSelection *fontsel)
1213 {
1214   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), NULL);
1215
1216   return fontsel->priv->family_list;
1217 }
1218
1219 /**
1220  * gtk_font_selection_get_face_list:
1221  * @fontsel: a #GtkFontSelection
1222  *
1223  * This returns the #GtkTreeView which lists all styles available for
1224  * the selected font. For example, 'Regular', 'Bold', etc.
1225  * 
1226  * Return value: A #GtkWidget that is part of @fontsel
1227  *
1228  * Since: 2.14
1229  */
1230 GtkWidget *
1231 gtk_font_selection_get_face_list (GtkFontSelection *fontsel)
1232 {
1233   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), NULL);
1234
1235   return fontsel->priv->face_list;
1236 }
1237
1238 /**
1239  * gtk_font_selection_get_size_entry:
1240  * @fontsel: a #GtkFontSelection
1241  *
1242  * This returns the #GtkEntry used to allow the user to edit the font
1243  * number manually instead of selecting it from the list of font sizes. 
1244  * 
1245  * Return value: A #GtkWidget that is part of @fontsel
1246  *
1247  * Since: 2.14
1248  */
1249 GtkWidget *
1250 gtk_font_selection_get_size_entry (GtkFontSelection *fontsel)
1251 {
1252   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), NULL);
1253
1254   return fontsel->priv->size_entry;
1255 }
1256
1257 /**
1258  * gtk_font_selection_get_size_list:
1259  * @fontsel: a #GtkFontSelection
1260  *
1261  * This returns the #GtkTreeeView used to list font sizes. 
1262  * 
1263  * Return value: A #GtkWidget that is part of @fontsel
1264  *
1265  * Since: 2.14
1266  */
1267 GtkWidget *
1268 gtk_font_selection_get_size_list (GtkFontSelection *fontsel)
1269 {
1270   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), NULL);
1271
1272   return fontsel->priv->size_list;
1273 }
1274
1275 /**
1276  * gtk_font_selection_get_preview_entry:
1277  * @fontsel: a #GtkFontSelection
1278  * 
1279  * This returns the #GtkEntry used to display the font as a preview.
1280  *
1281  * Return value: A #GtkWidget that is part of @fontsel
1282  *
1283  * Since: 2.14
1284  */
1285 GtkWidget *
1286 gtk_font_selection_get_preview_entry (GtkFontSelection *fontsel)
1287 {
1288   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), NULL);
1289
1290   return fontsel->priv->preview_entry;
1291 }
1292
1293 /**
1294  * gtk_font_selection_get_family:
1295  * @fontsel: a #GtkFontSelection
1296  * 
1297  * Gets the #PangoFontFamily representing the selected font family.
1298  *
1299  * Return value: A #PangoFontFamily representing the selected font
1300  *     family. Font families are a collection of font faces. The 
1301  *     returned object is owned by @fontsel and must not be modified 
1302  *     or freed.
1303  *
1304  * Since: 2.14
1305  */
1306 PangoFontFamily *
1307 gtk_font_selection_get_family (GtkFontSelection *fontsel)
1308 {
1309   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), NULL);
1310
1311   return fontsel->priv->family;
1312 }
1313
1314 /**
1315  * gtk_font_selection_get_face:
1316  * @fontsel: a #GtkFontSelection
1317  * 
1318  * Gets the #PangoFontFace representing the selected font group
1319  * details (i.e. family, slant, weight, width, etc).   
1320  *
1321  * Return value: A #PangoFontFace representing the selected font 
1322  *     group details. The returned object is owned by @fontsel and
1323  *     must not be modified or freed. 
1324  *
1325  * Since: 2.14
1326  */
1327 PangoFontFace *
1328 gtk_font_selection_get_face (GtkFontSelection *fontsel)
1329 {
1330   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), NULL);
1331
1332   return fontsel->priv->face;
1333 }
1334
1335 /**
1336  * gtk_font_selection_get_size:
1337  * @fontsel: a #GtkFontSelection
1338  * 
1339  * The selected font size.
1340  *
1341  * Return value: A n integer representing the selected font size, 
1342  *     or -1 if no font size is selected.
1343  *
1344  * Since: 2.14
1345  **/
1346 gint
1347 gtk_font_selection_get_size (GtkFontSelection *fontsel)
1348 {
1349   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), -1);
1350
1351   return fontsel->priv->size;
1352 }
1353
1354 /**
1355  * gtk_font_selection_get_font_name:
1356  * @fontsel: a #GtkFontSelection
1357  * 
1358  * Gets the currently-selected font name. 
1359  *
1360  * Note that this can be a different string than what you set with 
1361  * gtk_font_selection_set_font_name(), as the font selection widget may 
1362  * normalize font names and thus return a string with a different structure. 
1363  * For example, "Helvetica Italic Bold 12" could be normalized to 
1364  * "Helvetica Bold Italic 12". Use pango_font_description_equal()
1365  * if you want to compare two font descriptions.
1366  * 
1367  * Return value: A string with the name of the current font, or %NULL if 
1368  *     no font is selected. You must free this string with g_free().
1369  */
1370 gchar *
1371 gtk_font_selection_get_font_name (GtkFontSelection *fontsel)
1372 {
1373   gchar *result;
1374   
1375   PangoFontDescription *font_desc = gtk_font_selection_get_font_description (fontsel);
1376   result = pango_font_description_to_string (font_desc);
1377   pango_font_description_free (font_desc);
1378
1379   return result;
1380 }
1381
1382 /* This selects the appropriate list rows.
1383    First we check the fontname is valid and try to find the font family
1384    - i.e. the name in the main list. If we can't find that, then just return.
1385    Next we try to set each of the properties according to the fontname.
1386    Finally we select the font family & style in the lists. */
1387 static gboolean
1388 gtk_font_selection_select_font_desc (GtkFontSelection      *fontsel,
1389                                      PangoFontDescription  *new_desc,
1390                                      PangoFontFamily      **pfamily,
1391                                      PangoFontFace        **pface)
1392 {
1393   GtkFontSelectionPriv *priv = fontsel->priv;
1394   PangoFontFamily *new_family = NULL;
1395   PangoFontFace *new_face = NULL;
1396   PangoFontFace *fallback_face = NULL;
1397   GtkTreeModel *model;
1398   GtkTreeIter iter;
1399   GtkTreeIter match_iter;
1400   gboolean valid;
1401   const gchar *new_family_name;
1402
1403   new_family_name = pango_font_description_get_family (new_desc);
1404
1405   if (!new_family_name)
1406     return FALSE;
1407
1408   /* Check to make sure that this is in the list of allowed fonts 
1409    */
1410   model = gtk_tree_view_get_model (GTK_TREE_VIEW (priv->family_list));
1411   for (valid = gtk_tree_model_get_iter_first (model, &iter);
1412        valid;
1413        valid = gtk_tree_model_iter_next (model, &iter))
1414     {
1415       PangoFontFamily *family;
1416       
1417       gtk_tree_model_get (model, &iter, FAMILY_COLUMN, &family, -1);
1418       
1419       if (g_ascii_strcasecmp (pango_font_family_get_name (family),
1420                               new_family_name) == 0)
1421         new_family = g_object_ref (family);
1422
1423       g_object_unref (family);
1424       
1425       if (new_family)
1426         break;
1427     }
1428
1429   if (!new_family)
1430     return FALSE;
1431
1432   if (pfamily)
1433     *pfamily = new_family;
1434   else
1435     g_object_unref (new_family);
1436   set_cursor_to_iter (GTK_TREE_VIEW (priv->family_list), &iter);
1437   gtk_font_selection_show_available_styles (fontsel);
1438
1439   model = gtk_tree_view_get_model (GTK_TREE_VIEW (priv->face_list));
1440   for (valid = gtk_tree_model_get_iter_first (model, &iter);
1441        valid;
1442        valid = gtk_tree_model_iter_next (model, &iter))
1443     {
1444       PangoFontFace *face;
1445       PangoFontDescription *tmp_desc;
1446       
1447       gtk_tree_model_get (model, &iter, FACE_COLUMN, &face, -1);
1448       tmp_desc = pango_font_face_describe (face);
1449       
1450       if (font_description_style_equal (tmp_desc, new_desc))
1451         new_face = g_object_ref (face);
1452       
1453       if (!fallback_face)
1454         {
1455           fallback_face = g_object_ref (face);
1456           match_iter = iter;
1457         }
1458       
1459       pango_font_description_free (tmp_desc);
1460       g_object_unref (face);
1461       
1462       if (new_face)
1463         {
1464           match_iter = iter;
1465           break;
1466         }
1467     }
1468
1469   if (!new_face)
1470     new_face = fallback_face;
1471   else if (fallback_face)
1472     g_object_unref (fallback_face);
1473
1474   if (pface)
1475     *pface = new_face;
1476   else if (new_face)
1477     g_object_unref (new_face);
1478   set_cursor_to_iter (GTK_TREE_VIEW (priv->face_list), &match_iter);  
1479
1480   gtk_font_selection_set_size (fontsel, pango_font_description_get_size (new_desc));
1481
1482   return TRUE;
1483 }
1484
1485
1486 /* This sets the current font, then selecting the appropriate list rows. */
1487
1488 /**
1489  * gtk_font_selection_set_font_name:
1490  * @fontsel: a #GtkFontSelection
1491  * @fontname: a font name like "Helvetica 12" or "Times Bold 18"
1492  * 
1493  * Sets the currently-selected font. 
1494  *
1495  * Note that the @fontsel needs to know the screen in which it will appear 
1496  * for this to work; this can be guaranteed by simply making sure that the 
1497  * @fontsel is inserted in a toplevel window before you call this function.
1498  * 
1499  * Return value: %TRUE if the font could be set successfully; %FALSE if no 
1500  *     such font exists or if the @fontsel doesn't belong to a particular 
1501  *     screen yet.
1502  */
1503 gboolean
1504 gtk_font_selection_set_font_name (GtkFontSelection *fontsel,
1505                                   const gchar      *fontname)
1506 {
1507   PangoFontFamily *family = NULL;
1508   PangoFontFace *face = NULL;
1509   PangoFontDescription *new_desc;
1510   
1511   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), FALSE);
1512
1513   if (!gtk_widget_has_screen (GTK_WIDGET (fontsel)))
1514     return FALSE;
1515
1516   new_desc = pango_font_description_from_string (fontname);
1517
1518   if (gtk_font_selection_select_font_desc (fontsel, new_desc, &family, &face))
1519     {
1520       gtk_font_selection_ref_family (fontsel, family);
1521       if (family)
1522         g_object_unref (family);
1523
1524       gtk_font_selection_ref_face (fontsel, face);
1525       if (face)
1526         g_object_unref (face);
1527     }
1528
1529   pango_font_description_free (new_desc);
1530   
1531   g_object_freeze_notify (G_OBJECT (fontsel));
1532   g_object_notify (G_OBJECT (fontsel), "font-name");
1533   g_object_notify (G_OBJECT (fontsel), "font");
1534   g_object_thaw_notify (G_OBJECT (fontsel));
1535
1536   return TRUE;
1537 }
1538
1539 /**
1540  * gtk_font_selection_get_preview_text:
1541  * @fontsel: a #GtkFontSelection
1542  *
1543  * Gets the text displayed in the preview area.
1544  * 
1545  * Return value: the text displayed in the preview area. 
1546  *     This string is owned by the widget and should not be 
1547  *     modified or freed 
1548  */
1549 G_CONST_RETURN gchar*
1550 gtk_font_selection_get_preview_text (GtkFontSelection *fontsel)
1551 {
1552   GtkFontSelectionPriv *priv;
1553
1554   g_return_val_if_fail (GTK_IS_FONT_SELECTION (fontsel), NULL);
1555
1556   priv = fontsel->priv;
1557
1558   return gtk_entry_get_text (GTK_ENTRY (priv->preview_entry));
1559 }
1560
1561
1562 /**
1563  * gtk_font_selection_set_preview_text:
1564  * @fontsel: a #GtkFontSelection
1565  * @text: the text to display in the preview area 
1566  *
1567  * Sets the text displayed in the preview area.
1568  * The @text is used to show how the selected font looks.
1569  */
1570 void
1571 gtk_font_selection_set_preview_text  (GtkFontSelection *fontsel,
1572                                       const gchar      *text)
1573 {
1574   GtkFontSelectionPriv *priv;
1575
1576   g_return_if_fail (GTK_IS_FONT_SELECTION (fontsel));
1577   g_return_if_fail (text != NULL);
1578
1579   priv = fontsel->priv;
1580
1581   gtk_entry_set_text (GTK_ENTRY (priv->preview_entry), text);
1582 }
1583
1584 /*****************************************************************************
1585  * GtkFontSelectionDialog
1586  *****************************************************************************/
1587
1588 static void gtk_font_selection_dialog_buildable_interface_init     (GtkBuildableIface *iface);
1589 static GObject * gtk_font_selection_dialog_buildable_get_internal_child (GtkBuildable *buildable,
1590                                                                           GtkBuilder   *builder,
1591                                                                           const gchar  *childname);
1592
1593 G_DEFINE_TYPE_WITH_CODE (GtkFontSelectionDialog, gtk_font_selection_dialog,
1594                          GTK_TYPE_DIALOG,
1595                          G_IMPLEMENT_INTERFACE (GTK_TYPE_BUILDABLE,
1596                                                 gtk_font_selection_dialog_buildable_interface_init))
1597
1598 static GtkBuildableIface *parent_buildable_iface;
1599
1600 static void
1601 gtk_font_selection_dialog_class_init (GtkFontSelectionDialogClass *klass)
1602 {
1603   g_type_class_add_private (klass, sizeof (GtkFontSelectionDialogPriv));
1604 }
1605
1606 static void
1607 gtk_font_selection_dialog_init (GtkFontSelectionDialog *fontseldiag)
1608 {
1609   GtkFontSelectionDialogPriv *priv;
1610   GtkDialog *dialog = GTK_DIALOG (fontseldiag);
1611   GtkWidget *action_area, *content_area;
1612
1613   fontseldiag->priv = G_TYPE_INSTANCE_GET_PRIVATE (fontseldiag,
1614                                                    GTK_TYPE_FONT_SELECTION_DIALOG,
1615                                                    GtkFontSelectionDialogPriv);
1616   priv = fontseldiag->priv;
1617
1618   content_area = gtk_dialog_get_content_area (dialog);
1619   action_area = gtk_dialog_get_action_area (dialog);
1620
1621   gtk_dialog_set_has_separator (dialog, FALSE);
1622   gtk_container_set_border_width (GTK_CONTAINER (dialog), 5);
1623   gtk_box_set_spacing (GTK_BOX (content_area), 2); /* 2 * 5 + 2 = 12 */
1624   gtk_container_set_border_width (GTK_CONTAINER (action_area), 5);
1625   gtk_box_set_spacing (GTK_BOX (action_area), 6);
1626
1627   gtk_widget_push_composite_child ();
1628
1629   gtk_window_set_resizable (GTK_WINDOW (fontseldiag), TRUE);
1630
1631   /* Create the content area */
1632   priv->fontsel = gtk_font_selection_new ();
1633   gtk_container_set_border_width (GTK_CONTAINER (priv->fontsel), 5);
1634   gtk_widget_show (priv->fontsel);
1635   gtk_box_pack_start (GTK_BOX (content_area),
1636                       priv->fontsel, TRUE, TRUE, 0);
1637
1638   /* Create the action area */
1639   priv->cancel_button = gtk_dialog_add_button (dialog,
1640                                                GTK_STOCK_CANCEL,
1641                                                GTK_RESPONSE_CANCEL);
1642
1643   priv->apply_button = gtk_dialog_add_button (dialog,
1644                                               GTK_STOCK_APPLY,
1645                                               GTK_RESPONSE_APPLY);
1646   gtk_widget_hide (priv->apply_button);
1647
1648   priv->ok_button = gtk_dialog_add_button (dialog,
1649                                            GTK_STOCK_OK,
1650                                            GTK_RESPONSE_OK);
1651   gtk_widget_grab_default (priv->ok_button);
1652
1653   gtk_dialog_set_alternative_button_order (GTK_DIALOG (fontseldiag),
1654                                            GTK_RESPONSE_OK,
1655                                            GTK_RESPONSE_APPLY,
1656                                            GTK_RESPONSE_CANCEL,
1657                                            -1);
1658
1659   gtk_window_set_title (GTK_WINDOW (fontseldiag),
1660                         _("Font Selection"));
1661
1662   gtk_widget_pop_composite_child ();
1663
1664   _gtk_dialog_set_ignore_separator (dialog, TRUE);
1665 }
1666
1667 /**
1668  * gtk_font_selection_dialog_new:
1669  * @title: the title of the dialog window 
1670  *
1671  * Creates a new #GtkFontSelectionDialog.
1672  *
1673  * Return value: a new #GtkFontSelectionDialog
1674  */
1675 GtkWidget*
1676 gtk_font_selection_dialog_new (const gchar *title)
1677 {
1678   GtkFontSelectionDialog *fontseldiag;
1679   
1680   fontseldiag = g_object_new (GTK_TYPE_FONT_SELECTION_DIALOG, NULL);
1681
1682   if (title)
1683     gtk_window_set_title (GTK_WINDOW (fontseldiag), title);
1684   
1685   return GTK_WIDGET (fontseldiag);
1686 }
1687
1688 /**
1689  * gtk_font_selection_dialog_get_font_selection:
1690  * @colorsel: a #GtkFontSelectionDialog
1691  *
1692  * Retrieves the #GtkFontSelection widget embedded in the dialog.
1693  *
1694  * Returns: the embedded #GtkFontSelection
1695  *
1696  * Since: 2.22
1697  **/
1698 GtkWidget*
1699 gtk_font_selection_dialog_get_font_selection (GtkFontSelectionDialog *fsd)
1700 {
1701   g_return_val_if_fail (GTK_IS_FONT_SELECTION_DIALOG (fsd), NULL);
1702
1703   return fsd->priv->fontsel;
1704 }
1705
1706
1707 /**
1708  * gtk_font_selection_dialog_get_ok_button:
1709  * @fsd: a #GtkFontSelectionDialog
1710  *
1711  * Gets the 'OK' button.
1712  *
1713  * Return value: the #GtkWidget used in the dialog for the 'OK' button.
1714  *
1715  * Since: 2.14
1716  */
1717 GtkWidget *
1718 gtk_font_selection_dialog_get_ok_button (GtkFontSelectionDialog *fsd)
1719 {
1720   g_return_val_if_fail (GTK_IS_FONT_SELECTION_DIALOG (fsd), NULL);
1721
1722   return fsd->priv->ok_button;
1723 }
1724
1725 /**
1726  * gtk_font_selection_dialog_get_cancel_button:
1727  * @fsd: a #GtkFontSelectionDialog
1728  *
1729  * Gets the 'Cancel' button.
1730  *
1731  * Return value: the #GtkWidget used in the dialog for the 'Cancel' button.
1732  *
1733  * Since: 2.14
1734  */
1735 GtkWidget *
1736 gtk_font_selection_dialog_get_cancel_button (GtkFontSelectionDialog *fsd)
1737 {
1738   g_return_val_if_fail (GTK_IS_FONT_SELECTION_DIALOG (fsd), NULL);
1739
1740   return fsd->priv->cancel_button;
1741 }
1742
1743 static void
1744 gtk_font_selection_dialog_buildable_interface_init (GtkBuildableIface *iface)
1745 {
1746   parent_buildable_iface = g_type_interface_peek_parent (iface);
1747   iface->get_internal_child = gtk_font_selection_dialog_buildable_get_internal_child;
1748 }
1749
1750 static GObject *
1751 gtk_font_selection_dialog_buildable_get_internal_child (GtkBuildable *buildable,
1752                                                         GtkBuilder   *builder,
1753                                                         const gchar  *childname)
1754 {
1755   GtkFontSelectionDialogPriv *priv;
1756
1757   priv = GTK_FONT_SELECTION_DIALOG (buildable)->priv;
1758
1759   if (g_strcmp0 (childname, "ok_button") == 0)
1760     return G_OBJECT (priv->ok_button);
1761   else if (g_strcmp0 (childname, "cancel_button") == 0)
1762     return G_OBJECT (priv->cancel_button);
1763   else if (g_strcmp0 (childname, "apply_button") == 0)
1764     return G_OBJECT (priv->apply_button);
1765   else if (g_strcmp0 (childname, "font_selection") == 0)
1766     return G_OBJECT (priv->fontsel);
1767
1768   return parent_buildable_iface->get_internal_child (buildable, builder, childname);
1769 }
1770
1771 /**
1772  * gtk_font_selection_dialog_get_font_name:
1773  * @fsd: a #GtkFontSelectionDialog
1774  * 
1775  * Gets the currently-selected font name.
1776  *
1777  * Note that this can be a different string than what you set with 
1778  * gtk_font_selection_dialog_set_font_name(), as the font selection widget
1779  * may normalize font names and thus return a string with a different 
1780  * structure. For example, "Helvetica Italic Bold 12" could be normalized 
1781  * to "Helvetica Bold Italic 12".  Use pango_font_description_equal()
1782  * if you want to compare two font descriptions.
1783  * 
1784  * Return value: A string with the name of the current font, or %NULL if no 
1785  *     font is selected. You must free this string with g_free().
1786  */
1787 gchar*
1788 gtk_font_selection_dialog_get_font_name (GtkFontSelectionDialog *fsd)
1789 {
1790   GtkFontSelectionDialogPriv *priv;
1791
1792   g_return_val_if_fail (GTK_IS_FONT_SELECTION_DIALOG (fsd), NULL);
1793
1794   priv = fsd->priv;
1795
1796   return gtk_font_selection_get_font_name (GTK_FONT_SELECTION (priv->fontsel));
1797 }
1798
1799 /**
1800  * gtk_font_selection_dialog_set_font_name:
1801  * @fsd: a #GtkFontSelectionDialog
1802  * @fontname: a font name like "Helvetica 12" or "Times Bold 18"
1803  *
1804  * Sets the currently selected font. 
1805  * 
1806  * Return value: %TRUE if the font selected in @fsd is now the
1807  *     @fontname specified, %FALSE otherwise. 
1808  */
1809 gboolean
1810 gtk_font_selection_dialog_set_font_name (GtkFontSelectionDialog *fsd,
1811                                          const gchar            *fontname)
1812 {
1813   GtkFontSelectionDialogPriv *priv;
1814
1815   g_return_val_if_fail (GTK_IS_FONT_SELECTION_DIALOG (fsd), FALSE);
1816   g_return_val_if_fail (fontname, FALSE);
1817
1818   priv = fsd->priv;
1819
1820   return gtk_font_selection_set_font_name (GTK_FONT_SELECTION (priv->fontsel), fontname);
1821 }
1822
1823 /**
1824  * gtk_font_selection_dialog_get_preview_text:
1825  * @fsd: a #GtkFontSelectionDialog
1826  *
1827  * Gets the text displayed in the preview area.
1828  * 
1829  * Return value: the text displayed in the preview area. 
1830  *     This string is owned by the widget and should not be 
1831  *     modified or freed 
1832  */
1833 G_CONST_RETURN gchar*
1834 gtk_font_selection_dialog_get_preview_text (GtkFontSelectionDialog *fsd)
1835 {
1836   GtkFontSelectionDialogPriv *priv;
1837
1838   g_return_val_if_fail (GTK_IS_FONT_SELECTION_DIALOG (fsd), NULL);
1839
1840   priv = fsd->priv;
1841
1842   return gtk_font_selection_get_preview_text (GTK_FONT_SELECTION (priv->fontsel));
1843 }
1844
1845 /**
1846  * gtk_font_selection_dialog_set_preview_text:
1847  * @fsd: a #GtkFontSelectionDialog
1848  * @text: the text to display in the preview area
1849  *
1850  * Sets the text displayed in the preview area. 
1851  */
1852 void
1853 gtk_font_selection_dialog_set_preview_text (GtkFontSelectionDialog *fsd,
1854                                             const gchar            *text)
1855 {
1856   GtkFontSelectionDialogPriv *priv;
1857
1858   g_return_if_fail (GTK_IS_FONT_SELECTION_DIALOG (fsd));
1859   g_return_if_fail (text != NULL);
1860
1861   priv = fsd->priv;
1862
1863   gtk_font_selection_set_preview_text (GTK_FONT_SELECTION (priv->fontsel), text);
1864 }