1 /* Fo
2  * fo-property-space-after.c: 'space-after' property
3  *
4  * Copyright (C) 2001 Sun Microsystems
5  * Copyright (C) 2007 Menteith Consulting Ltd
6  *
7  * See COPYING for the status of this software.
8  */
9 
10 #include <string.h>
11 #include "fo-utils.h"
12 #include "fo-context.h"
13 #include "datatype/fo-datatype.h"
14 #include "property/fo-property-private.h"
15 #include "property/fo-property-font-size.h"
16 #include "property/fo-property-space-after.h"
17 
18 /* Inherited: FALSE */
19 /* Shorthand: FALSE */
20 /* space-after */
21 /* <space> | <percentage> | inherit */
22 /* NO ENUMERATED VALUE */
23 
24 
25 struct _FoPropertySpaceAfter
26 {
27   FoProperty parent_instance;
28 };
29 
30 struct _FoPropertySpaceAfterClass
31 {
32   FoPropertyClass parent_class;
33 };
34 
35 static void fo_property_space_after_init         (FoPropertySpaceAfter      *property_space_after);
36 static void fo_property_space_after_class_init   (FoPropertySpaceAfterClass *klass);
37 static void fo_property_space_after_finalize     (GObject       *object);
38 
39 static FoDatatype* fo_property_space_after_resolve_enum (const gchar *token,
40                                                        FoContext   *context,
41                                                        GError     **error);
42 static FoDatatype* fo_property_space_after_validate (FoDatatype *datatype,
43                                                    FoContext  *context,
44                                                    GError    **error);
45 
46 static const gchar class_name[] = "space-after";
47 static gpointer parent_class;
48 
49 /**
50  * fo_property_space_after_get_type:
51  *
52  * Register the #FoPropertySpaceAfter type if not already registered and
53  * return its #GType value.
54  *
55  * Return value: #GType of #FoPropertySpaceAfter.
56  **/
57 GType
fo_property_space_after_get_type(void)58 fo_property_space_after_get_type (void)
59 {
60   static GType object_type = 0;
61 
62   if (!object_type)
63     {
64       static const GTypeInfo object_info =
65       {
66         sizeof (FoPropertySpaceAfterClass),
67         NULL,           /* base_init */
68         NULL,           /* base_finalize */
69         (GClassInitFunc) fo_property_space_after_class_init,
70         NULL,           /* class_finalize */
71         NULL,           /* class_data */
72         sizeof (FoPropertySpaceAfter),
73         0,              /* n_preallocs */
74         (GInstanceInitFunc) fo_property_space_after_init,
75 	NULL		/* value_table */
76       };
77 
78       object_type = g_type_register_static (FO_TYPE_PROPERTY,
79                                             class_name,
80                                             &object_info, 0);
81     }
82 
83   return object_type;
84 }
85 
86 /**
87  * fo_property_space_after_init:
88  * @space_after: #FoPropertySpaceAfter object to initialise.
89  *
90  * Implements #GInstanceInitFunc for #FoPropertySpaceAfter.
91  **/
92 void
fo_property_space_after_init(FoPropertySpaceAfter * space_after)93 fo_property_space_after_init (FoPropertySpaceAfter *space_after)
94 {
95   FO_PROPERTY (space_after)->value =
96     g_object_ref (fo_space_get_space_0pt ());
97 }
98 
99 /**
100  * fo_property_space_after_class_init:
101  * @klass: #FoPropertySpaceAfterClass object to initialise.
102  *
103  * Implements #GClassInitFunc for #FoPropertySpaceAfterClass.
104  **/
105 void
fo_property_space_after_class_init(FoPropertySpaceAfterClass * klass)106 fo_property_space_after_class_init (FoPropertySpaceAfterClass *klass)
107 {
108   GObjectClass *object_class = G_OBJECT_CLASS (klass);
109   FoPropertyClass *property_class = FO_PROPERTY_CLASS (klass);
110 
111   parent_class = g_type_class_peek_parent (klass);
112 
113   object_class->finalize = fo_property_space_after_finalize;
114 
115   property_class->is_inherited = FALSE;
116   property_class->is_shorthand = FALSE;
117   property_class->resolve_enum =
118     fo_property_space_after_resolve_enum;
119   property_class->validate =
120     fo_property_space_after_validate;
121   property_class->get_initial =
122     fo_property_space_after_get_initial;
123 }
124 
125 /**
126  * fo_property_space_after_finalize:
127  * @object: #FoPropertySpaceAfter object to finalize.
128  *
129  * Implements #GObjectFinalizeFunc for #FoPropertySpaceAfter.
130  **/
131 void
fo_property_space_after_finalize(GObject * object)132 fo_property_space_after_finalize (GObject *object)
133 {
134   FoPropertySpaceAfter *space_after;
135 
136   space_after = FO_PROPERTY_SPACE_AFTER (object);
137 
138   G_OBJECT_CLASS (parent_class)->finalize (object);
139 }
140 
141 
142 /**
143  * fo_property_space_after_new:
144  *
145  * Creates a new #FoPropertySpaceAfter initialized to default value.
146  *
147  * Return value: the new #FoPropertySpaceAfter.
148  **/
149 FoProperty*
fo_property_space_after_new(void)150 fo_property_space_after_new (void)
151 {
152   FoProperty* space_after;
153 
154   space_after =
155     FO_PROPERTY (g_object_new (fo_property_space_after_get_type (),
156                                NULL));
157 
158   return space_after;
159 }
160 
161 /**
162  * fo_property_space_after_resolve_enum:
163  * @token:   Token from the XML attribute value to be evaluated as an
164  *           enumeration token.
165  * @context: #FoContext object from which to possibly inherit values.
166  * @error:   Information about any error that has occurred.
167  *
168  * Compare @token against the enumeration tokens that are valid for the
169  * current FO property.  If @token is valid, returns either an #FoEnum datatype
170  * representing the enumeration token or a different datatype representing
171  * the enumeration token's resolved value.  If @token is not valid,
172  * sets @error and returns NULL.
173  *
174  * Return value: Resolved enumeration value or NULL.
175  **/
176 FoDatatype*
fo_property_space_after_resolve_enum(const gchar * token,FoContext * context,GError ** error)177 fo_property_space_after_resolve_enum (const gchar *token,
178                                     FoContext   *context,
179                                     GError     **error)
180 {
181   g_return_val_if_fail (token != NULL, NULL);
182   g_return_val_if_fail (FO_IS_CONTEXT (context), NULL);
183   g_return_val_if_fail (error == NULL || *error == NULL, NULL);
184 
185       g_set_error (error,
186 		   FO_FO_ERROR,
187 		   FO_FO_ERROR_ENUMERATION_TOKEN,
188 		   _(fo_fo_error_messages[FO_FO_ERROR_ENUMERATION_TOKEN]),
189 		   class_name,
190 		   token);
191       return NULL;
192 }
193 
194 /**
195  * fo_property_space_after_validate:
196  * @datatype: #FoDatatype to be validated against allowed datatypes and
197  *            values for current property.
198  * @context:  #FoContext object from which to possibly inherit values.
199  * @error:    Information about any error that has occurred.
200  *
201  * Validates @datatype against allowed values.  Returns @datatype, a
202  * replacement datatype value, or NULL if validation failed.
203  *
204  * Return value: Valid datatype value or NULL.
205  **/
206 FoDatatype*
fo_property_space_after_validate(FoDatatype * datatype,FoContext * context,GError ** error)207 fo_property_space_after_validate (FoDatatype *datatype,
208                                 FoContext  *context,
209                                 GError    **error)
210 {
211   FoDatatype *new_datatype;
212 
213   g_return_val_if_fail (datatype != NULL, NULL);
214   g_return_val_if_fail (FO_IS_DATATYPE (datatype), NULL);
215   g_return_val_if_fail (context != NULL, NULL);
216   g_return_val_if_fail (FO_IS_CONTEXT (context), NULL);
217   g_return_val_if_fail (error == NULL || *error == NULL, NULL);
218 
219   if (FO_IS_SPACE (datatype))
220     {
221       return datatype;
222     }
223   else if (FO_IS_LENGTH (datatype))
224     {
225       new_datatype = fo_space_new_from_length (datatype);
226 
227       g_object_unref (datatype);
228 
229       return new_datatype;
230     }
231   else if (FO_IS_PERCENTAGE (datatype))
232     {
233       return datatype;
234     }
235   else
236     {
237       gchar *datatype_sprintf = fo_object_sprintf (datatype);
238 
239       g_set_error (error,
240 		   FO_FO_ERROR,
241 		   FO_FO_ERROR_DATATYPE,
242 		   _(fo_fo_error_messages[FO_FO_ERROR_DATATYPE]),
243 		   class_name,
244 		   datatype_sprintf,
245 		   g_type_name (G_TYPE_FROM_INSTANCE (datatype)));
246 
247       g_object_unref (datatype);
248 
249       g_free (datatype_sprintf);
250 
251       return NULL;
252     }
253 }
254 
255 /**
256  * fo_property_space_after_get_initial:
257  *
258  * Get an instance of the property with the correct initial value.
259  *
260  * Return value: An instance of the property.
261  **/
262 FoProperty*
fo_property_space_after_get_initial(void)263 fo_property_space_after_get_initial (void)
264 {
265   static FoProperty *space_after = NULL;
266 
267   if (space_after == NULL)
268     {
269       space_after = fo_property_space_after_new ();
270     }
271 
272   return space_after;
273 }
274