]> git.sur5r.net Git - glabels/blob - src/ui-property-bar.c
Renamed builder files to use '.ui' extension.
[glabels] / src / ui-property-bar.c
1 /*
2  *  ui-property-bar.c
3  *  Copyright (C) 2003-2009  Jim Evins <evins@snaught.com>.
4  *
5  *  This file is part of gLabels.
6  *
7  *  gLabels is free software: you can redistribute it and/or modify
8  *  it under the terms of the GNU General Public License as published by
9  *  the Free Software Foundation, either version 3 of the License, or
10  *  (at your option) any later version.
11  *
12  *  gLabels is distributed in the hope that it will be useful,
13  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  *  GNU General Public License for more details.
16  *
17  *  You should have received a copy of the GNU General Public License
18  *  along with gLabels.  If not, see <http://www.gnu.org/licenses/>.
19  */
20
21 #include <config.h>
22
23 #include "ui-property-bar.h"
24
25 #include <glib/gi18n.h>
26 #include <gtk/gtk.h>
27 #include <string.h>
28
29 #include "builder-util.h"
30 #include "font-combo.h"
31 #include "color-combo-button.h"
32 #include "stock-pixmaps/stockpixbufs.h"
33 #include "prefs.h"
34 #include "color.h"
35
36 #include "debug.h"
37
38
39 /*===========================================================================*/
40 /* Private macros and constants.                                             */
41 /*===========================================================================*/
42
43
44 /*===========================================================================*/
45 /* Private data types                                                        */
46 /*===========================================================================*/
47
48 struct _glUIPropertyBarPrivate {
49
50         glLabel    *label;
51
52         GtkBuilder *builder;
53
54         GtkWidget  *tool_bar;
55
56         /* Font selection */
57         GtkWidget  *font_family_eventbox;
58         GtkWidget  *font_family_combo;
59         GtkWidget  *font_size_spin;
60         GtkWidget  *font_bold_toggle;
61         GtkWidget  *font_italic_toggle;
62
63         /* Text alignemnt radios */
64         GtkWidget  *text_align_left_radio;
65         GtkWidget  *text_align_center_radio;
66         GtkWidget  *text_align_right_radio;
67
68         /* Color combos */
69         GtkWidget  *text_color_eventbox;
70         GtkWidget  *text_color_button;
71         GtkWidget  *fill_color_eventbox;
72         GtkWidget  *fill_color_button;
73         GtkWidget  *line_color_eventbox;
74         GtkWidget  *line_color_button;
75
76         /* Line width */
77         GtkWidget  *line_width_spin;
78
79         /* Prevent recursion */
80         gboolean    stop_signals;
81 };
82
83
84 /*===========================================================================*/
85 /* Private globals                                                           */
86 /*===========================================================================*/
87
88
89 /*===========================================================================*/
90 /* Local function prototypes                                                 */
91 /*===========================================================================*/
92
93 static void     gl_ui_property_bar_finalize      (GObject              *object);
94
95 static void     gl_ui_property_bar_construct     (glUIPropertyBar      *this);
96
97 static void     selection_changed_cb             (glUIPropertyBar      *this,
98                                                   glLabel              *label);
99
100 static void     font_family_changed_cb           (GtkComboBox          *combo,
101                                                   glUIPropertyBar      *this);
102
103 static void     font_size_changed_cb             (GtkSpinButton        *spin,
104                                                   glUIPropertyBar      *this);
105
106 static void     text_color_changed_cb            (glColorComboButton   *cc,
107                                                   guint                 color,
108                                                   gboolean              is_default,
109                                                   glUIPropertyBar      *this);
110
111 static void     fill_color_changed_cb            (glColorComboButton   *cc,
112                                                   guint                 color,
113                                                   gboolean              is_default,
114                                                   glUIPropertyBar      *this);
115
116 static void     line_color_changed_cb            (glColorComboButton   *cc,
117                                                   guint                 color,
118                                                   gboolean              is_default,
119                                                   glUIPropertyBar      *this);
120
121 static void     line_width_changed_cb            (GtkSpinButton        *spin,
122                                                   glUIPropertyBar      *this);
123
124 static void     font_bold_toggled_cb             (GtkToggleToolButton  *toggle,
125                                                   glUIPropertyBar      *this);
126                                                   
127 static void     font_italic_toggled_cb           (GtkToggleToolButton  *toggle,
128                                                   glUIPropertyBar      *this);
129                                                   
130 static void     text_align_toggled_cb            (GtkToggleToolButton  *toggle,
131                                                   glUIPropertyBar      *this);
132                                                   
133 static void     set_doc_items_sensitive          (glUIPropertyBar      *this,
134                                                   gboolean              state);
135
136 static void     set_text_items_sensitive         (glUIPropertyBar      *this,
137                                                   gboolean              state);
138
139 static void     set_fill_items_sensitive         (glUIPropertyBar      *this,
140                                                   gboolean              state);
141
142 static void     set_line_color_items_sensitive   (glUIPropertyBar      *this,
143                                                   gboolean              state);
144
145 static void     set_line_width_items_sensitive   (glUIPropertyBar      *this,
146                                                   gboolean              state);
147
148
149 /****************************************************************************/
150 /* Boilerplate Object stuff.                                                */
151 /****************************************************************************/
152 G_DEFINE_TYPE (glUIPropertyBar, gl_ui_property_bar, GTK_TYPE_HBOX);
153
154
155 static void
156 gl_ui_property_bar_class_init (glUIPropertyBarClass *class)
157 {
158         GObjectClass   *object_class     = G_OBJECT_CLASS (class);
159
160         gl_debug (DEBUG_PROPERTY_BAR, "START");
161
162         gl_ui_property_bar_parent_class = g_type_class_peek_parent (class);
163
164         object_class->finalize = gl_ui_property_bar_finalize;
165
166         gl_debug (DEBUG_PROPERTY_BAR, "END");
167 }
168
169
170 static void
171 gl_ui_property_bar_init (glUIPropertyBar *this)
172 {
173         gl_debug (DEBUG_PROPERTY_BAR, "START");
174
175         this->priv = g_new0 (glUIPropertyBarPrivate, 1);
176
177         gl_debug (DEBUG_PROPERTY_BAR, "END");
178 }
179
180
181 static void
182 gl_ui_property_bar_finalize (GObject *object)
183 {
184         glUIPropertyBar *this = GL_UI_PROPERTY_BAR (object);
185
186         gl_debug (DEBUG_PROPERTY_BAR, "START");
187
188         g_return_if_fail (object != NULL);
189         g_return_if_fail (GL_IS_UI_PROPERTY_BAR (object));
190
191         if (this->priv->label)
192         {
193                 g_object_unref (G_OBJECT(this->priv->label));
194         }
195         if (this->priv->builder)
196         {
197                 g_object_unref (G_OBJECT(this->priv->builder));
198         }
199         g_free (this->priv);
200
201         G_OBJECT_CLASS (gl_ui_property_bar_parent_class)->finalize (object);
202
203         gl_debug (DEBUG_PROPERTY_BAR, "END");
204 }
205
206
207 /****************************************************************************/
208 /* Create a NEW property_bar.                                               */
209 /****************************************************************************/
210 GtkWidget *
211 gl_ui_property_bar_new (void)
212 {
213         glUIPropertyBar *this;
214
215         gl_debug (DEBUG_PROPERTY_BAR, "START");
216
217         this = g_object_new (GL_TYPE_UI_PROPERTY_BAR, NULL);
218
219         gl_ui_property_bar_construct (this);
220
221         gl_debug (DEBUG_PROPERTY_BAR, "END");
222
223         return GTK_WIDGET (this);
224 }
225
226
227 /******************************************************************************/
228 /* Initialize property toolbar.                                               */
229 /******************************************************************************/
230 static void
231 gl_ui_property_bar_construct (glUIPropertyBar   *this)
232 {
233         gchar         *builder_filename;
234         GtkBuilder    *builder;
235         static gchar  *object_ids[] = { "property_toolbar",
236                                         "adjustment1", "adjustment2",
237                                         NULL };
238         GError        *error = NULL;
239         GdkPixbuf     *pixbuf = NULL;
240
241         gl_debug (DEBUG_PROPERTY_BAR, "START");
242
243         this->priv->stop_signals = TRUE;
244
245         builder = gtk_builder_new ();
246         builder_filename = g_build_filename (GLABELS_DATA_DIR, "ui", "property-bar.ui", NULL);
247         gtk_builder_add_objects_from_file (builder, builder_filename, object_ids, &error);
248         g_free (builder_filename);
249         if (error) {
250                 g_critical ("%s\n\ngLabels may not be installed correctly!", error->message);
251                 g_error_free (error);
252                 return;
253         }
254
255         gl_builder_util_get_widgets (builder,
256                                      "property_toolbar",        &this->priv->tool_bar,
257                                      "font_family_eventbox",    &this->priv->font_family_eventbox,
258                                      "font_size_spin",          &this->priv->font_size_spin,
259                                      "font_bold_toggle",        &this->priv->font_bold_toggle,
260                                      "font_italic_toggle",      &this->priv->font_italic_toggle,
261                                      "text_align_left_radio",   &this->priv->text_align_left_radio,
262                                      "text_align_center_radio", &this->priv->text_align_center_radio,
263                                      "text_align_right_radio",  &this->priv->text_align_right_radio,
264                                      "text_color_eventbox",     &this->priv->text_color_eventbox,
265                                      "fill_color_eventbox",     &this->priv->fill_color_eventbox,
266                                      "line_color_eventbox",     &this->priv->line_color_eventbox,
267                                      "line_width_spin",         &this->priv->line_width_spin,
268                                      NULL);
269
270         gtk_container_add (GTK_CONTAINER (this), this->priv->tool_bar);
271
272         this->priv->font_family_combo =
273                 gl_font_combo_new (gl_prefs_model_get_default_font_family (gl_prefs));
274         gtk_container_add (GTK_CONTAINER (this->priv->font_family_eventbox),
275                            this->priv->font_family_combo);
276
277         pixbuf = gdk_pixbuf_new_from_inline (-1, stock_text_24, FALSE, NULL);
278         this->priv->text_color_button =
279                 gl_color_combo_button_new (pixbuf,
280                                            _("Default"),
281                                            GL_COLOR_TEXT_DEFAULT,
282                                            gl_prefs_model_get_default_text_color (gl_prefs));
283         gl_color_combo_button_set_relief (GL_COLOR_COMBO_BUTTON(this->priv->text_color_button),
284                                           GTK_RELIEF_NONE);
285         g_object_unref (G_OBJECT (pixbuf));
286         gtk_container_add (GTK_CONTAINER (this->priv->text_color_eventbox),
287                            this->priv->text_color_button);
288
289         pixbuf = gdk_pixbuf_new_from_inline (-1, stock_bucket_fill_24, FALSE, NULL);
290         this->priv->fill_color_button =
291                 gl_color_combo_button_new (pixbuf,
292                                            _("No Fill"),
293                                            GL_COLOR_NO_FILL,
294                                            gl_prefs_model_get_default_fill_color (gl_prefs));
295         gl_color_combo_button_set_relief (GL_COLOR_COMBO_BUTTON(this->priv->fill_color_button),
296                                           GTK_RELIEF_NONE);
297         g_object_unref (G_OBJECT (pixbuf));
298         gtk_container_add (GTK_CONTAINER (this->priv->fill_color_eventbox),
299                            this->priv->fill_color_button);
300
301         pixbuf = gdk_pixbuf_new_from_inline (-1, stock_pencil_24, FALSE, NULL);
302         this->priv->line_color_button =
303                 gl_color_combo_button_new (pixbuf,
304                                            _("No Line"),
305                                            GL_COLOR_NO_LINE,
306                                            gl_prefs_model_get_default_line_color (gl_prefs));
307         gl_color_combo_button_set_relief (GL_COLOR_COMBO_BUTTON(this->priv->line_color_button),
308                                           GTK_RELIEF_NONE);
309         g_object_unref (G_OBJECT (pixbuf));
310         gtk_container_add (GTK_CONTAINER (this->priv->line_color_eventbox),
311                            this->priv->line_color_button);
312
313         /* Save reference to gui tree so we don't lose tooltips */
314         this->priv->builder = builder;
315
316         set_doc_items_sensitive (this, FALSE);
317
318         /* Font family entry widget */
319         g_signal_connect (G_OBJECT (this->priv->font_family_combo),
320                           "changed", G_CALLBACK (font_family_changed_cb), this);
321
322         /* Font size entry widget */
323         gtk_spin_button_set_value (GTK_SPIN_BUTTON(this->priv->font_size_spin),
324                                    gl_prefs_model_get_default_font_size (gl_prefs));
325
326         g_signal_connect (G_OBJECT (this->priv->font_size_spin),
327                           "changed", G_CALLBACK (font_size_changed_cb), this);
328
329
330         /* Bold and Italic toggles */
331         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->font_bold_toggle),
332                                            (gl_prefs_model_get_default_font_weight (gl_prefs) == PANGO_WEIGHT_BOLD));
333         g_signal_connect (G_OBJECT (this->priv->font_bold_toggle),
334                           "toggled", G_CALLBACK (font_bold_toggled_cb), this);
335         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->font_italic_toggle),
336                                            gl_prefs_model_get_default_font_italic_flag (gl_prefs));
337         g_signal_connect (G_OBJECT (this->priv->font_italic_toggle),
338                           "toggled", G_CALLBACK (font_italic_toggled_cb), this);
339
340
341         /* Text alignment radio group */
342         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_left_radio),
343                                            (gl_prefs_model_get_default_text_alignment (gl_prefs) == PANGO_ALIGN_LEFT));
344         g_signal_connect (G_OBJECT (this->priv->text_align_left_radio),
345                           "toggled", G_CALLBACK (text_align_toggled_cb), this);
346         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_center_radio),
347                                            (gl_prefs_model_get_default_text_alignment (gl_prefs) == PANGO_ALIGN_CENTER));
348         g_signal_connect (G_OBJECT (this->priv->text_align_center_radio),
349                           "toggled", G_CALLBACK (text_align_toggled_cb), this);
350         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_right_radio),
351                                            (gl_prefs_model_get_default_text_alignment (gl_prefs) == PANGO_ALIGN_RIGHT));
352         g_signal_connect (G_OBJECT (this->priv->text_align_right_radio),
353                           "toggled", G_CALLBACK (text_align_toggled_cb), this);
354
355         /* Text color widget */
356         gl_color_combo_button_set_color (GL_COLOR_COMBO_BUTTON (this->priv->text_color_button),
357                                          gl_prefs_model_get_default_text_color (gl_prefs));
358         g_signal_connect (G_OBJECT (this->priv->text_color_button),
359                           "color_changed",
360                           G_CALLBACK (text_color_changed_cb), this);
361
362         /* Fill color widget */
363         gl_color_combo_button_set_color (GL_COLOR_COMBO_BUTTON (this->priv->fill_color_button),
364                                          gl_prefs_model_get_default_fill_color (gl_prefs));
365         g_signal_connect (G_OBJECT (this->priv->fill_color_button),
366                           "color_changed",
367                           G_CALLBACK (fill_color_changed_cb), this);
368
369         /* Line color widget */
370         gl_color_combo_button_set_color (GL_COLOR_COMBO_BUTTON (this->priv->line_color_button),
371                                          gl_prefs_model_get_default_line_color (gl_prefs));
372         g_signal_connect (G_OBJECT (this->priv->line_color_button),
373                           "color_changed",
374                           G_CALLBACK (line_color_changed_cb), this);
375
376         /* Line width entry widget */
377         g_signal_connect (G_OBJECT (this->priv->line_width_spin),
378                           "changed",
379                           G_CALLBACK (line_width_changed_cb), this);
380
381         this->priv->stop_signals = FALSE;
382
383         gl_debug (DEBUG_PROPERTY_BAR, "END");
384 }
385
386
387 /****************************************************************************/
388 /* Fill widgets with default values.                                        */
389 /****************************************************************************/
390 static void
391 reset_to_default_properties (glLabel         *label,
392                              glUIPropertyBar *this)
393 {
394         gchar *family;
395
396         family = gl_label_get_default_font_family (label);
397         gl_font_combo_set_family (GL_FONT_COMBO (this->priv->font_family_combo), family);
398         g_free (family);
399
400         gtk_spin_button_set_value (GTK_SPIN_BUTTON(this->priv->font_size_spin),
401                                    gl_label_get_default_font_size (label));
402
403         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->font_bold_toggle),
404                                            (gl_label_get_default_font_weight (label) == PANGO_WEIGHT_BOLD));
405         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->font_italic_toggle),
406                                            gl_label_get_default_font_italic_flag (label));
407
408         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_left_radio),
409                                            (gl_label_get_default_text_alignment (label) == PANGO_ALIGN_LEFT));
410         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_center_radio),
411                                            (gl_label_get_default_text_alignment (label) == PANGO_ALIGN_CENTER));
412         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_right_radio),
413                                            (gl_label_get_default_text_alignment (label) == PANGO_ALIGN_RIGHT));
414
415         gl_color_combo_button_set_color (GL_COLOR_COMBO_BUTTON(this->priv->text_color_button),
416                                          gl_label_get_default_text_color (label));
417
418         gl_color_combo_button_set_color (GL_COLOR_COMBO_BUTTON(this->priv->fill_color_button),
419                                          gl_label_get_default_fill_color (label));
420
421         gl_color_combo_button_set_color (GL_COLOR_COMBO_BUTTON(this->priv->line_color_button),
422                                          gl_label_get_default_line_color (label));
423
424         gtk_spin_button_set_value (GTK_SPIN_BUTTON(this->priv->line_width_spin),
425                                    gl_label_get_default_line_width (label));
426 }
427
428
429 /****************************************************************************/
430 /* Set label associated with property_bar.                                  */
431 /****************************************************************************/
432 void
433 gl_ui_property_bar_set_label (glUIPropertyBar *this,
434                               glLabel         *label)
435 {
436         gl_debug (DEBUG_PROPERTY_BAR, "START");
437
438         g_return_if_fail (label && GL_IS_LABEL (label));
439
440         set_doc_items_sensitive (this, TRUE);
441
442         reset_to_default_properties (label, this);
443
444         this->priv->label = GL_LABEL (g_object_ref (G_OBJECT (label)));
445
446         g_signal_connect_swapped (G_OBJECT(label), "selection_changed",
447                                   G_CALLBACK(selection_changed_cb), this);
448
449         g_signal_connect_swapped (G_OBJECT(label), "changed",
450                                   G_CALLBACK(selection_changed_cb), this);
451
452         gl_debug (DEBUG_PROPERTY_BAR, "END");
453 }
454
455
456 /*---------------------------------------------------------------------------*/
457 /* PRIVATE.  Label "selection state changed" callback.                       */
458 /*---------------------------------------------------------------------------*/
459 static void
460 update_text_properties (glLabel         *label,
461                         glUIPropertyBar *this)
462 {
463         gboolean        can_text, is_first_object;
464         gboolean        is_same_font_family, is_same_font_size;
465         gboolean        is_same_text_color, is_same_is_italic;
466         gboolean        is_same_is_bold, is_same_align;
467         GList          *selection_list;
468         GList          *p;
469         glLabelObject  *object;
470         gchar          *selection_font_family, *font_family;
471         gdouble         selection_font_size, font_size;
472         guint           selection_text_color, text_color;
473         glColorNode    *text_color_node;
474         gboolean        selection_is_italic, is_italic;
475         gboolean        selection_is_bold, is_bold;
476         PangoAlignment  selection_align, align;
477
478         can_text = gl_label_can_selection_text (label);
479         set_text_items_sensitive (this, can_text);
480
481         if (!can_text) 
482                 return;
483
484         is_same_is_italic =
485         is_same_is_bold =
486         is_same_align =
487         is_same_text_color =
488         is_same_font_size =
489         is_same_font_family = TRUE;
490         selection_font_family = NULL;
491         selection_font_size = -1;
492         selection_align = PANGO_ALIGN_LEFT;
493         selection_is_italic = TRUE;
494         selection_is_bold = TRUE;
495         selection_text_color = 0;
496         
497         is_first_object = TRUE;
498         
499         selection_list = gl_label_get_selection_list (label);
500         for (p = selection_list; p != NULL; p = p->next)
501         {
502
503                 object = GL_LABEL_OBJECT (p->data);
504                 if (!gl_label_object_can_text (object)) 
505                         continue;
506
507                 font_family = gl_label_object_get_font_family (object);
508                 if (font_family != NULL)
509                 {
510                         if (selection_font_family == NULL)
511                         {
512                                 selection_font_family = g_strdup (font_family);
513                         }
514                         else 
515                         {
516                                 if (strcmp (font_family, selection_font_family) != 0)
517                                 {
518                                         is_same_font_family = FALSE;
519                                 }
520                         }
521                         g_free (font_family);
522                 }       
523
524                 font_size = gl_label_object_get_font_size (object);
525                 
526                 text_color_node = gl_label_object_get_text_color (object);
527                 if (text_color_node->field_flag)
528                 {
529                         /* If a merge field is set we use the default color for merged color*/
530                         text_color = GL_COLOR_MERGE_DEFAULT;
531                         
532                 }
533                 else
534                 {
535                         text_color = text_color_node->color;
536                 }
537                 gl_color_node_free (&text_color_node);
538                 
539                 is_italic = gl_label_object_get_font_italic_flag (object);
540                 is_bold = gl_label_object_get_font_weight (object) == PANGO_WEIGHT_BOLD;
541                 align = gl_label_object_get_text_alignment (object);
542
543                 if (is_first_object)
544                 {
545                         selection_font_size = font_size;
546                         selection_text_color = text_color;
547                         selection_is_italic = is_italic;
548                         selection_is_bold = is_bold;
549                         selection_align = align;
550                 }
551                 else
552                 {
553                         if (font_size != selection_font_size) 
554                                 is_same_font_size = FALSE;
555                         if (text_color != selection_text_color)
556                                 is_same_text_color = FALSE;
557                         if (is_italic != selection_is_italic)
558                                 is_same_is_italic = FALSE;
559                         if (is_bold != selection_is_bold)
560                                 is_same_is_bold = FALSE;
561                         if (align != selection_align)
562                                 is_same_align = FALSE;
563                 }
564                 is_first_object = FALSE;
565         }
566
567         g_list_free (selection_list);
568
569         if (is_same_font_family && (selection_font_family != NULL)) 
570                 gl_debug (DEBUG_PROPERTY_BAR, "same font family = %s", 
571                           selection_font_family);
572         gl_font_combo_set_family (GL_FONT_COMBO (this->priv->font_family_combo),
573                                   is_same_font_family?selection_font_family:"");
574         g_free (selection_font_family);
575
576         if (is_same_font_size)
577         {
578                 gl_debug (DEBUG_PROPERTY_BAR, "same font size = %g", 
579                           selection_font_size);
580                 gtk_spin_button_set_value (GTK_SPIN_BUTTON (this->priv->font_size_spin),
581                                            selection_font_size);
582         }
583         else
584         {
585                 gtk_entry_set_text (GTK_ENTRY (this->priv->font_size_spin), "");
586         }
587
588         if (is_same_text_color)
589         {
590                 gl_debug (DEBUG_PROPERTY_BAR, "same text color = %08x", selection_text_color);
591                 gl_color_combo_button_set_color (GL_COLOR_COMBO_BUTTON (this->priv->text_color_button),
592                                                  selection_text_color);
593         }
594
595         if (is_same_is_italic)
596         {
597                 gl_debug (DEBUG_PROPERTY_BAR, "same italic flag = %d", 
598                           selection_is_italic);
599         }
600         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->font_italic_toggle),
601                                            selection_is_italic && is_same_is_italic);
602
603         if (is_same_is_bold)
604         {
605                 gl_debug (DEBUG_PROPERTY_BAR, "same bold flag = %d",
606                           selection_is_bold);
607         }
608         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->font_bold_toggle),
609                                            selection_is_bold && is_same_is_bold);
610
611         if (is_same_align) 
612                 gl_debug (DEBUG_PROPERTY_BAR, "same align");
613         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_left_radio),
614                                            (selection_align == PANGO_ALIGN_LEFT) &&
615                                            is_same_align);
616         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_center_radio),
617                                            (selection_align == PANGO_ALIGN_CENTER) &&
618                                            is_same_align);
619         gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_right_radio),
620                                            (selection_align == PANGO_ALIGN_RIGHT) &&
621                                            is_same_align);
622 }
623
624
625 static void
626 update_fill_color (glLabel         *label,
627                    glUIPropertyBar *this)
628 {
629         gboolean can, is_first_object;
630         gboolean is_same_fill_color;
631         GList *selection_list;
632         GList *p;
633         glLabelObject *object;
634         guint selection_fill_color, fill_color;
635         glColorNode *fill_color_node;
636
637         can = gl_label_can_selection_fill (label);
638         set_fill_items_sensitive (this, can);
639
640         if (!can) 
641                 return;
642
643         is_same_fill_color = TRUE;
644         is_first_object = TRUE;
645         selection_fill_color = 0;
646
647         selection_list = gl_label_get_selection_list (label);
648         
649         for (p = selection_list; p != NULL; p = p->next)
650         {
651
652                 object = GL_LABEL_OBJECT (p->data);
653                 if (!gl_label_object_can_fill (object)) 
654                         continue;
655
656                 fill_color_node = gl_label_object_get_fill_color (object);
657                 if (fill_color_node->field_flag)
658                 {
659                         /* If a merge field is set we use the default color for merged color*/
660                         fill_color = GL_COLOR_FILL_MERGE_DEFAULT;
661                         
662                 }
663                 else
664                 {
665                         fill_color = fill_color_node->color;
666                 }
667                 gl_color_node_free (&fill_color_node);
668
669                 if (is_first_object)
670                 {
671                         selection_fill_color = fill_color;
672                 }
673                 else
674                 {
675                         if (fill_color != selection_fill_color)
676                         {
677                                 is_same_fill_color = FALSE;
678                         }
679                 }
680                 is_first_object = FALSE;
681         }
682
683         g_list_free (selection_list);
684
685         if (is_same_fill_color)
686         {
687                 gl_debug (DEBUG_PROPERTY_BAR, "same fill color = %08x", selection_fill_color);
688                 gl_color_combo_button_set_color (GL_COLOR_COMBO_BUTTON (this->priv->fill_color_button),
689                                                  selection_fill_color);
690         }
691 }
692
693
694 static void
695 update_line_color (glLabel         *label,
696                    glUIPropertyBar *this)
697 {
698         gboolean can, is_first_object;
699         gboolean is_same_line_color;
700         GList *selection_list;
701         GList *p;
702         glLabelObject *object;
703         guint selection_line_color, line_color;
704         glColorNode *line_color_node;
705
706         can = gl_label_can_selection_line_color (label);
707         set_line_color_items_sensitive (this, can);
708
709         if (!can) 
710                 return;
711
712         is_same_line_color = TRUE;
713         is_first_object = TRUE;
714         selection_line_color = 0;
715
716         selection_list = gl_label_get_selection_list (label);
717         
718         for (p = selection_list; p != NULL; p = p->next)
719         {
720
721                 object = GL_LABEL_OBJECT (p->data);
722                 if (!gl_label_object_can_line_color (object)) 
723                         continue;
724
725                 line_color_node = gl_label_object_get_line_color (object);
726                 if (line_color_node->field_flag)
727                 {
728                         /* If a merge field is set we use the default color for merged color*/
729                         line_color = GL_COLOR_MERGE_DEFAULT;
730                         
731                 }
732                 else
733                 {
734                         line_color = line_color_node->color;
735                 }
736                 gl_color_node_free (&line_color_node);
737
738                 if (is_first_object)
739                 {
740                         selection_line_color = line_color;
741                 }
742                 else
743                 {
744                         if (line_color != selection_line_color)
745                         {
746                                 is_same_line_color = FALSE;
747                         }
748                 }
749                 is_first_object = FALSE;
750         }
751
752         g_list_free (selection_list);
753
754         if (is_same_line_color)
755         {
756                 gl_debug (DEBUG_PROPERTY_BAR, "same line color = %08x", selection_line_color);
757                 gl_color_combo_button_set_color (GL_COLOR_COMBO_BUTTON (this->priv->line_color_button),
758                                                  selection_line_color);
759         }
760 }
761
762
763 static void
764 update_line_width (glLabel         *label,
765                    glUIPropertyBar *this)
766 {
767         gboolean can, is_first_object;
768         gboolean is_same_line_width;
769         GList *selection_list;
770         GList *p;
771         glLabelObject *object;
772         gdouble selection_line_width, line_width;
773
774         can = gl_label_can_selection_line_width (label);
775         set_line_width_items_sensitive (this, can);
776
777         if (!can) 
778                 return;
779
780         is_same_line_width = TRUE;
781         is_first_object = TRUE;
782         selection_line_width = 0;
783
784         selection_list = gl_label_get_selection_list (label);
785         
786         for (p = selection_list; p != NULL; p = p->next)
787         {
788
789                 object = GL_LABEL_OBJECT (p->data);
790                 if (!gl_label_object_can_line_width (object)) 
791                         continue;
792
793                 line_width = gl_label_object_get_line_width (object);
794
795                 if (is_first_object)
796                 {
797                         selection_line_width = line_width;
798                 }
799                 else
800                 {
801                         if (line_width != selection_line_width)
802                         {
803                                 is_same_line_width = FALSE;
804                         }
805                 }
806                 is_first_object = FALSE;
807         }
808
809         g_list_free (selection_list);
810
811         if (is_same_line_width)
812         {
813                 gl_debug (DEBUG_PROPERTY_BAR, "same line width = %g", selection_line_width);
814                 gtk_spin_button_set_value (GTK_SPIN_BUTTON (this->priv->line_width_spin),
815                                            selection_line_width);
816         }
817         else
818         {
819                 gtk_entry_set_text (GTK_ENTRY (this->priv->line_width_spin), "");
820         }
821 }
822
823
824 static void 
825 selection_changed_cb (glUIPropertyBar *this,
826                       glLabel         *label)
827 {
828         g_return_if_fail (label && GL_IS_LABEL (label));
829         g_return_if_fail (this && GL_IS_UI_PROPERTY_BAR (this));
830
831         if (this->priv->stop_signals) return;
832         this->priv->stop_signals = TRUE;
833
834         gl_debug (DEBUG_PROPERTY_BAR, "START");
835
836         if (gl_label_is_selection_empty (label))
837         {
838                 /* No selection: make all controls active. */
839                 reset_to_default_properties (label, this);
840                 set_doc_items_sensitive (this, TRUE);
841         }
842         else
843         {
844                 update_text_properties (label, this);
845                 update_fill_color (label, this);
846                 update_line_color (label, this);
847                 update_line_width (label, this);
848         }
849
850         gl_debug (DEBUG_PROPERTY_BAR, "END");
851
852         this->priv->stop_signals = FALSE;
853 }
854
855
856 /*--------------------------------------------------------------------------*/
857 /* PRIVATE.  Font family entry changed.                                     */
858 /*--------------------------------------------------------------------------*/
859 static void
860 font_family_changed_cb (GtkComboBox     *combo,
861                         glUIPropertyBar *this)
862 {
863         gchar *font_family;
864
865         if (this->priv->stop_signals) return;
866         this->priv->stop_signals = TRUE;
867
868         gl_debug (DEBUG_PROPERTY_BAR, "START");
869
870         font_family = gl_font_combo_get_family (GL_FONT_COMBO (combo));
871         if ( strlen(font_family) )
872         {
873                 gl_label_set_selection_font_family (this->priv->label,
874                                                     font_family);
875                 gl_label_set_default_font_family   (this->priv->label,
876                                                     font_family);
877         }
878         g_free (font_family);
879
880         gl_debug (DEBUG_PROPERTY_BAR, "END");
881
882         this->priv->stop_signals = FALSE;
883 }
884
885
886 /*--------------------------------------------------------------------------*/
887 /* PRIVATE.  Font size spin button changed.                                 */
888 /*--------------------------------------------------------------------------*/
889 static void
890 font_size_changed_cb (GtkSpinButton        *spin,
891                       glUIPropertyBar      *this)
892 {
893         gdouble font_size;
894
895         if (this->priv->stop_signals) return;
896         this->priv->stop_signals = TRUE;
897
898         gl_debug (DEBUG_PROPERTY_BAR, "START");
899
900         font_size = gtk_spin_button_get_value (spin);
901
902         gl_label_set_selection_font_size (this->priv->label,
903                                           font_size);
904         gl_label_set_default_font_size   (this->priv->label,
905                                           font_size);
906
907         gl_debug (DEBUG_PROPERTY_BAR, "END");
908
909         this->priv->stop_signals = FALSE;
910 }
911
912
913 /*--------------------------------------------------------------------------*/
914 /* PRIVATE.  Text color combo changed.                                      */
915 /*--------------------------------------------------------------------------*/
916 static void
917 text_color_changed_cb (glColorComboButton   *cc,
918                        guint                 color,
919                        gboolean              is_default,
920                        glUIPropertyBar      *this)
921 {
922         glColorNode *text_color_node;
923
924         g_return_if_fail (this && GL_IS_UI_PROPERTY_BAR (this));
925
926         if (this->priv->stop_signals) return;
927         this->priv->stop_signals = TRUE;
928
929         gl_debug (DEBUG_PROPERTY_BAR, "START");
930
931         text_color_node = gl_color_node_new_default ();
932         text_color_node->color = color;
933         
934         gl_debug (DEBUG_PROPERTY_BAR, "Color=%08x, Is_default=%d",
935                   color, is_default);
936
937         if (is_default)
938         {
939                 text_color_node->color = gl_prefs_model_get_default_text_color (gl_prefs);
940                 gl_label_set_selection_text_color (this->priv->label,
941                                                    text_color_node);
942                 gl_label_set_default_text_color   (this->priv->label,
943                                                    text_color_node->color);
944         }
945         else
946         {
947                 gl_label_set_selection_text_color (this->priv->label,
948                                                    text_color_node);
949                 gl_label_set_default_text_color   (this->priv->label,
950                                                    text_color_node->color);
951         }
952
953         gl_color_node_free (&text_color_node);
954         
955         gl_debug (DEBUG_PROPERTY_BAR, "END");
956
957         this->priv->stop_signals = FALSE;
958 }
959
960
961 /*--------------------------------------------------------------------------*/
962 /* PRIVATE.  Fill color combo changed.                                      */
963 /*--------------------------------------------------------------------------*/
964 static void
965 fill_color_changed_cb (glColorComboButton   *cc,
966                        guint                 color,
967                        gboolean              is_default,
968                        glUIPropertyBar      *this)
969 {
970         glColorNode *fill_color_node;
971
972         g_return_if_fail (this && GL_IS_UI_PROPERTY_BAR (this));
973
974         if (this->priv->stop_signals) return;
975         this->priv->stop_signals = TRUE;
976
977         gl_debug (DEBUG_PROPERTY_BAR, "START");
978
979         fill_color_node = gl_color_node_new_default ();
980
981         fill_color_node->color = color;
982
983         gl_debug (DEBUG_PROPERTY_BAR, "Color=%08x, Is_default=%d",
984                   color, is_default);
985
986         if (is_default)
987         {
988
989                 fill_color_node->color = GL_COLOR_NONE;
990                 gl_label_set_selection_fill_color (this->priv->label,
991                                                    fill_color_node);
992                 gl_label_set_default_fill_color   (this->priv->label,
993                                                    fill_color_node->color);
994         }
995         else
996         {
997                 gl_label_set_selection_fill_color (this->priv->label,
998                                                    fill_color_node);
999                 gl_label_set_default_fill_color   (this->priv->label,
1000                                                    fill_color_node->color);
1001         }
1002         gl_color_node_free (&fill_color_node);
1003         
1004         gl_debug (DEBUG_PROPERTY_BAR, "END");
1005
1006         this->priv->stop_signals = FALSE;
1007 }
1008
1009
1010 /*--------------------------------------------------------------------------*/
1011 /* PRIVATE.  Line color combo changed.                                      */
1012 /*--------------------------------------------------------------------------*/
1013 static void
1014 line_color_changed_cb (glColorComboButton   *cc,
1015                        guint                 color,
1016                        gboolean              is_default,
1017                        glUIPropertyBar      *this)
1018 {
1019         glColorNode *line_color_node;
1020
1021         g_return_if_fail (this && GL_IS_UI_PROPERTY_BAR (this));
1022
1023         if (this->priv->stop_signals) return;
1024         this->priv->stop_signals = TRUE;
1025
1026         gl_debug (DEBUG_PROPERTY_BAR, "START");
1027
1028         line_color_node = gl_color_node_new_default ();
1029         line_color_node->color = color;
1030
1031         gl_debug (DEBUG_PROPERTY_BAR, "Color=%08x, Is_default=%d",
1032                   color, is_default);
1033
1034         if (is_default)
1035         {
1036                 line_color_node->color = GL_COLOR_NONE;
1037                 gl_label_set_selection_line_color (this->priv->label,
1038                                                    line_color_node);
1039                 gl_label_set_default_line_color   (this->priv->label,
1040                                                    line_color_node->color);
1041         }
1042         else
1043         {
1044                 gl_label_set_selection_line_color (this->priv->label,
1045                                                    line_color_node);
1046                 gl_label_set_default_line_color   (this->priv->label,
1047                                                    line_color_node->color);
1048         }
1049         gl_color_node_free (&line_color_node);
1050
1051         gl_debug (DEBUG_PROPERTY_BAR, "END");
1052
1053         this->priv->stop_signals = FALSE;
1054 }
1055
1056
1057 /*--------------------------------------------------------------------------*/
1058 /* PRIVATE.  Line width spin button changed.                                */
1059 /*--------------------------------------------------------------------------*/
1060 static void
1061 line_width_changed_cb (GtkSpinButton        *spin,
1062                        glUIPropertyBar      *this)
1063 {
1064         gdouble line_width;
1065
1066         if (this->priv->stop_signals) return;
1067         this->priv->stop_signals = TRUE;
1068
1069         gl_debug (DEBUG_PROPERTY_BAR, "START");
1070
1071         if (this->priv->label)
1072         {
1073                 line_width = gtk_spin_button_get_value (spin);
1074
1075                 gl_label_set_selection_line_width (this->priv->label,
1076                                                    line_width);
1077                 gl_label_set_default_line_width   (this->priv->label,
1078                                                    line_width);
1079         }
1080
1081         gl_debug (DEBUG_PROPERTY_BAR, "END");
1082
1083         this->priv->stop_signals = FALSE;
1084 }
1085
1086
1087 /*---------------------------------------------------------------------------*/
1088 /* PRIVATE.  Font bold toggled callback.                                     */
1089 /*---------------------------------------------------------------------------*/
1090 static void
1091 font_bold_toggled_cb (GtkToggleToolButton  *toggle,
1092                       glUIPropertyBar      *this)
1093 {
1094         gboolean        state;
1095         PangoWeight     weight;
1096
1097
1098         if (this->priv->stop_signals) return;
1099         this->priv->stop_signals = TRUE;
1100
1101         gl_debug (DEBUG_PROPERTY_BAR, "START");
1102
1103         state = gtk_toggle_tool_button_get_active (toggle);
1104
1105         weight = state ? PANGO_WEIGHT_BOLD : PANGO_WEIGHT_NORMAL;
1106
1107         gl_label_set_selection_font_weight (this->priv->label, weight);
1108         gl_label_set_default_font_weight   (this->priv->label, weight);
1109
1110         gl_debug (DEBUG_PROPERTY_BAR, "END");
1111
1112         this->priv->stop_signals = FALSE;
1113 }
1114                                                   
1115
1116 /*---------------------------------------------------------------------------*/
1117 /* PRIVATE.  Font italic toggled callback.                                   */
1118 /*---------------------------------------------------------------------------*/
1119 static void
1120 font_italic_toggled_cb (GtkToggleToolButton  *toggle,
1121                         glUIPropertyBar      *this)
1122 {
1123         gboolean state;
1124
1125         if (this->priv->stop_signals) return;
1126         this->priv->stop_signals = TRUE;
1127
1128         gl_debug (DEBUG_PROPERTY_BAR, "START");
1129
1130         state = gtk_toggle_tool_button_get_active (toggle);
1131
1132         gl_label_set_selection_font_italic_flag (this->priv->label, state);
1133         gl_label_set_default_font_italic_flag   (this->priv->label, state);
1134
1135         gl_debug (DEBUG_PROPERTY_BAR, "END");
1136
1137         this->priv->stop_signals = FALSE;
1138 }
1139
1140
1141 /*---------------------------------------------------------------------------*/
1142 /* PRIVATE.  Text align toggled callback.                                    */
1143 /*---------------------------------------------------------------------------*/
1144 static void
1145 text_align_toggled_cb (GtkToggleToolButton  *toggle,
1146                        glUIPropertyBar      *this)
1147 {
1148         if (this->priv->stop_signals) return;
1149         this->priv->stop_signals = TRUE;
1150
1151         gl_debug (DEBUG_PROPERTY_BAR, "START");
1152
1153         if (gtk_toggle_tool_button_get_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_left_radio)))
1154         {               
1155                 gl_label_set_selection_text_alignment (this->priv->label,
1156                                                        PANGO_ALIGN_LEFT);
1157                 gl_label_set_default_text_alignment   (this->priv->label,
1158                                                        PANGO_ALIGN_LEFT);
1159         }
1160
1161         if (gtk_toggle_tool_button_get_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_center_radio)))
1162         {               
1163                 gl_label_set_selection_text_alignment (this->priv->label,
1164                                                        PANGO_ALIGN_CENTER);
1165                 gl_label_set_default_text_alignment   (this->priv->label,
1166                                                        PANGO_ALIGN_CENTER);
1167         }
1168
1169         if (gtk_toggle_tool_button_get_active (GTK_TOGGLE_TOOL_BUTTON (this->priv->text_align_right_radio)))
1170         {
1171                 gl_label_set_selection_text_alignment (this->priv->label,
1172                                                        PANGO_ALIGN_RIGHT);
1173                 gl_label_set_default_text_alignment   (this->priv->label,
1174                                                        PANGO_ALIGN_RIGHT);
1175         }
1176
1177         gl_debug (DEBUG_PROPERTY_BAR, "END");
1178
1179         this->priv->stop_signals = FALSE;
1180 }
1181
1182
1183 /*---------------------------------------------------------------------------*/
1184 /* PRIVATE.  Set sensitivity of doc controls.                                */
1185 /*---------------------------------------------------------------------------*/
1186 static void
1187 set_doc_items_sensitive (glUIPropertyBar      *this,
1188                          gboolean              state)
1189 {
1190         gtk_widget_set_sensitive (this->priv->font_family_combo,       state);
1191         gtk_widget_set_sensitive (this->priv->font_size_spin,          state);
1192         gtk_widget_set_sensitive (this->priv->font_bold_toggle,        state);
1193         gtk_widget_set_sensitive (this->priv->font_italic_toggle,      state);
1194         gtk_widget_set_sensitive (this->priv->text_align_left_radio,   state);
1195         gtk_widget_set_sensitive (this->priv->text_align_center_radio, state);
1196         gtk_widget_set_sensitive (this->priv->text_align_right_radio,  state);
1197         gtk_widget_set_sensitive (this->priv->text_color_button,       state);
1198         gtk_widget_set_sensitive (this->priv->fill_color_button,       state);
1199         gtk_widget_set_sensitive (this->priv->line_color_button,       state);
1200         gtk_widget_set_sensitive (this->priv->line_width_spin,         state);
1201 }
1202
1203
1204 /*---------------------------------------------------------------------------*/
1205 /* PRIVATE.  Set sensitivity of text related controls.                       */
1206 /*---------------------------------------------------------------------------*/
1207 static void
1208 set_text_items_sensitive (glUIPropertyBar      *this,
1209                           gboolean              state)
1210 {
1211         gtk_widget_set_sensitive (this->priv->font_family_combo,       state);
1212         gtk_widget_set_sensitive (this->priv->font_size_spin,          state);
1213         gtk_widget_set_sensitive (this->priv->font_bold_toggle,        state);
1214         gtk_widget_set_sensitive (this->priv->font_italic_toggle,      state);
1215         gtk_widget_set_sensitive (this->priv->text_align_left_radio,   state);
1216         gtk_widget_set_sensitive (this->priv->text_align_center_radio, state);
1217         gtk_widget_set_sensitive (this->priv->text_align_right_radio,  state);
1218         gtk_widget_set_sensitive (this->priv->text_color_button,       state);
1219 }
1220
1221
1222 /*---------------------------------------------------------------------------*/
1223 /* PRIVATE.  Set sensitivity of fill related controls.                       */
1224 /*---------------------------------------------------------------------------*/
1225 static void
1226 set_fill_items_sensitive (glUIPropertyBar      *this,
1227                           gboolean              state)
1228 {
1229         gtk_widget_set_sensitive (this->priv->fill_color_button,       state);
1230 }
1231
1232
1233 /*---------------------------------------------------------------------------*/
1234 /* PRIVATE.  Set sensitivity of line color related controls.                 */
1235 /*---------------------------------------------------------------------------*/
1236 static void
1237 set_line_color_items_sensitive (glUIPropertyBar      *this,
1238                                 gboolean              state)
1239 {
1240         gtk_widget_set_sensitive (this->priv->line_color_button,       state);
1241 }
1242
1243
1244 /*---------------------------------------------------------------------------*/
1245 /* PRIVATE.  Set sensitivity of line width related controls.                 */
1246 /*---------------------------------------------------------------------------*/
1247 static void
1248 set_line_width_items_sensitive (glUIPropertyBar      *this,
1249                                 gboolean              state)
1250 {
1251         gtk_widget_set_sensitive (this->priv->line_width_spin,         state);
1252 }
1253
1254
1255
1256 /*
1257  * Local Variables:       -- emacs
1258  * mode: C                -- emacs
1259  * c-basic-offset: 8      -- emacs
1260  * tab-width: 8           -- emacs
1261  * indent-tabs-mode: nil  -- emacs
1262  * End:                   -- emacs
1263  */