Code

Unify stat type for older glib.
[inkscape.git] / src / libcroco / cr-rgb.c
1 /* -*- Mode: C; indent-tabs-mode:nil; c-basic-offset: 8-*- */
3 /*
4  * This file is part of The Croco Library
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of version 2.1 of the GNU Lesser General Public
8  * License as published by the Free Software Foundation.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
18  * USA
19  * 
20  * Author: Dodji Seketeli
21  * See COPYRIGHTS file for copyrights information.
22  */
25 #include <stdio.h>
26 #include <string.h>
27 #include "cr-rgb.h"
28 #include "cr-term.h"
29 #include "cr-parser.h"
31 static CRRgb gv_standard_colors[] = {
32         {"aliceblue",   240, 248, 255, FALSE, FALSE, FALSE, {0,0,0}},
33         {"antiquewhite",        250, 235, 215, FALSE, FALSE, FALSE, {0,0,0}},
34         {"aqua",          0, 255, 255, FALSE, FALSE, FALSE, {0,0,0}},
35         {"aquamarine",  127, 255, 212, FALSE, FALSE, FALSE, {0,0,0}},
36         {"azure",       240, 255, 255, FALSE, FALSE, FALSE, {0,0,0}},
37         {"beige",       245, 245, 220, FALSE, FALSE, FALSE, {0,0,0}},
38         {"bisque",      255, 228, 196, FALSE, FALSE, FALSE, {0,0,0}},
39         {"black",         0,   0,   0, FALSE, FALSE, FALSE, {0,0,0}},
40         {"blanchedalmond",      255, 235, 205, FALSE, FALSE, FALSE, {0,0,0}},
41         {"blue",          0,   0, 255, FALSE, FALSE, FALSE, {0,0,0}},
42         {"blueviolet",  138,  43, 226, FALSE, FALSE, FALSE, {0,0,0}},
43         {"brown",       165,  42,  42, FALSE, FALSE, FALSE, {0,0,0}},
44         {"burlywood",   222, 184, 135, FALSE, FALSE, FALSE, {0,0,0}},
45         {"cadetblue",    95, 158, 160, FALSE, FALSE, FALSE, {0,0,0}},
46         {"chartreuse",  127, 255,   0, FALSE, FALSE, FALSE, {0,0,0}},
47         {"chocolate",   210, 105,  30, FALSE, FALSE, FALSE, {0,0,0}},
48         {"coral",       255, 127,  80, FALSE, FALSE, FALSE, {0,0,0}},
49         {"cornflowerblue",      100, 149, 237, FALSE, FALSE, FALSE, {0,0,0}},
50         {"cornsilk",    255, 248, 220, FALSE, FALSE, FALSE, {0,0,0}},
51         {"crimson",     220,  20,  60, FALSE, FALSE, FALSE, {0,0,0}},
52         {"cyan",          0, 255, 255, FALSE, FALSE, FALSE, {0,0,0}},
53         {"darkblue",      0,   0, 139, FALSE, FALSE, FALSE, {0,0,0}},
54         {"darkcyan",      0, 139, 139, FALSE, FALSE, FALSE, {0,0,0}},
55         {"darkgoldenrod",       184, 134,  11, FALSE, FALSE, FALSE, {0,0,0}},
56         {"darkgray",    169, 169, 169, FALSE, FALSE, FALSE, {0,0,0}},
57         {"darkgreen",     0, 100,   0, FALSE, FALSE, FALSE, {0,0,0}},
58         {"darkgrey",    169, 169, 169, FALSE, FALSE, FALSE, {0,0,0}},
59         {"darkkhaki",   189, 183, 107, FALSE, FALSE, FALSE, {0,0,0}},
60         {"darkmagenta", 139,   0, 139, FALSE, FALSE, FALSE, {0,0,0}},
61         {"darkolivegreen",       85, 107,  47, FALSE, FALSE, FALSE, {0,0,0}},
62         {"darkorange",  255, 140,   0, FALSE, FALSE, FALSE, {0,0,0}},
63         {"darkorchid",  153,  50, 204, FALSE, FALSE, FALSE, {0,0,0}},
64         {"darkred",     139,   0,   0, FALSE, FALSE, FALSE, {0,0,0}},
65         {"darksalmon",  233, 150, 122, FALSE, FALSE, FALSE, {0,0,0}},
66         {"darkseagreen",        143, 188, 143, FALSE, FALSE, FALSE, {0,0,0}},
67         {"darkslateblue",        72,  61, 139, FALSE, FALSE, FALSE, {0,0,0}},
68         {"darkslategray",        47,  79,  79, FALSE, FALSE, FALSE, {0,0,0}},
69         {"darkslategrey",        47,  79,  79, FALSE, FALSE, FALSE, {0,0,0}},
70         {"darkturquoise",         0, 206, 209, FALSE, FALSE, FALSE, {0,0,0}},
71         {"darkviolet",  148,   0, 211, FALSE, FALSE, FALSE, {0,0,0}},
72         {"deeppink",    255,  20, 147, FALSE, FALSE, FALSE, {0,0,0}},
73         {"deepskyblue",   0, 191, 255, FALSE, FALSE, FALSE, {0,0,0}},
74         {"dimgray",     105, 105, 105, FALSE, FALSE, FALSE, {0,0,0}},
75         {"dimgrey",     105, 105, 105, FALSE, FALSE, FALSE, {0,0,0}},
76         {"dodgerblue",   30, 144, 255, FALSE, FALSE, FALSE, {0,0,0}},
77         {"firebrick",   178,  34,  34, FALSE, FALSE, FALSE, {0,0,0}},
78         {"floralwhite", 255, 250, 240, FALSE, FALSE, FALSE, {0,0,0}},
79         {"forestgreen",  34, 139,  34, FALSE, FALSE, FALSE, {0,0,0}},
80         {"fuchsia",     255,   0, 255, FALSE, FALSE, FALSE, {0,0,0}},
81         {"gainsboro",   220, 220, 220, FALSE, FALSE, FALSE, {0,0,0}},
82         {"ghostwhite",  248, 248, 255, FALSE, FALSE, FALSE, {0,0,0}},
83         {"gold",        255, 215,   0, FALSE, FALSE, FALSE, {0,0,0}},
84         {"goldenrod",   218, 165,  32, FALSE, FALSE, FALSE, {0,0,0}},
85         {"gray",        128, 128, 128, FALSE, FALSE, FALSE, {0,0,0}},
86         {"grey",        128, 128, 128, FALSE, FALSE, FALSE, {0,0,0}},
87         {"green",         0, 128,   0, FALSE, FALSE, FALSE, {0,0,0}},
88         {"greenyellow", 173, 255,  47, FALSE, FALSE, FALSE, {0,0,0}},
89         {"honeydew",    240, 255, 240, FALSE, FALSE, FALSE, {0,0,0}},
90         {"hotpink",     255, 105, 180, FALSE, FALSE, FALSE, {0,0,0}},
91         {"indianred",   205,  92,  92, FALSE, FALSE, FALSE, {0,0,0}},
92         {"indigo",       75,   0, 130, FALSE, FALSE, FALSE, {0,0,0}},
93         {"ivory",       255, 255, 240, FALSE, FALSE, FALSE, {0,0,0}},
94         {"khaki",       240, 230, 140, FALSE, FALSE, FALSE, {0,0,0}},
95         {"lavender",    230, 230, 250, FALSE, FALSE, FALSE, {0,0,0}},
96         {"lavenderblush",       255, 240, 245, FALSE, FALSE, FALSE, {0,0,0}},
97         {"lawngreen",   124, 252,   0, FALSE, FALSE, FALSE, {0,0,0}},
98         {"lemonchiffon",        255, 250, 205, FALSE, FALSE, FALSE, {0,0,0}},
99         {"lightblue",   173, 216, 230, FALSE, FALSE, FALSE, {0,0,0}},
100         {"lightcoral",  240, 128, 128, FALSE, FALSE, FALSE, {0,0,0}},
101         {"lightcyan",   224, 255, 255, FALSE, FALSE, FALSE, {0,0,0}},
102         {"lightgoldenrodyellow",        250, 250, 210, FALSE, FALSE, FALSE, {0,0,0}},
103         {"lightgray",   211, 211, 211, FALSE, FALSE, FALSE, {0,0,0}},
104         {"lightgreen",  144, 238, 144, FALSE, FALSE, FALSE, {0,0,0}},
105         {"lightgrey",   211, 211, 211, FALSE, FALSE, FALSE, {0,0,0}},
106         {"lightpink",   255, 182, 193, FALSE, FALSE, FALSE, {0,0,0}},
107         {"lightsalmon", 255, 160, 122, FALSE, FALSE, FALSE, {0,0,0}},
108         {"lightseagreen",        32, 178, 170, FALSE, FALSE, FALSE, {0,0,0}},
109         {"lightskyblue",        135, 206, 250, FALSE, FALSE, FALSE, {0,0,0}},
110         {"lightslategray",      119, 136, 153, FALSE, FALSE, FALSE, {0,0,0}},
111         {"lightslategrey",      119, 136, 153, FALSE, FALSE, FALSE, {0,0,0}},
112         {"lightsteelblue",      176, 196, 222, FALSE, FALSE, FALSE, {0,0,0}},
113         {"lightyellow", 255, 255, 224, FALSE, FALSE, FALSE, {0,0,0}},
114         {"lime",          0, 255,   0, FALSE, FALSE, FALSE, {0,0,0}},
115         {"limegreen",    50, 205,  50, FALSE, FALSE, FALSE, {0,0,0}},
116         {"linen",       250, 240, 230, FALSE, FALSE, FALSE, {0,0,0}},
117         {"magenta",     255,   0, 255, FALSE, FALSE, FALSE, {0,0,0}},
118         {"maroon",      128,   0,   0, FALSE, FALSE, FALSE, {0,0,0}},
119         {"mediumaquamarine",    102, 205, 170, FALSE, FALSE, FALSE, {0,0,0}},
120         {"mediumblue",    0,   0, 205, FALSE, FALSE, FALSE, {0,0,0}},
121         {"mediumorchid",        186,  85, 211, FALSE, FALSE, FALSE, {0,0,0}},
122         {"mediumpurple",        147, 112, 219, FALSE, FALSE, FALSE, {0,0,0}},
123         {"mediumseagreen",       60, 179, 113, FALSE, FALSE, FALSE, {0,0,0}},
124         {"mediumslateblue",     123, 104, 238, FALSE, FALSE, FALSE, {0,0,0}},
125         {"mediumspringgreen",     0, 250, 154, FALSE, FALSE, FALSE, {0,0,0}},
126         {"mediumturquoise",      72, 209, 204, FALSE, FALSE, FALSE, {0,0,0}},
127         {"mediumvioletred",     199,  21, 133, FALSE, FALSE, FALSE, {0,0,0}},
128         {"midnightblue",         25,  25, 112, FALSE, FALSE, FALSE, {0,0,0}},
129         {"mintcream",   245, 255, 250, FALSE, FALSE, FALSE, {0,0,0}},
130         {"mistyrose",   255, 228, 225, FALSE, FALSE, FALSE, {0,0,0}},
131         {"moccasin",    255, 228, 181, FALSE, FALSE, FALSE, {0,0,0}},
132         {"navajowhite", 255, 222, 173, FALSE, FALSE, FALSE, {0,0,0}},
133         {"navy",          0,   0, 128, FALSE, FALSE, FALSE, {0,0,0}},
134         {"oldlace",     253, 245, 230, FALSE, FALSE, FALSE, {0,0,0}},
135         {"olive",       128, 128,   0, FALSE, FALSE, FALSE, {0,0,0}},
136         {"olivedrab",   107, 142,  35, FALSE, FALSE, FALSE, {0,0,0}},
137         {"orange",      255, 165,   0, FALSE, FALSE, FALSE, {0,0,0}},
138         {"orangered",   255,  69,   0, FALSE, FALSE, FALSE, {0,0,0}},
139         {"orchid",      218, 112, 214, FALSE, FALSE, FALSE, {0,0,0}},
140         {"palegoldenrod",       238, 232, 170, FALSE, FALSE, FALSE, {0,0,0}},
141         {"palegreen",   152, 251, 152, FALSE, FALSE, FALSE, {0,0,0}},
142         {"paleturquoise",       175, 238, 238, FALSE, FALSE, FALSE, {0,0,0}},
143         {"palevioletred",       219, 112, 147, FALSE, FALSE, FALSE, {0,0,0}},
144         {"papayawhip",  255, 239, 213, FALSE, FALSE, FALSE, {0,0,0}},
145         {"peachpuff",   255, 218, 185, FALSE, FALSE, FALSE, {0,0,0}},
146         {"peru",        205, 133,  63, FALSE, FALSE, FALSE, {0,0,0}},
147         {"pink",        255, 192, 203, FALSE, FALSE, FALSE, {0,0,0}},
148         {"plum",        221, 160, 221, FALSE, FALSE, FALSE, {0,0,0}},
149         {"powderblue",  176, 224, 230, FALSE, FALSE, FALSE, {0,0,0}},
150         {"purple",      128,   0, 128, FALSE, FALSE, FALSE, {0,0,0}},
151         {"red",         255,   0,   0, FALSE, FALSE, FALSE, {0,0,0}},
152         {"rosybrown",   188, 143, 143, FALSE, FALSE, FALSE, {0,0,0}},
153         {"royalblue",    65, 105, 225, FALSE, FALSE, FALSE, {0,0,0}},
154         {"saddlebrown", 139,  69,  19, FALSE, FALSE, FALSE, {0,0,0}},
155         {"salmon",      250, 128, 114, FALSE, FALSE, FALSE, {0,0,0}},
156         {"sandybrown",  244, 164,  96, FALSE, FALSE, FALSE, {0,0,0}},
157         {"seagreen",     46, 139,  87, FALSE, FALSE, FALSE, {0,0,0}},
158         {"seashell",    255, 245, 238, FALSE, FALSE, FALSE, {0,0,0}},
159         {"sienna",      160,  82,  45, FALSE, FALSE, FALSE, {0,0,0}},
160         {"silver",      192, 192, 192, FALSE, FALSE, FALSE, {0,0,0}},
161         {"skyblue",     135, 206, 235, FALSE, FALSE, FALSE, {0,0,0}},
162         {"slateblue",   106,  90, 205, FALSE, FALSE, FALSE, {0,0,0}},
163         {"slategray",   112, 128, 144, FALSE, FALSE, FALSE, {0,0,0}},
164         {"slategrey",   112, 128, 144, FALSE, FALSE, FALSE, {0,0,0}},
165         {"snow",        255, 250, 250, FALSE, FALSE, FALSE, {0,0,0}},
166         {"springgreen",   0, 255, 127, FALSE, FALSE, FALSE, {0,0,0}},
167         {"steelblue",    70, 130, 180, FALSE, FALSE, FALSE, {0,0,0}},
168         {"tan",         210, 180, 140, FALSE, FALSE, FALSE, {0,0,0}},
169         {"teal",          0, 128, 128, FALSE, FALSE, FALSE, {0,0,0}},
170         {"thistle",     216, 191, 216, FALSE, FALSE, FALSE, {0,0,0}},
171         {"tomato",      255,  99,  71, FALSE, FALSE, FALSE, {0,0,0}},
172         {"turquoise",    64, 224, 208, FALSE, FALSE, FALSE, {0,0,0}},
173         {"violet",      238, 130, 238, FALSE, FALSE, FALSE, {0,0,0}},
174         {"wheat",       245, 222, 179, FALSE, FALSE, FALSE, {0,0,0}},
175         {"white",       255, 255, 255, FALSE, FALSE, FALSE, {0,0,0}},
176         {"whitesmoke",  245, 245, 245, FALSE, FALSE, FALSE, {0,0,0}},
177         {"yellow",      255, 255,   0, FALSE, FALSE, FALSE, {0,0,0}},
178         {"yellowgreen", 154, 205,  50, FALSE, FALSE, FALSE, {0,0,0}},
179         {"transparent", 255, 255, 255, FALSE, FALSE, TRUE, {0,0,0}}
180 };
182 /**
183  *The default constructor of #CRRgb.
184  *@return the newly built instance of #CRRgb
185  */
186 CRRgb *
187 cr_rgb_new (void)
189         CRRgb *result = (CRRgb *)g_try_malloc (sizeof (CRRgb));
191         if (result == NULL) {
192                 cr_utils_trace_info ("No more memory");
193                 return NULL;
194         }
196         memset (result, 0, sizeof (CRRgb));
198         return result;
201 /**
202  *A constructor of #CRRgb.
203  *@param a_red the red component of the color.
204  *@param a_green the green component of the color.
205  *@param a_blue the blue component of the color.
206  *@param a_unit the unit of the rgb values.
207  *(either percentage or integer values)
208  *@return the newly built instance of #CRRgb.
209  */
210 CRRgb *
211 cr_rgb_new_with_vals (gulong a_red, gulong a_green,
212                       gulong a_blue, gboolean a_is_percentage)
214         CRRgb *result = NULL;
216         result = cr_rgb_new ();
218         g_return_val_if_fail (result, NULL);
220         result->red = a_red;
221         result->green = a_green;
222         result->blue = a_blue;
223         result->is_percentage = a_is_percentage;
225         return result;
228 /**
229  *Serializes the rgb into a zero terminated string.
230  *@param a_this the instance of #CRRgb to serialize.
231  *@return the zero terminated string containing the serialized
232  *rgb. MUST BE FREED by the caller using g_free().
233  */
234 guchar *
235 cr_rgb_to_string (CRRgb * a_this)
237         gchar *result = NULL;
238         GString *str_buf = (GString *)g_string_new (NULL);
239         g_return_val_if_fail (str_buf, NULL);
241         if (a_this->is_percentage == 1) {
242                 g_string_append_printf (str_buf, "%ld", a_this->red);
244                 g_string_append (str_buf, "%, ");
246                 g_string_append_printf (str_buf, "%ld", a_this->green);
247                 g_string_append (str_buf, "%, ");
249                 g_string_append_printf (str_buf, "%ld", a_this->blue);
250                 g_string_append_c (str_buf, '%');
251         } else {
252                 g_string_append_printf (str_buf, "%ld", a_this->red);
253                 g_string_append (str_buf, ", ");
255                 g_string_append_printf (str_buf, "%ld", a_this->green);
256                 g_string_append (str_buf, ", ");
258                 g_string_append_printf (str_buf, "%ld", a_this->blue);
259         }
261         if (str_buf) {
262                 result = str_buf->str;
263                 g_string_free (str_buf, FALSE);
264         }
266         return (guchar *)result;
269 /**
270  *Dumps the current instance of #CRRgb
271  *to a file.
272  *@param a_this the "this pointer" of
273  *the current instance of #CRRgb.
274  *@param a_fp the destination file pointer.
275  */
276 void
277 cr_rgb_dump (CRRgb * a_this, FILE * a_fp)
279         guchar *str = NULL;
281         g_return_if_fail (a_this);
283         str = cr_rgb_to_string (a_this);
285         if (str) {
286                 fprintf (a_fp, "%s", str);
287                 g_free (str);
288                 str = NULL;
289         }
292 /**
293  *If the rgb values are expressed in percentage,
294  *compute their real value.
295  *@param a_this the current instance of #CRRgb
296  *@return
297  */
298 enum CRStatus
299 cr_rgb_compute_from_percentage (CRRgb * a_this)
301         g_return_val_if_fail (a_this, CR_BAD_PARAM_ERROR);
303         if (a_this->is_percentage == FALSE)
304                 return CR_OK;
305         a_this->red = a_this->red * 255 / 100;
306         a_this->green = a_this->green * 255 / 100;
307         a_this->blue = a_this->blue * 255 / 100;
308         a_this->is_percentage = FALSE;
309         return CR_OK;
312 /**
313  *Sets rgb values to the RGB.
314  *@param a_this the current instance of #CRRgb.
315  *@param a_red the red value.
316  *@param a_green the green value.
317  *@param a_blue the blue value.
318  *@return CR_OK upon successful completion, an error code
319  *otherwise.
320  */
321 enum CRStatus
322 cr_rgb_set (CRRgb * a_this, gulong a_red,
323             gulong a_green, gulong a_blue, gboolean a_is_percentage)
325         g_return_val_if_fail (a_this, CR_BAD_PARAM_ERROR);
326         if (a_is_percentage != FALSE) {
327                 g_return_val_if_fail (a_red <= 100
328                                       && a_green <= 100
329                                       && a_blue <= 100, CR_BAD_PARAM_ERROR);
330         }
332         a_this->is_percentage = a_is_percentage;
334         a_this->red = a_red;
335         a_this->green = a_green;
336         a_this->blue = a_blue;
337         a_this->inherit = FALSE ;
338         a_this->is_transparent = FALSE ;
339         return CR_OK;
342 /**
343  *sets the value of the rgb to inherit.
344  *Look at the css spec from chapter 6.1 to 6.2 to understand
345  *the meaning of "inherit".
346  *@param a_this the current instance of #CRRgb
347  *
348  */
349 enum CRStatus 
350 cr_rgb_set_to_inherit (CRRgb *a_this, gboolean a_inherit)
352         g_return_val_if_fail (a_this, CR_BAD_PARAM_ERROR) ;
354         a_this->inherit = a_inherit ;
356         return CR_OK ;
359 gboolean
360 cr_rgb_is_set_to_inherit (CRRgb *a_this)
362         g_return_val_if_fail (a_this, CR_BAD_PARAM_ERROR) ;
364         return a_this->inherit ;
367 /**
368  *Tests if the the rgb is set to the
369  *value "transparent" or not.
370  *@param a_this the current instance of
371  *#CRRgb
372  *@return TRUE if the rgb has been set to
373  *transparent, FALSE otherwise.
374  */
375 gboolean 
376 cr_rgb_is_set_to_transparent (CRRgb *a_this)
378         g_return_val_if_fail (a_this, FALSE) ;
379         return a_this->is_transparent ;
383 /**
384  *Sets the rgb to the "transparent" value (or not)
385  *@param a_this the current instance of #CRRgb
386  *@param a_is_transparent set to transparent or not.
387  */
388 enum CRStatus 
389 cr_rgb_set_to_transparent (CRRgb *a_this, 
390                            gboolean a_is_transparent)
392         g_return_val_if_fail (a_this, CR_BAD_PARAM_ERROR) ;        
393         a_this->is_transparent = a_is_transparent ;
394         return CR_OK ;
397 /**
398  *Sets the rgb from an other one.
399  *@param a_this the current instance of #CRRgb.
400  *@param a_rgb the rgb to "copy"
401  *@return CR_OK upon successful completion, an error code otherwise.
402  */
403 enum CRStatus
404 cr_rgb_set_from_rgb (CRRgb * a_this, CRRgb * a_rgb)
406         g_return_val_if_fail (a_this && a_rgb, CR_BAD_PARAM_ERROR);
408         cr_rgb_copy (a_this, a_rgb) ;
410         return CR_OK;
413 enum CRStatus
414 cr_rgb_set_from_name (CRRgb * a_this, const guchar * a_color_name)
416         gulong i = 0;
417         enum CRStatus status = CR_OK;
419         g_return_val_if_fail (a_this && a_color_name, CR_BAD_PARAM_ERROR);
421         for (i = 0; i < sizeof (gv_standard_colors); i++) {
422                 if (!strcmp ((char *)a_color_name, gv_standard_colors[i].name)) {
423                         cr_rgb_set_from_rgb (a_this, &gv_standard_colors[i]);
424                         break;
425                 }
426         }
428         if (i < sizeof (gv_standard_colors))
429                 status = CR_OK;
430         else
431                status = CR_UNKNOWN_TYPE_ERROR;
433         return status;
436 enum CRStatus
437 cr_rgb_set_from_hex_str (CRRgb * a_this, const guchar * a_hex)
439         enum CRStatus status = CR_OK;
440         gulong i = 0;
441         guchar colors[3] = { 0 };
443         g_return_val_if_fail (a_this && a_hex, CR_BAD_PARAM_ERROR);
445         if (strlen ((char *)a_hex) == 3) {
446                 for (i = 0; i < 3; i++) {
447                         if (a_hex[i] >= '0' && a_hex[i] <= '9') {
448                                 colors[i] = a_hex[i] - '0';
449                                 colors[i] = (colors[i] << 4) | colors[i];
450                         } else if (a_hex[i] >= 'a' && a_hex[i] <= 'z') {
451                                 colors[i] = 10 + a_hex[i] - 'a';
452                                 colors[i] = (colors[i] << 4) | colors[i];
453                         } else if (a_hex[i] >= 'A' && a_hex[i] <= 'Z') {
454                                 colors[i] = 10 + a_hex[i] - 'A';
455                                 colors[i] = (colors[i] << 4) | colors[i];
456                         } else {
457                                 status = CR_UNKNOWN_TYPE_ERROR;
458                         }
459                 }
460         } else if (strlen ((char *)a_hex) == 6) {
461                 for (i = 0; i < 6; i++) {
462                         if (a_hex[i] >= '0' && a_hex[i] <= '9') {
463                                 colors[i / 2] <<= 4;
464                                 colors[i / 2] |= a_hex[i] - '0';
465                                 status = CR_OK;
466                         } else if (a_hex[i] >= 'a' && a_hex[i] <= 'z') {
467                                 colors[i / 2] <<= 4;
468                                 colors[i / 2] |= 10 + a_hex[i] - 'a';
469                                 status = CR_OK;
470                         } else if (a_hex[i] >= 'A' && a_hex[i] <= 'Z') {
471                                 colors[i / 2] <<= 4;
472                                 colors[i / 2] |= 10 + a_hex[i] - 'A';
473                                 status = CR_OK;
474                         } else {
475                                 status = CR_UNKNOWN_TYPE_ERROR;
476                         }
477                 }
478         } else {
479                 status = CR_UNKNOWN_TYPE_ERROR;
480         }
482         if (status == CR_OK) {
483                 status = cr_rgb_set (a_this, colors[0],
484                                      colors[1], colors[2], FALSE);
485                 cr_rgb_set_to_transparent (a_this, FALSE) ;
486         }
487         return status;
490 /**
491  *Set the rgb from a terminal symbol
492  *@param a_this the instance of #CRRgb to set
493  *@param a_value the terminal from which to set
494  */
495 enum CRStatus
496 cr_rgb_set_from_term (CRRgb *a_this, const struct _CRTerm *a_value)
498     enum CRStatus status = CR_OK ;
499     g_return_val_if_fail (a_this && a_value,
500                               CR_BAD_PARAM_ERROR) ;
502         switch(a_value->type) {
503         case TERM_RGB:
504                 if (a_value->content.rgb) {
505                         cr_rgb_set_from_rgb
506                                 (a_this, a_value->content.rgb) ;
507                 }
508                 break ;
509         case TERM_IDENT:
510                 if (a_value->content.str
511                     && a_value->content.str->stryng
512                     && a_value->content.str->stryng->str) {
513                         if (!strncmp ("inherit",
514                                       a_value->content.str->stryng->str,
515                                       sizeof ("inherit")-1)) {
516                                 a_this->inherit = TRUE;
517                                 a_this->is_transparent = FALSE ;
518                         } else  {
519                                 status = cr_rgb_set_from_name
520                                         (a_this,
521                                          (guchar *)a_value->content.str->stryng->str) ;
522                         }
523                 } else {
524                         cr_utils_trace_info 
525                                 ("a_value has NULL string value") ;
526                 }
527                 break ;
528         case TERM_HASH:
529                 if (a_value->content.str
530                     && a_value->content.str->stryng
531                     && a_value->content.str->stryng->str) {
532                         status = cr_rgb_set_from_hex_str
533                                 (a_this, 
534                                  (guchar *)a_value->content.str->stryng->str) ;
535                 } else {
536                         cr_utils_trace_info
537                                 ("a_value has NULL string value") ;
538                 }
539                 break ;
540         default:
541                 status =  CR_UNKNOWN_TYPE_ERROR ;
542         }
543         return status ;
546 enum CRStatus 
547 cr_rgb_copy (CRRgb *a_dest, CRRgb*a_src)
549         g_return_val_if_fail (a_dest && a_src,
550                               CR_BAD_PARAM_ERROR) ;
552         memcpy (a_dest, a_src, sizeof (CRRgb)) ;
553         return CR_OK ;
556 /**
557  *Destructor of #CRRgb.
558  *@param a_this the "this pointer" of the
559  *current instance of #CRRgb.
560  */
561 void
562 cr_rgb_destroy (CRRgb * a_this)
564         g_return_if_fail (a_this);
565         g_free (a_this);
568 /**
569  *Parses a text buffer that contains a rgb color
570  *
571  *@param a_str a string that contains a color description
572  *@param a_enc the encoding of a_str
573  *@return the parsed color, or NULL in case of error
574  */
575 CRRgb *cr_rgb_parse_from_buf (const guchar *a_str,
576                               enum CREncoding a_enc)
578         enum CRStatus status = CR_OK ;
579         CRTerm *value = NULL ;
580         CRParser * parser = NULL;
581         CRRgb *result = NULL;
582         
583         g_return_val_if_fail (a_str, NULL);
584         
585         parser = cr_parser_new_from_buf ((guchar *)a_str, strlen ((char *)a_str), 
586                                          a_enc, FALSE) ;
588         g_return_val_if_fail (parser, NULL);
590         status = cr_parser_try_to_skip_spaces_and_comments (parser) ;
591         if (status != CR_OK)
592                 goto cleanup;
594         status = cr_parser_parse_term (parser, &value);
595         if (status != CR_OK)
596                 goto cleanup;
598         result = cr_rgb_new ();
599         if (!result)
600                 goto cleanup;
602         status = cr_rgb_set_from_term (result, value);
604 cleanup:
605         if (parser) {
606                 cr_parser_destroy (parser);
607                 parser = NULL;
608         }
609         if (value) {
610                 cr_term_destroy(value);
611                 value = NULL;
612         }
613         return result ;
615           
617