From a225a8b2ef3a3a37469374a89b913b37b5ace709 Mon Sep 17 00:00:00 2001 From: Alessandro Ranellucci Date: Thu, 21 Nov 2013 15:12:06 +0100 Subject: [PATCH] Ported contains_line() to XS --- lib/Slic3r/ExPolygon.pm | 9 +----- xs/src/ClipperUtils.cpp | 64 ++++++++++++++++++++--------------------- xs/src/ClipperUtils.hpp | 52 ++++++++++++++++----------------- xs/src/ExPolygon.cpp | 22 ++++++++++++++ xs/src/ExPolygon.hpp | 2 ++ xs/src/Line.cpp | 9 ++++++ xs/src/Line.hpp | 2 ++ xs/xsp/ExPolygon.xsp | 1 + xs/xsp/Line.xsp | 2 +- xs/xsp/typemap.xspt | 1 + 10 files changed, 97 insertions(+), 67 deletions(-) diff --git a/lib/Slic3r/ExPolygon.pm b/lib/Slic3r/ExPolygon.pm index c9b42a92a..505d7e0ca 100644 --- a/lib/Slic3r/ExPolygon.pm +++ b/lib/Slic3r/ExPolygon.pm @@ -54,13 +54,6 @@ sub encloses_point_quick { return Boost::Geometry::Utils::point_within_polygon($point->pp, $self->pp); } -sub contains_line { - my $self = shift; - my ($line) = @_; - - return @{Slic3r::Geometry::Clipper::diff_pl([$line->as_polyline], \@$self)} ? 0 : 1; -} - sub bounding_box { my $self = shift; return $self->contour->bounding_box; @@ -72,7 +65,7 @@ sub clip_line { return [ map Slic3r::Line->new(@$_), - @{Slic3r::Geometry::Clipper::intersection_pl([ Slic3r::Polyline->new(@$line) ], \@$self)} + @{Slic3r::Geometry::Clipper::intersection_pl([ $line->as_polyline ], \@$self)} ]; } diff --git a/xs/src/ClipperUtils.cpp b/xs/src/ClipperUtils.cpp index e074a3b79..6dc3fb433 100644 --- a/xs/src/ClipperUtils.cpp +++ b/xs/src/ClipperUtils.cpp @@ -101,7 +101,7 @@ scaleClipperPolygons(ClipperLib::Paths &polygons, const double scale) } void -offset(Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta, +offset(const Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta, double scale, ClipperLib::JoinType joinType, double miterLimit) { // read input @@ -120,7 +120,7 @@ offset(Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta, } void -offset(Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta, +offset(const Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta, double scale, ClipperLib::JoinType joinType, double miterLimit) { // perform offset @@ -133,7 +133,7 @@ offset(Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta, } void -offset(Slic3r::Polylines &polylines, ClipperLib::Paths &retval, const float delta, +offset(const Slic3r::Polylines &polylines, ClipperLib::Paths &retval, const float delta, double scale, ClipperLib::JoinType joinType, double miterLimit) { // read input @@ -152,7 +152,7 @@ offset(Slic3r::Polylines &polylines, ClipperLib::Paths &retval, const float delt } void -offset(Slic3r::Polylines &polylines, Slic3r::Polygons &retval, const float delta, +offset(const Slic3r::Polylines &polylines, Slic3r::Polygons &retval, const float delta, double scale, ClipperLib::JoinType joinType, double miterLimit) { // perform offset @@ -165,7 +165,7 @@ offset(Slic3r::Polylines &polylines, Slic3r::Polygons &retval, const float delta } void -offset_ex(Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float delta, +offset_ex(const Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float delta, double scale, ClipperLib::JoinType joinType, double miterLimit) { // perform offset @@ -178,7 +178,7 @@ offset_ex(Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float de } void -offset2(Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta1, +offset2(const Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta1, const float delta2, const double scale, const ClipperLib::JoinType joinType, const double miterLimit) { // read input @@ -202,7 +202,7 @@ offset2(Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta } void -offset2(Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta1, +offset2(const Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta1, const float delta2, const double scale, const ClipperLib::JoinType joinType, const double miterLimit) { // perform offset @@ -215,7 +215,7 @@ offset2(Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta1 } void -offset2_ex(Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float delta1, +offset2_ex(const Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float delta1, const float delta2, const double scale, const ClipperLib::JoinType joinType, const double miterLimit) { // perform offset @@ -228,8 +228,8 @@ offset2_ex(Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float d } template -void _clipper_do(const ClipperLib::ClipType clipType, Slic3r::Polygons &subject, - Slic3r::Polygons &clip, T &retval, const ClipperLib::PolyFillType fillType, const bool safety_offset_) +void _clipper_do(const ClipperLib::ClipType clipType, const Slic3r::Polygons &subject, + const Slic3r::Polygons &clip, T &retval, const ClipperLib::PolyFillType fillType, const bool safety_offset_) { // read input ClipperLib::Paths* input_subject = new ClipperLib::Paths(); @@ -260,8 +260,8 @@ void _clipper_do(const ClipperLib::ClipType clipType, Slic3r::Polygons &subject, clipper.Execute(clipType, retval, fillType, fillType); } -void _clipper_do(const ClipperLib::ClipType clipType, Slic3r::Polylines &subject, - Slic3r::Polygons &clip, ClipperLib::PolyTree &retval, const ClipperLib::PolyFillType fillType) +void _clipper_do(const ClipperLib::ClipType clipType, const Slic3r::Polylines &subject, + const Slic3r::Polygons &clip, ClipperLib::PolyTree &retval, const ClipperLib::PolyFillType fillType) { // read input ClipperLib::Paths* input_subject = new ClipperLib::Paths(); @@ -283,8 +283,8 @@ void _clipper_do(const ClipperLib::ClipType clipType, Slic3r::Polylines &subject clipper.Execute(clipType, retval, fillType, fillType); } -void _clipper(ClipperLib::ClipType clipType, Slic3r::Polygons &subject, - Slic3r::Polygons &clip, Slic3r::Polygons &retval, bool safety_offset_) +void _clipper(ClipperLib::ClipType clipType, const Slic3r::Polygons &subject, + const Slic3r::Polygons &clip, Slic3r::Polygons &retval, bool safety_offset_) { // perform operation ClipperLib::Paths* output = new ClipperLib::Paths(); @@ -295,8 +295,8 @@ void _clipper(ClipperLib::ClipType clipType, Slic3r::Polygons &subject, delete output; } -void _clipper(ClipperLib::ClipType clipType, Slic3r::Polygons &subject, - Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_) +void _clipper(ClipperLib::ClipType clipType, const Slic3r::Polygons &subject, + const Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_) { // perform operation ClipperLib::PolyTree* polytree = new ClipperLib::PolyTree(); @@ -307,8 +307,8 @@ void _clipper(ClipperLib::ClipType clipType, Slic3r::Polygons &subject, delete polytree; } -void _clipper(ClipperLib::ClipType clipType, Slic3r::Polylines &subject, - Slic3r::Polygons &clip, Slic3r::Polylines &retval) +void _clipper(ClipperLib::ClipType clipType, const Slic3r::Polylines &subject, + const Slic3r::Polygons &clip, Slic3r::Polylines &retval) { // perform operation ClipperLib::PolyTree polytree; @@ -321,53 +321,53 @@ void _clipper(ClipperLib::ClipType clipType, Slic3r::Polylines &subject, } template -void diff(Slic3r::Polygons &subject, Slic3r::Polygons &clip, T &retval, bool safety_offset_) +void diff(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, T &retval, bool safety_offset_) { _clipper(ClipperLib::ctDifference, subject, clip, retval, safety_offset_); } -template void diff(Slic3r::Polygons &subject, Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_); -template void diff(Slic3r::Polygons &subject, Slic3r::Polygons &clip, Slic3r::Polygons &retval, bool safety_offset_); +template void diff(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_); +template void diff(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, Slic3r::Polygons &retval, bool safety_offset_); -void diff(Slic3r::Polylines &subject, Slic3r::Polygons &clip, Slic3r::Polylines &retval) +void diff(const Slic3r::Polylines &subject, const Slic3r::Polygons &clip, Slic3r::Polylines &retval) { _clipper(ClipperLib::ctDifference, subject, clip, retval); } template -void intersection(Slic3r::Polygons &subject, Slic3r::Polygons &clip, T &retval, bool safety_offset_) +void intersection(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, T &retval, bool safety_offset_) { _clipper(ClipperLib::ctIntersection, subject, clip, retval, safety_offset_); } -template void intersection(Slic3r::Polygons &subject, Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_); -template void intersection(Slic3r::Polygons &subject, Slic3r::Polygons &clip, Slic3r::Polygons &retval, bool safety_offset_); +template void intersection(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_); +template void intersection(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, Slic3r::Polygons &retval, bool safety_offset_); -void intersection(Slic3r::Polylines &subject, Slic3r::Polygons &clip, Slic3r::Polylines &retval) +void intersection(const Slic3r::Polylines &subject, const Slic3r::Polygons &clip, Slic3r::Polylines &retval) { _clipper(ClipperLib::ctIntersection, subject, clip, retval); } -void xor_ex(Slic3r::Polygons &subject, Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, +void xor_ex(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_) { _clipper(ClipperLib::ctXor, subject, clip, retval, safety_offset_); } template -void union_(Slic3r::Polygons &subject, T &retval, bool safety_offset_) +void union_(const Slic3r::Polygons &subject, T &retval, bool safety_offset_) { Slic3r::Polygons p; _clipper(ClipperLib::ctUnion, subject, p, retval, safety_offset_); } -template void union_(Slic3r::Polygons &subject, Slic3r::ExPolygons &retval, bool safety_offset_); -template void union_(Slic3r::Polygons &subject, Slic3r::Polygons &retval, bool safety_offset_); +template void union_(const Slic3r::Polygons &subject, Slic3r::ExPolygons &retval, bool safety_offset_); +template void union_(const Slic3r::Polygons &subject, Slic3r::Polygons &retval, bool safety_offset_); -void union_pt(Slic3r::Polygons &subject, ClipperLib::PolyTree &retval, bool safety_offset_) +void union_pt(const Slic3r::Polygons &subject, ClipperLib::PolyTree &retval, bool safety_offset_) { Slic3r::Polygons clip; _clipper_do(ClipperLib::ctUnion, subject, clip, retval, ClipperLib::pftEvenOdd, safety_offset_); } -void simplify_polygons(Slic3r::Polygons &subject, Slic3r::Polygons &retval) +void simplify_polygons(const Slic3r::Polygons &subject, Slic3r::Polygons &retval) { // convert into Clipper polygons ClipperLib::Paths* input_subject = new ClipperLib::Paths(); diff --git a/xs/src/ClipperUtils.hpp b/xs/src/ClipperUtils.hpp index 6759262c3..918c5c1e1 100644 --- a/xs/src/ClipperUtils.hpp +++ b/xs/src/ClipperUtils.hpp @@ -33,66 +33,66 @@ void ClipperPaths_to_Slic3rExPolygons(const ClipperLib::Paths &input, Slic3r::Ex void scaleClipperPolygons(ClipperLib::Paths &polygons, const double scale); // offset Polygons -void offset(Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta, +void offset(const Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta, double scale = 100000, ClipperLib::JoinType joinType = ClipperLib::jtMiter, double miterLimit = 3); -void offset(Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta, +void offset(const Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta, double scale = 100000, ClipperLib::JoinType joinType = ClipperLib::jtMiter, double miterLimit = 3); // offset Polylines -void offset(Slic3r::Polylines &polylines, ClipperLib::Paths &retval, const float delta, +void offset(const Slic3r::Polylines &polylines, ClipperLib::Paths &retval, const float delta, double scale = 100000, ClipperLib::JoinType joinType = ClipperLib::jtSquare, double miterLimit = 3); -void offset(Slic3r::Polylines &polylines, Slic3r::Polygons &retval, const float delta, +void offset(const Slic3r::Polylines &polylines, Slic3r::Polygons &retval, const float delta, double scale = 100000, ClipperLib::JoinType joinType = ClipperLib::jtSquare, double miterLimit = 3); -void offset_ex(Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float delta, +void offset_ex(const Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float delta, double scale = 100000, ClipperLib::JoinType joinType = ClipperLib::jtMiter, double miterLimit = 3); -void offset2(Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta1, +void offset2(const Slic3r::Polygons &polygons, ClipperLib::Paths &retval, const float delta1, const float delta2, double scale = 100000, ClipperLib::JoinType joinType = ClipperLib::jtMiter, double miterLimit = 3); -void offset2(Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta1, +void offset2(const Slic3r::Polygons &polygons, Slic3r::Polygons &retval, const float delta1, const float delta2, double scale = 100000, ClipperLib::JoinType joinType = ClipperLib::jtMiter, double miterLimit = 3); -void offset2_ex(Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float delta1, +void offset2_ex(const Slic3r::Polygons &polygons, Slic3r::ExPolygons &retval, const float delta1, const float delta2, double scale = 100000, ClipperLib::JoinType joinType = ClipperLib::jtMiter, double miterLimit = 3); template -void _clipper_do(ClipperLib::ClipType clipType, Slic3r::Polygons &subject, - Slic3r::Polygons &clip, T &retval, bool safety_offset_); -void _clipper_do(ClipperLib::ClipType clipType, Slic3r::Polylines &subject, - Slic3r::Polygons &clip, ClipperLib::Paths &retval); -void _clipper(ClipperLib::ClipType clipType, Slic3r::Polygons &subject, - Slic3r::Polygons &clip, Slic3r::Polygons &retval, bool safety_offset_); -void _clipper(ClipperLib::ClipType clipType, Slic3r::Polygons &subject, - Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_); -void _clipper(ClipperLib::ClipType clipType, Slic3r::Polylines &subject, - Slic3r::Polygons &clip, Slic3r::Polylines &retval); +void _clipper_do(ClipperLib::ClipType clipType, const Slic3r::Polygons &subject, + const Slic3r::Polygons &clip, T &retval, bool safety_offset_); +void _clipper_do(ClipperLib::ClipType clipType, const Slic3r::Polylines &subject, + const Slic3r::Polygons &clip, ClipperLib::Paths &retval); +void _clipper(ClipperLib::ClipType clipType, const Slic3r::Polygons &subject, + const Slic3r::Polygons &clip, Slic3r::Polygons &retval, bool safety_offset_); +void _clipper(ClipperLib::ClipType clipType, const Slic3r::Polygons &subject, + const Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_); +void _clipper(ClipperLib::ClipType clipType, const Slic3r::Polylines &subject, + const Slic3r::Polygons &clip, Slic3r::Polylines &retval); template -void diff(Slic3r::Polygons &subject, Slic3r::Polygons &clip, T &retval, bool safety_offset_); +void diff(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, T &retval, bool safety_offset_); -void diff(Slic3r::Polylines &subject, Slic3r::Polygons &clip, Slic3r::Polylines &retval); +void diff(const Slic3r::Polylines &subject, const Slic3r::Polygons &clip, Slic3r::Polylines &retval); template -void intersection(Slic3r::Polygons &subject, Slic3r::Polygons &clip, T &retval, bool safety_offset_); +void intersection(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, T &retval, bool safety_offset_); -void intersection(Slic3r::Polylines &subject, Slic3r::Polygons &clip, Slic3r::Polylines &retval); +void intersection(const Slic3r::Polylines &subject, const Slic3r::Polygons &clip, Slic3r::Polylines &retval); -void xor_ex(Slic3r::Polygons &subject, Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, +void xor_ex(const Slic3r::Polygons &subject, const Slic3r::Polygons &clip, Slic3r::ExPolygons &retval, bool safety_offset_ = false); template -void union_(Slic3r::Polygons &subject, T &retval, bool safety_offset_ = false); +void union_(const Slic3r::Polygons &subject, T &retval, bool safety_offset_ = false); -void union_pt(Slic3r::Polygons &subject, ClipperLib::PolyTree &retval, bool safety_offset_ = false); +void union_pt(const Slic3r::Polygons &subject, ClipperLib::PolyTree &retval, bool safety_offset_ = false); -void simplify_polygons(Slic3r::Polygons &subject, Slic3r::Polygons &retval); +void simplify_polygons(const Slic3r::Polygons &subject, Slic3r::Polygons &retval); void safety_offset(ClipperLib::Paths* &subject); diff --git a/xs/src/ExPolygon.cpp b/xs/src/ExPolygon.cpp index 7a58e969e..1e6dceaf4 100644 --- a/xs/src/ExPolygon.cpp +++ b/xs/src/ExPolygon.cpp @@ -1,8 +1,19 @@ #include "ExPolygon.hpp" #include "Polygon.hpp" +#include "ClipperUtils.hpp" namespace Slic3r { +ExPolygon::operator Polygons() const +{ + Polygons polygons(this->holes.size() + 1); + polygons.push_back(this->contour); + for (Polygons::const_iterator it = this->holes.begin(); it != this->holes.end(); ++it) { + polygons.push_back(*it); + } + return polygons; +} + void ExPolygon::scale(double factor) { @@ -50,6 +61,17 @@ ExPolygon::is_valid() const return true; } +bool +ExPolygon::contains_line(Line* line) const +{ + Polylines pl(1); + pl.push_back(*line); + + Polylines pl_out; + diff(pl, *this, pl_out); + return pl_out.empty(); +} + #ifdef SLIC3RXS SV* ExPolygon::to_AV() { diff --git a/xs/src/ExPolygon.hpp b/xs/src/ExPolygon.hpp index 05eb64d99..db733516c 100644 --- a/xs/src/ExPolygon.hpp +++ b/xs/src/ExPolygon.hpp @@ -11,11 +11,13 @@ class ExPolygon public: Polygon contour; Polygons holes; + operator Polygons() const; void scale(double factor); void translate(double x, double y); void rotate(double angle, Point* center); double area() const; bool is_valid() const; + bool contains_line(Line* line) const; #ifdef SLIC3RXS void from_SV(SV* poly_sv); diff --git a/xs/src/Line.cpp b/xs/src/Line.cpp index 0e4698b7f..66f3d860f 100644 --- a/xs/src/Line.cpp +++ b/xs/src/Line.cpp @@ -1,8 +1,17 @@ #include "Line.hpp" +#include "Polyline.hpp" #include namespace Slic3r { +Line::operator Polyline() const +{ + Polyline pl; + pl.points.push_back(this->a); + pl.points.push_back(this->b); + return pl; +} + void Line::scale(double factor) { diff --git a/xs/src/Line.hpp b/xs/src/Line.hpp index 5962970ba..c387f9b55 100644 --- a/xs/src/Line.hpp +++ b/xs/src/Line.hpp @@ -7,6 +7,7 @@ namespace Slic3r { class Line; +class Polyline; class Line { @@ -15,6 +16,7 @@ class Line Point b; Line() {}; explicit Line(Point _a, Point _b): a(_a), b(_b) {}; + operator Polyline() const; void scale(double factor); void translate(double x, double y); void rotate(double angle, Point* center); diff --git a/xs/xsp/ExPolygon.xsp b/xs/xsp/ExPolygon.xsp index 28876e232..82982d381 100644 --- a/xs/xsp/ExPolygon.xsp +++ b/xs/xsp/ExPolygon.xsp @@ -21,6 +21,7 @@ void translate(double x, double y); double area(); bool is_valid(); + bool contains_line(Line* line); %{ ExPolygon* diff --git a/xs/xsp/Line.xsp b/xs/xsp/Line.xsp index 28b60e056..8e8ff49c7 100644 --- a/xs/xsp/Line.xsp +++ b/xs/xsp/Line.xsp @@ -26,7 +26,7 @@ Point* point_at(double distance) %code{% const char* CLASS = "Slic3r::Point"; RETVAL = THIS->point_at(distance); %}; Polyline* as_polyline() - %code{% const char* CLASS = "Slic3r::Polyline"; RETVAL = new Polyline(); RETVAL->points.push_back(THIS->a); RETVAL->points.push_back(THIS->b); %}; + %code{% const char* CLASS = "Slic3r::Polyline"; RETVAL = new Polyline(*THIS); %}; %{ Line* diff --git a/xs/xsp/typemap.xspt b/xs/xsp/typemap.xspt index d20d5789d..1928e91f2 100644 --- a/xs/xsp/typemap.xspt +++ b/xs/xsp/typemap.xspt @@ -7,6 +7,7 @@ %typemap{AV*}; %typemap{Point*}; %typemap{ExPolygon*}; +%typemap{Line*}; %typemap{Polyline*}; %typemap{Polygon*}; %typemap{ExtrusionEntityCollection*};