KiCad PCB EDA Suite
Loading...
Searching...
No Matches
shape_line_chain.h
Go to the documentation of this file.
1/*
2 * This program source code file is part of KiCad, a free EDA CAD application.
3 *
4 * Copyright (C) 2013 CERN
5 * @author Tomasz Wlostowski <[email protected]>
6 * Copyright The KiCad Developers, see AUTHORS.txt for contributors.
7 *
8 * This program is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU General Public License
10 * as published by the Free Software Foundation; either version 2
11 * of the License, or (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, you may find one here:
20 * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
21 * or you may search the http://www.gnu.org website for the version 2 license,
22 * or you may write to the Free Software Foundation, Inc.,
23 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
24 */
25
26#ifndef __SHAPE_LINE_CHAIN
27#define __SHAPE_LINE_CHAIN
28
29
30#include <clipper2/clipper.h>
31#include <geometry/seg.h>
32#include <geometry/shape.h>
33#include <geometry/shape_arc.h>
35#include <math/vector2d.h>
36
42{
44 {
45 m_FirstArcIdx = -1;
46 m_SecondArcIdx = -1;
47 }
48
49 CLIPPER_Z_VALUE( const std::pair<ssize_t, ssize_t> aShapeIndices, ssize_t aOffset = 0 )
50 {
51 m_FirstArcIdx = aShapeIndices.first;
52 m_SecondArcIdx = aShapeIndices.second;
53
54 auto offsetVal = [&]( ssize_t& aVal )
55 {
56 if( aVal >= 0 )
57 aVal += aOffset;
58 };
59
60 offsetVal( m_FirstArcIdx );
61 offsetVal( m_SecondArcIdx );
62 }
63
66};
67
68
82{
83public:
84 typedef std::vector<VECTOR2I>::iterator point_iter;
85 typedef std::vector<VECTOR2I>::const_iterator point_citer;
86
91 {
94
97
101
104
109
113 bool valid;
114
116 index_our( -1 ),
117 index_their( -1 ),
118 is_corner_our( false ),
119 is_corner_their( false ),
120 valid( false )
121 {
122 }
123 };
124
125
131 {
132 public:
133 POINT_INSIDE_TRACKER( const VECTOR2I& aPoint );
134
135 void AddPolyline( const SHAPE_LINE_CHAIN& aPolyline );
136 bool IsInside();
137
138 private:
139
140 bool processVertex ( const VECTOR2I& ip, const VECTOR2I& ipNext );
141
148 };
149
150 typedef std::vector<INTERSECTION> INTERSECTIONS;
151
152
158 m_accuracy( 0 ),
159 m_closed( false ),
160 m_width( 0 )
161 {}
162
165 m_points( aShape.m_points ),
166 m_shapes( aShape.m_shapes ),
167 m_arcs( aShape.m_arcs ),
168 m_accuracy( aShape.m_accuracy ),
169 m_closed( aShape.m_closed ),
170 m_width( aShape.m_width ),
171 m_bbox( aShape.m_bbox )
172 {}
173
174 SHAPE_LINE_CHAIN( const std::vector<int>& aV );
175
176 SHAPE_LINE_CHAIN( const std::vector<VECTOR2I>& aV, bool aClosed = false );
177
178 SHAPE_LINE_CHAIN( const SHAPE_ARC& aArc, bool aClosed = false, std::optional<int> aMaxError = {} );
179
180 SHAPE_LINE_CHAIN( const Clipper2Lib::Path64& aPath,
181 const std::vector<CLIPPER_Z_VALUE>& aZValueBuffer,
182 const std::vector<SHAPE_ARC>& aArcBuffer );
183
185 {}
186
199 virtual bool Collide( const VECTOR2I& aP, int aClearance = 0, int* aActual = nullptr,
200 VECTOR2I* aLocation = nullptr ) const override;
201
214 virtual bool Collide( const SEG& aSeg, int aClearance = 0, int* aActual = nullptr,
215 VECTOR2I* aLocation = nullptr ) const override;
216
226 bool ClosestPoints( const SHAPE_LINE_CHAIN& aOther, VECTOR2I& aPt0, VECTOR2I& aPt1 ) const;
227
228 static bool ClosestPoints( const point_citer& aMyStart, const point_citer& aMyEnd,
229 const point_citer& aOtherStart, const point_citer& aOtherEnd,
230 VECTOR2I& aPt0, VECTOR2I& aPt1, int64_t& aDistSq );
231
232 static bool ClosestSegments( const VECTOR2I& aMyPrevPt, const point_citer& aMyStart,
233 const point_citer& aMyEnd, const VECTOR2I& aOtherPrevPt,
234 const point_citer& aOtherStart, const point_citer& aOtherEnd,
235 VECTOR2I& aPt0, VECTOR2I& aPt1, int64_t& aDistSq );
236
248 bool ClosestSegmentsFast( const SHAPE_LINE_CHAIN& aOther, VECTOR2I& aPt0,
249 VECTOR2I& aPt1 ) const;
250
252
253 // Move assignment operator
255 {
256 if (this != &aOther)
257 {
258 SHAPE_LINE_CHAIN_BASE::operator=( aOther );
259
260 m_points = std::move( aOther.m_points );
261 m_shapes = std::move( aOther.m_shapes );
262 m_arcs = std::move( aOther.m_arcs );
263
264 m_accuracy = aOther.m_accuracy;
265 m_closed = aOther.m_closed;
266 m_width = aOther.m_width;
267 m_bbox = aOther.m_bbox;
268 }
269
270 return *this;
271 }
272
273 SHAPE* Clone() const override;
274
278 void Clear()
279 {
280 m_points.clear();
281 m_arcs.clear();
282 m_shapes.clear();
283 m_closed = false;
284 }
285
292 void SetClosed( bool aClosed )
293 {
294 m_closed = aClosed;
296 }
297
301 bool IsClosed() const override
302 {
303 return m_closed;
304 }
305
311 void SetWidth( int aWidth )
312 {
313 m_width = aWidth;
314 }
315
321 int Width() const
322 {
323 return m_width;
324 }
325
331 int SegmentCount() const
332 {
333 int c = m_points.size() - 1;
334
335 if( m_closed )
336 c++;
337
338 return std::max( 0, c );
339 }
340
348 int ShapeCount() const;
349
350
355
362 void Simplify( int aTolerance = 0 );
363
364 // legacy function, used by the router. Please do not remove until I'll figure out
365 // the root cause of rounding errors - Tom
366 SHAPE_LINE_CHAIN& Simplify2( bool aRemoveColinear = true );
367
373 int PointCount() const
374 {
375 return m_points.size();
376 }
377
385 SEG Segment( int aIndex ) const;
386
394 const SEG CSegment( int aIndex ) const { return Segment( aIndex ); }
395
408 int NextShape( int aPointIndex ) const;
409
416 void SetPoint( int aIndex, const VECTOR2I& aPos );
417
424 const VECTOR2I& CPoint( int aIndex ) const
425 {
426 if( aIndex < 0 )
427 aIndex += PointCount();
428 else if( aIndex >= PointCount() )
429 aIndex -= PointCount();
430
431 return m_points[aIndex];
432 }
433
434 const std::vector<VECTOR2I>& CPoints() const { return m_points; }
435
439 const VECTOR2I& CLastPoint() const
440 {
441 return m_points[static_cast<size_t>( PointCount() ) - 1];
442 }
443
447 const std::vector<SHAPE_ARC>& CArcs() const
448 {
449 return m_arcs;
450 }
451
455 const std::vector<std::pair<ssize_t, ssize_t>>& CShapes() const
456 {
457 return m_shapes;
458 }
459
461 const BOX2I BBox( int aClearance = 0 ) const override
462 {
463 BOX2I bbox;
464 bbox.Compute( m_points );
465
466 if( aClearance != 0 || m_width != 0 )
467 bbox.Inflate( aClearance + m_width );
468
469 return bbox;
470 }
471
472 void GenerateBBoxCache() const
473 {
475
476 if( m_width != 0 )
478 }
479
480 BOX2I* GetCachedBBox() const override
481 {
482 return &m_bbox;
483 }
484
490 const SHAPE_LINE_CHAIN Reverse() const;
491
497 void ClearArcs();
498
504 long long int Length() const;
505
509 void ReservePoints( size_t aSize )
510 {
511 m_points.reserve( aSize );
512 m_shapes.reserve( aSize );
513 }
514
524 void Append( int aX, int aY, bool aAllowDuplication = false )
525 {
526 VECTOR2I v( aX, aY );
527 Append( v, aAllowDuplication );
528 }
529
538 void Append( const VECTOR2I& aP, bool aAllowDuplication = false )
539 {
540 if( m_points.size() == 0 )
541 m_bbox = BOX2I( aP, VECTOR2I( 0, 0 ) );
542
543 if( m_points.size() == 0 || aAllowDuplication || CLastPoint() != aP )
544 {
545 m_points.push_back( aP );
546 m_shapes.push_back( SHAPES_ARE_PT );
547 m_bbox.Merge( aP );
548 }
549 }
550
556 void Append( const SHAPE_LINE_CHAIN& aOtherLine );
557
558 void Append( const SHAPE_ARC& aArc );
559 void Append( const SHAPE_ARC& aArc, int aMaxError );
560
561 void Insert( size_t aVertex, const VECTOR2I& aP );
562
563 void Insert( size_t aVertex, const SHAPE_ARC& aArc );
564 void Insert( size_t aVertex, const SHAPE_ARC& aArc, int aMaxError );
565
573 void Replace( int aStartIndex, int aEndIndex, const VECTOR2I& aP );
574
583 void Replace( int aStartIndex, int aEndIndex, const SHAPE_LINE_CHAIN& aLine );
584
591 void Remove( int aStartIndex, int aEndIndex );
592
598 void Remove( int aIndex )
599 {
600 Remove( aIndex, aIndex );
601 }
602
611 void RemoveShape( int aPointIndex );
612
621 int Split( const VECTOR2I& aP, bool aExact = false );
622
629 int Find( const VECTOR2I& aP, int aThreshold = 0 ) const;
630
637 int FindSegment( const VECTOR2I& aP, int aThreshold = 1 ) const;
638
646 const SHAPE_LINE_CHAIN Slice( int aStartIndex, int aEndIndex ) const;
647 const SHAPE_LINE_CHAIN Slice( int aStartIndex, int aEndIndex, int aMaxError ) const;
648
650 {
652 m_origin( aOrigin )
653 {}
654
655 bool operator()( const INTERSECTION& aA, const INTERSECTION& aB )
656 {
657 return ( m_origin - aA.p ).EuclideanNorm() < ( m_origin - aB.p ).EuclideanNorm();
658 }
659
661 };
662
663 bool Intersects( const SEG& aSeg) const;
664 bool Intersects( const SHAPE_LINE_CHAIN& aChain ) const;
665
674 int Intersect( const SEG& aSeg, INTERSECTIONS& aIp ) const;
675
684 int Intersect( const SHAPE_LINE_CHAIN& aChain, INTERSECTIONS& aIp,
685 bool aExcludeColinearAndTouching = false,
686 BOX2I* aChainBBox = nullptr ) const;
687
694 int PathLength( const VECTOR2I& aP, int aIndex = -1 ) const;
695
703 bool CheckClearance( const VECTOR2I& aP, const int aDist) const;
704
710 const std::optional<INTERSECTION> SelfIntersecting() const;
711
717 const std::optional<INTERSECTION> SelfIntersectingWithArcs() const;
718
725 int NearestSegment( const VECTOR2I& aP ) const;
726
735 const VECTOR2I NearestPoint( const VECTOR2I& aP, bool aAllowInternalShapePoints = true ) const;
736
745 const VECTOR2I NearestPoint( const SEG& aSeg, int& dist ) const;
746
748 const std::string Format( bool aCplusPlus = true ) const override;
749
751 bool Parse( std::stringstream& aStream ) override;
752
753 bool operator!=( const SHAPE_LINE_CHAIN& aRhs ) const
754 {
755 if( PointCount() != aRhs.PointCount() )
756 return true;
757
758 for( int i = 0; i < PointCount(); i++ )
759 {
760 if( CPoint( i ) != aRhs.CPoint( i ) )
761 return true;
762 }
763
764 return false;
765 }
766
767 bool CompareGeometry( const SHAPE_LINE_CHAIN& aOther ) const;
768
769 void Move( const VECTOR2I& aVector ) override
770 {
771 for( auto& pt : m_points )
772 pt += aVector;
773
774 for( auto& arc : m_arcs )
775 arc.Move( aVector );
776
777 m_bbox.Move( aVector );
778 }
779
786 void Mirror( const VECTOR2I& aRef, FLIP_DIRECTION aFlipDirection );
787
793 void Mirror( const SEG& axis );
794
801 void Rotate( const EDA_ANGLE& aAngle, const VECTOR2I& aCenter = { 0, 0 } ) override;
802
803 bool IsSolid() const override
804 {
805 return false;
806 }
807
808 const VECTOR2I PointAlong( int aPathLength ) const;
809
815 double Area( bool aAbsolute = true ) const;
816
826 void Split( const VECTOR2I& aStart, const VECTOR2I& aEnd, SHAPE_LINE_CHAIN& aPre,
827 SHAPE_LINE_CHAIN& aMid, SHAPE_LINE_CHAIN& aPost ) const;
828
839 bool OffsetLine( int aAmount, CORNER_STRATEGY aCornerStrategy, int aMaxError,
840 SHAPE_LINE_CHAIN& aLeft, SHAPE_LINE_CHAIN& aRight,
841 bool aSimplify = false ) const;
842
843 size_t ArcCount() const
844 {
845 return m_arcs.size();
846 }
847
851 ssize_t ArcIndex( size_t aSegment ) const
852 {
853 if( IsSharedPt( aSegment ) )
854 return m_shapes[aSegment].second;
855 else
856 return m_shapes[aSegment].first;
857 }
858
859 const SHAPE_ARC& Arc( size_t aArc ) const
860 {
861 return m_arcs[aArc];
862 }
863
869 bool IsSharedPt( size_t aIndex ) const;
870
871 bool IsPtOnArc( size_t aPtIndex ) const;
872
873 bool IsArcSegment( size_t aSegment ) const;
874
875 bool IsArcStart( size_t aIndex ) const;
876
877 bool IsArcEnd( size_t aIndex ) const;
878
879 using SHAPE::Distance;
880
881 int Distance( const VECTOR2I& aP, bool aOutlineOnly ) const
882 {
883 return sqrt( SquaredDistance( aP, aOutlineOnly ) );
884 }
885
886 virtual const VECTOR2I GetPoint( int aIndex ) const override { return CPoint(aIndex); }
887 virtual const SEG GetSegment( int aIndex ) const override { return CSegment(aIndex); }
888 virtual size_t GetPointCount() const override { return PointCount(); }
889 virtual size_t GetSegmentCount() const override { return SegmentCount(); }
890
891 void TransformToPolygon( SHAPE_POLY_SET& aBuffer, int aError,
892 ERROR_LOC aErrorLoc ) const override;
893
894protected:
895 friend class SHAPE_POLY_SET;
896
902 void convertArc( ssize_t aArcIndex );
903
916 void splitArc( ssize_t aPtIndex, bool aCoincident = false );
917
918 void amendArc( size_t aArcIndex, const VECTOR2I& aNewStart, const VECTOR2I& aNewEnd );
919
920 void amendArcStart( size_t aArcIndex, const VECTOR2I& aNewStart )
921 {
922 amendArc( aArcIndex, aNewStart, m_arcs[aArcIndex].GetP1() );
923 }
924
925 void amendArcEnd( size_t aArcIndex, const VECTOR2I& aNewEnd )
926 {
927 amendArc( aArcIndex, m_arcs[aArcIndex].GetP0(), aNewEnd );
928 }
929
933 ssize_t reversedArcIndex( size_t aSegment ) const
934 {
935 if( IsSharedPt( aSegment ) )
936 return m_shapes[aSegment].first;
937 else
938 return m_shapes[aSegment].second;
939 }
940
944 Clipper2Lib::Path64 convertToClipper2( bool aRequiredOrientation,
945 std::vector<CLIPPER_Z_VALUE> &aZValueBuffer,
946 std::vector<SHAPE_ARC> &aArcBuffer ) const;
947
951 void fixIndicesRotation();
952
957
958private:
959
960 static const ssize_t SHAPE_IS_PT;
961
962 static const std::pair<ssize_t, ssize_t> SHAPES_ARE_PT;
963
965 std::vector<VECTOR2I> m_points;
966
981 std::vector<std::pair<ssize_t, ssize_t>> m_shapes;
982
983 std::vector<SHAPE_ARC> m_arcs;
984
985 // the maxError to use when converting arcs to points
987
990
997
999 mutable BOX2I m_bbox;
1000};
1001
1002
1003#endif // __SHAPE_LINE_CHAIN
ERROR_LOC
When approximating an arc or circle, should the error be placed on the outside or inside of the curve...
Definition: approximation.h:32
BOX2< VECTOR2I > BOX2I
Definition: box2.h:922
constexpr BOX2< Vec > & Inflate(coord_type dx, coord_type dy)
Inflates the rectangle horizontally by dx and vertically by dy.
Definition: box2.h:558
constexpr BOX2< Vec > & Merge(const BOX2< Vec > &aRect)
Modify the position and size of the rectangle in order to contain aRect.
Definition: box2.h:658
constexpr void Move(const Vec &aMoveVector)
Move the rectangle by the aMoveVector.
Definition: box2.h:138
void Compute(const Container &aPointList)
Compute the bounding box from a given list of points.
Definition: box2.h:109
Definition: seg.h:42
A dynamic state checking if a point lies within polygon with a dynamically built outline ( with each ...
bool processVertex(const VECTOR2I &ip, const VECTOR2I &ipNext)
void AddPolyline(const SHAPE_LINE_CHAIN &aPolyline)
SEG::ecoord SquaredDistance(const VECTOR2I &aP, bool aOutlineOnly=false) const override
Represent a polyline containing arcs as well as line segments: A chain of connected line and/or arc s...
std::vector< std::pair< ssize_t, ssize_t > > m_shapes
Array of indices that refer to the index of the shape if the point is part of a larger shape,...
const SHAPE_LINE_CHAIN Reverse() const
Reverse point order in the line chain.
void Move(const VECTOR2I &aVector) override
bool IsPtOnArc(size_t aPtIndex) const
void amendArcStart(size_t aArcIndex, const VECTOR2I &aNewStart)
void Remove(int aIndex)
Remove the aIndex-th point from the line chain.
void amendArcEnd(size_t aArcIndex, const VECTOR2I &aNewEnd)
int Width() const
Get the current width of the segments in the chain.
const SHAPE_ARC & Arc(size_t aArc) const
void splitArc(ssize_t aPtIndex, bool aCoincident=false)
Splits an arc into two arcs at aPtIndex.
void Append(const VECTOR2I &aP, bool aAllowDuplication=false)
Append a new point at the end of the line chain.
const std::optional< INTERSECTION > SelfIntersecting() const
Check if the line chain is self-intersecting.
bool Parse(std::stringstream &aStream) override
bool CheckClearance(const VECTOR2I &aP, const int aDist) const
Check if point aP is closer to (or on) an edge or vertex of the line chain.
std::vector< SHAPE_ARC > m_arcs
int Distance(const VECTOR2I &aP, bool aOutlineOnly) const
bool IsClosed() const override
virtual const VECTOR2I GetPoint(int aIndex) const override
void SetPoint(int aIndex, const VECTOR2I &aPos)
Move a point to a specific location.
const VECTOR2I PointAlong(int aPathLength) const
int Split(const VECTOR2I &aP, bool aExact=false)
Insert the point aP belonging to one of the our segments, splitting the adjacent segment in two.
SHAPE_LINE_CHAIN & operator=(const SHAPE_LINE_CHAIN &)=default
void fixIndicesRotation()
Fix indices of this chain to ensure arcs are not split between the end and start indices.
std::vector< VECTOR2I > m_points
array of vertices
void GenerateBBoxCache() const
int FindSegment(const VECTOR2I &aP, int aThreshold=1) const
Search for segment containing point aP.
int ShapeCount() const
Return the number of shapes (line segments or arcs) in this line chain.
void SetClosed(bool aClosed)
Mark the line chain as closed (i.e.
ssize_t reversedArcIndex(size_t aSegment) const
Return the arc index for the given segment index, looking backwards.
int Intersect(const SEG &aSeg, INTERSECTIONS &aIp) const
Find all intersection points between our line chain and the segment aSeg.
SHAPE_LINE_CHAIN()
Initialize an empty line chain.
int m_width
Width of the segments (for BBox calculations in RTree) TODO Adjust usage of SHAPE_LINE_CHAIN to accou...
virtual ~SHAPE_LINE_CHAIN()
int PointCount() const
Return the number of points (vertices) in this line chain.
bool IsArcEnd(size_t aIndex) const
void Replace(int aStartIndex, int aEndIndex, const VECTOR2I &aP)
Replace points with indices in range [start_index, end_index] with a single point aP.
void TransformToPolygon(SHAPE_POLY_SET &aBuffer, int aError, ERROR_LOC aErrorLoc) const override
Fills a SHAPE_POLY_SET with a polygon representation of this shape.
virtual bool Collide(const VECTOR2I &aP, int aClearance=0, int *aActual=nullptr, VECTOR2I *aLocation=nullptr) const override
Check if point aP lies closer to us than aClearance.
void ClearArcs()
Remove all arc references in the line chain, resulting in a chain formed only of straight segments.
void ReservePoints(size_t aSize)
Allocate a number of points all at once (for performance).
void mergeFirstLastPointIfNeeded()
Merge the first and last point if they are the same and this chain is closed.
bool CompareGeometry(const SHAPE_LINE_CHAIN &aOther) const
ssize_t ArcIndex(size_t aSegment) const
Return the arc index for the given segment index.
void Clear()
Remove all points from the line chain.
void Simplify(int aTolerance=0)
Simplify the line chain by removing colinear adjacent segments and duplicate vertices.
SEG Segment(int aIndex) const
Return a copy of the aIndex-th segment in the line chain.
BOX2I m_bbox
cached bounding box
BOX2I * GetCachedBBox() const override
bool m_closed
is the line chain closed?
const std::vector< SHAPE_ARC > & CArcs() const
const std::optional< INTERSECTION > SelfIntersectingWithArcs() const
Check if the line chain is self-intersecting.
bool Intersects(const SEG &aSeg) const
int NearestSegment(const VECTOR2I &aP) const
Find the segment nearest the given point.
int NextShape(int aPointIndex) const
Return the vertex index of the next shape in the chain, or -1 if aPointIndex is the last shape.
double Area(bool aAbsolute=true) const
Return the area of this chain.
SHAPE_LINE_CHAIN & Simplify2(bool aRemoveColinear=true)
void amendArc(size_t aArcIndex, const VECTOR2I &aNewStart, const VECTOR2I &aNewEnd)
virtual size_t GetPointCount() const override
bool ClosestPoints(const SHAPE_LINE_CHAIN &aOther, VECTOR2I &aPt0, VECTOR2I &aPt1) const
Finds closest points between this and the other line chain.
void Append(int aX, int aY, bool aAllowDuplication=false)
Append a new point at the end of the line chain.
void Rotate(const EDA_ANGLE &aAngle, const VECTOR2I &aCenter={ 0, 0 }) override
Rotate all vertices by a given angle.
virtual const SEG GetSegment(int aIndex) const override
const VECTOR2I & CPoint(int aIndex) const
Return a reference to a given point in the line chain.
bool operator!=(const SHAPE_LINE_CHAIN &aRhs) const
const std::vector< std::pair< ssize_t, ssize_t > > & CShapes() const
const VECTOR2I NearestPoint(const VECTOR2I &aP, bool aAllowInternalShapePoints=true) const
Find a point on the line chain that is closest to point aP.
std::vector< VECTOR2I >::iterator point_iter
const SHAPE_LINE_CHAIN Slice(int aStartIndex, int aEndIndex) const
Return a subset of this line chain containing the [start_index, end_index] range of points.
int SegmentCount() const
Return the number of segments in this line chain.
int PathLength(const VECTOR2I &aP, int aIndex=-1) const
Compute the walk path length from the beginning of the line chain and the point aP belonging to our l...
const VECTOR2I & CLastPoint() const
Return the last point in the line chain.
void Mirror(const VECTOR2I &aRef, FLIP_DIRECTION aFlipDirection)
Mirror the line points about y or x (or both).
bool ClosestSegmentsFast(const SHAPE_LINE_CHAIN &aOther, VECTOR2I &aPt0, VECTOR2I &aPt1) const
Finds closest points between segments of this and the other line chain.
const std::string Format(bool aCplusPlus=true) const override
static bool ClosestSegments(const VECTOR2I &aMyPrevPt, const point_citer &aMyStart, const point_citer &aMyEnd, const VECTOR2I &aOtherPrevPt, const point_citer &aOtherStart, const point_citer &aOtherEnd, VECTOR2I &aPt0, VECTOR2I &aPt1, int64_t &aDistSq)
SHAPE_LINE_CHAIN(const SHAPE_LINE_CHAIN &aShape)
Clipper2Lib::Path64 convertToClipper2(bool aRequiredOrientation, std::vector< CLIPPER_Z_VALUE > &aZValueBuffer, std::vector< SHAPE_ARC > &aArcBuffer) const
Create a new Clipper2 path from the SHAPE_LINE_CHAIN in a given orientation.
static const std::pair< ssize_t, ssize_t > SHAPES_ARE_PT
void convertArc(ssize_t aArcIndex)
Convert an arc to only a point chain by removing the arc and references.
virtual size_t GetSegmentCount() const override
void Remove(int aStartIndex, int aEndIndex)
Remove the range of points [start_index, end_index] from the line chain.
void RemoveDuplicatePoints()
Remove the duplicate points from the line chain.
size_t ArcCount() const
const SEG CSegment(int aIndex) const
Return a constant copy of the aIndex segment in the line chain.
bool IsArcSegment(size_t aSegment) const
void RemoveShape(int aPointIndex)
Remove the shape at the given index from the line chain.
void Insert(size_t aVertex, const VECTOR2I &aP)
bool IsArcStart(size_t aIndex) const
void SetWidth(int aWidth)
Set the width of all segments in the chain.
SHAPE_LINE_CHAIN & operator=(SHAPE_LINE_CHAIN &&aOther) noexcept
bool IsSharedPt(size_t aIndex) const
Test if a point is shared between multiple shapes.
std::vector< INTERSECTION > INTERSECTIONS
long long int Length() const
Return length of the line chain in Euclidean metric.
int Find(const VECTOR2I &aP, int aThreshold=0) const
Search for point aP.
const std::vector< VECTOR2I > & CPoints() const
const BOX2I BBox(int aClearance=0) const override
Compute a bounding box of the shape, with a margin of aClearance a collision.
std::vector< VECTOR2I >::const_iterator point_citer
SHAPE * Clone() const override
Return a dynamically allocated copy of the shape.
bool IsSolid() const override
static const ssize_t SHAPE_IS_PT
bool OffsetLine(int aAmount, CORNER_STRATEGY aCornerStrategy, int aMaxError, SHAPE_LINE_CHAIN &aLeft, SHAPE_LINE_CHAIN &aRight, bool aSimplify=false) const
Creates line chains aLeft and aRight offset to this line chain.
Represent a set of closed polygons.
An abstract shape on 2D plane.
Definition: shape.h:126
virtual int Distance(const VECTOR2I &aP) const
Returns the minimum distance from a given point to this shape.
Definition: shape.cpp:109
CORNER_STRATEGY
define how inflate transform build inflated polygon
FLIP_DIRECTION
Definition: mirror.h:27
@ SH_LINE_CHAIN
line chain (polyline)
Definition: shape.h:49
Holds information on each point of a SHAPE_LINE_CHAIN that is retrievable after an operation with Cli...
CLIPPER_Z_VALUE(const std::pair< ssize_t, ssize_t > aShapeIndices, ssize_t aOffset=0)
Represent an intersection between two line segments.
bool is_corner_their
When true, the corner [index_their] of the 'their' line lies exactly on 'our' line.
bool is_corner_our
When true, the corner [index_our] of the 'our' line lies exactly on 'their' line.
int index_our
Index of the intersecting corner/segment in the 'our' (== this) line.
VECTOR2I p
Point of intersection between our and their.
bool valid
Auxiliary flag to avoid copying intersection info to intersection refining code, used by the refining...
int index_their
index of the intersecting corner/segment in the 'their' (Intersect() method parameter) line.
compareOriginDistance(const VECTOR2I &aOrigin)
bool operator()(const INTERSECTION &aA, const INTERSECTION &aB)
VECTOR2< int32_t > VECTOR2I
Definition: vector2d.h:695