38 sum += ( ( p2.
x - p1.
x ) * ( p2.
y + p1.
y ) );
44 auto addVertex = [&](
int i )
58 for(
int i = points.
PointCount() - 1; i >= 0; i-- )
67 if( tail && ( *tail == *tail->
next ) )
83 double limit_x = std::clamp( ( aX -
m_bbox.GetX() ) /
m_bbox.GetWidth(), 0.0, 1.0 );
84 double limit_y = std::clamp( ( aY -
m_bbox.GetY() ) /
m_bbox.GetHeight(), 0.0, 1.0 );
86 uint32_t x =
static_cast<uint32_t
>( limit_x * 32767.0 );
87 uint32_t y =
static_cast<uint32_t
>( limit_y * 32767.0 );
89 x = ( x | ( x << 8 ) ) & 0x00FF00FF;
90 x = ( x | ( x << 4 ) ) & 0x0F0F0F0F;
91 x = ( x | ( x << 2 ) ) & 0x33333333;
92 x = ( x | ( x << 1 ) ) & 0x55555555;
94 y = ( y | ( y << 8 ) ) & 0x00FF00FF;
95 y = ( y | ( y << 4 ) ) & 0x0F0F0F0F;
96 y = ( y | ( y << 2 ) ) & 0x33333333;
97 y = ( y | ( y << 1 ) ) & 0x55555555;
99 return x | ( y << 1 );
108 return ( q->
y - p->
y ) * ( r->
x - q->
x ) - ( q->
x - p->
x ) * ( r->
y - q->
y );
130 }
while( p != aStart );
135 return aLhs.z < aRhs.z;
144 return aA && aB && aA->
x == aB->
x && aA->
y == aB->
y;
160 && aPt->
y == aPt->
next->
y )
166 && aPt->
y == aPt->
next->
y )
187 && aPt->
y == aPt->
prev->
y)
193 && aPt->
y == aPt->
prev->
y )
208 if(
area( ap, a, an ) < 0 )
209 return area( a, b, an ) >= 0 &&
area( a, ap, b ) >= 0;
211 return area( a, b, ap ) < 0 ||
area( a, an, b ) < 0;
219 double px = ( a->
x + b->
x ) / 2;
220 double py = ( a->
y + b->
y ) / 2;
224 if( ( ( p->
y > py ) != ( p->
next->
y > py ) )
225 && ( px < ( p->
next->
x - p->
x ) * ( py - p->
y ) / ( p->
next->
y - p->
y ) + p->
x ) )
242 m_vertices.emplace_back( aIndex, pt.
x, pt.
y,
this, aUserData );
310 if(
parent->area( a, b, c ) >= 0 )
316 return ( !aMatchUserData || p->GetUserData() ==
m_userData )
319 &&
parent->area( p->prev, p, p->next ) >= 0;
327 const double minTX = std::min( a->
x, std::min( b->
x, c->
x ) );
328 const double minTY = std::min( a->
y, std::min( b->
y, c->
y ) );
329 const double maxTX = std::max( a->
x, std::max( b->
x, c->
x ) );
330 const double maxTY = std::max( a->
y, std::max( b->
y, c->
y ) );
333 const uint32_t minZ =
parent->zOrder( minTX, minTY );
334 const uint32_t maxZ =
parent->zOrder( maxTX, maxTY );
336 if( !aMatchUserData &&
parent->m_reflexIndexValid )
338 const std::vector<VERTEX_SET::REFLEX_ENTRY>&
index =
parent->m_reflexIndex;
340 auto it = std::lower_bound(
index.begin(),
index.end(), minZ,
343 return aEntry.z < aZ;
346 for( ; it !=
index.end() && it->z <= maxZ; ++it )
349 if( ( c->
x - it->x ) * ( a->
y - it->y ) - ( a->
x - it->x ) * ( c->
y - it->y ) < 0
350 || ( a->
x - it->x ) * ( b->
y - it->y ) - ( b->
x - it->x ) * ( a->
y - it->y ) < 0
351 || ( b->
x - it->x ) * ( c->
y - it->y ) - ( c->
x - it->x ) * ( b->
y - it->y ) < 0 )
357 if( it->v->next && blocksEar( it->v ) )
370 while( p && p->
z <= maxZ )
384 while( p && p->
z >= minZ )
Represent a polyline containing arcs as well as line segments: A chain of connected line and/or arc s...
int PointCount() const
Return the number of points (vertices) in this line chain.
const VECTOR2I & CPoint(int aIndex) const
Return a reference to a given point in the line chain.
constexpr extended_type SquaredDistance(const VECTOR2< T > &aVector) const
Compute the squared distance between two vectors.
std::deque< VERTEX > m_vertices
bool middleInside(const VERTEX *a, const VERTEX *b) const
Check if the middle of the segment from a to b is inside the polygon.
VERTEX * createList(const SHAPE_LINE_CHAIN &points, VERTEX *aTail=nullptr, void *aUserData=nullptr)
Create a list of vertices from a line chain.
bool locallyInside(const VERTEX *a, const VERTEX *b) const
Check whether the segment from vertex a -> vertex b is inside the polygon around the immediate area o...
VERTEX * getPrevOutlineVertex(const VERTEX *aPt) const
Get the previous vertex in the outline, avoiding steiner points and points that overlap with splits.
void SetBoundingBox(const BOX2I &aBBox)
void buildReflexIndex(VERTEX *aStart)
Index the reflex vertices of the ring containing aStart in z-order.
std::vector< REFLEX_ENTRY > m_reflexIndex
double area(const VERTEX *p, const VERTEX *q, const VERTEX *r) const
Return the twice the signed area of the triangle formed by vertices p, q, and r.
VERTEX * insertVertex(int aIndex, const VECTOR2I &pt, VERTEX *last, void *aUserData=nullptr)
Insert a vertex into the vertex set.
VECTOR2I::extended_type m_simplificationLevel
VERTEX * getNextOutlineVertex(const VERTEX *aPt) const
Get the next vertex in the outline, avoiding steiner points and points that overlap with splits.
uint32_t zOrder(const double aX, const double aY) const
Note that while the inputs are doubles, these are scaled by the size of the bounding box to fit into ...
bool same_point(const VERTEX *aA, const VERTEX *aB) const
Check if two vertices are at the same point.
VERTEX * split(VERTEX *b)
Split the referenced polygon between the reference point and vertex b, assuming they are in the same ...
bool inTriangle(const VERTEX &a, const VERTEX &b, const VERTEX &c)
Check to see if triangle surrounds our current vertex.
void * GetUserData() const
void remove()
Remove the node from the linked list and z-ordered linked list.
VERTEX(int aIndex, double aX, double aY, VERTEX_SET *aParent, void *aUserData=nullptr)
bool isEar(bool aMatchUserData=false) const
Check whether the given vertex is in the middle of an ear.
VECTOR2< int32_t > VECTOR2I
VECTOR2< double > VECTOR2D
VECTOR2< int64_t > VECTOR2L