1 /* Fo
2  * fo-region-before-after.c: Abstract 'before or after region' formatting object
3  *
4  * Copyright (C) 2010 Menteith Consulting Ltd
5  *
6  * See COPYING for the status of this software.
7  */
8 
9 #include "fo/fo-region-before-after-private.h"
10 #include "fo-context-util.h"
11 #include "property/fo-property-precedence.h"
12 
13 enum {
14   PROP_0,
15   PROP_PRECEDENCE
16 };
17 
18 static void fo_region_before_after_base_class_init  (FoRegionBeforeAfterClass *klass);
19 static void fo_region_before_after_class_init  (FoRegionBeforeAfterClass *klass);
20 static void fo_region_before_after_get_property (GObject      *object,
21                                            guint         prop_id,
22                                            GValue       *value,
23                                            GParamSpec   *pspec);
24 static void fo_region_before_after_set_property (GObject      *object,
25                                            guint         prop_id,
26                                            const GValue *value,
27                                            GParamSpec   *pspec);
28 static void fo_region_before_after_finalize    (GObject           *object);
29 static void fo_region_before_after_validate (FoFo      *fo,
30                                        FoContext *current_context,
31                                        FoContext *parent_context,
32                                        GError   **error);
33 static void fo_region_before_after_update_from_context (FoFo      *fo,
34                                                   FoContext *context);
35 static void fo_region_before_after_debug_dump_properties (FoFo *fo,
36                                                     gint  depth);
37 
38 static gpointer parent_class;
39 
40 /**
41  * fo_region_before_after_get_type:
42  *
43  * Register the #FoRegionBeforeAfter object type.
44  *
45  * Return value: #GType value of the #FoRegionBeforeAfter object type.
46  **/
47 GType
fo_region_before_after_get_type(void)48 fo_region_before_after_get_type (void)
49 {
50   static GType object_type = 0;
51 
52   if (!object_type)
53     {
54       static const GTypeInfo object_info =
55 	{
56 	  sizeof (FoRegionBeforeAfterClass),
57 	  (GBaseInitFunc) fo_region_before_after_base_class_init,
58 	  NULL,           /* base_finalize */
59 	  (GClassInitFunc) fo_region_before_after_class_init,
60 	  NULL,           /* class_finalize */
61 	  NULL,           /* class_data */
62 	  sizeof (FoRegionBeforeAfter),
63 	  0,              /* n_preallocs */
64 	  NULL,		  /* instance_init */
65 	  NULL		  /* value_table */
66 	};
67 
68       object_type = g_type_register_static (FO_TYPE_REGION_OUTER,
69                                             "FoRegionBeforeAfter",
70                                             &object_info,
71 					    G_TYPE_FLAG_ABSTRACT);
72     }
73 
74   return object_type;
75 }
76 
77 /**
78  * fo_region_before_after_base_class_init:
79  * @klass: #FoRegionBaseClass base class object to initialise.
80  *
81  * Implements #GBaseInitFunc for #FoRegionBaseClass.
82  **/
83 void
fo_region_before_after_base_class_init(FoRegionBeforeAfterClass * klass)84 fo_region_before_after_base_class_init (FoRegionBeforeAfterClass *klass)
85 {
86   FoObjectClass *fo_object_class = FO_OBJECT_CLASS (klass);
87   FoNodeClass *fo_node_class = FO_NODE_CLASS (klass);
88   FoFoClass *fofo_class = FO_FO_CLASS (klass);
89 
90   fofo_class->update_from_context = fo_region_before_after_update_from_context;
91   fofo_class->debug_dump_properties = fo_region_before_after_debug_dump_properties;
92 }
93 
94 /**
95  * fo_region_before_after_class_init:
96  * @klass: #FoRegionBeforeAfterClass object to initialise.
97  *
98  * Implements #GClassInitFunc for #FoRegionBeforeAfterClass.
99  **/
100 void
fo_region_before_after_class_init(FoRegionBeforeAfterClass * klass)101 fo_region_before_after_class_init (FoRegionBeforeAfterClass *klass)
102 {
103   GObjectClass *object_class = G_OBJECT_CLASS (klass);
104   FoFoClass *fofo_class = FO_FO_CLASS (klass);
105 
106   parent_class = g_type_class_peek_parent (klass);
107 
108   object_class->finalize = fo_region_before_after_finalize;
109 
110   object_class->get_property = fo_region_before_after_get_property;
111   object_class->set_property = fo_region_before_after_set_property;
112 
113   fofo_class->validate2 =
114     fo_region_before_after_validate;
115   fofo_class->update_from_context = fo_region_before_after_update_from_context;
116   fofo_class->debug_dump_properties = fo_region_before_after_debug_dump_properties;
117 
118   g_object_class_install_property
119     (object_class,
120      PROP_PRECEDENCE,
121      g_param_spec_object ("precedence",
122 			  _("Precedence"),
123 			  _("Precedence property"),
124 			  FO_TYPE_PROPERTY,
125 			  G_PARAM_READABLE));
126 }
127 
128 /**
129  * fo_region_before_after_finalize:
130  * @object: #FoRegionBeforeAfter object to finalize.
131  *
132  * Implements #GObjectFinalizeFunc for #FoRegionBeforeAfter.
133  **/
134 void
fo_region_before_after_finalize(GObject * object)135 fo_region_before_after_finalize (GObject *object)
136 {
137   FoFo *fo = FO_FO (object);
138 
139   /* Release references to all property objects. */
140   fo_region_before_after_set_precedence (fo, NULL);
141 
142   G_OBJECT_CLASS (parent_class)->finalize (object);
143 }
144 
145 /**
146  * fo_region_before_after_get_property:
147  * @object:  #GObject whose property will be retrieved.
148  * @prop_id: Property ID assigned when property registered.
149  * @value:   GValue to set with property value.
150  * @pspec:   Parameter specification for this property type.
151  *
152  * Implements #GObjectGetPropertyFunc for #FoRegionBeforeAfter.
153  **/
154 void
fo_region_before_after_get_property(GObject * object,guint prop_id,GValue * value,GParamSpec * pspec)155 fo_region_before_after_get_property (GObject    *object,
156 				     guint       prop_id,
157 				     GValue     *value,
158 				     GParamSpec *pspec)
159 {
160   FoFo *fo_fo;
161 
162   fo_fo = FO_FO (object);
163 
164   switch (prop_id)
165     {
166     case PROP_PRECEDENCE:
167       g_value_set_object (value, G_OBJECT (fo_region_before_after_get_precedence (fo_fo)));
168       break;
169     default:
170       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
171       break;
172     }
173 }
174 
175 /**
176  * fo_region_before_after_set_property:
177  * @object:  #GObject whose property will be set.
178  * @prop_id: Property ID assigned when property registered.
179  * @value:   New value for property.
180  * @pspec:   Parameter specification for this property type.
181  *
182  * Implements #GObjectSetPropertyFunc for #FoRegionBeforeAfter.
183  **/
184 void
fo_region_before_after_set_property(GObject * object,guint prop_id,const GValue * value,GParamSpec * pspec)185 fo_region_before_after_set_property (GObject      *object,
186 				     guint         prop_id,
187 				     const GValue *value,
188 				     GParamSpec   *pspec)
189 {
190   FoFo *fo_fo;
191 
192   fo_fo = FO_FO (object);
193 
194   switch (prop_id)
195     {
196     case PROP_PRECEDENCE:
197       fo_region_before_after_set_precedence (fo_fo, g_value_get_object (value));
198       break;
199     default:
200       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
201       break;
202     }
203 }
204 
205 /**
206  * fo_region_before_after_new:
207  *
208  * Creates a new #FoRegionBeforeAfter initialized to default value.
209  *
210  * Return value: the new #FoRegionBeforeAfter.
211  **/
212 FoFo*
fo_region_before_after_new(void)213 fo_region_before_after_new (void)
214 {
215   return FO_FO (g_object_new (fo_region_before_after_get_type (),
216                               NULL));
217 }
218 
219 /**
220  * fo_region_before_after_validate:
221  * @fo:              #FoRegionBeforeAfter object to validate.
222  * @current_context: #FoContext associated with current object.
223  * @parent_context:  #FoContext associated with parent FO.
224  * @error:           Information about any error that has occurred.
225  *
226  * Validate and possibly update interrelated property values in
227  * @current_context, then update @fo property values.  Set @error if
228  * an error occurred.
229  **/
230 void
fo_region_before_after_validate(FoFo * fo,FoContext * current_context,FoContext * parent_context,GError ** error)231 fo_region_before_after_validate (FoFo      *fo,
232 				 FoContext *current_context,
233 				 FoContext *parent_context,
234 				 GError   **error)
235 {
236   g_return_if_fail (fo != NULL);
237   g_return_if_fail (FO_IS_REGION_BEFORE_AFTER (fo));
238   g_return_if_fail (FO_IS_CONTEXT (current_context));
239   g_return_if_fail (FO_IS_CONTEXT (parent_context));
240   g_return_if_fail (error == NULL || *error == NULL);
241 }
242 
243 /**
244  * fo_region_before_after_update_from_context:
245  * @fo:      The #FoFo object.
246  * @context: The #FoContext object from which to update the properties of @fo.
247  *
248  * Sets the properties of @fo to the corresponding property values in @context.
249  **/
250 void
fo_region_before_after_update_from_context(FoFo * fo,FoContext * context)251 fo_region_before_after_update_from_context (FoFo      *fo,
252 					    FoContext *context)
253 {
254   g_return_if_fail (fo != NULL);
255   g_return_if_fail (FO_IS_REGION_BEFORE_AFTER (fo));
256   g_return_if_fail (context != NULL);
257   g_return_if_fail (FO_IS_CONTEXT (context));
258 
259   FO_FO_CLASS (parent_class)->update_from_context (fo, context);
260 
261   fo_region_before_after_set_precedence (fo,
262 			      fo_context_get_precedence (context));
263 }
264 
265 /**
266  * fo_region_before_after_debug_dump_properties:
267  * @fo:    The #FoFo object.
268  * @depth: Indent level to add to the output.
269  *
270  * Calls #fo_object_debug_dump on each property of @fo then calls
271  * debug_dump_properties method of parent class.
272  **/
273 void
fo_region_before_after_debug_dump_properties(FoFo * fo,gint depth)274 fo_region_before_after_debug_dump_properties (FoFo *fo,
275 					      gint  depth)
276 {
277   FoRegionBeforeAfter *fo_region_before_after;
278 
279   g_return_if_fail (fo != NULL);
280   g_return_if_fail (FO_IS_REGION_BEFORE_AFTER (fo));
281 
282   fo_region_before_after = FO_REGION_BEFORE_AFTER (fo);
283 
284   fo_object_debug_dump (fo_region_before_after->precedence, depth);
285 
286   FO_FO_CLASS (parent_class)->debug_dump_properties (fo, depth + 1);
287 }
288 
289 /**
290  * fo_region_before_after_get_precedence:
291  * @fo_fo: The @FoFo object.
292  *
293  * Gets the "precedence" property of @fo_fo.
294  *
295  * Return value: The "precedence" property value.
296 **/
297 FoProperty *
fo_region_before_after_get_precedence(FoFo * fo_fo)298 fo_region_before_after_get_precedence (FoFo *fo_fo)
299 {
300   FoRegionBeforeAfter *fo_region_before_after = (FoRegionBeforeAfter *) fo_fo;
301 
302   g_return_val_if_fail (fo_region_before_after != NULL, NULL);
303   g_return_val_if_fail (FO_IS_REGION_BEFORE_AFTER (fo_region_before_after), NULL);
304 
305   return fo_region_before_after->precedence;
306 }
307 
308 /**
309  * fo_region_before_after_set_precedence:
310  * @fo_fo: The #FoFo object.
311  * @new_precedence: The new "precedence" property value.
312  *
313  * Sets the "precedence" property of @fo_fo to @new_precedence.
314  **/
315 void
fo_region_before_after_set_precedence(FoFo * fo_fo,FoProperty * new_precedence)316 fo_region_before_after_set_precedence (FoFo *fo_fo,
317 				       FoProperty *new_precedence)
318 {
319   FoRegionBeforeAfter *fo_region_before_after = (FoRegionBeforeAfter *) fo_fo;
320 
321   g_return_if_fail (fo_region_before_after != NULL);
322   g_return_if_fail (FO_IS_REGION_BEFORE_AFTER (fo_region_before_after));
323   g_return_if_fail ((new_precedence == NULL) ||
324 		    FO_IS_PROPERTY_PRECEDENCE (new_precedence));
325 
326   if (new_precedence != NULL)
327     {
328       g_object_ref (new_precedence);
329     }
330   if (fo_region_before_after->precedence != NULL)
331     {
332       g_object_unref (fo_region_before_after->precedence);
333     }
334   fo_region_before_after->precedence = new_precedence;
335   /*g_object_notify (G_OBJECT (fo_region_before_after), "precedence");*/
336 }
337