1 /* ADG - Automatic Drawing Generation
2 * Copyright (C) 2007,2008,2009 Nicola Fontana <ntd at entidi.it>
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 * Boston, MA 02110-1301, USA.
23 * @Section_Id:AdgPoint
25 * @short_description: A struct holding x, y coordinates
26 * (either named or explicit)
28 * AdgPoint is an opaque structure that manages 2D coordinates,
29 * either set explicitely throught adg_point_set_pair() and
30 * adg_point_set_pair_explicit() or taken from a model with
31 * adg_point_set_pair_from_model(). It can be thought as an
32 * #AdgPair on steroid, because it adds named pair support to
33 * a simple pair, enabling coordinates depending on #AdgModel.
39 * This is an opaque struct: all its fields are privates.
43 #include "adg-point.h"
57 adg_point_get_type(void)
61 if (G_UNLIKELY(type
== 0))
62 type
= g_boxed_type_register_static("AdgPoint",
63 (GBoxedCopyFunc
) adg_point_dup
,
64 (GBoxedFreeFunc
) adg_point_destroy
);
71 * @point: an #AdgPoint
72 * @src: the source point to copy
74 * Copies @src into @point. If @point was linked to a named pair, the
75 * reference to the old model is dropped. Similary, if @src is linked
76 * to a model, a new reference to this new model is added.
78 * Returns: @point or %NULL on error
81 adg_point_copy(AdgPoint
*point
, const AdgPoint
*src
)
83 g_return_val_if_fail(point
!= NULL
, NULL
);
84 g_return_val_if_fail(src
!= NULL
, NULL
);
86 if (src
->model
!= NULL
)
87 g_object_ref(src
->model
);
89 if (point
->model
!= NULL
)
90 g_object_unref(point
->model
);
92 return memcpy(point
, src
, sizeof(AdgPoint
));
97 * @point: an #AdgPoint structure
99 * Duplicates @point. This operation also adds a new reference
100 * to the internal model if @point is linked to a named pair.
102 * The returned value should be freed with adg_point_destroy()
103 * when no longer needed.
105 * Returns: the duplicated #AdgPoint struct or %NULL on errors
108 adg_point_dup(const AdgPoint
*point
)
110 g_return_val_if_fail(point
!= NULL
, NULL
);
112 if (point
->model
!= NULL
)
113 g_object_ref(point
->model
);
115 return g_memdup(point
, sizeof(AdgPoint
));
121 * Creates a new empty #AdgPoint. The returned pointer
122 * should be freed with adg_point_destroy() when no longer needed.
124 * The returned value should be freed with adg_point_destroy()
125 * when no longer needed.
127 * Returns: a newly created #AdgPoint
132 return g_new0(AdgPoint
, 1);
137 * @point: an #AdgPoint
139 * Destroys the @point instance, unreferencing the internal model if
140 * @point is linked to a named pair.
143 adg_point_destroy(AdgPoint
*point
)
145 g_return_if_fail(point
!= NULL
);
147 adg_point_set_pair_from_model(point
, NULL
, NULL
);
153 * adg_point_set_pair:
154 * @point: an #AdgPoint
155 * @pair: the #AdgPair to use
157 * Sets an explicit pair in @point by using the given @pair. If
158 * @point was linked to a named pair in a model, this link is
159 * dropped before setting the pair.
162 adg_point_set_pair(AdgPoint
*point
, const AdgPair
*pair
)
164 g_return_if_fail(point
!= NULL
);
165 g_return_if_fail(pair
!= NULL
);
167 adg_point_set_pair_explicit(point
, pair
->x
, pair
->y
);
171 * adg_point_set_pair_explicit:
172 * @point: an #AdgPoint
173 * @x: the x coordinate of the point
174 * @y: the y coordinate of the point
176 * Works in the same way of adg_point_set_pair() but accept direct numbers
177 * instead of an #AdgPair structure.
180 adg_point_set_pair_explicit(AdgPoint
*point
, gdouble x
, gdouble y
)
182 g_return_if_fail(point
!= NULL
);
184 /* Unlink the named pair dependency, if any */
185 adg_point_set_pair_from_model(point
, NULL
, NULL
);
189 point
->is_uptodate
= TRUE
;
193 * adg_point_set_pair_from_model:
194 * @point: an #AdgPoint
195 * @model: the #AdgModel
196 * @name: the id of a named pair in @model
198 * Links the @name named pair of @model to @point, so any subsequent
199 * call to adg_point_update() will read the named pair content. A
200 * new reference is added to @model while the previous model (if any)
203 * It is allowed to use %NULL as @model, in which case the link
204 * between @point and the named pair is dropped.
207 adg_point_set_pair_from_model(AdgPoint
*point
,
208 AdgModel
*model
, const gchar
*name
)
210 g_return_if_fail(point
!= NULL
);
211 g_return_if_fail(model
== NULL
|| name
!= NULL
);
213 /* Check if unlinking a yet unlinked point */
214 if (model
== NULL
&& point
->model
== NULL
)
217 /* Return if the named pair is not changed */
218 if (model
== point
->model
&&
219 (model
== NULL
|| strcmp(point
->name
, name
) == 0)) {
226 if (point
->model
!= NULL
) {
227 /* Remove the old named pair */
228 g_object_unref(point
->model
);
234 point
->is_uptodate
= FALSE
;
237 /* Set the new named pair */
238 point
->model
= model
;
239 point
->name
= g_strdup(name
);
244 * adg_point_get_pair:
245 * @point: an #AdgPoint
247 * #AdgPoint is an evolution of the pair concept, but internally the
248 * relevant data is still stored in an #AdgPair struct. This function
249 * gets this struct, optionally updating the internal value from the
250 * linked named pair if necessary.
252 * Returns: the pair of @point
255 adg_point_get_pair(AdgPoint
*point
)
257 g_return_val_if_fail(point
!= NULL
, NULL
);
259 if (!point
->is_uptodate
) {
262 if (point
->model
== NULL
) {
263 /* A point with explicit coordinates not up to date
264 * is an unexpected condition */
265 g_warning(_("%s: trying to get a pair from an undefined point"),
270 pair
= adg_model_get_named_pair(point
->model
, point
->name
);
273 g_warning(_("%s: `%s' named pair not found in `%s' model instance"),
274 G_STRLOC
, point
->name
,
275 g_type_name(G_TYPE_FROM_INSTANCE(point
->model
)));
279 cpml_pair_copy(&point
->pair
, pair
);
282 return (AdgPair
*) point
;
286 * adg_point_invalidate:
287 * @point: an #AdgPoint
289 * Invalidates @point, forcing a refresh of its internal #AdgPair if
290 * the point is linked to a named pair. If @point is explicitely set,
291 * this function has no effect.
294 adg_point_invalidate(AdgPoint
*point
)
296 g_return_if_fail(point
!= NULL
);
298 if (point
->model
!= NULL
)
299 point
->is_uptodate
= FALSE
;