evolution-3.6.4/filter/e-filter-element.c

No issues found

  1 /*
  2  * This program is free software; you can redistribute it and/or
  3  * modify it under the terms of the GNU Lesser General Public
  4  * License as published by the Free Software Foundation; either
  5  * version 2 of the License, or (at your option) version 3.
  6  *
  7  * This program is distributed in the hope that it will be useful,
  8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 10  * Lesser General Public License for more details.
 11  *
 12  * You should have received a copy of the GNU Lesser General Public
 13  * License along with the program; if not, see <http://www.gnu.org/licenses/>
 14  *
 15  *
 16  * Authors:
 17  *		Not Zed <notzed@lostzed.mmc.com.au>
 18  *      Jeffrey Stedfast <fejj@ximian.com>
 19  *
 20  * Copyright (C) 1999-2008 Novell, Inc. (www.novell.com)
 21  *
 22  */
 23 
 24 #ifdef HAVE_CONFIG_H
 25 #include <config.h>
 26 #endif
 27 
 28 #include <string.h>
 29 #include <stdlib.h>
 30 
 31 #include "e-filter-element.h"
 32 #include "e-filter-part.h"
 33 
 34 struct _element_type {
 35 	gchar *name;
 36 
 37 	EFilterElementFunc create;
 38 	gpointer data;
 39 };
 40 
 41 G_DEFINE_TYPE (
 42 	EFilterElement,
 43 	e_filter_element,
 44 	G_TYPE_OBJECT)
 45 
 46 static gboolean
 47 filter_element_validate (EFilterElement *element,
 48                          EAlert **alert)
 49 {
 50 	return TRUE;
 51 }
 52 
 53 static gint
 54 filter_element_eq (EFilterElement *element_a,
 55                    EFilterElement *element_b)
 56 {
 57 	return (g_strcmp0 (element_a->name, element_b->name) == 0);
 58 }
 59 
 60 static void
 61 filter_element_xml_create (EFilterElement *element,
 62                            xmlNodePtr node)
 63 {
 64 	element->name = (gchar *) xmlGetProp (node, (xmlChar *) "name");
 65 }
 66 
 67 static EFilterElement *
 68 filter_element_clone (EFilterElement *element)
 69 {
 70 	EFilterElement *clone;
 71 	xmlNodePtr node;
 72 
 73 	clone = g_object_new (G_OBJECT_TYPE (element), NULL);
 74 
 75 	node = e_filter_element_xml_encode (element);
 76 	e_filter_element_xml_decode (clone, node);
 77 	xmlFreeNodeList (node);
 78 
 79 	return clone;
 80 }
 81 
 82 /* This is somewhat hackish, implement all the base cases in here */
 83 #include "e-filter-input.h"
 84 #include "e-filter-option.h"
 85 #include "e-filter-code.h"
 86 #include "e-filter-color.h"
 87 #include "e-filter-datespec.h"
 88 #include "e-filter-int.h"
 89 #include "e-filter-file.h"
 90 
 91 static void
 92 filter_element_copy_value (EFilterElement *dst_element,
 93                            EFilterElement *src_element)
 94 {
 95 	if (E_IS_FILTER_INPUT (src_element)) {
 96 		EFilterInput *src_input;
 97 
 98 		src_input = E_FILTER_INPUT (src_element);
 99 
100 		if (E_IS_FILTER_INPUT (dst_element)) {
101 			EFilterInput *dst_input;
102 
103 			dst_input = E_FILTER_INPUT (dst_element);
104 
105 			if (src_input->values)
106 				e_filter_input_set_value (
107 					dst_input,
108 					src_input->values->data);
109 
110 		} else if (E_IS_FILTER_INT (dst_element)) {
111 			EFilterInt *dst_int;
112 
113 			dst_int = E_FILTER_INT (dst_element);
114 
115 			dst_int->val = atoi (src_input->values->data);
116 		}
117 
118 	} else if (E_IS_FILTER_COLOR (src_element)) {
119 		EFilterColor *src_color;
120 
121 		src_color = E_FILTER_COLOR (src_element);
122 
123 		if (E_IS_FILTER_COLOR (dst_element)) {
124 			EFilterColor *dst_color;
125 
126 			dst_color = E_FILTER_COLOR (dst_element);
127 
128 			dst_color->color = src_color->color;
129 		}
130 
131 	} else if (E_IS_FILTER_DATESPEC (src_element)) {
132 		EFilterDatespec *src_datespec;
133 
134 		src_datespec = E_FILTER_DATESPEC (src_element);
135 
136 		if (E_IS_FILTER_DATESPEC (dst_element)) {
137 			EFilterDatespec *dst_datespec;
138 
139 			dst_datespec = E_FILTER_DATESPEC (dst_element);
140 
141 			dst_datespec->type = src_datespec->type;
142 			dst_datespec->value = src_datespec->value;
143 		}
144 
145 	} else if (E_IS_FILTER_INT (src_element)) {
146 		EFilterInt *src_int;
147 
148 		src_int = E_FILTER_INT (src_element);
149 
150 		if (E_IS_FILTER_INT (dst_element)) {
151 			EFilterInt *dst_int;
152 
153 			dst_int = E_FILTER_INT (dst_element);
154 
155 			dst_int->val = src_int->val;
156 
157 		} else if (E_IS_FILTER_INPUT (dst_element)) {
158 			EFilterInput *dst_input;
159 			gchar *values;
160 
161 			dst_input = E_FILTER_INPUT (dst_element);
162 
163 			values = g_strdup_printf ("%d", src_int->val);
164 			e_filter_input_set_value (dst_input, values);
165 			g_free (values);
166 		}
167 
168 	} else if (E_IS_FILTER_OPTION (src_element)) {
169 		EFilterOption *src_option;
170 
171 		src_option = E_FILTER_OPTION (src_element);
172 
173 		if (E_IS_FILTER_OPTION (dst_element)) {
174 			EFilterOption *dst_option;
175 
176 			dst_option = E_FILTER_OPTION (dst_element);
177 
178 			if (src_option->current)
179 				e_filter_option_set_current (
180 					dst_option,
181 					src_option->current->value);
182 		}
183 	}
184 }
185 
186 static void
187 filter_element_finalize (GObject *object)
188 {
189 	EFilterElement *element = E_FILTER_ELEMENT (object);
190 
191 	xmlFree (element->name);
192 
193 	/* Chain up to parent's finalize () method. */
194 	G_OBJECT_CLASS (e_filter_element_parent_class)->finalize (object);
195 }
196 
197 static void
198 e_filter_element_class_init (EFilterElementClass *class)
199 {
200 	GObjectClass *object_class;
201 
202 	object_class = G_OBJECT_CLASS (class);
203 	object_class->finalize = filter_element_finalize;
204 
205 	class->validate = filter_element_validate;
206 	class->eq = filter_element_eq;
207 	class->xml_create = filter_element_xml_create;
208 	class->clone = filter_element_clone;
209 	class->copy_value = filter_element_copy_value;
210 }
211 
212 static void
213 e_filter_element_init (EFilterElement *element)
214 {
215 }
216 
217 /**
218  * filter_element_new:
219  *
220  * Create a new EFilterElement object.
221  *
222  * Return value: A new #EFilterElement object.
223  **/
224 EFilterElement *
225 e_filter_element_new (void)
226 {
227 	return g_object_new (E_TYPE_FILTER_ELEMENT, NULL);
228 }
229 
230 gboolean
231 e_filter_element_validate (EFilterElement *element,
232                            EAlert **alert)
233 {
234 	EFilterElementClass *class;
235 
236 	g_return_val_if_fail (E_IS_FILTER_ELEMENT (element), FALSE);
237 
238 	class = E_FILTER_ELEMENT_GET_CLASS (element);
239 	g_return_val_if_fail (class->validate != NULL, FALSE);
240 
241 	return class->validate (element, alert);
242 }
243 
244 gint
245 e_filter_element_eq (EFilterElement *element_a,
246                      EFilterElement *element_b)
247 {
248 	EFilterElementClass *class;
249 
250 	g_return_val_if_fail (E_IS_FILTER_ELEMENT (element_a), FALSE);
251 	g_return_val_if_fail (E_IS_FILTER_ELEMENT (element_b), FALSE);
252 
253 	/* The elements must be the same type. */
254 	if (G_OBJECT_TYPE (element_a) != G_OBJECT_TYPE (element_b))
255 		return FALSE;
256 
257 	class = E_FILTER_ELEMENT_GET_CLASS (element_a);
258 	g_return_val_if_fail (class->eq != NULL, FALSE);
259 
260 	return class->eq (element_a, element_b);
261 }
262 
263 /**
264  * filter_element_xml_create:
265  * @fe: filter element
266  * @node: xml node
267  *
268  * Create a new filter element based on an xml definition of
269  * that element.
270  **/
271 void
272 e_filter_element_xml_create (EFilterElement *element,
273                              xmlNodePtr node)
274 {
275 	EFilterElementClass *class;
276 
277 	g_return_if_fail (E_IS_FILTER_ELEMENT (element));
278 	g_return_if_fail (node != NULL);
279 
280 	class = E_FILTER_ELEMENT_GET_CLASS (element);
281 	g_return_if_fail (class->xml_create != NULL);
282 
283 	class->xml_create (element, node);
284 }
285 
286 /**
287  * filter_element_xml_encode:
288  * @fe: filter element
289  *
290  * Encode the values of a filter element into xml format.
291  *
292  * Return value:
293  **/
294 xmlNodePtr
295 e_filter_element_xml_encode (EFilterElement *element)
296 {
297 	EFilterElementClass *class;
298 
299 	g_return_val_if_fail (E_IS_FILTER_ELEMENT (element), NULL);
300 
301 	class = E_FILTER_ELEMENT_GET_CLASS (element);
302 	g_return_val_if_fail (class->xml_encode != NULL, NULL);
303 
304 	return class->xml_encode (element);
305 }
306 
307 /**
308  * filter_element_xml_decode:
309  * @fe: filter element
310  * @node: xml node
311  *
312  * Decode the values of a fitler element from xml format.
313  *
314  * Return value:
315  **/
316 gint
317 e_filter_element_xml_decode (EFilterElement *element,
318                              xmlNodePtr node)
319 {
320 	EFilterElementClass *class;
321 
322 	g_return_val_if_fail (E_IS_FILTER_ELEMENT (element), FALSE);
323 	g_return_val_if_fail (node != NULL, FALSE);
324 
325 	class = E_FILTER_ELEMENT_GET_CLASS (element);
326 	g_return_val_if_fail (class->xml_decode != NULL, FALSE);
327 
328 	return class->xml_decode (element, node);
329 }
330 
331 /**
332  * filter_element_clone:
333  * @fe: filter element
334  *
335  * Clones the EFilterElement @fe.
336  *
337  * Return value:
338  **/
339 EFilterElement *
340 e_filter_element_clone (EFilterElement *element)
341 {
342 	EFilterElementClass *class;
343 
344 	g_return_val_if_fail (E_IS_FILTER_ELEMENT (element), NULL);
345 
346 	class = E_FILTER_ELEMENT_GET_CLASS (element);
347 	g_return_val_if_fail (class->clone != NULL, NULL);
348 
349 	return class->clone (element);
350 }
351 
352 /**
353  * filter_element_get_widget:
354  * @fe: filter element
355  * @node: xml node
356  *
357  * Create a widget to represent this element.
358  *
359  * Return value:
360  **/
361 GtkWidget *
362 e_filter_element_get_widget (EFilterElement *element)
363 {
364 	EFilterElementClass *class;
365 
366 	g_return_val_if_fail (E_IS_FILTER_ELEMENT (element), NULL);
367 
368 	class = E_FILTER_ELEMENT_GET_CLASS (element);
369 	g_return_val_if_fail (class->get_widget != NULL, NULL);
370 
371 	return class->get_widget (element);
372 }
373 
374 /**
375  * filter_element_build_code:
376  * @fe: filter element
377  * @out: output buffer
378  * @ff:
379  *
380  * Add the code representing this element to the output string @out.
381  **/
382 void
383 e_filter_element_build_code (EFilterElement *element,
384                              GString *out,
385                              EFilterPart *part)
386 {
387 	EFilterElementClass *class;
388 
389 	g_return_if_fail (E_IS_FILTER_ELEMENT (element));
390 	g_return_if_fail (out != NULL);
391 	g_return_if_fail (E_IS_FILTER_PART (part));
392 
393 	class = E_FILTER_ELEMENT_GET_CLASS (element);
394 
395 	/* This method is optional. */
396 	if (class->build_code != NULL)
397 		class->build_code (element, out, part);
398 }
399 
400 /**
401  * filter_element_format_sexp:
402  * @fe: filter element
403  * @out: output buffer
404  *
405  * Format the value(s) of this element in a method suitable for the context of
406  * sexp where it is used.  Usually as space separated, double-quoted strings.
407  **/
408 void
409 e_filter_element_format_sexp (EFilterElement *element,
410                               GString *out)
411 {
412 	EFilterElementClass *class;
413 
414 	g_return_if_fail (E_IS_FILTER_ELEMENT (element));
415 	g_return_if_fail (out != NULL);
416 
417 	class = E_FILTER_ELEMENT_GET_CLASS (element);
418 	g_return_if_fail (class->format_sexp != NULL);
419 
420 	class->format_sexp (element, out);
421 }
422 
423 void
424 e_filter_element_set_data (EFilterElement *element,
425                            gpointer data)
426 {
427 	g_return_if_fail (E_IS_FILTER_ELEMENT (element));
428 
429 	element->data = data;
430 }
431 
432 /* only copies the value, not the name/type */
433 void
434 e_filter_element_copy_value (EFilterElement *dst_element,
435                              EFilterElement *src_element)
436 {
437 	EFilterElementClass *class;
438 
439 	g_return_if_fail (E_IS_FILTER_ELEMENT (dst_element));
440 	g_return_if_fail (E_IS_FILTER_ELEMENT (src_element));
441 
442 	class = E_FILTER_ELEMENT_GET_CLASS (dst_element);
443 	g_return_if_fail (class->copy_value != NULL);
444 
445 	class->copy_value (dst_element, src_element);
446 }