summaryrefslogtreecommitdiff
path: root/gtk/gtkcssstylefuncs.c
diff options
context:
space:
mode:
authorBenjamin Otte <otte@redhat.com>2012-01-02 15:44:45 +0100
committerBenjamin Otte <otte@redhat.com>2012-01-09 18:37:55 +0100
commite87cf5d7896746c8e9b81b037843c670f728287c (patch)
tree3e7cd8614154e458243d4e5e93d6db8d3bb16380 /gtk/gtkcssstylefuncs.c
parent29382c130529caf94e037767b6dd3e2897071c0d (diff)
downloadgtk+-e87cf5d7896746c8e9b81b037843c670f728287c.tar.gz
css: Redo value resolving
Instead of on-demand resolvage, we now resolve during lookup. The step is done via _gtk_css_style_property_compute_value() which currently calls into _gtk_css_style_compute_value() That function has all the old resolving machinery. The only part missing for now is the handling of win32 code. It will be added back later.
Diffstat (limited to 'gtk/gtkcssstylefuncs.c')
-rw-r--r--gtk/gtkcssstylefuncs.c189
1 files changed, 166 insertions, 23 deletions
diff --git a/gtk/gtkcssstylefuncs.c b/gtk/gtkcssstylefuncs.c
index 5ba366c0c9..a7b31f1cab 100644
--- a/gtk/gtkcssstylefuncs.c
+++ b/gtk/gtkcssstylefuncs.c
@@ -35,6 +35,7 @@
#include "gtkgradient.h"
#include "gtkprivatetypebuiltins.h"
#include "gtkshadowprivate.h"
+#include "gtkstylecontextprivate.h"
#include "gtkthemingengine.h"
#include "gtktypebuiltins.h"
#include "gtkwin32themeprivate.h"
@@ -46,22 +47,31 @@
static GHashTable *parse_funcs = NULL;
static GHashTable *print_funcs = NULL;
+static GHashTable *compute_funcs = NULL;
typedef gboolean (* GtkStyleParseFunc) (GtkCssParser *parser,
GFile *base,
GValue *value);
typedef void (* GtkStylePrintFunc) (const GValue *value,
GString *string);
+typedef void (* GtkStylePrintFunc) (const GValue *value,
+ GString *string);
+typedef void (* GtkStyleComputeFunc) (GValue *computed,
+ GtkStyleContext *context,
+ const GValue *specified);
static void
-register_conversion_function (GType type,
- GtkStyleParseFunc parse,
- GtkStylePrintFunc print)
+register_conversion_function (GType type,
+ GtkStyleParseFunc parse,
+ GtkStylePrintFunc print,
+ GtkStyleComputeFunc compute)
{
if (parse)
g_hash_table_insert (parse_funcs, GSIZE_TO_POINTER (type), parse);
if (print)
g_hash_table_insert (print_funcs, GSIZE_TO_POINTER (type), print);
+ if (compute)
+ g_hash_table_insert (compute_funcs, GSIZE_TO_POINTER (type), compute);
}
static void
@@ -197,6 +207,26 @@ rgba_value_print (const GValue *value,
}
}
+static void
+rgba_value_compute (GValue *computed,
+ GtkStyleContext *context,
+ const GValue *specified)
+{
+ GdkRGBA rgba, white = { 1, 1, 1, 1 };
+
+ if (G_VALUE_HOLDS (specified, GTK_TYPE_SYMBOLIC_COLOR))
+ {
+ if (_gtk_style_context_resolve_color (context,
+ g_value_get_boxed (specified),
+ &rgba))
+ g_value_set_boxed (computed, &rgba);
+ else
+ g_value_set_boxed (computed, &white);
+ }
+ else
+ g_value_copy (specified, computed);
+}
+
static gboolean
color_value_parse (GtkCssParser *parser,
GFile *base,
@@ -245,6 +275,31 @@ color_value_print (const GValue *value,
}
}
+static void
+color_value_compute (GValue *computed,
+ GtkStyleContext *context,
+ const GValue *specified)
+{
+ GdkRGBA rgba;
+ GdkColor color = { 0, 65535, 65535, 65535 };
+
+ if (G_VALUE_HOLDS (specified, GTK_TYPE_SYMBOLIC_COLOR))
+ {
+ if (_gtk_style_context_resolve_color (context,
+ g_value_get_boxed (specified),
+ &rgba))
+ {
+ color.red = rgba.red * 65535. + 0.5;
+ color.green = rgba.green * 65535. + 0.5;
+ color.blue = rgba.blue * 65535. + 0.5;
+ }
+
+ g_value_set_boxed (computed, &color);
+ }
+ else
+ g_value_copy (specified, computed);
+}
+
static gboolean
symbolic_color_value_parse (GtkCssParser *parser,
GFile *base,
@@ -1044,6 +1099,23 @@ pattern_value_print (const GValue *value,
}
}
+static void
+pattern_value_compute (GValue *computed,
+ GtkStyleContext *context,
+ const GValue *specified)
+{
+ if (G_VALUE_HOLDS (specified, GTK_TYPE_GRADIENT))
+ {
+ cairo_pattern_t *gradient;
+
+ gradient = gtk_gradient_resolve_for_context (g_value_get_boxed (specified), context);
+
+ g_value_take_boxed (computed, gradient);
+ }
+ else
+ g_value_copy (specified, computed);
+}
+
static gboolean
shadow_value_parse (GtkCssParser *parser,
GFile *base,
@@ -1146,6 +1218,20 @@ shadow_value_print (const GValue *value,
_gtk_shadow_print (shadow, string);
}
+static void
+shadow_value_compute (GValue *computed,
+ GtkStyleContext *context,
+ const GValue *specified)
+{
+ GtkShadow *shadow;
+
+ shadow = g_value_get_boxed (specified);
+ if (shadow)
+ shadow = _gtk_shadow_resolve (shadow, context);
+
+ g_value_take_boxed (computed, shadow);
+}
+
static gboolean
background_repeat_value_parse (GtkCssParser *parser,
GFile *file,
@@ -1326,67 +1412,88 @@ gtk_css_style_funcs_init (void)
parse_funcs = g_hash_table_new (NULL, NULL);
print_funcs = g_hash_table_new (NULL, NULL);
+ compute_funcs = g_hash_table_new (NULL, NULL);
register_conversion_function (GDK_TYPE_RGBA,
rgba_value_parse,
- rgba_value_print);
+ rgba_value_print,
+ rgba_value_compute);
register_conversion_function (GDK_TYPE_COLOR,
color_value_parse,
- color_value_print);
+ color_value_print,
+ color_value_compute);
register_conversion_function (GTK_TYPE_SYMBOLIC_COLOR,
symbolic_color_value_parse,
- symbolic_color_value_print);
+ symbolic_color_value_print,
+ NULL);
register_conversion_function (PANGO_TYPE_FONT_DESCRIPTION,
font_description_value_parse,
- font_description_value_print);
+ font_description_value_print,
+ NULL);
register_conversion_function (G_TYPE_BOOLEAN,
boolean_value_parse,
- boolean_value_print);
+ boolean_value_print,
+ NULL);
register_conversion_function (G_TYPE_INT,
int_value_parse,
- int_value_print);
+ int_value_print,
+ NULL);
register_conversion_function (G_TYPE_UINT,
uint_value_parse,
- uint_value_print);
+ uint_value_print,
+ NULL);
register_conversion_function (G_TYPE_DOUBLE,
double_value_parse,
- double_value_print);
+ double_value_print,
+ NULL);
register_conversion_function (G_TYPE_FLOAT,
float_value_parse,
- float_value_print);
+ float_value_print,
+ NULL);
register_conversion_function (G_TYPE_STRING,
string_value_parse,
- string_value_print);
+ string_value_print,
+ NULL);
register_conversion_function (GTK_TYPE_THEMING_ENGINE,
theming_engine_value_parse,
- theming_engine_value_print);
+ theming_engine_value_print,
+ NULL);
register_conversion_function (GTK_TYPE_ANIMATION_DESCRIPTION,
animation_description_value_parse,
- animation_description_value_print);
+ animation_description_value_print,
+ NULL);
register_conversion_function (GTK_TYPE_BORDER,
border_value_parse,
- border_value_print);
+ border_value_print,
+ NULL);
register_conversion_function (GTK_TYPE_GRADIENT,
gradient_value_parse,
- gradient_value_print);
+ gradient_value_print,
+ NULL);
register_conversion_function (CAIRO_GOBJECT_TYPE_PATTERN,
pattern_value_parse,
- pattern_value_print);
+ pattern_value_print,
+ pattern_value_compute);
register_conversion_function (GTK_TYPE_CSS_BORDER_IMAGE_REPEAT,
border_image_repeat_value_parse,
- border_image_repeat_value_print);
+ border_image_repeat_value_print,
+ NULL);
register_conversion_function (GTK_TYPE_SHADOW,
shadow_value_parse,
- shadow_value_print);
+ shadow_value_print,
+ shadow_value_compute);
register_conversion_function (G_TYPE_ENUM,
enum_value_parse,
- enum_value_print);
+ enum_value_print,
+ NULL);
register_conversion_function (G_TYPE_FLAGS,
flags_value_parse,
- flags_value_print);
+ flags_value_print,
+ NULL);
register_conversion_function (GTK_TYPE_CSS_BACKGROUND_REPEAT,
background_repeat_value_parse,
- background_repeat_value_print);
+ background_repeat_value_print,
+ NULL);
}
/**
@@ -1463,3 +1570,39 @@ _gtk_css_style_print_value (const GValue *value,
func (value, string);
}
+/**
+ * _gtk_css_style_compute_value:
+ * @computed: (out): a value to be filled with the result
+ * @context: the context to use for computing the value
+ * @specified: the value to use for the computation
+ *
+ * Converts the @specified value into the @computed value using the
+ * information in @context. The values must have matching types, ie
+ * @specified must be a result of a call to
+ * _gtk_css_style_parse_value() with the same type as @computed.
+ **/
+void
+_gtk_css_style_compute_value (GValue *computed,
+ GtkStyleContext *context,
+ const GValue *specified)
+{
+ GtkStyleComputeFunc func;
+
+ g_return_if_fail (G_IS_VALUE (computed));
+ g_return_if_fail (GTK_IS_STYLE_CONTEXT (context));
+ g_return_if_fail (G_IS_VALUE (specified));
+
+ gtk_css_style_funcs_init ();
+
+ func = g_hash_table_lookup (compute_funcs,
+ GSIZE_TO_POINTER (G_VALUE_TYPE (computed)));
+ if (func == NULL)
+ func = g_hash_table_lookup (compute_funcs,
+ GSIZE_TO_POINTER (g_type_fundamental (G_VALUE_TYPE (computed))));
+
+ if (func)
+ func (computed, context, specified);
+ else
+ g_value_copy (specified, computed);
+}
+