83 for(
int i=0; i<4; i++)
102 for(
int i=0; i<4; i++)
143 if( x != pLeaf->
Get_X() || y != pLeaf->
Get_Y() )
197 Create(Extent, bStatistics);
207 Create(pShapes, Attribute, bStatistics);
256 if( Attribute < 0 || !pShape->is_NoData(Attribute) )
258 double z = Attribute < 0 ? iShape : pShape->
asDouble(Attribute);
270 return( m_nPoints > 0 );
299 if( _Check_Root(x, y) && m_pRoot->
Add_Point(x, y, z) )
321 bool CSG_PRQuadTree::_Check_Root(
double x,
double y)
334 int Quadrant = y < m_pRoot->
Get_yMin()
336 : (x < m_pRoot->Get_xMin() ? 1 : 2);
369 return( _Check_Root(x, y) );
378 inline bool CSG_PRQuadTree::_Quadrant_Contains(
double x,
double y,
int iQuadrant,
const TSG_Point &p)
const
382 case 0:
return( x < p.
x && y < p.
y );
383 case 1:
return( x < p.x && y >= p.
y );
384 case 2:
return( x >= p.
x && y >= p.
y );
385 case 3:
return( x >= p.
x && y < p.
y );
392 inline bool CSG_PRQuadTree::_Radius_Contains(
double x,
double y,
double r,
const TSG_Point &p)
const
396 if( fabs(dx = x - p.
x) <= r && fabs(dy = y - p.
y) <= r )
398 return( dx*dx + dy*dy < r*r );
405 inline bool CSG_PRQuadTree::_Radius_Contains(
double x,
double y,
double r,
int iQuadrant,
const TSG_Point &p)
const
407 return( _Quadrant_Contains(x, y, iQuadrant, p) && _Radius_Contains(x, y, r, p) );
411 inline bool CSG_PRQuadTree::_Quadrant_Intersects(
double x,
double y,
int iQuadrant,
CSG_PRQuadTree_Item *pItem)
const
415 case 0:
return( x < pItem->Get_xMax() && y < pItem->Get_yMax() );
416 case 1:
return( x < pItem->Get_xMax() && y >= pItem->
Get_yMin() );
418 case 3:
return( x >= pItem->
Get_xMin() && y < pItem->Get_yMax() );
425 inline bool CSG_PRQuadTree::_Radius_Intersects(
double x,
double y,
double r,
CSG_PRQuadTree_Item *pItem)
const
438 if( (pItem->
Get_xMin() <= x && x <= pItem->Get_xMax())
439 || (pItem->
Get_yMin() <= y && y <= pItem->Get_yMax()) )
457 return( _Radius_Contains(x, y, r, p) );
461 inline bool CSG_PRQuadTree::_Radius_Intersects(
double x,
double y,
double r,
int iQuadrant,
CSG_PRQuadTree_Item *pItem)
const
463 return( _Quadrant_Intersects(x, y, iQuadrant, pItem) && _Radius_Intersects(x, y, r, pItem) );
479 return( _Get_Nearest_Point(m_pRoot, x, y, Distance = -1) );
496 Value = pLeaf->
Get_Z();
517 if( Distance < 0.0 || Distance > d )
533 if( pChild && pChild->
Contains(x, y) && (pLeaf = _Get_Nearest_Point(pChild, x, y, Distance)) != NULL )
544 if( pChild && pChild->
Contains(x, y) ==
false && (Distance < 0.0
546 && Distance > (y < pChild->Get_yCenter() ? pChild->
Get_yMin() - y : y - pChild->
Get_yMax()) ))
547 && (pLeaf = _Get_Nearest_Point(pChild, x, y, Distance)) != NULL )
564 inline CSG_PRQuadTree::TLeaf * CSG_PRQuadTree::_Get_Selected(
const CSG_Array &Selection,
size_t i)
const
566 return( (TLeaf *)Selection.
Get_Entry(i) );
577 pL->Distance = Distance;
588 TLeaf *pL = (TLeaf *)Selection.
Get_Entry(i);
593 pL->Distance = Distance;
615 return( _Select_Nearest_Points(m_Selection, x, y, maxPoints, Radius, iQuadrant) );
619 size_t CSG_PRQuadTree::_Select_Nearest_Points(
CSG_Array &Selection,
double x,
double y,
size_t maxPoints,
double Radius,
int iQuadrant)
const
623 Selection.
Create(
sizeof(TLeaf), 0, TSG_Array_Growth::SG_ARRAY_GROWTH_3);
636 maxPoints = m_nPoints;
641 _Select_Nearest_Points(Selection, m_pRoot, x, y, Distance = 0.0, Radius, maxPoints, iQuadrant);
645 for(iQuadrant=0; iQuadrant<4; iQuadrant++)
647 _Select_Nearest_Points(Selection, m_pRoot, x, y, Distance = 0.0, Radius, maxPoints, iQuadrant);
656 void CSG_PRQuadTree::_Select_Nearest_Points(
CSG_Array &Selection,
CSG_PRQuadTree_Item *pItem,
double x,
double y,
double &Distance,
double Radius,
size_t maxPoints,
int iQuadrant)
const
663 if( _Quadrant_Contains(x, y, iQuadrant, pLeaf->
Get_Point()) == false )
670 if( Radius > 0.0 && Radius < d )
676 if( (
int)Selection.
Get_Size() < maxPoints )
683 _Add_Selected(Selection, pLeaf, d);
685 else if( d < Distance )
687 for(
size_t i=0; i<(int)Selection.
Get_Size(); i++)
689 if( Distance <= _Get_Selected(Selection, i)->Distance )
691 _Set_Selected(Selection, i, pLeaf, d);
699 for(
size_t i=0; i<maxPoints; i++)
701 if( Distance < _Get_Selected(Selection, i)->Distance )
703 Distance = _Get_Selected(Selection, i)->Distance;
720 _Select_Nearest_Points(Selection, pChild, x, y, Distance, Radius, maxPoints, iQuadrant);
728 if( _Radius_Intersects(x, y, Radius, iQuadrant, pChild) )
731 || ( Distance > (x < pChild->Get_xCenter() ? pChild->
Get_xMin() - x : x - pChild->
Get_xMax())
732 && Distance > (y < pChild->Get_yCenter() ? pChild->
Get_yMin() - y : y - pChild->
Get_yMax()) ) )
734 _Select_Nearest_Points(Selection, pChild, x, y, Distance, Radius, maxPoints, iQuadrant);
758 _Select_Nearest_Points(Selection, x, y, maxPoints, Radius, iQuadrant);
762 for(
size_t i=0; i<(int)Selection.
Get_Size(); i++)