Merge lp:~inkscape+alexander/inkscape/move-boolops into lp:~inkscape.dev/inkscape/trunk
- move-boolops
- Merge into trunk
Proposed by
Alexander Brock
Status: | Merged |
---|---|
Approved by: | Mc |
Approved revision: | no longer in the source branch. |
Merged at revision: | 15232 |
Proposed branch: | lp:~inkscape+alexander/inkscape/move-boolops |
Merge into: | lp:~inkscape.dev/inkscape/trunk |
Diff against target: |
545 lines (+128/-171) 11 files modified
src/livarot/LivarotDefs.h (+0/-12) src/livarot/Shape.h (+1/-0) src/livarot/int-line.h (+1/-0) src/object-set.h (+36/-1) src/splivarot.cpp (+72/-121) src/splivarot.h (+1/-20) src/ui/tools/calligraphic-tool.cpp (+2/-2) src/ui/tools/eraser-tool.cpp (+6/-6) src/ui/tools/flood-tool.cpp (+1/-1) src/ui/tools/spray-tool.cpp (+2/-2) src/verbs.cpp (+6/-6) |
To merge this branch: | bzr merge lp:~inkscape+alexander/inkscape/move-boolops |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Mc | Pending | ||
Review via email: mp+310388@code.launchpad.net |
Commit message
Description of the change
Move boolop functions from sp_selected_
To post a comment you must log in.
- 15230. By Tavmjong Bah
-
Enable swapping of fill and stroke when one is a mesh.
- 15231. By Tavmjong Bah
-
Click-drag selects nodes rather than creates new mesh if mesh already exists.
- 15232. By Mc
-
merge boolop branch: Move boolop functions from sp_selected_
path_<op> to ObjectSet::path<op>
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | === modified file 'src/livarot/LivarotDefs.h' | |||
2 | --- src/livarot/LivarotDefs.h 2016-04-11 12:56:03 +0000 | |||
3 | +++ src/livarot/LivarotDefs.h 2016-11-09 00:34:30 +0000 | |||
4 | @@ -40,18 +40,6 @@ | |||
5 | 40 | found_between = 4 | 40 | found_between = 4 |
6 | 41 | }; | 41 | }; |
7 | 42 | 42 | ||
8 | 43 | // boolean operation | ||
9 | 44 | enum bool_op | ||
10 | 45 | { | ||
11 | 46 | bool_op_union, // A OR B | ||
12 | 47 | bool_op_inters, // A AND B | ||
13 | 48 | bool_op_diff, // A \ B | ||
14 | 49 | bool_op_symdiff, // A XOR B | ||
15 | 50 | bool_op_cut, // coupure (pleines) | ||
16 | 51 | bool_op_slice // coupure (contour) | ||
17 | 52 | }; | ||
18 | 53 | typedef enum bool_op BooleanOp; | ||
19 | 54 | |||
20 | 55 | // types of cap for stroking polylines | 43 | // types of cap for stroking polylines |
21 | 56 | enum butt_typ | 44 | enum butt_typ |
22 | 57 | { | 45 | { |
23 | 58 | 46 | ||
24 | === modified file 'src/livarot/Shape.h' | |||
25 | --- src/livarot/Shape.h 2014-03-30 22:08:13 +0000 | |||
26 | +++ src/livarot/Shape.h 2016-11-09 00:34:30 +0000 | |||
27 | @@ -17,6 +17,7 @@ | |||
28 | 17 | #include <2geom/point.h> | 17 | #include <2geom/point.h> |
29 | 18 | 18 | ||
30 | 19 | #include "livarot/LivarotDefs.h" | 19 | #include "livarot/LivarotDefs.h" |
31 | 20 | #include "object-set.h" | ||
32 | 20 | 21 | ||
33 | 21 | class Path; | 22 | class Path; |
34 | 22 | class FloatLigne; | 23 | class FloatLigne; |
35 | 23 | 24 | ||
36 | === modified file 'src/livarot/int-line.h' | |||
37 | --- src/livarot/int-line.h 2011-10-04 05:43:09 +0000 | |||
38 | +++ src/livarot/int-line.h 2016-11-09 00:34:30 +0000 | |||
39 | @@ -2,6 +2,7 @@ | |||
40 | 2 | #define INKSCAPE_LIVAROT_INT_LINE_H | 2 | #define INKSCAPE_LIVAROT_INT_LINE_H |
41 | 3 | 3 | ||
42 | 4 | #include "livarot/LivarotDefs.h" | 4 | #include "livarot/LivarotDefs.h" |
43 | 5 | #include "object-set.h" | ||
44 | 5 | 6 | ||
45 | 6 | /** \file | 7 | /** \file |
46 | 7 | * Coverage with integer boundaries. | 8 | * Coverage with integer boundaries. |
47 | 8 | 9 | ||
48 | === modified file 'src/object-set.h' | |||
49 | --- src/object-set.h 2016-11-06 22:07:52 +0000 | |||
50 | +++ src/object-set.h 2016-11-09 00:34:30 +0000 | |||
51 | @@ -33,6 +33,29 @@ | |||
52 | 33 | #include "sp-item-group.h" | 33 | #include "sp-item-group.h" |
53 | 34 | #include "desktop.h" | 34 | #include "desktop.h" |
54 | 35 | #include "document.h" | 35 | #include "document.h" |
55 | 36 | #include "verbs.h" | ||
56 | 37 | |||
57 | 38 | enum BoolOpErrors { | ||
58 | 39 | DONE, | ||
59 | 40 | DONE_NO_PATH, | ||
60 | 41 | DONE_NO_ACTION, | ||
61 | 42 | ERR_TOO_LESS_PATHS_1, | ||
62 | 43 | ERR_TOO_LESS_PATHS_2, | ||
63 | 44 | ERR_NO_PATHS, | ||
64 | 45 | ERR_Z_ORDER | ||
65 | 46 | }; | ||
66 | 47 | |||
67 | 48 | // boolean operation | ||
68 | 49 | enum bool_op | ||
69 | 50 | { | ||
70 | 51 | bool_op_union, // A OR B | ||
71 | 52 | bool_op_inters, // A AND B | ||
72 | 53 | bool_op_diff, // A \ B | ||
73 | 54 | bool_op_symdiff, // A XOR B | ||
74 | 55 | bool_op_cut, // coupure (pleines) | ||
75 | 56 | bool_op_slice // coupure (contour) | ||
76 | 57 | }; | ||
77 | 58 | typedef enum bool_op BooleanOp; | ||
78 | 36 | 59 | ||
79 | 37 | class SPBox3D; | 60 | class SPBox3D; |
80 | 38 | class Persp3D; | 61 | class Persp3D; |
81 | @@ -376,7 +399,16 @@ | |||
82 | 376 | void toCurves(bool skip_undo = false); | 399 | void toCurves(bool skip_undo = false); |
83 | 377 | void toLPEItems(); | 400 | void toLPEItems(); |
84 | 378 | void pathReverse(); | 401 | void pathReverse(); |
86 | 379 | 402 | ||
87 | 403 | // Boolean operations | ||
88 | 404 | // in splivarot.cpp | ||
89 | 405 | bool pathUnion(const bool skip_undo = false); | ||
90 | 406 | bool pathIntersect(const bool skip_undo = false); | ||
91 | 407 | bool pathDiff(const bool skip_undo = false); | ||
92 | 408 | bool pathSymDiff(const bool skip_undo = false); | ||
93 | 409 | bool pathCut(const bool skip_undo = false); | ||
94 | 410 | bool pathSlice(const bool skip_undo = false); | ||
95 | 411 | |||
96 | 380 | //Other path operations | 412 | //Other path operations |
97 | 381 | //in selection-chemistry.cpp | 413 | //in selection-chemistry.cpp |
98 | 382 | void toMarker(bool apply = true); | 414 | void toMarker(bool apply = true); |
99 | @@ -438,6 +470,9 @@ | |||
100 | 438 | std::list<SPBox3D *> _3dboxes; | 470 | std::list<SPBox3D *> _3dboxes; |
101 | 439 | std::unordered_map<SPObject*, sigc::connection> _releaseConnections; | 471 | std::unordered_map<SPObject*, sigc::connection> _releaseConnections; |
102 | 440 | 472 | ||
103 | 473 | private: | ||
104 | 474 | BoolOpErrors pathBoolOp(bool_op bop, const bool skip_undo, const unsigned int verb = SP_VERB_NONE, const Glib::ustring description = ""); | ||
105 | 475 | |||
106 | 441 | }; | 476 | }; |
107 | 442 | 477 | ||
108 | 443 | typedef ObjectSet::SPItemRange SPItemRange; | 478 | typedef ObjectSet::SPItemRange SPItemRange; |
109 | 444 | 479 | ||
110 | === modified file 'src/splivarot.cpp' | |||
111 | --- src/splivarot.cpp 2016-09-02 19:32:55 +0000 | |||
112 | +++ src/splivarot.cpp 2016-11-09 00:34:30 +0000 | |||
113 | @@ -47,96 +47,51 @@ | |||
114 | 47 | #include "verbs.h" | 47 | #include "verbs.h" |
115 | 48 | #include "2geom/svg-path-parser.h" // to get from SVG on boolean to Geom::Path | 48 | #include "2geom/svg-path-parser.h" // to get from SVG on boolean to Geom::Path |
116 | 49 | 49 | ||
117 | 50 | enum BoolOpErrors { | ||
118 | 51 | DONE, | ||
119 | 52 | DONE_NO_PATH, | ||
120 | 53 | DONE_NO_ACTION, | ||
121 | 54 | ERR_TOO_LESS_PATHS_1, | ||
122 | 55 | ERR_TOO_LESS_PATHS_2, | ||
123 | 56 | ERR_NO_PATHS, | ||
124 | 57 | ERR_Z_ORDER | ||
125 | 58 | }; | ||
126 | 59 | |||
127 | 60 | using Inkscape::DocumentUndo; | 50 | using Inkscape::DocumentUndo; |
128 | 61 | 51 | ||
129 | 62 | bool Ancetre(Inkscape::XML::Node *a, Inkscape::XML::Node *who); | 52 | bool Ancetre(Inkscape::XML::Node *a, Inkscape::XML::Node *who); |
130 | 63 | 53 | ||
131 | 64 | void sp_selected_path_boolop_ui(Inkscape::Selection *selection, SPDesktop *desktop, bool_op bop, | ||
132 | 65 | const unsigned int verb = SP_VERB_NONE, const Glib::ustring description = ""); | ||
133 | 66 | BoolOpErrors sp_selected_path_boolop(Inkscape::ObjectSet *set, bool_op bop); | ||
134 | 67 | void sp_selected_path_do_offset(SPDesktop *desktop, bool expand, double prefOffset); | 54 | void sp_selected_path_do_offset(SPDesktop *desktop, bool expand, double prefOffset); |
135 | 68 | void sp_selected_path_create_offset_object(SPDesktop *desktop, int expand, bool updating); | 55 | void sp_selected_path_create_offset_object(SPDesktop *desktop, int expand, bool updating); |
136 | 69 | 56 | ||
207 | 70 | void | 57 | bool Inkscape::ObjectSet::pathUnion(const bool skip_undo) { |
208 | 71 | sp_selected_path_union(Inkscape::Selection *selection, SPDesktop *desktop) | 58 | BoolOpErrors result = pathBoolOp(bool_op_union, skip_undo, SP_VERB_SELECTION_UNION, _("Union")); |
209 | 72 | { | 59 | return DONE == result; |
210 | 73 | sp_selected_path_boolop_ui(selection, desktop, bool_op_union, SP_VERB_SELECTION_UNION, _("Union")); | 60 | } |
211 | 74 | } | 61 | |
212 | 75 | 62 | bool | |
213 | 76 | void | 63 | Inkscape::ObjectSet::pathIntersect(const bool skip_undo) |
214 | 77 | sp_selected_path_union_skip_undo(Inkscape::ObjectSet *set) | 64 | { |
215 | 78 | { | 65 | BoolOpErrors result = pathBoolOp(bool_op_inters, skip_undo, SP_VERB_SELECTION_INTERSECT, _("Intersection")); |
216 | 79 | sp_selected_path_boolop(set, bool_op_union); | 66 | return DONE == result; |
217 | 80 | } | 67 | } |
218 | 81 | 68 | ||
219 | 82 | void | 69 | bool |
220 | 83 | sp_selected_path_intersect(Inkscape::Selection *selection, SPDesktop *desktop) | 70 | Inkscape::ObjectSet::pathDiff(const bool skip_undo) |
221 | 84 | { | 71 | { |
222 | 85 | sp_selected_path_boolop_ui(selection, desktop, bool_op_inters, SP_VERB_SELECTION_INTERSECT, _("Intersection")); | 72 | BoolOpErrors result = pathBoolOp(bool_op_diff, skip_undo, SP_VERB_SELECTION_DIFF, _("Difference")); |
223 | 86 | } | 73 | return DONE == result; |
224 | 87 | 74 | } | |
225 | 88 | void | 75 | |
226 | 89 | sp_selected_path_intersect_skip_undo(Inkscape::ObjectSet *set) | 76 | bool |
227 | 90 | { | 77 | Inkscape::ObjectSet::pathSymDiff(const bool skip_undo) |
228 | 91 | sp_selected_path_boolop(set, bool_op_inters); | 78 | { |
229 | 92 | } | 79 | BoolOpErrors result = pathBoolOp(bool_op_symdiff, skip_undo, SP_VERB_SELECTION_SYMDIFF, _("Exclusion")); |
230 | 93 | 80 | return DONE == result; | |
231 | 94 | void | 81 | } |
232 | 95 | sp_selected_path_diff(Inkscape::Selection *selection, SPDesktop *desktop) | 82 | |
233 | 96 | { | 83 | bool |
234 | 97 | sp_selected_path_boolop_ui(selection, desktop, bool_op_diff, SP_VERB_SELECTION_DIFF, _("Difference")); | 84 | Inkscape::ObjectSet::pathCut(const bool skip_undo) |
235 | 98 | } | 85 | { |
236 | 99 | 86 | BoolOpErrors result = pathBoolOp(bool_op_cut, skip_undo, SP_VERB_SELECTION_CUT, _("Division")); | |
237 | 100 | void | 87 | return DONE == result; |
238 | 101 | sp_selected_path_diff_skip_undo(Inkscape::ObjectSet *set) | 88 | } |
239 | 102 | { | 89 | |
240 | 103 | sp_selected_path_boolop(set, bool_op_diff); | 90 | bool |
241 | 104 | } | 91 | Inkscape::ObjectSet::pathSlice(const bool skip_undo) |
242 | 105 | 92 | { | |
243 | 106 | void | 93 | BoolOpErrors result = pathBoolOp(bool_op_slice, skip_undo, SP_VERB_SELECTION_SLICE, _("Cut path")); |
244 | 107 | sp_selected_path_symdiff(Inkscape::Selection *selection, SPDesktop *desktop) | 94 | return DONE == result; |
175 | 108 | { | ||
176 | 109 | sp_selected_path_boolop_ui(selection, desktop, bool_op_symdiff, SP_VERB_SELECTION_SYMDIFF, _("Exclusion")); | ||
177 | 110 | } | ||
178 | 111 | |||
179 | 112 | void | ||
180 | 113 | sp_selected_path_symdiff_skip_undo(Inkscape::ObjectSet *set) | ||
181 | 114 | { | ||
182 | 115 | sp_selected_path_boolop(set, bool_op_symdiff); | ||
183 | 116 | } | ||
184 | 117 | |||
185 | 118 | void | ||
186 | 119 | sp_selected_path_cut(Inkscape::Selection *selection, SPDesktop *desktop) | ||
187 | 120 | { | ||
188 | 121 | sp_selected_path_boolop_ui(selection, desktop, bool_op_cut, SP_VERB_SELECTION_CUT, _("Division")); | ||
189 | 122 | } | ||
190 | 123 | |||
191 | 124 | void | ||
192 | 125 | sp_selected_path_cut_skip_undo(Inkscape::ObjectSet *set) | ||
193 | 126 | { | ||
194 | 127 | sp_selected_path_boolop(set, bool_op_cut); | ||
195 | 128 | } | ||
196 | 129 | |||
197 | 130 | void | ||
198 | 131 | sp_selected_path_slice(Inkscape::Selection *selection, SPDesktop *desktop) | ||
199 | 132 | { | ||
200 | 133 | sp_selected_path_boolop_ui(selection, desktop, bool_op_slice, SP_VERB_SELECTION_SLICE, _("Cut path")); | ||
201 | 134 | } | ||
202 | 135 | |||
203 | 136 | void | ||
204 | 137 | sp_selected_path_slice_skip_undo(Inkscape::ObjectSet *set) | ||
205 | 138 | { | ||
206 | 139 | sp_selected_path_boolop(set, bool_op_slice); | ||
245 | 140 | } | 95 | } |
246 | 141 | 96 | ||
247 | 142 | // helper for printing error messages, regardless of whether we have a GUI or not | 97 | // helper for printing error messages, regardless of whether we have a GUI or not |
248 | @@ -352,10 +307,36 @@ | |||
249 | 352 | 307 | ||
250 | 353 | // boolean operations on the desktop | 308 | // boolean operations on the desktop |
251 | 354 | // take the source paths from the file, do the operation, delete the originals and add the results | 309 | // take the source paths from the file, do the operation, delete the originals and add the results |
253 | 355 | BoolOpErrors sp_selected_path_boolop(Inkscape::ObjectSet * set, bool_op bop) | 310 | BoolOpErrors Inkscape::ObjectSet::pathBoolOp(bool_op bop, const bool skip_undo, const unsigned int verb, const Glib::ustring description) |
254 | 356 | { | 311 | { |
257 | 357 | SPDocument *doc = set->desktop()->getDocument(); | 312 | if (nullptr != desktop() && !skip_undo) { |
258 | 358 | std::vector<SPItem*> il(set->items().begin(), set->items().end()); | 313 | SPDocument *doc = desktop()->getDocument(); |
259 | 314 | BoolOpErrors returnCode = ObjectSet::pathBoolOp(bop, true); | ||
260 | 315 | switch(returnCode) { | ||
261 | 316 | case ERR_TOO_LESS_PATHS_1: | ||
262 | 317 | boolop_display_error_message(desktop(), _("Select <b>at least 1 path</b> to perform a boolean union.")); | ||
263 | 318 | break; | ||
264 | 319 | case ERR_TOO_LESS_PATHS_2: | ||
265 | 320 | boolop_display_error_message(desktop(), _("Select <b>at least 2 paths</b> to perform a boolean operation.")); | ||
266 | 321 | break; | ||
267 | 322 | case ERR_NO_PATHS: | ||
268 | 323 | boolop_display_error_message(desktop(), _("One of the objects is <b>not a path</b>, cannot perform boolean operation.")); | ||
269 | 324 | break; | ||
270 | 325 | case ERR_Z_ORDER: | ||
271 | 326 | boolop_display_error_message(desktop(), _("Unable to determine the <b>z-order</b> of the objects selected for difference, XOR, division, or path cut.")); | ||
272 | 327 | break; | ||
273 | 328 | case DONE_NO_PATH: | ||
274 | 329 | DocumentUndo::done(doc, SP_VERB_NONE, description); | ||
275 | 330 | break; | ||
276 | 331 | case DONE: | ||
277 | 332 | DocumentUndo::done(doc, verb, description); | ||
278 | 333 | break; | ||
279 | 334 | } | ||
280 | 335 | return returnCode; | ||
281 | 336 | } | ||
282 | 337 | |||
283 | 338 | SPDocument *doc = document(); | ||
284 | 339 | std::vector<SPItem*> il(items().begin(), items().end()); | ||
285 | 359 | 340 | ||
286 | 360 | // allow union on a single object for the purpose of removing self overlapse (svn log, revision 13334) | 341 | // allow union on a single object for the purpose of removing self overlapse (svn log, revision 13334) |
287 | 361 | if (il.size() < 2 && bop != bool_op_union) { | 342 | if (il.size() < 2 && bop != bool_op_union) { |
288 | @@ -687,7 +668,7 @@ | |||
289 | 687 | for (std::vector<SPItem*>::const_iterator l = il.begin(); l != il.end(); l++){ | 668 | for (std::vector<SPItem*>::const_iterator l = il.begin(); l != il.end(); l++){ |
290 | 688 | (*l)->deleteObject(); | 669 | (*l)->deleteObject(); |
291 | 689 | } | 670 | } |
293 | 690 | set->clear(); | 671 | clear(); |
294 | 691 | 672 | ||
295 | 692 | delete res; | 673 | delete res; |
296 | 693 | return DONE_NO_PATH; | 674 | return DONE_NO_PATH; |
297 | @@ -703,7 +684,7 @@ | |||
298 | 703 | } | 684 | } |
299 | 704 | } else { | 685 | } else { |
300 | 705 | // find out the bottom object | 686 | // find out the bottom object |
302 | 706 | std::vector<Inkscape::XML::Node*> sorted(set->xmlNodes().begin(), set->xmlNodes().end()); | 687 | std::vector<Inkscape::XML::Node*> sorted(xmlNodes().begin(), xmlNodes().end()); |
303 | 707 | 688 | ||
304 | 708 | sort(sorted.begin(),sorted.end(),sp_repr_compare_position_bool); | 689 | sort(sorted.begin(),sorted.end(),sp_repr_compare_position_bool); |
305 | 709 | 690 | ||
306 | @@ -731,7 +712,7 @@ | |||
307 | 731 | gchar *title = source->title(); | 712 | gchar *title = source->title(); |
308 | 732 | gchar *desc = source->desc(); | 713 | gchar *desc = source->desc(); |
309 | 733 | // remove source paths | 714 | // remove source paths |
311 | 734 | set->clear(); | 715 | clear(); |
312 | 735 | for (std::vector<SPItem*>::const_iterator l = il.begin(); l != il.end(); l++){ | 716 | for (std::vector<SPItem*>::const_iterator l = il.begin(); l != il.end(); l++){ |
313 | 736 | // if this is the bottommost object, | 717 | // if this is the bottommost object, |
314 | 737 | if (!strcmp(reinterpret_cast<SPObject *>(*l)->getRepr()->attribute("id"), id)) { | 718 | if (!strcmp(reinterpret_cast<SPObject *>(*l)->getRepr()->attribute("id"), id)) { |
315 | @@ -810,7 +791,7 @@ | |||
316 | 810 | // move to the saved position | 791 | // move to the saved position |
317 | 811 | repr->setPosition(pos > 0 ? pos : 0); | 792 | repr->setPosition(pos > 0 ? pos : 0); |
318 | 812 | 793 | ||
320 | 813 | set->add(doc->getObjectByRepr(repr)); | 794 | add(doc->getObjectByRepr(repr)); |
321 | 814 | Inkscape::GC::release(repr); | 795 | Inkscape::GC::release(repr); |
322 | 815 | 796 | ||
323 | 816 | delete resPath[i]; | 797 | delete resPath[i]; |
324 | @@ -845,7 +826,7 @@ | |||
325 | 845 | } | 826 | } |
326 | 846 | repr->setPosition(pos > 0 ? pos : 0); | 827 | repr->setPosition(pos > 0 ? pos : 0); |
327 | 847 | 828 | ||
329 | 848 | set->add(doc->getObjectByRepr(repr)); | 829 | add(doc->getObjectByRepr(repr)); |
330 | 849 | Inkscape::GC::release(repr); | 830 | Inkscape::GC::release(repr); |
331 | 850 | } | 831 | } |
332 | 851 | 832 | ||
333 | @@ -858,36 +839,6 @@ | |||
334 | 858 | return DONE; | 839 | return DONE; |
335 | 859 | } | 840 | } |
336 | 860 | 841 | ||
337 | 861 | void sp_selected_path_boolop_ui(Inkscape::Selection *selection, SPDesktop *desktop, bool_op bop, const unsigned int verb, | ||
338 | 862 | const Glib::ustring description) | ||
339 | 863 | { | ||
340 | 864 | SPDocument *doc = selection->desktop()->getDocument(); | ||
341 | 865 | BoolOpErrors returnCode = sp_selected_path_boolop(selection, bop); | ||
342 | 866 | switch(returnCode) { | ||
343 | 867 | case ERR_TOO_LESS_PATHS_1: | ||
344 | 868 | boolop_display_error_message(desktop, _("Select <b>at least 1 path</b> to perform a boolean union.")); | ||
345 | 869 | return; | ||
346 | 870 | case ERR_TOO_LESS_PATHS_2: | ||
347 | 871 | boolop_display_error_message(desktop, _("Select <b>at least 2 paths</b> to perform a boolean operation.")); | ||
348 | 872 | return; | ||
349 | 873 | case ERR_NO_PATHS: | ||
350 | 874 | boolop_display_error_message(desktop, _("One of the objects is <b>not a path</b>, cannot perform boolean operation.")); | ||
351 | 875 | return; | ||
352 | 876 | case ERR_Z_ORDER: | ||
353 | 877 | boolop_display_error_message(desktop, _("Unable to determine the <b>z-order</b> of the objects selected for difference, XOR, division, or path cut.")); | ||
354 | 878 | return; | ||
355 | 879 | case DONE_NO_PATH: | ||
356 | 880 | DocumentUndo::done(doc, SP_VERB_NONE, description); | ||
357 | 881 | return; | ||
358 | 882 | case DONE: | ||
359 | 883 | DocumentUndo::done(doc, verb, description); | ||
360 | 884 | return; | ||
361 | 885 | case DONE_NO_ACTION: | ||
362 | 886 | default: | ||
363 | 887 | return; | ||
364 | 888 | } | ||
365 | 889 | } | ||
366 | 890 | |||
367 | 891 | static | 842 | static |
368 | 892 | void sp_selected_path_outline_add_marker( SPObject *marker_object, Geom::Affine marker_transform, | 843 | void sp_selected_path_outline_add_marker( SPObject *marker_object, Geom::Affine marker_transform, |
369 | 893 | Geom::Scale stroke_scale, Geom::Affine transform, | 844 | Geom::Scale stroke_scale, Geom::Affine transform, |
370 | 894 | 845 | ||
371 | === modified file 'src/splivarot.h' | |||
372 | --- src/splivarot.h 2016-08-09 09:33:34 +0000 | |||
373 | +++ src/splivarot.h 2016-11-09 00:34:30 +0000 | |||
374 | @@ -10,6 +10,7 @@ | |||
375 | 10 | #include <2geom/forward.h> | 10 | #include <2geom/forward.h> |
376 | 11 | #include <2geom/path.h> | 11 | #include <2geom/path.h> |
377 | 12 | #include "livarot/Path.h" | 12 | #include "livarot/Path.h" |
378 | 13 | #include "object-set.h" | ||
379 | 13 | 14 | ||
380 | 14 | class SPCurve; | 15 | class SPCurve; |
381 | 15 | class SPDesktop; | 16 | class SPDesktop; |
382 | @@ -20,26 +21,6 @@ | |||
383 | 20 | class ObjectSet; | 21 | class ObjectSet; |
384 | 21 | } | 22 | } |
385 | 22 | 23 | ||
386 | 23 | // boolean operations | ||
387 | 24 | // work on the current selection | ||
388 | 25 | // selection has 2 contain exactly 2 items | ||
389 | 26 | |||
390 | 27 | // UPDATE: these signatures have been modified so they may work in | ||
391 | 28 | // command-line mode, i.e. without a desktop. If a desktop is not | ||
392 | 29 | // provided (desktop == NULL), error messages will be shown on stderr. | ||
393 | 30 | void sp_selected_path_union (Inkscape::Selection *selection, SPDesktop *desktop); | ||
394 | 31 | void sp_selected_path_union_skip_undo (Inkscape::ObjectSet *set); | ||
395 | 32 | void sp_selected_path_intersect (Inkscape::Selection *selection, SPDesktop *desktop); | ||
396 | 33 | void sp_selected_path_intersect_skip_undo (Inkscape::ObjectSet *set); | ||
397 | 34 | void sp_selected_path_diff (Inkscape::Selection *selection, SPDesktop *desktop); | ||
398 | 35 | void sp_selected_path_diff_skip_undo (Inkscape::ObjectSet *set); | ||
399 | 36 | void sp_selected_path_symdiff (Inkscape::Selection *selection, SPDesktop *desktop); | ||
400 | 37 | void sp_selected_path_symdiff_skip_undo (Inkscape::ObjectSet *set); | ||
401 | 38 | void sp_selected_path_cut (Inkscape::Selection *selection, SPDesktop *desktop); | ||
402 | 39 | void sp_selected_path_cut_skip_undo (Inkscape::ObjectSet *set); | ||
403 | 40 | void sp_selected_path_slice (Inkscape::Selection *selection, SPDesktop *desktop); | ||
404 | 41 | void sp_selected_path_slice_skip_undo (Inkscape::ObjectSet *set); | ||
405 | 42 | |||
406 | 43 | // offset/inset of a curve | 24 | // offset/inset of a curve |
407 | 44 | // takes the fill-rule in consideration | 25 | // takes the fill-rule in consideration |
408 | 45 | // offset amount is the stroke-width of the curve | 26 | // offset amount is the stroke-width of the curve |
409 | 46 | 27 | ||
410 | === modified file 'src/ui/tools/calligraphic-tool.cpp' | |||
411 | --- src/ui/tools/calligraphic-tool.cpp 2016-08-29 20:39:07 +0000 | |||
412 | +++ src/ui/tools/calligraphic-tool.cpp 2016-11-09 00:34:30 +0000 | |||
413 | @@ -921,10 +921,10 @@ | |||
414 | 921 | 921 | ||
415 | 922 | if (unionize) { | 922 | if (unionize) { |
416 | 923 | desktop->getSelection()->add(this->repr); | 923 | desktop->getSelection()->add(this->repr); |
418 | 924 | sp_selected_path_union_skip_undo(desktop->getSelection()); | 924 | desktop->getSelection()->pathUnion(true); |
419 | 925 | } else if (subtract) { | 925 | } else if (subtract) { |
420 | 926 | desktop->getSelection()->add(this->repr); | 926 | desktop->getSelection()->add(this->repr); |
422 | 927 | sp_selected_path_diff_skip_undo(desktop->getSelection()); | 927 | desktop->getSelection()->pathDiff(true); |
423 | 928 | } else { | 928 | } else { |
424 | 929 | if (this->keep_selected) { | 929 | if (this->keep_selected) { |
425 | 930 | desktop->getSelection()->set(this->repr); | 930 | desktop->getSelection()->set(this->repr); |
426 | 931 | 931 | ||
427 | === modified file 'src/ui/tools/eraser-tool.cpp' | |||
428 | --- src/ui/tools/eraser-tool.cpp 2016-10-24 22:58:43 +0000 | |||
429 | +++ src/ui/tools/eraser-tool.cpp 2016-11-09 00:34:30 +0000 | |||
430 | @@ -714,7 +714,7 @@ | |||
431 | 714 | Inkscape::GC::release(dup); // parent takes over | 714 | Inkscape::GC::release(dup); // parent takes over |
432 | 715 | selection->set(dup); | 715 | selection->set(dup); |
433 | 716 | if (!this->nowidth) { | 716 | if (!this->nowidth) { |
435 | 717 | sp_selected_path_union_skip_undo(selection); | 717 | selection->pathUnion(true); |
436 | 718 | } | 718 | } |
437 | 719 | selection->add(item); | 719 | selection->add(item); |
438 | 720 | if(item->style->fill_rule.value == SP_WIND_RULE_EVENODD){ | 720 | if(item->style->fill_rule.value == SP_WIND_RULE_EVENODD){ |
439 | @@ -725,9 +725,9 @@ | |||
440 | 725 | css = 0; | 725 | css = 0; |
441 | 726 | } | 726 | } |
442 | 727 | if (this->nowidth) { | 727 | if (this->nowidth) { |
444 | 728 | sp_selected_path_cut_skip_undo(selection); | 728 | selection->pathCut(true); |
445 | 729 | } else { | 729 | } else { |
447 | 730 | sp_selected_path_diff_skip_undo(selection); | 730 | selection->pathDiff(true); |
448 | 731 | } | 731 | } |
449 | 732 | workDone = true; // TODO set this only if something was cut. | 732 | workDone = true; // TODO set this only if something was cut. |
450 | 733 | bool break_apart = prefs->getBool("/tools/eraser/break_apart", false); | 733 | bool break_apart = prefs->getBool("/tools/eraser/break_apart", false); |
451 | @@ -762,7 +762,7 @@ | |||
452 | 762 | this->repr->parent()->appendChild(dup); | 762 | this->repr->parent()->appendChild(dup); |
453 | 763 | Inkscape::GC::release(dup); // parent takes over | 763 | Inkscape::GC::release(dup); // parent takes over |
454 | 764 | selection->set(dup); | 764 | selection->set(dup); |
456 | 765 | sp_selected_path_union_skip_undo(selection); | 765 | selection->pathUnion(true); |
457 | 766 | if (bbox && bbox->intersects(*eraserBbox)) { | 766 | if (bbox && bbox->intersects(*eraserBbox)) { |
458 | 767 | SPClipPath *clip_path = item->clip_ref->getObject(); | 767 | SPClipPath *clip_path = item->clip_ref->getObject(); |
459 | 768 | if (clip_path) { | 768 | if (clip_path) { |
460 | @@ -786,7 +786,7 @@ | |||
461 | 786 | sp_object_unref(clip_path); | 786 | sp_object_unref(clip_path); |
462 | 787 | selection->raiseToTop(true); | 787 | selection->raiseToTop(true); |
463 | 788 | selection->add(dup_clip); | 788 | selection->add(dup_clip); |
465 | 789 | sp_selected_path_diff_skip_undo(selection); | 789 | selection->pathDiff(true); |
466 | 790 | SPItem * clip = SP_ITEM(*(selection->items().begin())); | 790 | SPItem * clip = SP_ITEM(*(selection->items().begin())); |
467 | 791 | } | 791 | } |
468 | 792 | } | 792 | } |
469 | @@ -802,7 +802,7 @@ | |||
470 | 802 | rect->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); | 802 | rect->requestDisplayUpdate(SP_OBJECT_MODIFIED_FLAG); |
471 | 803 | selection->raiseToTop(true); | 803 | selection->raiseToTop(true); |
472 | 804 | selection->add(rect); | 804 | selection->add(rect); |
474 | 805 | sp_selected_path_diff_skip_undo(selection); | 805 | selection->pathDiff(true); |
475 | 806 | } | 806 | } |
476 | 807 | selection->raiseToTop(true); | 807 | selection->raiseToTop(true); |
477 | 808 | selection->add(item); | 808 | selection->add(item); |
478 | 809 | 809 | ||
479 | === modified file 'src/ui/tools/flood-tool.cpp' | |||
480 | --- src/ui/tools/flood-tool.cpp 2016-08-03 14:56:48 +0000 | |||
481 | +++ src/ui/tools/flood-tool.cpp 2016-11-09 00:34:30 +0000 | |||
482 | @@ -446,7 +446,7 @@ | |||
483 | 446 | ngettext("Area filled, path with <b>%d</b> node created and unioned with selection.","Area filled, path with <b>%d</b> nodes created and unioned with selection.", | 446 | ngettext("Area filled, path with <b>%d</b> node created and unioned with selection.","Area filled, path with <b>%d</b> nodes created and unioned with selection.", |
484 | 447 | SP_PATH(reprobj)->nodesInPath()), SP_PATH(reprobj)->nodesInPath() ); | 447 | SP_PATH(reprobj)->nodesInPath()), SP_PATH(reprobj)->nodesInPath() ); |
485 | 448 | selection->add(reprobj); | 448 | selection->add(reprobj); |
487 | 449 | sp_selected_path_union_skip_undo(desktop->getSelection()); | 449 | selection->pathUnion(true); |
488 | 450 | } else { | 450 | } else { |
489 | 451 | desktop->messageStack()->flashF( Inkscape::WARNING_MESSAGE, | 451 | desktop->messageStack()->flashF( Inkscape::WARNING_MESSAGE, |
490 | 452 | ngettext("Area filled, path with <b>%d</b> node created.","Area filled, path with <b>%d</b> nodes created.", | 452 | ngettext("Area filled, path with <b>%d</b> node created.","Area filled, path with <b>%d</b> nodes created.", |
491 | 453 | 453 | ||
492 | === modified file 'src/ui/tools/spray-tool.cpp' | |||
493 | --- src/ui/tools/spray-tool.cpp 2016-08-03 14:56:48 +0000 | |||
494 | +++ src/ui/tools/spray-tool.cpp 2016-11-09 00:34:30 +0000 | |||
495 | @@ -1026,7 +1026,7 @@ | |||
496 | 1026 | if (unionResult) { // No need to add the very first item (initialized with NULL). | 1026 | if (unionResult) { // No need to add the very first item (initialized with NULL). |
497 | 1027 | set->add(unionResult); | 1027 | set->add(unionResult); |
498 | 1028 | } | 1028 | } |
500 | 1029 | sp_selected_path_union_skip_undo(set); | 1029 | set->pathUnion(true); |
501 | 1030 | set->add(parent_item); | 1030 | set->add(parent_item); |
502 | 1031 | Inkscape::GC::release(copy); | 1031 | Inkscape::GC::release(copy); |
503 | 1032 | did = true; | 1032 | did = true; |
504 | @@ -1364,7 +1364,7 @@ | |||
505 | 1364 | SP_VERB_CONTEXT_SPRAY, _("Spray with clones")); | 1364 | SP_VERB_CONTEXT_SPRAY, _("Spray with clones")); |
506 | 1365 | break; | 1365 | break; |
507 | 1366 | case SPRAY_MODE_SINGLE_PATH: | 1366 | case SPRAY_MODE_SINGLE_PATH: |
509 | 1367 | sp_selected_path_union_skip_undo(objectSet()); | 1367 | objectSet()->pathUnion(true); |
510 | 1368 | desktop->getSelection()->add(object_set.objects().begin(), object_set.objects().end()); | 1368 | desktop->getSelection()->add(object_set.objects().begin(), object_set.objects().end()); |
511 | 1369 | DocumentUndo::done(this->desktop->getDocument(), | 1369 | DocumentUndo::done(this->desktop->getDocument(), |
512 | 1370 | SP_VERB_CONTEXT_SPRAY, _("Spray in single path")); | 1370 | SP_VERB_CONTEXT_SPRAY, _("Spray in single path")); |
513 | 1371 | 1371 | ||
514 | === modified file 'src/verbs.cpp' | |||
515 | --- src/verbs.cpp 2016-11-06 22:07:52 +0000 | |||
516 | +++ src/verbs.cpp 2016-11-09 00:34:30 +0000 | |||
517 | @@ -1115,22 +1115,22 @@ | |||
518 | 1115 | bool handled = true; | 1115 | bool handled = true; |
519 | 1116 | switch (reinterpret_cast<std::size_t>(data)) { | 1116 | switch (reinterpret_cast<std::size_t>(data)) { |
520 | 1117 | case SP_VERB_SELECTION_UNION: | 1117 | case SP_VERB_SELECTION_UNION: |
522 | 1118 | sp_selected_path_union(selection, dt); | 1118 | selection->pathUnion(); |
523 | 1119 | break; | 1119 | break; |
524 | 1120 | case SP_VERB_SELECTION_INTERSECT: | 1120 | case SP_VERB_SELECTION_INTERSECT: |
526 | 1121 | sp_selected_path_intersect(selection, dt); | 1121 | selection->pathIntersect(); |
527 | 1122 | break; | 1122 | break; |
528 | 1123 | case SP_VERB_SELECTION_DIFF: | 1123 | case SP_VERB_SELECTION_DIFF: |
530 | 1124 | sp_selected_path_diff(selection, dt); | 1124 | selection->pathDiff(); |
531 | 1125 | break; | 1125 | break; |
532 | 1126 | case SP_VERB_SELECTION_SYMDIFF: | 1126 | case SP_VERB_SELECTION_SYMDIFF: |
534 | 1127 | sp_selected_path_symdiff(selection, dt); | 1127 | selection->pathSymDiff(); |
535 | 1128 | break; | 1128 | break; |
536 | 1129 | case SP_VERB_SELECTION_CUT: | 1129 | case SP_VERB_SELECTION_CUT: |
538 | 1130 | sp_selected_path_cut(selection, dt); | 1130 | selection->pathCut(); |
539 | 1131 | break; | 1131 | break; |
540 | 1132 | case SP_VERB_SELECTION_SLICE: | 1132 | case SP_VERB_SELECTION_SLICE: |
542 | 1133 | sp_selected_path_slice(selection, dt); | 1133 | selection->pathSlice(); |
543 | 1134 | break; | 1134 | break; |
544 | 1135 | case SP_VERB_SELECTION_GROW: | 1135 | case SP_VERB_SELECTION_GROW: |
545 | 1136 | { | 1136 | { |