1 /* Aravis - Digital camera library
2 *
3 * Copyright © 2009-2017 Emmanuel Pacaud
4 *
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation; either
8 * version 2 of the License, or (at your option) any later version.
9 *
10 * This library 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 GNU
13 * Lesser General Public License for more details.
14 *
15 * You should have received a copy of the GNU Lesser General
16 * Public License along with this library; if not, write to the
17 * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18 * Boston, MA 02110-1301, USA.
19 *
20 * Author: Emmanuel Pacaud <emmanuel@gnome.org>
21 */
22
23 /**
24 * SECTION: arvgcintegernode
25 * @short_description: Class for Integer nodes
26 */
27
28 #include <arvgcintegernode.h>
29 #include <arvgcinteger.h>
30 #include <arvgcvalueindexednode.h>
31 #include <arvgc.h>
32 #include <arvmisc.h>
33 #include <string.h>
34 #include <stdlib.h>
35
36 static GObjectClass *parent_class = NULL;
37
38 /* ArvDomNode implementation */
39
40 static const char *
arv_gc_integer_node_get_node_name(ArvDomNode * node)41 arv_gc_integer_node_get_node_name (ArvDomNode *node)
42 {
43 return "Integer";
44 }
45
46 static void
arv_gc_integer_node_post_new_child(ArvDomNode * self,ArvDomNode * child)47 arv_gc_integer_node_post_new_child (ArvDomNode *self, ArvDomNode *child)
48 {
49 ArvGcIntegerNode *node = ARV_GC_INTEGER_NODE (self);
50
51 if (ARV_IS_GC_PROPERTY_NODE (child)) {
52 ArvGcPropertyNode *property_node = ARV_GC_PROPERTY_NODE (child);
53
54 switch (arv_gc_property_node_get_node_type (property_node)) {
55 case ARV_GC_PROPERTY_NODE_TYPE_VALUE:
56 case ARV_GC_PROPERTY_NODE_TYPE_P_VALUE:
57 node->value = property_node;
58 break;
59 case ARV_GC_PROPERTY_NODE_TYPE_MINIMUM:
60 case ARV_GC_PROPERTY_NODE_TYPE_P_MINIMUM:
61 node->minimum = property_node;
62 break;
63 case ARV_GC_PROPERTY_NODE_TYPE_MAXIMUM:
64 case ARV_GC_PROPERTY_NODE_TYPE_P_MAXIMUM:
65 node->maximum = property_node;
66 break;
67 case ARV_GC_PROPERTY_NODE_TYPE_INCREMENT:
68 case ARV_GC_PROPERTY_NODE_TYPE_P_INCREMENT:
69 node->increment = property_node;
70 break;
71 case ARV_GC_PROPERTY_NODE_TYPE_UNIT:
72 node->unit = property_node;
73 break;
74 case ARV_GC_PROPERTY_NODE_TYPE_P_INDEX:
75 node->index = property_node;
76 break;
77 case ARV_GC_PROPERTY_NODE_TYPE_VALUE_INDEXED:
78 case ARV_GC_PROPERTY_NODE_TYPE_P_VALUE_INDEXED:
79 node->value_indexed_nodes = g_slist_prepend (node->value_indexed_nodes, property_node);
80 break;
81 case ARV_GC_PROPERTY_NODE_TYPE_VALUE_DEFAULT:
82 case ARV_GC_PROPERTY_NODE_TYPE_P_VALUE_DEFAULT:
83 node->value_default = property_node;
84 break;
85 default:
86 ARV_DOM_NODE_CLASS (parent_class)->post_new_child (self, child);
87 break;
88 }
89 }
90 }
91
92 static void
arv_gc_integer_node_pre_remove_child(ArvDomNode * self,ArvDomNode * child)93 arv_gc_integer_node_pre_remove_child (ArvDomNode *self, ArvDomNode *child)
94 {
95 g_assert_not_reached ();
96 }
97
98 /* ArvGcFeatureNode implementation */
99
100 static ArvGcPropertyNode *
_get_value_node(ArvGcIntegerNode * gc_integer_node,GError ** error)101 _get_value_node (ArvGcIntegerNode *gc_integer_node, GError **error)
102 {
103 GError *local_error = NULL;
104
105 if (gc_integer_node->value != NULL)
106 return gc_integer_node->value;
107
108 if (gc_integer_node->index != NULL) {
109 gint64 index;
110 GSList *iter;
111
112 index = arv_gc_property_node_get_int64 (ARV_GC_PROPERTY_NODE (gc_integer_node->index), &local_error);
113 if (local_error != NULL) {
114 g_propagate_error (error, local_error);
115 return NULL;
116 }
117
118 for (iter = gc_integer_node->value_indexed_nodes; iter != NULL; iter = iter->next) {
119 if (arv_gc_value_indexed_node_get_index (iter->data) == index)
120 return iter->data;
121 }
122
123 if (gc_integer_node->value_default != NULL)
124 return gc_integer_node->value_default;
125 }
126
127 return NULL;
128 }
129
130 static GType
arv_gc_integer_node_get_value_type(ArvGcFeatureNode * node)131 arv_gc_integer_node_get_value_type (ArvGcFeatureNode *node)
132 {
133 return G_TYPE_INT64;
134 }
135
136 static void
arv_gc_integer_node_set_value_from_string(ArvGcFeatureNode * node,const char * string,GError ** error)137 arv_gc_integer_node_set_value_from_string (ArvGcFeatureNode *node, const char *string, GError **error)
138 {
139 arv_gc_integer_set_value (ARV_GC_INTEGER (node), g_ascii_strtoll (string, NULL, 0), error);
140 }
141
142 static const char *
arv_gc_integer_node_get_value_as_string(ArvGcFeatureNode * node,GError ** error)143 arv_gc_integer_node_get_value_as_string (ArvGcFeatureNode *node, GError **error)
144 {
145 ArvGcIntegerNode *integer_node = ARV_GC_INTEGER_NODE (node);
146 ArvGcPropertyNode *value_node;
147 GError *local_error = NULL;
148 const char *string;
149
150 value_node = _get_value_node (integer_node, error);
151 if (value_node == NULL)
152 return NULL;
153
154 string = arv_gc_property_node_get_string (value_node, &local_error);
155 if (local_error != NULL) {
156 g_propagate_error (error, local_error);
157 return NULL;
158 }
159
160 return string;
161 }
162
163 /* ArvGcIntegerNode implementation */
164
165 ArvGcNode *
arv_gc_integer_node_new(void)166 arv_gc_integer_node_new (void)
167 {
168 ArvGcNode *node;
169
170 node = g_object_new (ARV_TYPE_GC_INTEGER_NODE, NULL);
171
172 return node;
173 }
174
175 static void
arv_gc_integer_node_init(ArvGcIntegerNode * gc_integer_node)176 arv_gc_integer_node_init (ArvGcIntegerNode *gc_integer_node)
177 {
178 }
179
180 static void
arv_gc_integer_node_finalize(GObject * object)181 arv_gc_integer_node_finalize (GObject *object)
182 {
183 ArvGcIntegerNode *gc_integer_node = ARV_GC_INTEGER_NODE (object);
184
185 parent_class->finalize (object);
186
187 g_slist_free (gc_integer_node->value_indexed_nodes);
188 }
189
190 static void
arv_gc_integer_node_class_init(ArvGcIntegerNodeClass * this_class)191 arv_gc_integer_node_class_init (ArvGcIntegerNodeClass *this_class)
192 {
193 GObjectClass *object_class = G_OBJECT_CLASS (this_class);
194 ArvDomNodeClass *dom_node_class = ARV_DOM_NODE_CLASS (this_class);
195 ArvGcFeatureNodeClass *gc_feature_node_class = ARV_GC_FEATURE_NODE_CLASS (this_class);
196
197 parent_class = g_type_class_peek_parent (this_class);
198
199 object_class->finalize = arv_gc_integer_node_finalize;
200 dom_node_class->get_node_name = arv_gc_integer_node_get_node_name;
201 dom_node_class->post_new_child = arv_gc_integer_node_post_new_child;
202 dom_node_class->pre_remove_child = arv_gc_integer_node_pre_remove_child;
203 gc_feature_node_class->get_value_type = arv_gc_integer_node_get_value_type;
204 gc_feature_node_class->set_value_from_string = arv_gc_integer_node_set_value_from_string;
205 gc_feature_node_class->get_value_as_string = arv_gc_integer_node_get_value_as_string;
206 }
207
208 /* ArvGcInteger interface implementation */
209
210 static gint64
arv_gc_integer_node_get_integer_value(ArvGcInteger * gc_integer,GError ** error)211 arv_gc_integer_node_get_integer_value (ArvGcInteger *gc_integer, GError **error)
212 {
213 ArvGcIntegerNode *gc_integer_node = ARV_GC_INTEGER_NODE (gc_integer);
214 ArvGcPropertyNode *value_node;
215 GError *local_error = NULL;
216 gint64 value;
217
218 value_node = _get_value_node (gc_integer_node, error);
219 if (value_node == NULL)
220 return 0;
221
222 value = arv_gc_property_node_get_int64 (ARV_GC_PROPERTY_NODE (value_node), &local_error);
223 if (local_error != NULL) {
224 g_propagate_error (error, local_error);
225 return 0;
226 }
227
228 return value;
229 }
230
231 static void
arv_gc_integer_node_set_integer_value(ArvGcInteger * gc_integer,gint64 value,GError ** error)232 arv_gc_integer_node_set_integer_value (ArvGcInteger *gc_integer, gint64 value, GError **error)
233 {
234 ArvGcIntegerNode *gc_integer_node = ARV_GC_INTEGER_NODE (gc_integer);
235 ArvGcPropertyNode *value_node;
236 GError *local_error = NULL;
237
238 value_node = _get_value_node (gc_integer_node, error);
239 if (value_node == NULL)
240 return;
241
242 arv_gc_property_node_set_int64 (ARV_GC_PROPERTY_NODE (value_node), value, &local_error);
243 if (local_error != NULL)
244 g_propagate_error (error, local_error);
245 }
246
247 static gint64
arv_gc_integer_node_get_min(ArvGcInteger * gc_integer,GError ** error)248 arv_gc_integer_node_get_min (ArvGcInteger *gc_integer, GError **error)
249 {
250 ArvGcIntegerNode *gc_integer_node = ARV_GC_INTEGER_NODE (gc_integer);
251 GError *local_error = NULL;
252 gint64 value;
253
254 if (gc_integer_node->minimum == NULL)
255 return G_MININT64;
256
257 value = arv_gc_property_node_get_int64 (ARV_GC_PROPERTY_NODE (gc_integer_node->minimum), &local_error);
258
259 if (local_error != NULL) {
260 g_propagate_error (error, local_error);
261 return G_MININT64;
262 }
263
264 return value;
265 }
266
267 static gint64
arv_gc_integer_node_get_max(ArvGcInteger * gc_integer,GError ** error)268 arv_gc_integer_node_get_max (ArvGcInteger *gc_integer, GError **error)
269 {
270 ArvGcIntegerNode *gc_integer_node = ARV_GC_INTEGER_NODE (gc_integer);
271 GError *local_error = NULL;
272 gint64 value;
273
274 if (gc_integer_node->maximum == NULL)
275 return G_MAXINT64;
276
277 value = arv_gc_property_node_get_int64 (ARV_GC_PROPERTY_NODE (gc_integer_node->maximum), &local_error);
278
279 if (local_error != NULL) {
280 g_propagate_error (error, local_error);
281 return G_MAXINT64;
282 }
283
284 return value;
285 }
286
287 static gint64
arv_gc_integer_node_get_inc(ArvGcInteger * gc_integer,GError ** error)288 arv_gc_integer_node_get_inc (ArvGcInteger *gc_integer, GError **error)
289 {
290 ArvGcIntegerNode *gc_integer_node = ARV_GC_INTEGER_NODE (gc_integer);
291 GError *local_error = NULL;
292 gint64 value;
293
294 if (gc_integer_node->increment == NULL)
295 return 1;
296
297 value = arv_gc_property_node_get_int64 (ARV_GC_PROPERTY_NODE (gc_integer_node->increment), &local_error);
298
299 if (local_error != NULL) {
300 g_propagate_error (error, local_error);
301 return 1;
302 }
303
304 return value;
305 }
306
307 static const char *
arv_gc_integer_node_get_unit(ArvGcInteger * gc_integer,GError ** error)308 arv_gc_integer_node_get_unit (ArvGcInteger *gc_integer, GError **error)
309 {
310 ArvGcIntegerNode *gc_integer_node = ARV_GC_INTEGER_NODE (gc_integer);
311 GError *local_error = NULL;
312 const char *string;
313
314 if (gc_integer_node->unit == NULL)
315 return NULL;
316
317 string = arv_gc_property_node_get_string (ARV_GC_PROPERTY_NODE (gc_integer_node->unit), &local_error);
318
319 if (local_error != NULL) {
320 g_propagate_error (error, local_error);
321 return NULL;
322 }
323
324 return string;
325 }
326
327 static void
arv_gc_integer_node_impose_min(ArvGcInteger * gc_integer,gint64 minimum,GError ** error)328 arv_gc_integer_node_impose_min (ArvGcInteger *gc_integer, gint64 minimum, GError **error)
329 {
330 ArvGcIntegerNode *gc_integer_node = ARV_GC_INTEGER_NODE (gc_integer);
331 GError *local_error = NULL;
332
333 if (gc_integer_node->minimum == NULL)
334 return;
335
336 arv_gc_property_node_set_int64 (ARV_GC_PROPERTY_NODE (gc_integer_node->minimum), minimum, &local_error);
337
338 if (local_error != NULL)
339 g_propagate_error (error, local_error);
340 }
341
342 static void
arv_gc_integer_node_impose_max(ArvGcInteger * gc_integer,gint64 maximum,GError ** error)343 arv_gc_integer_node_impose_max (ArvGcInteger *gc_integer, gint64 maximum, GError **error)
344 {
345 ArvGcIntegerNode *gc_integer_node = ARV_GC_INTEGER_NODE (gc_integer);
346 GError *local_error = NULL;
347
348 if (gc_integer_node->maximum == NULL)
349 return;
350
351 arv_gc_property_node_set_int64 (ARV_GC_PROPERTY_NODE (gc_integer_node->maximum), maximum, &local_error);
352
353 if (local_error != NULL)
354 g_propagate_error (error, local_error);
355 }
356
357 static void
arv_gc_integer_node_integer_interface_init(ArvGcIntegerInterface * interface)358 arv_gc_integer_node_integer_interface_init (ArvGcIntegerInterface *interface)
359 {
360 interface->get_value = arv_gc_integer_node_get_integer_value;
361 interface->set_value = arv_gc_integer_node_set_integer_value;
362 interface->get_min = arv_gc_integer_node_get_min;
363 interface->get_max = arv_gc_integer_node_get_max;
364 interface->get_inc = arv_gc_integer_node_get_inc;
365 interface->get_unit = arv_gc_integer_node_get_unit;
366 interface->impose_min = arv_gc_integer_node_impose_min;
367 interface->impose_max = arv_gc_integer_node_impose_max;
368 }
369
370 G_DEFINE_TYPE_WITH_CODE (ArvGcIntegerNode, arv_gc_integer_node, ARV_TYPE_GC_FEATURE_NODE,
371 G_IMPLEMENT_INTERFACE (ARV_TYPE_GC_INTEGER, arv_gc_integer_node_integer_interface_init))
372