1 /* GTK - The GIMP Toolkit
2 * Copyright (C) 2010 Carlos Garnacho <carlosg@gnome.org>
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
24 #include <gobject/gvaluecollector.h>
26 #include "gtkstylecontext.h"
27 #include "gtktypebuiltins.h"
28 #include "gtkthemingengine.h"
30 #include "gtkwidget.h"
31 #include "gtkprivate.h"
35 typedef struct GtkStyleContextPrivate GtkStyleContextPrivate;
36 typedef struct GtkStyleProviderData GtkStyleProviderData;
37 typedef struct GtkStyleInfo GtkStyleInfo;
38 typedef struct GtkChildClass GtkChildClass;
39 typedef struct PropertyValue PropertyValue;
44 GtkChildClassFlags flags;
47 struct GtkStyleProviderData
49 GtkStyleProvider *provider;
62 GArray *style_classes;
63 GArray *child_style_classes;
64 GtkJunctionSides junction_sides;
67 struct GtkStyleContextPrivate
72 GList *providers_last;
74 GSList *icon_factories;
77 GtkWidgetPath *widget_path;
79 GArray *property_cache;
81 GtkStateFlags state_flags;
84 GtkThemingEngine *theming_engine;
86 GtkTextDirection direction;
95 static void gtk_style_context_finalize (GObject *object);
97 static void gtk_style_context_impl_set_property (GObject *object,
101 static void gtk_style_context_impl_get_property (GObject *object,
107 G_DEFINE_TYPE (GtkStyleContext, gtk_style_context, G_TYPE_OBJECT)
110 gtk_style_context_class_init (GtkStyleContextClass *klass)
112 GObjectClass *object_class = G_OBJECT_CLASS (klass);
114 object_class->finalize = gtk_style_context_finalize;
115 object_class->set_property = gtk_style_context_impl_set_property;
116 object_class->get_property = gtk_style_context_impl_get_property;
118 g_object_class_install_property (object_class,
120 g_param_spec_object ("screen",
122 P_("The associated GdkScreen"),
124 GTK_PARAM_READWRITE));
125 g_object_class_install_property (object_class,
127 g_param_spec_enum ("direction",
129 P_("Text direction"),
130 GTK_TYPE_TEXT_DIRECTION,
132 GTK_PARAM_READWRITE));
134 g_type_class_add_private (object_class, sizeof (GtkStyleContextPrivate));
137 static GtkStyleInfo *
138 style_info_new (void)
142 info = g_slice_new0 (GtkStyleInfo);
143 info->style_classes = g_array_new (FALSE, FALSE, sizeof (GQuark));
144 info->child_style_classes = g_array_new (FALSE, FALSE, sizeof (GtkChildClass));
150 style_info_free (GtkStyleInfo *info)
152 g_array_free (info->style_classes, TRUE);
153 g_array_free (info->child_style_classes, TRUE);
154 g_slice_free (GtkStyleInfo, info);
157 static GtkStyleInfo *
158 style_info_copy (const GtkStyleInfo *info)
162 copy = style_info_new ();
163 g_array_insert_vals (copy->style_classes, 0,
164 info->style_classes->data,
165 info->style_classes->len);
167 g_array_insert_vals (copy->child_style_classes, 0,
168 info->child_style_classes->data,
169 info->child_style_classes->len);
171 copy->junction_sides = info->junction_sides;
177 gtk_style_context_init (GtkStyleContext *style_context)
179 GtkStyleContextPrivate *priv;
182 priv = style_context->priv = G_TYPE_INSTANCE_GET_PRIVATE (style_context,
183 GTK_TYPE_STYLE_CONTEXT,
184 GtkStyleContextPrivate);
186 priv->store = gtk_style_set_new ();
187 priv->theming_engine = (GtkThemingEngine *) gtk_theming_engine_load (NULL);
189 priv->direction = GTK_TEXT_DIR_RTL;
191 /* Create default info store */
192 info = style_info_new ();
193 priv->info_stack = g_slist_prepend (priv->info_stack, info);
196 static GtkStyleProviderData *
197 style_provider_data_new (GtkStyleProvider *provider,
200 GtkStyleProviderData *data;
202 data = g_slice_new (GtkStyleProviderData);
203 data->provider = g_object_ref (provider);
204 data->priority = priority;
210 style_provider_data_free (GtkStyleProviderData *data)
212 g_object_unref (data->provider);
213 g_slice_free (GtkStyleProviderData, data);
217 clear_property_cache (GtkStyleContext *context)
219 GtkStyleContextPrivate *priv;
221 priv = context->priv;
223 if (priv->property_cache)
227 for (i = 0; i < priv->property_cache->len; i++)
229 PropertyValue *node = &g_array_index (priv->property_cache, PropertyValue, i);
231 g_param_spec_unref (node->pspec);
232 g_value_unset (&node->value);
235 g_array_free (priv->property_cache, TRUE);
236 priv->property_cache = NULL;
241 gtk_style_context_finalize (GObject *object)
243 GtkStyleContextPrivate *priv;
244 GtkStyleContext *style_context;
246 style_context = GTK_STYLE_CONTEXT (object);
247 priv = style_context->priv;
249 g_list_foreach (priv->providers, (GFunc) style_provider_data_free, NULL);
250 g_list_free (priv->providers);
252 clear_property_cache (GTK_STYLE_CONTEXT (object));
254 g_slist_foreach (priv->info_stack, (GFunc) style_info_free, NULL);
255 g_slist_free (priv->info_stack);
257 g_slist_foreach (priv->icon_factories, (GFunc) g_object_unref, NULL);
258 g_slist_free (priv->icon_factories);
260 G_OBJECT_CLASS (gtk_style_context_parent_class)->finalize (object);
264 gtk_style_context_impl_set_property (GObject *object,
269 GtkStyleContextPrivate *priv;
270 GtkStyleContext *style_context;
272 style_context = GTK_STYLE_CONTEXT (object);
273 priv = style_context->priv;
278 gtk_style_context_set_screen (style_context,
279 g_value_get_object (value));
282 gtk_style_context_set_direction (style_context,
283 g_value_get_enum (value));
286 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
292 gtk_style_context_impl_get_property (GObject *object,
297 GtkStyleContextPrivate *priv;
298 GtkStyleContext *style_context;
300 style_context = GTK_STYLE_CONTEXT (object);
301 priv = style_context->priv;
306 g_value_set_object (value, priv->screen);
309 g_value_set_enum (value, priv->direction);
312 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
318 rebuild_properties (GtkStyleContext *context)
320 GtkStyleContextPrivate *priv;
323 priv = context->priv;
324 list = priv->providers;
326 gtk_style_set_clear (priv->store);
330 GtkStyleProviderData *data;
331 GtkStyleSet *provider_style;
336 provider_style = gtk_style_provider_get_style (data->provider,
341 gtk_style_set_merge (priv->store, provider_style, TRUE);
342 g_object_unref (provider_style);
346 gtk_style_set_get (priv->store, GTK_STATE_NORMAL,
347 "engine", &priv->theming_engine,
352 rebuild_icon_factories (GtkStyleContext *context)
354 GtkStyleContextPrivate *priv;
357 priv = context->priv;
359 g_slist_foreach (priv->icon_factories, (GFunc) g_object_unref, NULL);
360 g_slist_free (priv->icon_factories);
361 priv->icon_factories = NULL;
363 for (providers = priv->providers_last; providers; providers = providers->prev)
365 GtkIconFactory *factory;
366 GtkStyleProviderData *data;
368 data = providers->data;
369 factory = gtk_style_provider_get_icon_factory (data->provider,
373 priv->icon_factories = g_slist_prepend (priv->icon_factories, factory);
378 gtk_style_context_add_provider (GtkStyleContext *context,
379 GtkStyleProvider *provider,
382 GtkStyleContextPrivate *priv;
383 GtkStyleProviderData *new_data;
384 gboolean added = FALSE;
387 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
388 g_return_if_fail (GTK_IS_STYLE_PROVIDER (provider));
390 priv = context->priv;
391 new_data = style_provider_data_new (provider, priority);
392 list = priv->providers;
396 GtkStyleProviderData *data;
400 /* Provider was already attached to the style
401 * context, remove in order to add the new data
403 if (data->provider == provider)
410 /* Remove and free link */
411 priv->providers = g_list_remove_link (priv->providers, link);
412 style_provider_data_free (link->data);
413 g_list_free_1 (link);
419 data->priority > priority)
421 priv->providers = g_list_insert_before (priv->providers, list, new_data);
429 priv->providers = g_list_append (priv->providers, new_data);
431 priv->providers_last = g_list_last (priv->providers);
433 if (priv->widget_path)
435 rebuild_properties (context);
436 clear_property_cache (context);
437 rebuild_icon_factories (context);
442 gtk_style_context_remove_provider (GtkStyleContext *context,
443 GtkStyleProvider *provider)
445 GtkStyleContextPrivate *priv;
446 gboolean removed = FALSE;
449 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
450 g_return_if_fail (GTK_IS_STYLE_PROVIDER (provider));
452 priv = context->priv;
453 list = priv->providers;
457 GtkStyleProviderData *data;
461 if (data->provider == provider)
463 priv->providers = g_list_remove_link (priv->providers, list);
464 style_provider_data_free (list->data);
465 g_list_free_1 (list);
477 priv->providers_last = g_list_last (priv->providers);
479 if (priv->widget_path)
481 rebuild_properties (context);
482 clear_property_cache (context);
483 rebuild_icon_factories (context);
489 gtk_style_context_get_property (GtkStyleContext *context,
490 const gchar *property,
494 GtkStyleContextPrivate *priv;
496 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
497 g_return_if_fail (property != NULL);
498 g_return_if_fail (state < GTK_STATE_LAST);
499 g_return_if_fail (value != NULL);
501 priv = context->priv;
502 gtk_style_set_get_property (priv->store, property, state, value);
506 gtk_style_context_get_valist (GtkStyleContext *context,
510 GtkStyleContextPrivate *priv;
512 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
513 g_return_if_fail (state < GTK_STATE_LAST);
515 priv = context->priv;
516 gtk_style_set_get_valist (priv->store, state, args);
520 gtk_style_context_get (GtkStyleContext *context,
524 GtkStyleContextPrivate *priv;
527 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
528 g_return_if_fail (state < GTK_STATE_LAST);
530 priv = context->priv;
532 va_start (args, state);
533 gtk_style_set_get_valist (priv->store, state, args);
538 gtk_style_context_set_state (GtkStyleContext *context,
541 GtkStyleContextPrivate *priv;
543 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
545 priv = context->priv;
546 priv->state_flags = flags;
550 gtk_style_context_get_state (GtkStyleContext *context)
552 GtkStyleContextPrivate *priv;
554 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), 0);
556 priv = context->priv;
557 return priv->state_flags;
561 gtk_style_context_is_state_set (GtkStyleContext *context,
564 GtkStyleContextPrivate *priv;
566 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), FALSE);
568 priv = context->priv;
572 case GTK_STATE_NORMAL:
573 return priv->state_flags == 0;
574 case GTK_STATE_ACTIVE:
575 return priv->state_flags & GTK_STATE_FLAG_ACTIVE;
576 case GTK_STATE_PRELIGHT:
577 return priv->state_flags & GTK_STATE_FLAG_PRELIGHT;
578 case GTK_STATE_SELECTED:
579 return priv->state_flags & GTK_STATE_FLAG_SELECTED;
580 case GTK_STATE_INSENSITIVE:
581 return priv->state_flags & GTK_STATE_FLAG_INSENSITIVE;
582 case GTK_STATE_INCONSISTENT:
583 return priv->state_flags & GTK_STATE_FLAG_INCONSISTENT;
584 case GTK_STATE_FOCUSED:
585 return priv->state_flags & GTK_STATE_FLAG_FOCUSED;
592 gtk_style_context_set_path (GtkStyleContext *context,
595 GtkStyleContextPrivate *priv;
597 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
598 g_return_if_fail (path != NULL);
600 priv = context->priv;
602 if (priv->widget_path)
604 gtk_widget_path_free (priv->widget_path);
605 priv->widget_path = NULL;
610 priv->widget_path = gtk_widget_path_copy (path);
611 rebuild_properties (context);
612 clear_property_cache (context);
613 rebuild_icon_factories (context);
617 G_CONST_RETURN GtkWidgetPath *
618 gtk_style_context_get_path (GtkStyleContext *context)
620 GtkStyleContextPrivate *priv;
622 priv = context->priv;
623 return priv->widget_path;
627 gtk_style_context_save (GtkStyleContext *context)
629 GtkStyleContextPrivate *priv;
632 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
634 priv = context->priv;
636 g_assert (priv->info_stack != NULL);
638 info = style_info_copy (priv->info_stack->data);
639 priv->info_stack = g_slist_prepend (priv->info_stack, info);
643 gtk_style_context_restore (GtkStyleContext *context)
645 GtkStyleContextPrivate *priv;
648 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
650 priv = context->priv;
652 if (priv->info_stack)
654 info = priv->info_stack->data;
655 priv->info_stack = g_slist_remove (priv->info_stack, info);
656 style_info_free (info);
659 if (!priv->info_stack)
661 g_warning ("Unpaired gtk_style_context_restore() call");
663 /* Create default region */
664 info = style_info_new ();
665 priv->info_stack = g_slist_prepend (priv->info_stack, info);
668 if (priv->widget_path)
672 /* Update widget path regions */
673 gtk_widget_path_iter_clear_regions (priv->widget_path, 0);
674 info = priv->info_stack->data;
676 for (i = 0; i < info->child_style_classes->len; i++)
678 GtkChildClass *child_class;
680 child_class = &g_array_index (info->child_style_classes, GtkChildClass, i);
681 gtk_widget_path_iter_add_region (priv->widget_path, 0,
682 g_quark_to_string (child_class->class_quark),
689 style_class_find (GArray *array,
694 gboolean found = FALSE;
699 if (!array || array->len == 0)
703 max = array->len - 1;
710 item = g_array_index (array, GQuark, mid);
712 if (class_quark == item)
714 else if (class_quark > item)
719 while (!found && min <= max);
731 child_style_class_find (GArray *array,
736 gboolean found = FALSE;
741 if (!array || array->len == 0)
745 max = array->len - 1;
749 GtkChildClass *child_class;
752 child_class = &g_array_index (array, GtkChildClass, mid);
754 if (child_class->class_quark == class_quark)
756 else if (child_class->class_quark > class_quark)
761 while (!found && min <= max);
773 gtk_style_context_set_class (GtkStyleContext *context,
774 const gchar *class_name)
776 GtkStyleContextPrivate *priv;
781 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
782 g_return_if_fail (class_name != NULL);
784 priv = context->priv;
785 class_quark = g_quark_from_string (class_name);
787 g_assert (priv->info_stack != NULL);
788 info = priv->info_stack->data;
790 if (!style_class_find (info->style_classes, class_quark, &position))
791 g_array_insert_val (info->style_classes, position, class_quark);
795 gtk_style_context_unset_class (GtkStyleContext *context,
796 const gchar *class_name)
798 GtkStyleContextPrivate *priv;
803 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
804 g_return_if_fail (class_name != NULL);
806 class_quark = g_quark_try_string (class_name);
811 priv = context->priv;
813 g_assert (priv->info_stack != NULL);
814 info = priv->info_stack->data;
816 if (style_class_find (info->style_classes, class_quark, &position))
817 g_array_remove_index (info->style_classes, position);
821 gtk_style_context_has_class (GtkStyleContext *context,
822 const gchar *class_name)
824 GtkStyleContextPrivate *priv;
828 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), FALSE);
829 g_return_val_if_fail (class_name != NULL, FALSE);
831 class_quark = g_quark_try_string (class_name);
836 priv = context->priv;
838 g_assert (priv->info_stack != NULL);
839 info = priv->info_stack->data;
841 if (style_class_find (info->style_classes, class_quark, NULL))
848 gtk_style_context_list_child_classes (GtkStyleContext *context)
850 GtkStyleContextPrivate *priv;
852 GList *classes = NULL;
855 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), NULL);
857 priv = context->priv;
859 g_assert (priv->info_stack != NULL);
860 info = priv->info_stack->data;
862 for (i = 0; i < info->child_style_classes->len; i++)
864 GtkChildClass *child_class;
865 const gchar *class_name;
867 child_class = &g_array_index (info->child_style_classes,
871 class_name = g_quark_to_string (child_class->class_quark);
872 classes = g_list_prepend (classes, (gchar *) class_name);
879 gtk_style_context_set_child_class (GtkStyleContext *context,
880 const gchar *class_name,
881 GtkChildClassFlags flags)
883 GtkStyleContextPrivate *priv;
888 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
889 g_return_if_fail (class_name != NULL);
891 priv = context->priv;
892 class_quark = g_quark_from_string (class_name);
894 g_assert (priv->info_stack != NULL);
895 info = priv->info_stack->data;
897 if (!child_style_class_find (info->child_style_classes, class_quark, &position))
899 GtkChildClass child_class;
901 child_class.class_quark = class_quark;
902 child_class.flags = flags;
904 g_array_insert_val (info->child_style_classes, position, child_class);
906 if (priv->widget_path)
908 gtk_widget_path_iter_add_region (priv->widget_path, 0, class_name, flags);
909 rebuild_properties (context);
915 gtk_style_context_unset_child_class (GtkStyleContext *context,
916 const gchar *class_name)
918 GtkStyleContextPrivate *priv;
923 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
924 g_return_if_fail (class_name != NULL);
926 class_quark = g_quark_try_string (class_name);
931 priv = context->priv;
933 g_assert (priv->info_stack != NULL);
934 info = priv->info_stack->data;
936 if (child_style_class_find (info->child_style_classes, class_quark, &position))
938 g_array_remove_index (info->child_style_classes, position);
940 if (priv->widget_path)
942 gtk_widget_path_iter_remove_region (priv->widget_path, 0, class_name);
943 rebuild_properties (context);
949 gtk_style_context_has_child_class (GtkStyleContext *context,
950 const gchar *class_name,
951 GtkChildClassFlags *flags_return)
953 GtkStyleContextPrivate *priv;
958 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), FALSE);
959 g_return_val_if_fail (class_name != NULL, FALSE);
964 class_quark = g_quark_try_string (class_name);
969 priv = context->priv;
971 g_assert (priv->info_stack != NULL);
972 info = priv->info_stack->data;
974 if (child_style_class_find (info->child_style_classes, class_quark, &position))
978 GtkChildClass *child_class;
980 child_class = &g_array_index (info->child_style_classes,
981 GtkChildClass, position);
983 *flags_return = child_class->flags;
992 style_property_values_cmp (gconstpointer bsearch_node1,
993 gconstpointer bsearch_node2)
995 const PropertyValue *val1 = bsearch_node1;
996 const PropertyValue *val2 = bsearch_node2;
998 if (val1->widget_type == val2->widget_type)
999 return val1->pspec < val2->pspec ? -1 : val1->pspec == val2->pspec ? 0 : 1;
1001 return val1->widget_type < val2->widget_type ? -1 : 1;
1005 _gtk_style_context_peek_style_property (GtkStyleContext *context,
1009 GtkStyleContextPrivate *priv;
1010 PropertyValue *pcache, key = { 0 };
1014 priv = context->priv;
1016 key.widget_type = widget_type;
1019 /* need value cache array */
1020 if (!priv->property_cache)
1021 priv->property_cache = g_array_new (FALSE, FALSE, sizeof (PropertyValue));
1024 pcache = bsearch (&key,
1025 priv->property_cache->data, priv->property_cache->len,
1026 sizeof (PropertyValue), style_property_values_cmp);
1028 return &pcache->value;
1032 while (i < priv->property_cache->len &&
1033 style_property_values_cmp (&key, &g_array_index (priv->property_cache, PropertyValue, i)) >= 0)
1036 g_array_insert_val (priv->property_cache, i, key);
1037 pcache = &g_array_index (priv->property_cache, PropertyValue, i);
1039 /* cache miss, initialize value type, then set contents */
1040 g_param_spec_ref (pcache->pspec);
1041 g_value_init (&pcache->value, G_PARAM_SPEC_VALUE_TYPE (pspec));
1043 if (priv->widget_path)
1045 for (list = priv->providers_last; list; list = list->prev)
1047 GtkStyleProviderData *data;
1051 if (gtk_style_provider_get_style_property (data->provider, priv->widget_path,
1052 pspec->name, &pcache->value))
1053 return &pcache->value;
1057 /* not supplied by any provider, revert to default */
1058 g_param_value_set_default (pspec, &pcache->value);
1060 return &pcache->value;
1064 gtk_style_context_get_style_property (GtkStyleContext *context,
1065 const gchar *property_name,
1068 GtkStyleContextPrivate *priv;
1069 GtkWidgetClass *widget_class;
1071 const GValue *peek_value;
1074 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1075 g_return_if_fail (property_name != NULL);
1076 g_return_if_fail (value != NULL);
1078 priv = context->priv;
1080 if (!priv->widget_path)
1083 widget_type = gtk_widget_path_get_widget_type (priv->widget_path);
1085 widget_class = g_type_class_ref (widget_type);
1086 pspec = gtk_widget_class_find_style_property (widget_class, property_name);
1087 g_type_class_unref (widget_class);
1091 g_warning ("%s: widget class `%s' has no style property named `%s'",
1093 g_type_name (widget_type),
1098 peek_value = _gtk_style_context_peek_style_property (context,
1102 if (G_VALUE_TYPE (value) == G_VALUE_TYPE (peek_value))
1103 g_value_copy (peek_value, value);
1104 else if (g_value_type_transformable (G_VALUE_TYPE (peek_value), G_VALUE_TYPE (value)))
1105 g_value_transform (peek_value, value);
1107 g_warning ("can't retrieve style property `%s' of type `%s' as value of type `%s'",
1109 G_VALUE_TYPE_NAME (peek_value),
1110 G_VALUE_TYPE_NAME (value));
1114 gtk_style_context_get_style_valist (GtkStyleContext *context,
1117 GtkStyleContextPrivate *priv;
1118 const gchar *prop_name;
1120 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1122 prop_name = va_arg (args, const gchar *);
1123 priv = context->priv;
1125 if (!priv->widget_path)
1130 GtkWidgetClass *widget_class;
1132 const GValue *peek_value;
1136 widget_type = gtk_widget_path_get_widget_type (priv->widget_path);
1138 widget_class = g_type_class_ref (widget_type);
1139 pspec = gtk_widget_class_find_style_property (widget_class, prop_name);
1140 g_type_class_unref (widget_class);
1144 g_warning ("%s: widget class `%s' has no style property named `%s'",
1146 g_type_name (widget_type),
1151 peek_value = _gtk_style_context_peek_style_property (context,
1155 G_VALUE_LCOPY (peek_value, args, 0, &error);
1159 g_warning ("can't retrieve style property `%s' of type `%s': %s",
1161 G_VALUE_TYPE_NAME (peek_value),
1166 prop_name = va_arg (args, const gchar *);
1171 gtk_style_context_get_style (GtkStyleContext *context,
1176 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1178 va_start (args, context);
1179 gtk_style_context_get_style_valist (context, args);
1185 gtk_style_context_lookup_icon_set (GtkStyleContext *context,
1186 const gchar *stock_id)
1188 GtkStyleContextPrivate *priv;
1191 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), NULL);
1192 g_return_val_if_fail (stock_id != NULL, NULL);
1194 priv = context->priv;
1196 for (list = priv->icon_factories; list; list = list->next)
1198 GtkIconFactory *factory;
1199 GtkIconSet *icon_set;
1201 factory = list->data;
1202 icon_set = gtk_icon_factory_lookup (factory, stock_id);
1208 return gtk_icon_factory_lookup_default (stock_id);
1212 gtk_style_context_set_screen (GtkStyleContext *context,
1215 GtkStyleContextPrivate *priv;
1217 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1219 priv = context->priv;
1220 priv->screen = screen;
1222 g_object_notify (G_OBJECT (context), "screen");
1226 gtk_style_context_get_screen (GtkStyleContext *context)
1228 GtkStyleContextPrivate *priv;
1230 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), NULL);
1232 priv = context->priv;
1233 return priv->screen;
1237 gtk_style_context_set_direction (GtkStyleContext *context,
1238 GtkTextDirection direction)
1240 GtkStyleContextPrivate *priv;
1242 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1244 priv = context->priv;
1245 priv->direction = direction;
1247 g_object_notify (G_OBJECT (context), "direction");
1251 gtk_style_context_get_direction (GtkStyleContext *context)
1253 GtkStyleContextPrivate *priv;
1255 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), GTK_TEXT_DIR_LTR);
1257 priv = context->priv;
1258 return priv->direction;
1262 gtk_style_context_set_junction_sides (GtkStyleContext *context,
1263 GtkJunctionSides sides)
1265 GtkStyleContextPrivate *priv;
1268 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1270 priv = context->priv;
1271 info = priv->info_stack->data;
1272 info->junction_sides = sides;
1276 gtk_style_context_get_junction_sides (GtkStyleContext *context)
1278 GtkStyleContextPrivate *priv;
1281 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), 0);
1283 priv = context->priv;
1284 info = priv->info_stack->data;
1285 return info->junction_sides;
1289 gtk_style_context_lookup_color (GtkStyleContext *context,
1290 const gchar *color_name,
1293 GtkStyleContextPrivate *priv;
1294 GtkSymbolicColor *sym_color;
1296 g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), FALSE);
1297 g_return_val_if_fail (color_name != NULL, FALSE);
1298 g_return_val_if_fail (color != NULL, FALSE);
1300 priv = context->priv;
1301 sym_color = gtk_style_set_lookup_color (priv->store, color_name);
1306 return gtk_symbolic_color_resolve (sym_color, priv->store, color);
1311 gtk_render_check (GtkStyleContext *context,
1318 GtkStyleContextPrivate *priv;
1319 GtkThemingEngineClass *engine_class;
1321 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1322 g_return_if_fail (cr != NULL);
1324 priv = context->priv;
1325 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1327 _gtk_theming_engine_set_context (priv->theming_engine, context);
1328 engine_class->render_check (priv->theming_engine, cr,
1329 x, y, width, height);
1333 gtk_render_option (GtkStyleContext *context,
1340 GtkStyleContextPrivate *priv;
1341 GtkThemingEngineClass *engine_class;
1343 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1344 g_return_if_fail (cr != NULL);
1346 priv = context->priv;
1347 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1349 _gtk_theming_engine_set_context (priv->theming_engine, context);
1350 engine_class->render_option (priv->theming_engine, cr,
1351 x, y, width, height);
1355 gtk_render_arrow (GtkStyleContext *context,
1362 GtkStyleContextPrivate *priv;
1363 GtkThemingEngineClass *engine_class;
1365 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1366 g_return_if_fail (cr != NULL);
1368 priv = context->priv;
1369 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1371 _gtk_theming_engine_set_context (priv->theming_engine, context);
1372 engine_class->render_arrow (priv->theming_engine, cr,
1377 gtk_render_background (GtkStyleContext *context,
1384 GtkStyleContextPrivate *priv;
1385 GtkThemingEngineClass *engine_class;
1387 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1388 g_return_if_fail (cr != NULL);
1390 priv = context->priv;
1391 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1393 _gtk_theming_engine_set_context (priv->theming_engine, context);
1394 engine_class->render_background (priv->theming_engine, cr, x, y, width, height);
1398 gtk_render_frame (GtkStyleContext *context,
1405 GtkStyleContextPrivate *priv;
1406 GtkThemingEngineClass *engine_class;
1408 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1409 g_return_if_fail (cr != NULL);
1411 priv = context->priv;
1412 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1414 _gtk_theming_engine_set_context (priv->theming_engine, context);
1415 engine_class->render_frame (priv->theming_engine, cr, x, y, width, height);
1419 gtk_render_expander (GtkStyleContext *context,
1426 GtkStyleContextPrivate *priv;
1427 GtkThemingEngineClass *engine_class;
1429 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1430 g_return_if_fail (cr != NULL);
1432 priv = context->priv;
1433 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1435 _gtk_theming_engine_set_context (priv->theming_engine, context);
1436 engine_class->render_expander (priv->theming_engine, cr, x, y, width, height);
1440 gtk_render_focus (GtkStyleContext *context,
1447 GtkStyleContextPrivate *priv;
1448 GtkThemingEngineClass *engine_class;
1450 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1451 g_return_if_fail (cr != NULL);
1453 priv = context->priv;
1454 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1456 _gtk_theming_engine_set_context (priv->theming_engine, context);
1457 engine_class->render_focus (priv->theming_engine, cr, x, y, width, height);
1461 gtk_render_layout (GtkStyleContext *context,
1465 PangoLayout *layout)
1467 GtkStyleContextPrivate *priv;
1468 GtkThemingEngineClass *engine_class;
1470 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1471 g_return_if_fail (cr != NULL);
1473 priv = context->priv;
1474 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1476 _gtk_theming_engine_set_context (priv->theming_engine, context);
1477 engine_class->render_layout (priv->theming_engine, cr, x, y, layout);
1481 gtk_render_line (GtkStyleContext *context,
1488 GtkStyleContextPrivate *priv;
1489 GtkThemingEngineClass *engine_class;
1491 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1492 g_return_if_fail (cr != NULL);
1494 priv = context->priv;
1495 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1497 _gtk_theming_engine_set_context (priv->theming_engine, context);
1498 engine_class->render_line (priv->theming_engine, cr, x0, y0, x1, y1);
1502 gtk_render_slider (GtkStyleContext *context,
1508 GtkOrientation orientation)
1510 GtkStyleContextPrivate *priv;
1511 GtkThemingEngineClass *engine_class;
1513 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1514 g_return_if_fail (cr != NULL);
1516 priv = context->priv;
1517 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1519 _gtk_theming_engine_set_context (priv->theming_engine, context);
1520 engine_class->render_slider (priv->theming_engine, cr, x, y, width, height, orientation);
1524 gtk_render_frame_gap (GtkStyleContext *context,
1530 GtkPositionType gap_side,
1534 GtkStyleContextPrivate *priv;
1535 GtkThemingEngineClass *engine_class;
1537 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1538 g_return_if_fail (cr != NULL);
1540 priv = context->priv;
1541 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1543 _gtk_theming_engine_set_context (priv->theming_engine, context);
1544 engine_class->render_frame_gap (priv->theming_engine, cr,
1545 x, y, width, height, gap_side,
1550 gtk_render_extension (GtkStyleContext *context,
1556 GtkPositionType gap_side)
1558 GtkStyleContextPrivate *priv;
1559 GtkThemingEngineClass *engine_class;
1561 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1562 g_return_if_fail (cr != NULL);
1564 priv = context->priv;
1565 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1567 _gtk_theming_engine_set_context (priv->theming_engine, context);
1568 engine_class->render_extension (priv->theming_engine, cr, x, y, width, height, gap_side);
1572 gtk_render_handle (GtkStyleContext *context,
1578 GtkOrientation orientation)
1580 GtkStyleContextPrivate *priv;
1581 GtkThemingEngineClass *engine_class;
1583 g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
1584 g_return_if_fail (cr != NULL);
1586 priv = context->priv;
1587 engine_class = GTK_THEMING_ENGINE_GET_CLASS (priv->theming_engine);
1589 _gtk_theming_engine_set_context (priv->theming_engine, context);
1590 engine_class->render_handle (priv->theming_engine, cr, x, y, width, height, orientation);
1593 #define __GTK_STYLE_CONTEXT_C__
1594 #include "gtkaliasdef.c"