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 * See COPYRIGHTS file for copyrights information.
21 */
23 #include <stdio.h>
24 #include "cr-attr-sel.h"
26 /**
27 *@file
28 *The class that abstracts an attribute selector.
29 *Attributes selectors are described in the css2 spec [5.8].
30 *There are more generally used in the css2 selectors described in
31 *css2 spec [5] .
32 */
34 /**
35 *The constructor of #CRAttrSel.
36 *@return the newly allocated instance
37 *of #CRAttrSel.
38 */
39 CRAttrSel *
40 cr_attr_sel_new (void)
41 {
42 CRAttrSel *result = NULL;
44 result = g_malloc0 (sizeof (CRAttrSel));
46 return result;
47 }
49 /**
50 *Appends an attribute selector to the current list of
51 *attribute selectors represented by a_this.
52 *
53 *@param a_this the this pointer of the current instance of
54 *#CRAttrSel.
55 *@param a_attr_sel selector to append.
56 *@return CR_OK upon successfull completion, an error code otherwise.
57 */
58 enum CRStatus
59 cr_attr_sel_append_attr_sel (CRAttrSel * a_this, CRAttrSel * a_attr_sel)
60 {
61 CRAttrSel *cur_sel = NULL;
63 g_return_val_if_fail (a_this && a_attr_sel,
64 CR_BAD_PARAM_ERROR);
66 for (cur_sel = a_this;
67 cur_sel->next;
68 cur_sel = cur_sel->next) ;
70 cur_sel->next = a_attr_sel;
71 a_attr_sel->prev = cur_sel;
73 return CR_OK;
74 }
76 /**
77 *Prepends an attribute selector to the list of
78 *attributes selector represented by a_this.
79 *
80 *@param a_this the "this pointer" of the current instance
81 *of #CRAttrSel.
82 *@param a_attr_sel the attribute selector to append.
83 *@return CR_OK upon successfull completion, an error code otherwise.
84 */
85 enum CRStatus
86 cr_attr_sel_prepend_attr_sel (CRAttrSel * a_this,
87 CRAttrSel * a_attr_sel)
88 {
89 g_return_val_if_fail (a_this && a_attr_sel,
90 CR_BAD_PARAM_ERROR);
92 a_attr_sel->next = a_this;
93 a_this->prev = a_attr_sel;
95 return CR_OK;
96 }
98 guchar *
99 cr_attr_sel_to_string (CRAttrSel * a_this)
100 {
101 CRAttrSel *cur = NULL;
102 guchar *result = NULL;
103 GString *str_buf = NULL;
105 g_return_val_if_fail (a_this, NULL);
107 str_buf = g_string_new (NULL);
109 for (cur = a_this; cur; cur = cur->next) {
110 if (cur->prev) {
111 g_string_append_c (str_buf, ' ');
112 }
114 if (cur->name) {
115 guchar *name = NULL;
117 name = g_strndup (cur->name->stryng->str,
118 cur->name->stryng->len);
119 if (name) {
120 g_string_append (str_buf, name);
121 g_free (name);
122 name = NULL;
123 }
124 }
126 if (cur->value) {
127 guchar *value = NULL;
129 value = g_strndup (cur->value->stryng->str,
130 cur->value->stryng->len);
131 if (value) {
132 switch (cur->match_way) {
133 case SET:
134 break;
136 case EQUALS:
137 g_string_append_c (str_buf, '=');
138 break;
140 case INCLUDES:
141 g_string_append (str_buf, "~=");
142 break;
144 case DASHMATCH:
145 g_string_append (str_buf, "|=");
146 break;
148 default:
149 break;
150 }
152 g_string_append_printf
153 (str_buf, "\"%s\"", value);
155 g_free (value);
156 value = NULL;
157 }
158 }
159 }
161 if (str_buf) {
162 result = str_buf->str;
163 g_string_free (str_buf, FALSE);
164 }
166 return result;
167 }
169 /**
170 *Dumps the current instance of #CRAttrSel to a file.
171 *@param a_this the "this pointer" of the current instance of
172 *#CRAttrSel.
173 *@param a_fp the destination file.
174 */
175 void
176 cr_attr_sel_dump (CRAttrSel * a_this, FILE * a_fp)
177 {
178 guchar *tmp_str = NULL;
180 g_return_if_fail (a_this);
182 tmp_str = cr_attr_sel_to_string (a_this);
184 if (tmp_str) {
185 fprintf (a_fp, "%s", tmp_str);
186 g_free (tmp_str);
187 tmp_str = NULL;
188 }
189 }
191 /**
192 *Destroys the current instance of #CRAttrSel.
193 *Frees all the fields if they are non null.
194 *@param a_this the "this pointer" of the current
195 *instance of #CRAttrSel.
196 */
197 void
198 cr_attr_sel_destroy (CRAttrSel * a_this)
199 {
200 g_return_if_fail (a_this);
202 if (a_this->name) {
203 cr_string_destroy (a_this->name);
204 a_this->name = NULL;
205 }
207 if (a_this->value) {
208 cr_string_destroy (a_this->value);
209 a_this->value = NULL;
210 }
212 if (a_this->next) {
213 cr_attr_sel_destroy (a_this->next);
214 a_this->next = NULL;
215 }
217 if (a_this) {
218 g_free (a_this);
219 a_this = NULL;
220 }
221 }