* added GDK_PIXBUF_LIBS in order to create pixbuf.dll
[dia.git] / lib / prop_attr.c
blob3aaba1ce9ad656f7b14bab20b4dc3904ee1b3274
1 /* Dia -- a diagram creation/manipulation program -*- c -*-
2 * Copyright (C) 1998 Alexander Larsson
4 * Property system for dia objects/shapes.
5 * Copyright (C) 2000 James Henstridge
6 * Copyright (C) 2001 Cyrille Chepelov
7 * Major restructuration done in August 2001 by C. Chépélov
9 * Property types for "attribute" types (line style, arrow, colour, font)
11 * This program is free software; you can redistribute it and/or modify
12 * it under the terms of the GNU General Public License as published by
13 * the Free Software Foundation; either version 2 of the License, or
14 * (at your option) any later version.
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU General Public License for more details.
21 * You should have received a copy of the GNU General Public License
22 * along with this program; if not, write to the Free Software
23 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
25 #ifdef HAVE_CONFIG_H
26 #include <config.h>
27 #endif
29 #include <gtk/gtk.h>
30 #include "dia_xml.h"
31 #include "widgets.h"
32 #include "properties.h"
33 #include "propinternals.h"
35 /***************************/
36 /* The LINESTYLE property type. */
37 /***************************/
39 static LinestyleProperty *
40 linestyleprop_new(const PropDescription *pdesc,
41 PropDescToPropPredicate reason)
43 LinestyleProperty *prop = g_new0(LinestyleProperty,1);
44 initialize_property(&prop->common,pdesc,reason);
45 prop->style = LINESTYLE_SOLID;
46 prop->dash = 0.0;
47 return prop;
50 static LinestyleProperty *
51 linestyleprop_copy(LinestyleProperty *src)
53 LinestyleProperty *prop =
54 (LinestyleProperty *)src->common.ops->new_prop(src->common.descr,
55 src->common.reason);
56 copy_init_property(&prop->common,&src->common);
57 prop->style = src->style;
58 prop->dash = src->dash;
59 return prop;
62 static WIDGET *
63 linestyleprop_get_widget(LinestyleProperty *prop, PropDialog *dialog)
65 GtkWidget *ret = dia_line_style_selector_new();
66 prophandler_connect(&prop->common,GTK_OBJECT(ret),"FIXME");
67 return ret;
70 static void
71 linestyleprop_reset_widget(LinestyleProperty *prop, WIDGET *widget)
73 dia_line_style_selector_set_linestyle(DIALINESTYLESELECTOR(widget),
74 prop->style,
75 prop->dash);
78 static void
79 linestyleprop_set_from_widget(LinestyleProperty *prop, WIDGET *widget)
81 dia_line_style_selector_get_linestyle(DIALINESTYLESELECTOR(widget),
82 &prop->style,
83 &prop->dash);
86 static void
87 linestyleprop_load(LinestyleProperty *prop, AttributeNode attr, DataNode data)
89 prop->style = data_enum(data);
90 prop->dash = 1.0;
91 /* don't bother checking dash length if we have a solid line. */
92 if (prop->style != LINESTYLE_SOLID) {
93 data = data_next(data);
94 if (data)
95 prop->dash = data_real(data);
96 else {
97 ObjectNode obj_node = attr->parent;
98 /* backward compatibility */
99 if ((attr = object_find_attribute(obj_node, "dashlength")) &&
100 (data = attribute_first_data(attr)))
101 prop->dash = data_real(data);
106 static void
107 linestyleprop_save(LinestyleProperty *prop, AttributeNode attr)
109 data_add_enum(attr, prop->style);
110 data_add_real(attr, prop->dash);
111 /* for compatibility. It makes more sense to link the two together */
113 data_add_real(new_attribute(attr->parent, "dashlength"),
114 prop->dash);
116 To hell with compatibility with very old dias ! -- CC */
119 static void
120 linestyleprop_get_from_offset(LinestyleProperty *prop,
121 void *base, guint offset, guint offset2)
123 prop->style = struct_member(base, offset, LineStyle);
124 prop->dash = struct_member(base, offset2, real);
127 static void
128 linestyleprop_set_from_offset(LinestyleProperty *prop,
129 void *base, guint offset, guint offset2)
131 struct_member(base, offset, LineStyle) = prop->style;
132 struct_member(base, offset2, real) = prop->dash;
135 static const PropertyOps linestyleprop_ops = {
136 (PropertyType_New) linestyleprop_new,
137 (PropertyType_Free) noopprop_free,
138 (PropertyType_Copy) linestyleprop_copy,
139 (PropertyType_Load) linestyleprop_load,
140 (PropertyType_Save) linestyleprop_save,
141 (PropertyType_GetWidget) linestyleprop_get_widget,
142 (PropertyType_ResetWidget) linestyleprop_reset_widget,
143 (PropertyType_SetFromWidget) linestyleprop_set_from_widget,
145 (PropertyType_CanMerge) noopprop_can_merge,
146 (PropertyType_GetFromOffset) linestyleprop_get_from_offset,
147 (PropertyType_SetFromOffset) linestyleprop_set_from_offset
150 /***************************/
151 /* The ARROW property type. */
152 /***************************/
154 static ArrowProperty *
155 arrowprop_new(const PropDescription *pdesc, PropDescToPropPredicate reason)
157 ArrowProperty *prop = g_new0(ArrowProperty,1);
158 initialize_property(&prop->common,pdesc,reason);
159 prop->arrow_data.type = ARROW_NONE;
160 prop->arrow_data.length = 0.0;
161 prop->arrow_data.width = 0.0;
162 return prop;
165 static ArrowProperty *
166 arrowprop_copy(ArrowProperty *src)
168 ArrowProperty *prop =
169 (ArrowProperty *)src->common.ops->new_prop(src->common.descr,
170 src->common.reason);
171 copy_init_property(&prop->common,&src->common);
172 prop->arrow_data = src->arrow_data;
173 return prop;
176 static WIDGET *
177 arrowprop_get_widget(ArrowProperty *prop, PropDialog *dialog)
179 GtkWidget *ret = dia_arrow_selector_new();
180 prophandler_connect(&prop->common,GTK_OBJECT(ret),"FIXME");
181 return ret;
184 static void
185 arrowprop_reset_widget(ArrowProperty *prop, WIDGET *widget)
187 dia_arrow_selector_set_arrow(DIAARROWSELECTOR(widget),
188 prop->arrow_data);
191 static void
192 arrowprop_set_from_widget(ArrowProperty *prop, WIDGET *widget)
194 prop->arrow_data = dia_arrow_selector_get_arrow(DIAARROWSELECTOR(widget));
197 static void
198 arrowprop_load(ArrowProperty *prop, AttributeNode attr, DataNode data)
200 /* Maybe it would be better to store arrows as a single composite
201 * attribute rather than three seperate attributes. This would break
202 * binary compatibility though.*/
203 prop->arrow_data.type = data_enum(data);
204 prop->arrow_data.length = 0.8;
205 prop->arrow_data.width = 0.8;
206 if (prop->arrow_data.type != ARROW_NONE) {
207 ObjectNode obj_node = attr->parent;
208 gchar *str = g_strconcat(prop->common.name, "_length", NULL);
209 if ((attr = object_find_attribute(obj_node, str)) &&
210 (data = attribute_first_data(attr)))
211 prop->arrow_data.length = data_real(data);
212 g_free(str);
213 str = g_strconcat(prop->common.name, "_width", NULL);
214 if ((attr = object_find_attribute(obj_node, str)) &&
215 (data = attribute_first_data(attr)))
216 prop->arrow_data.width = data_real(data);
217 g_free(str);
221 static void
222 arrowprop_save(ArrowProperty *prop, AttributeNode attr)
224 data_add_enum(attr, prop->arrow_data.type);
225 if (prop->arrow_data.type != ARROW_NONE) {
226 ObjectNode obj_node = attr->parent;
227 gchar *str = g_strconcat(prop->common.name, "_length", NULL);
228 attr = new_attribute(obj_node, str);
229 g_free(str);
230 data_add_real(attr, prop->arrow_data.length);
231 str = g_strconcat(prop->common.name, "_width", NULL);
232 attr = new_attribute(obj_node, str);
233 g_free(str);
234 data_add_real(attr, prop->arrow_data.width);
238 static void
239 arrowprop_get_from_offset(ArrowProperty *prop,
240 void *base, guint offset, guint offset2)
242 prop->arrow_data = struct_member(base,offset,Arrow);
245 static void
246 arrowprop_set_from_offset(ArrowProperty *prop,
247 void *base, guint offset, guint offset2)
249 struct_member(base,offset,Arrow) = prop->arrow_data;
252 static const PropertyOps arrowprop_ops = {
253 (PropertyType_New) arrowprop_new,
254 (PropertyType_Free) noopprop_free,
255 (PropertyType_Copy) arrowprop_copy,
256 (PropertyType_Load) arrowprop_load,
257 (PropertyType_Save) arrowprop_save,
258 (PropertyType_GetWidget) arrowprop_get_widget,
259 (PropertyType_ResetWidget) arrowprop_reset_widget,
260 (PropertyType_SetFromWidget) arrowprop_set_from_widget,
262 (PropertyType_CanMerge) noopprop_can_merge,
263 (PropertyType_GetFromOffset) arrowprop_get_from_offset,
264 (PropertyType_SetFromOffset) arrowprop_set_from_offset
267 /***************************/
268 /* The COLOR property type. */
269 /***************************/
271 static ColorProperty *
272 colorprop_new(const PropDescription *pdesc, PropDescToPropPredicate reason)
274 ColorProperty *prop = g_new0(ColorProperty,1);
275 initialize_property(&prop->common,pdesc,reason);
276 prop->color_data.red = 0.0;
277 prop->color_data.green = 0.0;
278 prop->color_data.blue = 1.0;
279 return prop;
282 static ColorProperty *
283 colorprop_copy(ColorProperty *src)
285 ColorProperty *prop =
286 (ColorProperty *)src->common.ops->new_prop(src->common.descr,
287 src->common.reason);
288 copy_init_property(&prop->common,&src->common);
289 prop->color_data = src->color_data;
290 return prop;
293 static WIDGET *
294 colorprop_get_widget(ColorProperty *prop, PropDialog *dialog)
296 GtkWidget *ret = dia_color_selector_new();
297 prophandler_connect(&prop->common,GTK_OBJECT(ret),"FIXME");
298 return ret;
301 static void
302 colorprop_reset_widget(ColorProperty *prop, WIDGET *widget)
304 dia_color_selector_set_color(DIACOLORSELECTOR(widget),
305 &prop->color_data);
308 static void
309 colorprop_set_from_widget(ColorProperty *prop, WIDGET *widget)
311 dia_color_selector_get_color(DIACOLORSELECTOR(widget),
312 &prop->color_data);
315 static void
316 colorprop_load(ColorProperty *prop, AttributeNode attr, DataNode data)
318 data_color(data,&prop->color_data);
321 static void
322 colorprop_save(ColorProperty *prop, AttributeNode attr)
324 data_add_color(attr,&prop->color_data);
327 static void
328 colorprop_get_from_offset(ColorProperty *prop,
329 void *base, guint offset, guint offset2)
331 prop->color_data = struct_member(base,offset,Color);
334 static void
335 colorprop_set_from_offset(ColorProperty *prop,
336 void *base, guint offset, guint offset2)
338 struct_member(base,offset,Color) = prop->color_data;
341 static const PropertyOps colorprop_ops = {
342 (PropertyType_New) colorprop_new,
343 (PropertyType_Free) noopprop_free,
344 (PropertyType_Copy) colorprop_copy,
345 (PropertyType_Load) colorprop_load,
346 (PropertyType_Save) colorprop_save,
347 (PropertyType_GetWidget) colorprop_get_widget,
348 (PropertyType_ResetWidget) colorprop_reset_widget,
349 (PropertyType_SetFromWidget) colorprop_set_from_widget,
351 (PropertyType_CanMerge) noopprop_can_merge,
352 (PropertyType_GetFromOffset) colorprop_get_from_offset,
353 (PropertyType_SetFromOffset) colorprop_set_from_offset
357 /***************************/
358 /* The FONT property type. */
359 /***************************/
361 static FontProperty *
362 fontprop_new(const PropDescription *pdesc, PropDescToPropPredicate reason)
364 FontProperty *prop = g_new0(FontProperty,1);
365 initialize_property(&prop->common,pdesc,reason);
366 prop->font_data = NULL;
367 return prop;
370 static void
371 fontprop_free(FontProperty *prop)
373 if (prop->font_data)
374 dia_font_unref(prop->font_data);
377 static FontProperty *
378 fontprop_copy(FontProperty *src)
380 FontProperty *prop =
381 (FontProperty *)src->common.ops->new_prop(src->common.descr,
382 src->common.reason);
383 copy_init_property(&prop->common,&src->common);
385 if (prop->font_data)
386 dia_font_unref(prop->font_data);
387 prop->font_data = dia_font_ref(src->font_data);
389 return prop;
392 static WIDGET *
393 fontprop_get_widget(FontProperty *prop, PropDialog *dialog)
395 GtkWidget *ret = dia_font_selector_new();
396 prophandler_connect(&prop->common,GTK_OBJECT(ret),"FIXME");
397 return ret;
400 static void
401 fontprop_reset_widget(FontProperty *prop, WIDGET *widget)
403 dia_font_selector_set_font(DIAFONTSELECTOR(widget),
404 prop->font_data);
407 static void
408 fontprop_set_from_widget(FontProperty *prop, WIDGET *widget)
410 prop->font_data = dia_font_selector_get_font(DIAFONTSELECTOR(widget));
413 static void
414 fontprop_load(FontProperty *prop, AttributeNode attr, DataNode data)
416 if (prop->font_data)
417 dia_font_unref(prop->font_data);
418 prop->font_data = data_font(data);
421 static void
422 fontprop_save(FontProperty *prop, AttributeNode attr)
424 data_add_font(attr,prop->font_data);
427 static void
428 fontprop_get_from_offset(FontProperty *prop,
429 void *base, guint offset, guint offset2)
431 if (prop->font_data)
432 dia_font_unref(prop->font_data);
433 prop->font_data = dia_font_ref(struct_member(base,offset,DiaFont *));
436 static void
437 fontprop_set_from_offset(FontProperty *prop,
438 void *base, guint offset, guint offset2)
440 if (prop->font_data) {
441 dia_font_unref(struct_member(base,offset,DiaFont *));
442 struct_member(base,offset,DiaFont *) = dia_font_ref(prop->font_data);
446 static const PropertyOps fontprop_ops = {
447 (PropertyType_New) fontprop_new,
448 (PropertyType_Free) fontprop_free,
449 (PropertyType_Copy) fontprop_copy,
450 (PropertyType_Load) fontprop_load,
451 (PropertyType_Save) fontprop_save,
452 (PropertyType_GetWidget) fontprop_get_widget,
453 (PropertyType_ResetWidget) fontprop_reset_widget,
454 (PropertyType_SetFromWidget) fontprop_set_from_widget,
456 (PropertyType_CanMerge) noopprop_can_merge,
457 (PropertyType_GetFromOffset) fontprop_get_from_offset,
458 (PropertyType_SetFromOffset) fontprop_set_from_offset
461 /* ************************************************************** */
463 void
464 prop_attr_register(void)
466 prop_type_register(PROP_TYPE_LINESTYLE,&linestyleprop_ops);
467 prop_type_register(PROP_TYPE_ARROW,&arrowprop_ops);
468 prop_type_register(PROP_TYPE_COLOUR,&colorprop_ops);
469 prop_type_register(PROP_TYPE_FONT,&fontprop_ops);