]> Pileus Git - ~andy/gtk/blob - gtk/gtkcssenumvalue.c
cssvalue: Add _gtk_css_value_transition()
[~andy/gtk] / gtk / gtkcssenumvalue.c
1 /* GTK - The GIMP Toolkit
2  * Copyright (C) 2011 Red Hat, Inc.
3  *
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.
8  *
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.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with this library. If not, see <http://www.gnu.org/licenses/>.
16  */
17
18 #include "config.h"
19
20 #include "gtkcssenumvalueprivate.h"
21
22 #include "gtkstylepropertyprivate.h"
23
24 /* repeated API */
25
26 struct _GtkCssValue {
27   GTK_CSS_VALUE_BASE
28   int value;
29   const char *name;
30 };
31
32 static void
33 gtk_css_value_enum_free (GtkCssValue *value)
34 {
35   g_slice_free (GtkCssValue, value);
36 }
37
38 static gboolean
39 gtk_css_value_enum_equal (const GtkCssValue *enum1,
40                           const GtkCssValue *enum2)
41 {
42   return enum1 == enum2;
43 }
44
45 static GtkCssValue *
46 gtk_css_value_enum_transition (GtkCssValue *start,
47                                GtkCssValue *end,
48                                double       progress)
49 {
50   return NULL;
51 }
52
53 static void
54 gtk_css_value_enum_print (const GtkCssValue *value,
55                           GString           *string)
56 {
57   g_string_append (string, value->name);
58 }
59
60 /* GtkBorderStyle */
61
62 static const GtkCssValueClass GTK_CSS_VALUE_BORDER_STYLE = {
63   gtk_css_value_enum_free,
64   gtk_css_value_enum_equal,
65   gtk_css_value_enum_transition,
66   gtk_css_value_enum_print
67 };
68
69 static GtkCssValue border_style_values[] = {
70   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_NONE, "none" },
71   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_SOLID, "solid" },
72   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_INSET, "inset" },
73   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_OUTSET, "outset" },
74   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_HIDDEN, "hidden" },
75   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_DOTTED, "dotted" },
76   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_DASHED, "dashed" },
77   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_DOUBLE, "double" },
78   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_GROOVE, "groove" },
79   { &GTK_CSS_VALUE_BORDER_STYLE, 1, GTK_BORDER_STYLE_RIDGE, "ridge" }
80 };
81
82 GtkCssValue *
83 _gtk_css_border_style_value_new (GtkBorderStyle border_style)
84 {
85   g_return_val_if_fail (border_style < G_N_ELEMENTS (border_style_values), NULL);
86
87   return _gtk_css_value_ref (&border_style_values[border_style]);
88 }
89
90 GtkCssValue *
91 _gtk_css_border_style_value_try_parse (GtkCssParser *parser)
92 {
93   guint i;
94
95   g_return_val_if_fail (parser != NULL, NULL);
96
97   for (i = 0; i < G_N_ELEMENTS (border_style_values); i++)
98     {
99       if (_gtk_css_parser_try (parser, border_style_values[i].name, TRUE))
100         return _gtk_css_value_ref (&border_style_values[i]);
101     }
102
103   return NULL;
104 }
105
106 GtkBorderStyle
107 _gtk_css_border_style_value_get (const GtkCssValue *value)
108 {
109   g_return_val_if_fail (value->class == &GTK_CSS_VALUE_BORDER_STYLE, GTK_BORDER_STYLE_NONE);
110
111   return value->value;
112 }
113
114 /* PangoStyle */
115
116 static const GtkCssValueClass GTK_CSS_VALUE_FONT_STYLE = {
117   gtk_css_value_enum_free,
118   gtk_css_value_enum_equal,
119   gtk_css_value_enum_transition,
120   gtk_css_value_enum_print
121 };
122
123 static GtkCssValue font_style_values[] = {
124   { &GTK_CSS_VALUE_FONT_STYLE, 1, PANGO_STYLE_NORMAL, "normal" },
125   { &GTK_CSS_VALUE_FONT_STYLE, 1, PANGO_STYLE_OBLIQUE, "oblique" },
126   { &GTK_CSS_VALUE_FONT_STYLE, 1, PANGO_STYLE_ITALIC, "italic" }
127 };
128
129 GtkCssValue *
130 _gtk_css_font_style_value_new (PangoStyle font_style)
131 {
132   g_return_val_if_fail (font_style < G_N_ELEMENTS (font_style_values), NULL);
133
134   return _gtk_css_value_ref (&font_style_values[font_style]);
135 }
136
137 GtkCssValue *
138 _gtk_css_font_style_value_try_parse (GtkCssParser *parser)
139 {
140   guint i;
141
142   g_return_val_if_fail (parser != NULL, NULL);
143
144   for (i = 0; i < G_N_ELEMENTS (font_style_values); i++)
145     {
146       if (_gtk_css_parser_try (parser, font_style_values[i].name, TRUE))
147         return _gtk_css_value_ref (&font_style_values[i]);
148     }
149
150   return NULL;
151 }
152
153 PangoStyle
154 _gtk_css_font_style_value_get (const GtkCssValue *value)
155 {
156   g_return_val_if_fail (value->class == &GTK_CSS_VALUE_FONT_STYLE, PANGO_STYLE_NORMAL);
157
158   return value->value;
159 }
160
161 /* PangoVariant */
162
163 static const GtkCssValueClass GTK_CSS_VALUE_FONT_VARIANT = {
164   gtk_css_value_enum_free,
165   gtk_css_value_enum_equal,
166   gtk_css_value_enum_transition,
167   gtk_css_value_enum_print
168 };
169
170 static GtkCssValue font_variant_values[] = {
171   { &GTK_CSS_VALUE_FONT_VARIANT, 1, PANGO_VARIANT_NORMAL, "normal" },
172   { &GTK_CSS_VALUE_FONT_VARIANT, 1, PANGO_VARIANT_SMALL_CAPS, "small-caps" }
173 };
174
175 GtkCssValue *
176 _gtk_css_font_variant_value_new (PangoVariant font_variant)
177 {
178   g_return_val_if_fail (font_variant < G_N_ELEMENTS (font_variant_values), NULL);
179
180   return _gtk_css_value_ref (&font_variant_values[font_variant]);
181 }
182
183 GtkCssValue *
184 _gtk_css_font_variant_value_try_parse (GtkCssParser *parser)
185 {
186   guint i;
187
188   g_return_val_if_fail (parser != NULL, NULL);
189
190   for (i = 0; i < G_N_ELEMENTS (font_variant_values); i++)
191     {
192       if (_gtk_css_parser_try (parser, font_variant_values[i].name, TRUE))
193         return _gtk_css_value_ref (&font_variant_values[i]);
194     }
195
196   return NULL;
197 }
198
199 PangoVariant
200 _gtk_css_font_variant_value_get (const GtkCssValue *value)
201 {
202   g_return_val_if_fail (value->class == &GTK_CSS_VALUE_FONT_VARIANT, PANGO_VARIANT_NORMAL);
203
204   return value->value;
205 }
206
207 /* PangoWeight */
208
209 static const GtkCssValueClass GTK_CSS_VALUE_FONT_WEIGHT = {
210   gtk_css_value_enum_free,
211   gtk_css_value_enum_equal,
212   gtk_css_value_enum_transition,
213   gtk_css_value_enum_print
214 };
215
216 static GtkCssValue font_weight_values[] = {
217   { &GTK_CSS_VALUE_FONT_WEIGHT, 1, PANGO_WEIGHT_THIN, "100" },
218   { &GTK_CSS_VALUE_FONT_WEIGHT, 1, PANGO_WEIGHT_ULTRALIGHT, "200" },
219   { &GTK_CSS_VALUE_FONT_WEIGHT, 1, PANGO_WEIGHT_LIGHT, "300" },
220   { &GTK_CSS_VALUE_FONT_WEIGHT, 1, PANGO_WEIGHT_NORMAL, "normal" },
221   { &GTK_CSS_VALUE_FONT_WEIGHT, 1, PANGO_WEIGHT_MEDIUM, "500" },
222   { &GTK_CSS_VALUE_FONT_WEIGHT, 1, PANGO_WEIGHT_SEMIBOLD, "600" },
223   { &GTK_CSS_VALUE_FONT_WEIGHT, 1, PANGO_WEIGHT_BOLD, "bold" },
224   { &GTK_CSS_VALUE_FONT_WEIGHT, 1, PANGO_WEIGHT_ULTRABOLD, "800" },
225   { &GTK_CSS_VALUE_FONT_WEIGHT, 1, PANGO_WEIGHT_HEAVY, "900" }
226 };
227
228 GtkCssValue *
229 _gtk_css_font_weight_value_new (PangoWeight font_weight)
230 {
231   guint i;
232
233   for (i = 0; i < G_N_ELEMENTS (font_weight_values); i++)
234     {
235       if (font_weight_values[i].value == font_weight)
236         return _gtk_css_value_ref (&font_weight_values[i]);
237     }
238
239   g_return_val_if_reached (NULL);
240 }
241
242 GtkCssValue *
243 _gtk_css_font_weight_value_try_parse (GtkCssParser *parser)
244 {
245   guint i;
246
247   g_return_val_if_fail (parser != NULL, NULL);
248
249   for (i = 0; i < G_N_ELEMENTS (font_weight_values); i++)
250     {
251       if (_gtk_css_parser_try (parser, font_weight_values[i].name, TRUE))
252         return _gtk_css_value_ref (&font_weight_values[i]);
253     }
254   /* special cases go here */
255   if (_gtk_css_parser_try (parser, "400", TRUE))
256     return _gtk_css_value_ref (&font_weight_values[3]);
257   if (_gtk_css_parser_try (parser, "700", TRUE))
258     return _gtk_css_value_ref (&font_weight_values[6]);
259
260   return NULL;
261 }
262
263 PangoWeight
264 _gtk_css_font_weight_value_get (const GtkCssValue *value)
265 {
266   g_return_val_if_fail (value->class == &GTK_CSS_VALUE_FONT_WEIGHT, PANGO_WEIGHT_NORMAL);
267
268   return value->value;
269 }
270
271 /* GtkCssArea */
272
273 static const GtkCssValueClass GTK_CSS_VALUE_AREA = {
274   gtk_css_value_enum_free,
275   gtk_css_value_enum_equal,
276   gtk_css_value_enum_transition,
277   gtk_css_value_enum_print
278 };
279
280 static GtkCssValue area_values[] = {
281   { &GTK_CSS_VALUE_AREA, 1, GTK_CSS_AREA_BORDER_BOX, "border-box" },
282   { &GTK_CSS_VALUE_AREA, 1, GTK_CSS_AREA_PADDING_BOX, "padding-box" },
283   { &GTK_CSS_VALUE_AREA, 1, GTK_CSS_AREA_CONTENT_BOX, "content-box" }
284 };
285
286 GtkCssValue *
287 _gtk_css_area_value_new (GtkCssArea area)
288 {
289   guint i;
290
291   for (i = 0; i < G_N_ELEMENTS (area_values); i++)
292     {
293       if (area_values[i].value == area)
294         return _gtk_css_value_ref (&area_values[i]);
295     }
296
297   g_return_val_if_reached (NULL);
298 }
299
300 GtkCssValue *
301 _gtk_css_area_value_try_parse (GtkCssParser *parser)
302 {
303   guint i;
304
305   g_return_val_if_fail (parser != NULL, NULL);
306
307   for (i = 0; i < G_N_ELEMENTS (area_values); i++)
308     {
309       if (_gtk_css_parser_try (parser, area_values[i].name, TRUE))
310         return _gtk_css_value_ref (&area_values[i]);
311     }
312
313   return NULL;
314 }
315
316 GtkCssArea
317 _gtk_css_area_value_get (const GtkCssValue *value)
318 {
319   g_return_val_if_fail (value->class == &GTK_CSS_VALUE_AREA, GTK_CSS_AREA_BORDER_BOX);
320
321   return value->value;
322 }
323