1 /* GIMP - The GNU Image Manipulation Program
2 * Copyright (C) 1995 Spencer Kimball and Peter Mattis
3 *
4 * This program is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 3 of the License, or
7 * (at your option) any later version.
8 *
9 * This program 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
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <https://www.gnu.org/licenses/>.
16 */
17
18 #include "config.h"
19
20 #include <string.h>
21
22 #include <gegl.h>
23 #include <gtk/gtk.h>
24
25 #include "libgimpbase/gimpbase.h"
26 #include "libgimpconfig/gimpconfig.h"
27 #include "libgimpwidgets/gimpwidgets.h"
28
29 #include "actions-types.h"
30
31 #include "config/gimpdialogconfig.h"
32
33 #include "core/gimp.h"
34 #include "core/gimp-utils.h"
35 #include "core/gimpchannel.h"
36 #include "core/gimpcontext.h"
37 #include "core/gimpimage.h"
38 #include "core/gimpimage-merge.h"
39 #include "core/gimpimage-undo.h"
40 #include "core/gimpparamspecs.h"
41 #include "core/gimpprogress.h"
42 #include "core/gimptoolinfo.h"
43
44 #include "pdb/gimppdb.h"
45 #include "pdb/gimpprocedure.h"
46
47 #include "vectors/gimpvectors.h"
48 #include "vectors/gimpvectors-export.h"
49 #include "vectors/gimpvectors-import.h"
50
51 #include "widgets/gimpaction.h"
52 #include "widgets/gimpclipboard.h"
53 #include "widgets/gimphelp-ids.h"
54
55 #include "display/gimpdisplay.h"
56
57 #include "tools/gimpvectortool.h"
58 #include "tools/tool_manager.h"
59
60 #include "dialogs/dialogs.h"
61 #include "dialogs/vectors-export-dialog.h"
62 #include "dialogs/vectors-import-dialog.h"
63 #include "dialogs/vectors-options-dialog.h"
64
65 #include "actions.h"
66 #include "items-commands.h"
67 #include "vectors-commands.h"
68
69 #include "gimp-intl.h"
70
71
72 /* local function prototypes */
73
74 static void vectors_new_callback (GtkWidget *dialog,
75 GimpImage *image,
76 GimpVectors *vectors,
77 GimpContext *context,
78 const gchar *vectors_name,
79 gboolean vectors_visible,
80 gboolean vectors_linked,
81 GimpColorTag vectors_color_tag,
82 gboolean vectors_lock_content,
83 gboolean vectors_lock_position,
84 gpointer user_data);
85 static void vectors_edit_attributes_callback (GtkWidget *dialog,
86 GimpImage *image,
87 GimpVectors *vectors,
88 GimpContext *context,
89 const gchar *vectors_name,
90 gboolean vectors_visible,
91 gboolean vectors_linked,
92 GimpColorTag vectors_color_tag,
93 gboolean vectors_lock_content,
94 gboolean vectors_lock_position,
95 gpointer user_data);
96 static void vectors_import_callback (GtkWidget *dialog,
97 GimpImage *image,
98 GFile *file,
99 GFile *import_folder,
100 gboolean merge_vectors,
101 gboolean scale_vectors,
102 gpointer user_data);
103 static void vectors_export_callback (GtkWidget *dialog,
104 GimpImage *image,
105 GFile *file,
106 GFile *export_folder,
107 gboolean active_only,
108 gpointer user_data);
109
110
111 /* public functions */
112
113 void
vectors_edit_cmd_callback(GimpAction * action,GVariant * value,gpointer data)114 vectors_edit_cmd_callback (GimpAction *action,
115 GVariant *value,
116 gpointer data)
117 {
118 GimpImage *image;
119 GimpVectors *vectors;
120 GimpTool *active_tool;
121 return_if_no_vectors (image, vectors, data);
122
123 active_tool = tool_manager_get_active (image->gimp);
124
125 if (! GIMP_IS_VECTOR_TOOL (active_tool))
126 {
127 GimpToolInfo *tool_info = gimp_get_tool_info (image->gimp,
128 "gimp-vector-tool");
129
130 if (GIMP_IS_TOOL_INFO (tool_info))
131 {
132 gimp_context_set_tool (action_data_get_context (data), tool_info);
133 active_tool = tool_manager_get_active (image->gimp);
134 }
135 }
136
137 if (GIMP_IS_VECTOR_TOOL (active_tool))
138 gimp_vector_tool_set_vectors (GIMP_VECTOR_TOOL (active_tool), vectors);
139 }
140
141 void
vectors_edit_attributes_cmd_callback(GimpAction * action,GVariant * value,gpointer data)142 vectors_edit_attributes_cmd_callback (GimpAction *action,
143 GVariant *value,
144 gpointer data)
145 {
146 GimpImage *image;
147 GimpVectors *vectors;
148 GtkWidget *widget;
149 GtkWidget *dialog;
150 return_if_no_vectors (image, vectors, data);
151 return_if_no_widget (widget, data);
152
153 #define EDIT_DIALOG_KEY "gimp-vectors-edit-attributes-dialog"
154
155 dialog = dialogs_get_dialog (G_OBJECT (vectors), EDIT_DIALOG_KEY);
156
157 if (! dialog)
158 {
159 GimpItem *item = GIMP_ITEM (vectors);
160
161 dialog = vectors_options_dialog_new (image, vectors,
162 action_data_get_context (data),
163 widget,
164 _("Path Attributes"),
165 "gimp-vectors-edit",
166 GIMP_ICON_EDIT,
167 _("Edit Path Attributes"),
168 GIMP_HELP_PATH_EDIT,
169 gimp_object_get_name (vectors),
170 gimp_item_get_visible (item),
171 gimp_item_get_linked (item),
172 gimp_item_get_color_tag (item),
173 gimp_item_get_lock_content (item),
174 gimp_item_get_lock_position (item),
175 vectors_edit_attributes_callback,
176 NULL);
177
178 dialogs_attach_dialog (G_OBJECT (vectors), EDIT_DIALOG_KEY, dialog);
179 }
180
181 gtk_window_present (GTK_WINDOW (dialog));
182 }
183
184 void
vectors_new_cmd_callback(GimpAction * action,GVariant * value,gpointer data)185 vectors_new_cmd_callback (GimpAction *action,
186 GVariant *value,
187 gpointer data)
188 {
189 GimpImage *image;
190 GtkWidget *widget;
191 GtkWidget *dialog;
192 return_if_no_image (image, data);
193 return_if_no_widget (widget, data);
194
195 #define NEW_DIALOG_KEY "gimp-vectors-new-dialog"
196
197 dialog = dialogs_get_dialog (G_OBJECT (image), NEW_DIALOG_KEY);
198
199 if (! dialog)
200 {
201 GimpDialogConfig *config = GIMP_DIALOG_CONFIG (image->gimp->config);
202
203 dialog = vectors_options_dialog_new (image, NULL,
204 action_data_get_context (data),
205 widget,
206 _("New Path"),
207 "gimp-vectors-new",
208 GIMP_ICON_PATH,
209 _("Create a New Path"),
210 GIMP_HELP_PATH_NEW,
211 config->vectors_new_name,
212 FALSE,
213 FALSE,
214 GIMP_COLOR_TAG_NONE,
215 FALSE,
216 FALSE,
217 vectors_new_callback,
218 NULL);
219
220 dialogs_attach_dialog (G_OBJECT (image), NEW_DIALOG_KEY, dialog);
221 }
222
223 gtk_window_present (GTK_WINDOW (dialog));
224 }
225
226 void
vectors_new_last_vals_cmd_callback(GimpAction * action,GVariant * value,gpointer data)227 vectors_new_last_vals_cmd_callback (GimpAction *action,
228 GVariant *value,
229 gpointer data)
230 {
231 GimpImage *image;
232 GimpVectors *vectors;
233 GimpDialogConfig *config;
234 return_if_no_image (image, data);
235
236 config = GIMP_DIALOG_CONFIG (image->gimp->config);
237
238 vectors = gimp_vectors_new (image, config->vectors_new_name);
239 gimp_image_add_vectors (image, vectors,
240 GIMP_IMAGE_ACTIVE_PARENT, -1, TRUE);
241 gimp_image_flush (image);
242 }
243
244 void
vectors_raise_cmd_callback(GimpAction * action,GVariant * value,gpointer data)245 vectors_raise_cmd_callback (GimpAction *action,
246 GVariant *value,
247 gpointer data)
248 {
249 GimpImage *image;
250 GimpVectors *vectors;
251 return_if_no_vectors (image, vectors, data);
252
253 gimp_image_raise_item (image, GIMP_ITEM (vectors), NULL);
254 gimp_image_flush (image);
255 }
256
257 void
vectors_raise_to_top_cmd_callback(GimpAction * action,GVariant * value,gpointer data)258 vectors_raise_to_top_cmd_callback (GimpAction *action,
259 GVariant *value,
260 gpointer data)
261 {
262 GimpImage *image;
263 GimpVectors *vectors;
264 return_if_no_vectors (image, vectors, data);
265
266 gimp_image_raise_item_to_top (image, GIMP_ITEM (vectors));
267 gimp_image_flush (image);
268 }
269
270 void
vectors_lower_cmd_callback(GimpAction * action,GVariant * value,gpointer data)271 vectors_lower_cmd_callback (GimpAction *action,
272 GVariant *value,
273 gpointer data)
274 {
275 GimpImage *image;
276 GimpVectors *vectors;
277 return_if_no_vectors (image, vectors, data);
278
279 gimp_image_lower_item (image, GIMP_ITEM (vectors), NULL);
280 gimp_image_flush (image);
281 }
282
283 void
vectors_lower_to_bottom_cmd_callback(GimpAction * action,GVariant * value,gpointer data)284 vectors_lower_to_bottom_cmd_callback (GimpAction *action,
285 GVariant *value,
286 gpointer data)
287 {
288 GimpImage *image;
289 GimpVectors *vectors;
290 return_if_no_vectors (image, vectors, data);
291
292 gimp_image_lower_item_to_bottom (image, GIMP_ITEM (vectors));
293 gimp_image_flush (image);
294 }
295
296 void
vectors_duplicate_cmd_callback(GimpAction * action,GVariant * value,gpointer data)297 vectors_duplicate_cmd_callback (GimpAction *action,
298 GVariant *value,
299 gpointer data)
300 {
301 GimpImage *image;
302 GimpVectors *vectors;
303 GimpVectors *new_vectors;
304 return_if_no_vectors (image, vectors, data);
305
306 new_vectors = GIMP_VECTORS (gimp_item_duplicate (GIMP_ITEM (vectors),
307 G_TYPE_FROM_INSTANCE (vectors)));
308 /* use the actual parent here, not GIMP_IMAGE_ACTIVE_PARENT because
309 * the latter would add a duplicated group inside itself instead of
310 * above it
311 */
312 gimp_image_add_vectors (image, new_vectors,
313 gimp_vectors_get_parent (vectors), -1,
314 TRUE);
315 gimp_image_flush (image);
316 }
317
318 void
vectors_delete_cmd_callback(GimpAction * action,GVariant * value,gpointer data)319 vectors_delete_cmd_callback (GimpAction *action,
320 GVariant *value,
321 gpointer data)
322 {
323 GimpImage *image;
324 GimpVectors *vectors;
325 return_if_no_vectors (image, vectors, data);
326
327 gimp_image_remove_vectors (image, vectors, TRUE, NULL);
328 gimp_image_flush (image);
329 }
330
331 void
vectors_merge_visible_cmd_callback(GimpAction * action,GVariant * value,gpointer data)332 vectors_merge_visible_cmd_callback (GimpAction *action,
333 GVariant *value,
334 gpointer data)
335 {
336 GimpImage *image;
337 GimpVectors *vectors;
338 GtkWidget *widget;
339 GError *error = NULL;
340 return_if_no_vectors (image, vectors, data);
341 return_if_no_widget (widget, data);
342
343 if (! gimp_image_merge_visible_vectors (image, &error))
344 {
345 gimp_message_literal (image->gimp,
346 G_OBJECT (widget), GIMP_MESSAGE_WARNING,
347 error->message);
348 g_clear_error (&error);
349 return;
350 }
351
352 gimp_image_flush (image);
353 }
354
355 void
vectors_to_selection_cmd_callback(GimpAction * action,GVariant * value,gpointer data)356 vectors_to_selection_cmd_callback (GimpAction *action,
357 GVariant *value,
358 gpointer data)
359 {
360 GimpImage *image;
361 GimpVectors *vectors;
362 GimpChannelOps operation;
363 return_if_no_vectors (image, vectors, data);
364
365 operation = (GimpChannelOps) g_variant_get_int32 (value);
366
367 gimp_item_to_selection (GIMP_ITEM (vectors), operation,
368 TRUE, FALSE, 0, 0);
369 gimp_image_flush (image);
370 }
371
372 void
vectors_selection_to_vectors_cmd_callback(GimpAction * action,GVariant * value,gpointer data)373 vectors_selection_to_vectors_cmd_callback (GimpAction *action,
374 GVariant *value,
375 gpointer data)
376 {
377 GimpImage *image;
378 GtkWidget *widget;
379 GimpProcedure *procedure;
380 GimpValueArray *args;
381 GimpDisplay *display;
382 gboolean advanced;
383 GError *error = NULL;
384 return_if_no_image (image, data);
385 return_if_no_widget (widget, data);
386
387 advanced = (gboolean) g_variant_get_int32 (value);
388
389 if (advanced)
390 procedure = gimp_pdb_lookup_procedure (image->gimp->pdb,
391 "plug-in-sel2path-advanced");
392 else
393 procedure = gimp_pdb_lookup_procedure (image->gimp->pdb,
394 "plug-in-sel2path");
395
396 if (! procedure)
397 {
398 gimp_message_literal (image->gimp,
399 G_OBJECT (widget), GIMP_MESSAGE_ERROR,
400 "Selection to path procedure lookup failed.");
401 return;
402 }
403
404 display = gimp_context_get_display (action_data_get_context (data));
405
406 args = gimp_procedure_get_arguments (procedure);
407 gimp_value_array_truncate (args, 2);
408
409 g_value_set_int (gimp_value_array_index (args, 0),
410 GIMP_RUN_INTERACTIVE);
411 gimp_value_set_image (gimp_value_array_index (args, 1),
412 image);
413
414 gimp_procedure_execute_async (procedure, image->gimp,
415 action_data_get_context (data),
416 GIMP_PROGRESS (display), args,
417 GIMP_OBJECT (display), &error);
418
419 gimp_value_array_unref (args);
420
421 if (error)
422 {
423 gimp_message_literal (image->gimp,
424 G_OBJECT (widget), GIMP_MESSAGE_ERROR,
425 error->message);
426 g_error_free (error);
427 }
428 }
429
430 void
vectors_fill_cmd_callback(GimpAction * action,GVariant * value,gpointer data)431 vectors_fill_cmd_callback (GimpAction *action,
432 GVariant *value,
433 gpointer data)
434 {
435 GimpImage *image;
436 GimpVectors *vectors;
437 return_if_no_vectors (image, vectors, data);
438
439 items_fill_cmd_callback (action,
440 image, GIMP_ITEM (vectors),
441 "gimp-vectors-fill-dialog",
442 _("Fill Path"),
443 GIMP_ICON_TOOL_BUCKET_FILL,
444 GIMP_HELP_PATH_FILL,
445 data);
446 }
447
448 void
vectors_fill_last_vals_cmd_callback(GimpAction * action,GVariant * value,gpointer data)449 vectors_fill_last_vals_cmd_callback (GimpAction *action,
450 GVariant *value,
451 gpointer data)
452 {
453 GimpImage *image;
454 GimpVectors *vectors;
455 return_if_no_vectors (image, vectors, data);
456
457 items_fill_last_vals_cmd_callback (action,
458 image, GIMP_ITEM (vectors),
459 data);
460 }
461
462 void
vectors_stroke_cmd_callback(GimpAction * action,GVariant * value,gpointer data)463 vectors_stroke_cmd_callback (GimpAction *action,
464 GVariant *value,
465 gpointer data)
466 {
467 GimpImage *image;
468 GimpVectors *vectors;
469 return_if_no_vectors (image, vectors, data);
470
471 items_stroke_cmd_callback (action,
472 image, GIMP_ITEM (vectors),
473 "gimp-vectors-stroke-dialog",
474 _("Stroke Path"),
475 GIMP_ICON_PATH_STROKE,
476 GIMP_HELP_PATH_STROKE,
477 data);
478 }
479
480 void
vectors_stroke_last_vals_cmd_callback(GimpAction * action,GVariant * value,gpointer data)481 vectors_stroke_last_vals_cmd_callback (GimpAction *action,
482 GVariant *value,
483 gpointer data)
484 {
485 GimpImage *image;
486 GimpVectors *vectors;
487 return_if_no_vectors (image, vectors, data);
488
489 items_stroke_last_vals_cmd_callback (action,
490 image, GIMP_ITEM (vectors),
491 data);
492 }
493
494 void
vectors_copy_cmd_callback(GimpAction * action,GVariant * value,gpointer data)495 vectors_copy_cmd_callback (GimpAction *action,
496 GVariant *value,
497 gpointer data)
498 {
499 GimpImage *image;
500 GimpVectors *vectors;
501 gchar *svg;
502 return_if_no_vectors (image, vectors, data);
503
504 svg = gimp_vectors_export_string (image, vectors);
505
506 if (svg)
507 {
508 gimp_clipboard_set_svg (image->gimp, svg);
509 g_free (svg);
510 }
511 }
512
513 void
vectors_paste_cmd_callback(GimpAction * action,GVariant * value,gpointer data)514 vectors_paste_cmd_callback (GimpAction *action,
515 GVariant *value,
516 gpointer data)
517 {
518 GimpImage *image;
519 GtkWidget *widget;
520 gchar *svg;
521 gsize svg_size;
522 return_if_no_image (image, data);
523 return_if_no_widget (widget, data);
524
525 svg = gimp_clipboard_get_svg (image->gimp, &svg_size);
526
527 if (svg)
528 {
529 GError *error = NULL;
530
531 if (! gimp_vectors_import_buffer (image, svg, svg_size,
532 TRUE, FALSE,
533 GIMP_IMAGE_ACTIVE_PARENT, -1,
534 NULL, &error))
535 {
536 gimp_message (image->gimp, G_OBJECT (widget), GIMP_MESSAGE_ERROR,
537 "%s", error->message);
538 g_clear_error (&error);
539 }
540 else
541 {
542 gimp_image_flush (image);
543 }
544
545 g_free (svg);
546 }
547 }
548
549 void
vectors_export_cmd_callback(GimpAction * action,GVariant * value,gpointer data)550 vectors_export_cmd_callback (GimpAction *action,
551 GVariant *value,
552 gpointer data)
553 {
554 GimpImage *image;
555 GimpVectors *vectors;
556 GtkWidget *widget;
557 GtkWidget *dialog;
558 return_if_no_vectors (image, vectors, data);
559 return_if_no_widget (widget, data);
560
561 #define EXPORT_DIALOG_KEY "gimp-vectors-export-dialog"
562
563 dialog = dialogs_get_dialog (G_OBJECT (image), EXPORT_DIALOG_KEY);
564
565 if (! dialog)
566 {
567 GimpDialogConfig *config = GIMP_DIALOG_CONFIG (image->gimp->config);
568 GFile *folder = NULL;
569
570 if (config->vectors_export_path)
571 folder = gimp_file_new_for_config_path (config->vectors_export_path,
572 NULL);
573
574 dialog = vectors_export_dialog_new (image, widget,
575 folder,
576 config->vectors_export_active_only,
577 vectors_export_callback,
578 NULL);
579
580 if (folder)
581 g_object_unref (folder);
582
583 dialogs_attach_dialog (G_OBJECT (image), EXPORT_DIALOG_KEY, dialog);
584 }
585
586 gtk_window_present (GTK_WINDOW (dialog));
587 }
588
589 void
vectors_import_cmd_callback(GimpAction * action,GVariant * value,gpointer data)590 vectors_import_cmd_callback (GimpAction *action,
591 GVariant *value,
592 gpointer data)
593 {
594 GimpImage *image;
595 GtkWidget *widget;
596 GtkWidget *dialog;
597 return_if_no_image (image, data);
598 return_if_no_widget (widget, data);
599
600 #define IMPORT_DIALOG_KEY "gimp-vectors-import-dialog"
601
602 dialog = dialogs_get_dialog (G_OBJECT (image), IMPORT_DIALOG_KEY);
603
604 if (! dialog)
605 {
606 GimpDialogConfig *config = GIMP_DIALOG_CONFIG (image->gimp->config);
607 GFile *folder = NULL;
608
609 if (config->vectors_import_path)
610 folder = gimp_file_new_for_config_path (config->vectors_import_path,
611 NULL);
612
613 dialog = vectors_import_dialog_new (image, widget,
614 folder,
615 config->vectors_import_merge,
616 config->vectors_import_scale,
617 vectors_import_callback,
618 NULL);
619
620 dialogs_attach_dialog (G_OBJECT (image), IMPORT_DIALOG_KEY, dialog);
621 }
622
623 gtk_window_present (GTK_WINDOW (dialog));
624 }
625
626 void
vectors_visible_cmd_callback(GimpAction * action,GVariant * value,gpointer data)627 vectors_visible_cmd_callback (GimpAction *action,
628 GVariant *value,
629 gpointer data)
630 {
631 GimpImage *image;
632 GimpVectors *vectors;
633 return_if_no_vectors (image, vectors, data);
634
635 items_visible_cmd_callback (action, value, image, GIMP_ITEM (vectors));
636 }
637
638 void
vectors_linked_cmd_callback(GimpAction * action,GVariant * value,gpointer data)639 vectors_linked_cmd_callback (GimpAction *action,
640 GVariant *value,
641 gpointer data)
642 {
643 GimpImage *image;
644 GimpVectors *vectors;
645 return_if_no_vectors (image, vectors, data);
646
647 items_linked_cmd_callback (action, value, image, GIMP_ITEM (vectors));
648 }
649
650 void
vectors_lock_content_cmd_callback(GimpAction * action,GVariant * value,gpointer data)651 vectors_lock_content_cmd_callback (GimpAction *action,
652 GVariant *value,
653 gpointer data)
654 {
655 GimpImage *image;
656 GimpVectors *vectors;
657 return_if_no_vectors (image, vectors, data);
658
659 items_lock_content_cmd_callback (action, value, image, GIMP_ITEM (vectors));
660 }
661
662 void
vectors_lock_position_cmd_callback(GimpAction * action,GVariant * value,gpointer data)663 vectors_lock_position_cmd_callback (GimpAction *action,
664 GVariant *value,
665 gpointer data)
666 {
667 GimpImage *image;
668 GimpVectors *vectors;
669 return_if_no_vectors (image, vectors, data);
670
671 items_lock_position_cmd_callback (action, value, image, GIMP_ITEM (vectors));
672 }
673
674 void
vectors_color_tag_cmd_callback(GimpAction * action,GVariant * value,gpointer data)675 vectors_color_tag_cmd_callback (GimpAction *action,
676 GVariant *value,
677 gpointer data)
678 {
679 GimpImage *image;
680 GimpVectors *vectors;
681 GimpColorTag color_tag;
682 return_if_no_vectors (image, vectors, data);
683
684 color_tag = (GimpColorTag) g_variant_get_int32 (value);
685
686 items_color_tag_cmd_callback (action, image, GIMP_ITEM (vectors),
687 color_tag);
688 }
689
690
691 /* private functions */
692
693 static void
vectors_new_callback(GtkWidget * dialog,GimpImage * image,GimpVectors * vectors,GimpContext * context,const gchar * vectors_name,gboolean vectors_visible,gboolean vectors_linked,GimpColorTag vectors_color_tag,gboolean vectors_lock_content,gboolean vectors_lock_position,gpointer user_data)694 vectors_new_callback (GtkWidget *dialog,
695 GimpImage *image,
696 GimpVectors *vectors,
697 GimpContext *context,
698 const gchar *vectors_name,
699 gboolean vectors_visible,
700 gboolean vectors_linked,
701 GimpColorTag vectors_color_tag,
702 gboolean vectors_lock_content,
703 gboolean vectors_lock_position,
704 gpointer user_data)
705 {
706 GimpDialogConfig *config = GIMP_DIALOG_CONFIG (image->gimp->config);
707
708 g_object_set (config,
709 "path-new-name", vectors_name,
710 NULL);
711
712 vectors = gimp_vectors_new (image, config->vectors_new_name);
713 gimp_item_set_visible (GIMP_ITEM (vectors), vectors_visible, FALSE);
714 gimp_item_set_linked (GIMP_ITEM (vectors), vectors_linked, FALSE);
715 gimp_item_set_color_tag (GIMP_ITEM (vectors), vectors_color_tag, FALSE);
716 gimp_item_set_lock_content (GIMP_ITEM (vectors), vectors_lock_content, FALSE);
717 gimp_item_set_lock_position (GIMP_ITEM (vectors), vectors_lock_position, FALSE);
718
719 gimp_image_add_vectors (image, vectors,
720 GIMP_IMAGE_ACTIVE_PARENT, -1, TRUE);
721 gimp_image_flush (image);
722
723 gtk_widget_destroy (dialog);
724 }
725
726 static void
vectors_edit_attributes_callback(GtkWidget * dialog,GimpImage * image,GimpVectors * vectors,GimpContext * context,const gchar * vectors_name,gboolean vectors_visible,gboolean vectors_linked,GimpColorTag vectors_color_tag,gboolean vectors_lock_content,gboolean vectors_lock_position,gpointer user_data)727 vectors_edit_attributes_callback (GtkWidget *dialog,
728 GimpImage *image,
729 GimpVectors *vectors,
730 GimpContext *context,
731 const gchar *vectors_name,
732 gboolean vectors_visible,
733 gboolean vectors_linked,
734 GimpColorTag vectors_color_tag,
735 gboolean vectors_lock_content,
736 gboolean vectors_lock_position,
737 gpointer user_data)
738 {
739 GimpItem *item = GIMP_ITEM (vectors);
740
741 if (strcmp (vectors_name, gimp_object_get_name (vectors)) ||
742 vectors_visible != gimp_item_get_visible (item) ||
743 vectors_linked != gimp_item_get_linked (item) ||
744 vectors_color_tag != gimp_item_get_color_tag (item) ||
745 vectors_lock_content != gimp_item_get_lock_content (item) ||
746 vectors_lock_position != gimp_item_get_lock_position (item))
747 {
748 gimp_image_undo_group_start (image,
749 GIMP_UNDO_GROUP_ITEM_PROPERTIES,
750 _("Path Attributes"));
751
752 if (strcmp (vectors_name, gimp_object_get_name (vectors)))
753 gimp_item_rename (GIMP_ITEM (vectors), vectors_name, NULL);
754
755 if (vectors_visible != gimp_item_get_visible (item))
756 gimp_item_set_visible (item, vectors_visible, TRUE);
757
758 if (vectors_linked != gimp_item_get_linked (item))
759 gimp_item_set_linked (item, vectors_linked, TRUE);
760
761 if (vectors_color_tag != gimp_item_get_color_tag (item))
762 gimp_item_set_color_tag (item, vectors_color_tag, TRUE);
763
764 if (vectors_lock_content != gimp_item_get_lock_content (item))
765 gimp_item_set_lock_content (item, vectors_lock_content, TRUE);
766
767 if (vectors_lock_position != gimp_item_get_lock_position (item))
768 gimp_item_set_lock_position (item, vectors_lock_position, TRUE);
769
770 gimp_image_undo_group_end (image);
771
772 gimp_image_flush (image);
773 }
774
775 gtk_widget_destroy (dialog);
776 }
777
778 static void
vectors_import_callback(GtkWidget * dialog,GimpImage * image,GFile * file,GFile * import_folder,gboolean merge_vectors,gboolean scale_vectors,gpointer user_data)779 vectors_import_callback (GtkWidget *dialog,
780 GimpImage *image,
781 GFile *file,
782 GFile *import_folder,
783 gboolean merge_vectors,
784 gboolean scale_vectors,
785 gpointer user_data)
786 {
787 GimpDialogConfig *config = GIMP_DIALOG_CONFIG (image->gimp->config);
788 gchar *path = NULL;
789 GError *error = NULL;
790
791 if (import_folder)
792 path = gimp_file_get_config_path (import_folder, NULL);
793
794 g_object_set (config,
795 "path-import-path", path,
796 "path-import-merge", merge_vectors,
797 "path-import-scale", scale_vectors,
798 NULL);
799
800 if (path)
801 g_free (path);
802
803 if (gimp_vectors_import_file (image, file,
804 config->vectors_import_merge,
805 config->vectors_import_scale,
806 GIMP_IMAGE_ACTIVE_PARENT, -1,
807 NULL, &error))
808 {
809 gimp_image_flush (image);
810 }
811 else
812 {
813 gimp_message (image->gimp, G_OBJECT (dialog),
814 GIMP_MESSAGE_ERROR,
815 "%s", error->message);
816 g_error_free (error);
817 return;
818 }
819
820 gtk_widget_destroy (dialog);
821 }
822
823 static void
vectors_export_callback(GtkWidget * dialog,GimpImage * image,GFile * file,GFile * export_folder,gboolean active_only,gpointer user_data)824 vectors_export_callback (GtkWidget *dialog,
825 GimpImage *image,
826 GFile *file,
827 GFile *export_folder,
828 gboolean active_only,
829 gpointer user_data)
830 {
831 GimpDialogConfig *config = GIMP_DIALOG_CONFIG (image->gimp->config);
832 GimpVectors *vectors = NULL;
833 gchar *path = NULL;
834 GError *error = NULL;
835
836 if (export_folder)
837 path = gimp_file_get_config_path (export_folder, NULL);
838
839 g_object_set (config,
840 "path-export-path", path,
841 "path-export-active-only", active_only,
842 NULL);
843
844 if (path)
845 g_free (path);
846
847 if (config->vectors_export_active_only)
848 vectors = gimp_image_get_active_vectors (image);
849
850 if (! gimp_vectors_export_file (image, vectors, file, &error))
851 {
852 gimp_message (image->gimp, G_OBJECT (dialog),
853 GIMP_MESSAGE_ERROR,
854 "%s", error->message);
855 g_clear_error (&error);
856 return;
857 }
858
859 gtk_widget_destroy (dialog);
860 }
861
862 void
vectors_select_cmd_callback(GimpAction * action,GVariant * value,gpointer data)863 vectors_select_cmd_callback (GimpAction *action,
864 GVariant *value,
865 gpointer data)
866 {
867 GimpImage *image;
868 GimpVectors *vectors;
869 GimpContainer *container;
870 GimpVectors *new_vectors;
871 GimpActionSelectType select_type;
872 return_if_no_image (image, data);
873
874 select_type = (GimpActionSelectType) g_variant_get_int32 (value);
875
876 vectors = gimp_image_get_active_vectors (image);
877
878 if (vectors)
879 container = gimp_item_get_container (GIMP_ITEM (vectors));
880 else
881 container = gimp_image_get_vectors (image);
882
883 new_vectors = (GimpVectors *) action_select_object (select_type,
884 container,
885 (GimpObject *) vectors);
886
887 if (new_vectors && new_vectors != vectors)
888 {
889 gimp_image_set_active_vectors (image, new_vectors);
890 gimp_image_flush (image);
891 }
892 }
893