diff --git a/gtk/Makefile.am b/gtk/Makefile.am index 5559b074ec..4a19f2ae43 100644 --- a/gtk/Makefile.am +++ b/gtk/Makefile.am @@ -445,6 +445,7 @@ gtk_private_h_sources = \ gtkcssrgbavalueprivate.h \ gtkcsssectionprivate.h \ gtkcssselectorprivate.h \ + gtkcssshadowsvalueprivate.h \ gtkcssshadowvalueprivate.h \ gtkcssshorthandpropertyprivate.h \ gtkcssstringvalueprivate.h \ @@ -653,6 +654,7 @@ gtk_base_c_sources = \ gtkcsssection.c \ gtkcssselector.c \ gtkcssstringvalue.c \ + gtkcssshadowsvalue.c \ gtkcssshadowvalue.c \ gtkcssshorthandproperty.c \ gtkcssshorthandpropertyimpl.c \ diff --git a/gtk/gtkcssshadowsvalue.c b/gtk/gtkcssshadowsvalue.c new file mode 100644 index 0000000000..41b521fb6d --- /dev/null +++ b/gtk/gtkcssshadowsvalue.c @@ -0,0 +1,234 @@ +/* GTK - The GIMP Toolkit + * Copyright (C) 2011 Red Hat, Inc. + * + * Author: Cosimo Cecchi + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see . + */ + +#include "config.h" + +#include "gtkcssshadowsvalueprivate.h" + +#include "gtkcssshadowvalueprivate.h" + +#include + +struct _GtkCssValue { + GTK_CSS_VALUE_BASE + guint len; + GtkCssValue *values[1]; +}; + +static void +gtk_css_value_shadows_free (GtkCssValue *value) +{ + guint i; + + for (i = 0; i < value->len; i++) + { + _gtk_css_value_unref (value->values[i]); + } + + g_slice_free1 (sizeof (GtkCssValue) + sizeof (GtkCssValue *) * (value->len - 1), value); +} + +static gboolean +gtk_css_value_shadows_equal (const GtkCssValue *value1, + const GtkCssValue *value2) +{ + guint i; + + /* XXX: Should we fill up here? */ + if (value1->len != value2->len) + return FALSE; + + for (i = 0; i < value1->len; i++) + { + if (!_gtk_css_value_equal (value1->values[i], + value2->values[i])) + return FALSE; + } + + return TRUE; +} + +static GtkCssValue * +gtk_css_value_shadows_transition (GtkCssValue *start, + GtkCssValue *end, + double progress) +{ + return NULL; +} + +static void +gtk_css_value_shadows_print (const GtkCssValue *value, + GString *string) +{ + guint i; + + if (value->len == 0) + { + g_string_append (string, "none"); + return; + } + + for (i = 0; i < value->len; i++) + { + if (i > 0) + g_string_append (string, ", "); + _gtk_css_value_print (value->values[i], string); + } +} + +static const GtkCssValueClass GTK_CSS_VALUE_SHADOWS = { + gtk_css_value_shadows_free, + gtk_css_value_shadows_equal, + gtk_css_value_shadows_transition, + gtk_css_value_shadows_print +}; + +static GtkCssValue none_singleton = { >K_CSS_VALUE_SHADOWS, 1, 0, { NULL } }; + +GtkCssValue * +_gtk_css_shadows_value_new_none (void) +{ + return _gtk_css_value_ref (&none_singleton); +} + +GtkCssValue * +gtk_css_shadows_value_new (GtkCssValue **values, + guint len) +{ + GtkCssValue *result; + + g_return_val_if_fail (values != NULL, NULL); + g_return_val_if_fail (len > 0, NULL); + + result = _gtk_css_value_alloc (>K_CSS_VALUE_SHADOWS, sizeof (GtkCssValue) + sizeof (GtkCssValue *) * (len - 1)); + result->len = len; + memcpy (&result->values[0], values, sizeof (GtkCssValue *) * len); + + return result; +} + +GtkCssValue * +_gtk_css_shadows_value_parse (GtkCssParser *parser) +{ + GtkCssValue *value, *result; + GPtrArray *values; + + if (_gtk_css_parser_try (parser, "none", TRUE)) + return _gtk_css_shadows_value_new_none (); + + values = g_ptr_array_new (); + + do { + value = _gtk_css_shadow_value_parse (parser); + + if (value == NULL) + { + g_ptr_array_set_free_func (values, (GDestroyNotify) _gtk_css_value_unref); + g_ptr_array_free (values, TRUE); + return NULL; + } + + g_ptr_array_add (values, value); + } while (_gtk_css_parser_try (parser, ",", TRUE)); + + result = gtk_css_shadows_value_new ((GtkCssValue **) values->pdata, values->len); + g_ptr_array_free (values, TRUE); + return result; +} + +GtkCssValue * +_gtk_css_shadows_value_compute (GtkCssValue *value, + GtkStyleContext *context) +{ + GtkCssValue *result; + guint i; + + g_return_val_if_fail (value->class == >K_CSS_VALUE_SHADOWS, NULL); + + if (value->len == 0) + return _gtk_css_value_ref (value); + + result = gtk_css_shadows_value_new (value->values, value->len); + for (i = 0; i < value->len; i++) + { + result->values[i] = _gtk_css_shadow_value_compute (value->values[i], context); + } + + return result; +} + +void +_gtk_css_shadows_value_paint_layout (const GtkCssValue *shadows, + cairo_t *cr, + PangoLayout *layout) +{ + guint i; + + g_return_if_fail (shadows->class == >K_CSS_VALUE_SHADOWS); + + for (i = 0; i < shadows->len; i++) + { + _gtk_css_shadow_value_paint_layout (shadows->values[i], cr, layout); + } +} + +void +_gtk_css_shadows_value_paint_icon (const GtkCssValue *shadows, + cairo_t *cr) +{ + guint i; + + g_return_if_fail (shadows->class == >K_CSS_VALUE_SHADOWS); + + for (i = 0; i < shadows->len; i++) + { + _gtk_css_shadow_value_paint_icon (shadows->values[i], cr); + } +} + +void +_gtk_css_shadows_value_paint_spinner (const GtkCssValue *shadows, + cairo_t *cr, + gdouble radius, + gdouble progress) +{ + guint i; + + g_return_if_fail (shadows->class == >K_CSS_VALUE_SHADOWS); + + for (i = 0; i < shadows->len; i++) + { + _gtk_css_shadow_value_paint_spinner (shadows->values[i], cr, radius, progress); + } +} + +void +_gtk_css_shadows_value_paint_box (const GtkCssValue *shadows, + cairo_t *cr, + const GtkRoundedBox *padding_box) +{ + guint i; + + g_return_if_fail (shadows->class == >K_CSS_VALUE_SHADOWS); + + for (i = 0; i < shadows->len; i++) + { + _gtk_css_shadow_value_paint_box (shadows->values[i], cr, padding_box); + } +} diff --git a/gtk/gtkcssshadowsvalueprivate.h b/gtk/gtkcssshadowsvalueprivate.h new file mode 100644 index 0000000000..0918278b4e --- /dev/null +++ b/gtk/gtkcssshadowsvalueprivate.h @@ -0,0 +1,56 @@ +/* GTK - The GIMP Toolkit + * Copyright (C) 2011 Red Hat, Inc. + * + * Author: Cosimo Cecchi + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library. If not, see . + */ + +#ifndef __GTK_CSS_SHADOWS_VALUE_H__ +#define __GTK_CSS_SHADOWS_VALUE_H__ + +#include +#include + +#include "gtktypes.h" +#include "gtkcssparserprivate.h" +#include "gtkcssvalueprivate.h" +#include "gtkroundedboxprivate.h" + +G_BEGIN_DECLS + +GtkCssValue * _gtk_css_shadows_value_new_none (void); +GtkCssValue * _gtk_css_shadows_value_parse (GtkCssParser *parser); + +GtkCssValue * _gtk_css_shadows_value_compute (GtkCssValue *shadows, + GtkStyleContext *context); + +void _gtk_css_shadows_value_paint_layout (const GtkCssValue *shadows, + cairo_t *cr, + PangoLayout *layout); + +void _gtk_css_shadows_value_paint_icon (const GtkCssValue *shadows, + cairo_t *cr); + +void _gtk_css_shadows_value_paint_spinner (const GtkCssValue *shadows, + cairo_t *cr, + gdouble radius, + gdouble progress); +void _gtk_css_shadows_value_paint_box (const GtkCssValue *shadows, + cairo_t *cr, + const GtkRoundedBox *padding_box); + +G_END_DECLS + +#endif /* __GTK_CSS_SHADOWS_VALUE_H__ */ diff --git a/gtk/gtkcssstylepropertyimpl.c b/gtk/gtkcssstylepropertyimpl.c index 68b2eede02..dc814ca604 100644 --- a/gtk/gtkcssstylepropertyimpl.c +++ b/gtk/gtkcssstylepropertyimpl.c @@ -48,7 +48,7 @@ #include "gtkcssenumvalueprivate.h" #include "gtkcssnumbervalueprivate.h" #include "gtkcssrgbavalueprivate.h" -#include "gtkcssshadowvalueprivate.h" +#include "gtkcssshadowsvalueprivate.h" #include "gtkcssstringvalueprivate.h" #include "gtksymboliccolorprivate.h" #include "gtkthemingengine.h" @@ -486,7 +486,7 @@ shadow_value_parse (GtkCssStyleProperty *property, GtkCssParser *parser, GFile *base) { - return _gtk_css_array_value_parse (parser, _gtk_css_shadow_value_parse, TRUE); + return _gtk_css_shadows_value_parse (parser); } static GtkCssValue * @@ -494,7 +494,7 @@ shadow_value_compute (GtkCssStyleProperty *property, GtkStyleContext *context, GtkCssValue *specified) { - return _gtk_css_array_value_compute (specified, _gtk_css_shadow_value_compute, context); + return _gtk_css_shadows_value_compute (specified, context); } static GtkCssValue * @@ -1337,7 +1337,7 @@ _gtk_css_style_property_init_properties (void) NULL, NULL, NULL, - _gtk_css_array_value_new (NULL)); + _gtk_css_shadows_value_new_none ()); gtk_css_style_property_register ("icon-shadow", GTK_CSS_PROPERTY_ICON_SHADOW, @@ -1349,7 +1349,7 @@ _gtk_css_style_property_init_properties (void) NULL, NULL, NULL, - _gtk_css_array_value_new (NULL)); + _gtk_css_shadows_value_new_none ()); gtk_css_style_property_register ("box-shadow", GTK_CSS_PROPERTY_BOX_SHADOW, @@ -1361,7 +1361,7 @@ _gtk_css_style_property_init_properties (void) NULL, NULL, NULL, - _gtk_css_array_value_new (NULL)); + _gtk_css_shadows_value_new_none ()); gtk_css_style_property_register ("margin-top", GTK_CSS_PROPERTY_MARGIN_TOP, diff --git a/gtk/gtkthemingbackground.c b/gtk/gtkthemingbackground.c index d4d133940b..4da48ca6c0 100644 --- a/gtk/gtkthemingbackground.c +++ b/gtk/gtkthemingbackground.c @@ -26,6 +26,7 @@ #include "gtkcssarrayvalueprivate.h" #include "gtkcssenumvalueprivate.h" #include "gtkcssimagevalueprivate.h" +#include "gtkcssshadowsvalueprivate.h" #include "gtkcsstypesprivate.h" #include "gtkthemingengineprivate.h" @@ -299,17 +300,9 @@ static void _gtk_theming_background_apply_shadow (GtkThemingBackground *bg, cairo_t *cr) { - GtkCssValue *shadows; - guint i; - - shadows = _gtk_style_context_peek_property (bg->context, GTK_CSS_PROPERTY_BOX_SHADOW); - - for (i = 0; i < _gtk_css_array_value_get_n_values (shadows); i++) - { - _gtk_css_shadow_value_paint_box (_gtk_css_array_value_get_nth (shadows, i), - cr, - &bg->padding_box); - } + _gtk_css_shadows_value_paint_box (_gtk_style_context_peek_property (bg->context, GTK_CSS_PROPERTY_BOX_SHADOW), + cr, + &bg->padding_box); } static void diff --git a/gtk/gtkthemingbackgroundprivate.h b/gtk/gtkthemingbackgroundprivate.h index de9bd6cd7b..e3e19745cd 100644 --- a/gtk/gtkthemingbackgroundprivate.h +++ b/gtk/gtkthemingbackgroundprivate.h @@ -26,7 +26,6 @@ #include "gtkcssimageprivate.h" #include "gtkstylecontextprivate.h" #include "gtkroundedboxprivate.h" -#include "gtkcssshadowvalueprivate.h" G_BEGIN_DECLS diff --git a/gtk/gtkthemingengine.c b/gtk/gtkthemingengine.c index cd7ecad9df..631cc35cfe 100644 --- a/gtk/gtkthemingengine.c +++ b/gtk/gtkthemingengine.c @@ -31,7 +31,7 @@ #include "gtkcssarrayvalueprivate.h" #include "gtkcssenumvalueprivate.h" #include "gtkcssrgbavalueprivate.h" -#include "gtkcssshadowvalueprivate.h" +#include "gtkcssshadowsvalueprivate.h" #include "gtkcsstypesprivate.h" #include "gtkthemingengineprivate.h" #include "gtkroundedboxprivate.h" @@ -2101,11 +2101,9 @@ gtk_theming_engine_render_layout (GtkThemingEngine *engine, PangoLayout *layout) { GdkRGBA fg_color; - GtkCssValue *shadows; GtkStateFlags flags; gdouble progress; gboolean running; - guint i; cairo_save (cr); flags = gtk_theming_engine_get_state (engine); @@ -2134,14 +2132,10 @@ gtk_theming_engine_render_layout (GtkThemingEngine *engine, fg_color.alpha = CLAMP (fg_color.alpha + ((other_fg.alpha - fg_color.alpha) * progress), 0, 1); } - shadows = _gtk_theming_engine_peek_property (engine, GTK_CSS_PROPERTY_TEXT_SHADOW); - prepare_context_for_layout (cr, x, y, layout); - for (i = 0; i < _gtk_css_array_value_get_n_values (shadows); i++) - { - _gtk_css_shadow_value_paint_layout (_gtk_css_array_value_get_nth (shadows, i), cr, layout); - } + _gtk_css_shadows_value_paint_layout (_gtk_theming_engine_peek_property (engine, GTK_CSS_PROPERTY_TEXT_SHADOW), + cr, layout); gdk_cairo_set_source_rgba (cr, &fg_color); pango_cairo_show_layout (cr, layout); @@ -2755,11 +2749,9 @@ render_spinner (GtkThemingEngine *engine, gdouble height) { GtkStateFlags state; - GtkCssValue *shadows; GdkRGBA color; gdouble progress; gdouble radius; - guint i; state = gtk_theming_engine_get_state (engine); @@ -2769,18 +2761,14 @@ render_spinner (GtkThemingEngine *engine, radius = MIN (width / 2, height / 2); gtk_theming_engine_get_color (engine, state, &color); - shadows = _gtk_theming_engine_peek_property (engine, GTK_CSS_PROPERTY_ICON_SHADOW); cairo_save (cr); cairo_translate (cr, x + width / 2, y + height / 2); - for (i = 0; i < _gtk_css_array_value_get_n_values (shadows); i++) - { - _gtk_css_shadow_value_paint_spinner (_gtk_css_array_value_get_nth (shadows, i), - cr, - radius, - progress); - } + _gtk_css_shadows_value_paint_spinner (_gtk_theming_engine_peek_property (engine, GTK_CSS_PROPERTY_ICON_SHADOW), + cr, + radius, + progress); _gtk_theming_engine_paint_spinner (cr, radius, @@ -2947,18 +2935,11 @@ gtk_theming_engine_render_icon (GtkThemingEngine *engine, gdouble x, gdouble y) { - GtkCssValue *shadows; - guint i; - cairo_save (cr); gdk_cairo_set_source_pixbuf (cr, pixbuf, x, y); - shadows = _gtk_theming_engine_peek_property (engine, GTK_CSS_PROPERTY_ICON_SHADOW); - for (i = 0; i < _gtk_css_array_value_get_n_values (shadows); i++) - { - _gtk_css_shadow_value_paint_icon (_gtk_css_array_value_get_nth (shadows, i), cr); - } + _gtk_css_shadows_value_paint_icon (_gtk_theming_engine_peek_property (engine, GTK_CSS_PROPERTY_ICON_SHADOW), cr); cairo_paint (cr);