23 #include <SpatialIndex.h> 25 #include <QLinkedListIterator> 36 return Point( plow, 2 );
42 double pLow[2], pHigh[2];
47 return SpatialIndex::Region( pLow, pHigh, 2 );
69 virtual IData*
getNext()
override {
return mIt.next(); }
70 virtual bool hasNext()
override {
return mIt.hasNext(); }
72 virtual uint32_t
size()
override { Q_ASSERT( 0 &&
"not available" );
return 0; }
73 virtual void rewind()
override { Q_ASSERT( 0 &&
"not available" ); }
91 : mLocator( pl ), mBest( m ), mSrcPoint( srcPoint ), mFilter( filter ) {}
93 void visitNode(
const INode& n )
override { Q_UNUSED( n ); }
94 void visitData( std::vector<const IData*>& v )
override { Q_UNUSED( v ); }
100 int vertexIndex, beforeVertex, afterVertex;
108 if ( mFilter && !mFilter->acceptMatch( m ) )
111 if ( !mBest.isValid() || m.
distance() < mBest.distance() )
133 : mLocator( pl ), mBest( m ), mSrcPoint( srcPoint ), mFilter( filter ) {}
135 void visitNode(
const INode& n )
override { Q_UNUSED( n ); }
136 void visitData( std::vector<const IData*>& v )
override { Q_UNUSED( v ); }
149 edgePoints[0] = geom->
vertexAt( afterVertex - 1 );
150 edgePoints[1] = geom->
vertexAt( afterVertex );
153 if ( mFilter && !mFilter->acceptMatch( m ) )
156 if ( !mBest.isValid() || m.
distance() < mBest.distance() )
179 : mLocator( pl ), mList( list ), mGeomPt(
QgsGeometry::fromPoint( origPt ) ) {}
183 void visitNode(
const INode& n )
override { Q_UNUSED( n ); }
184 void visitData( std::vector<const IData*>& v )
override { Q_UNUSED( v ); }
210 static const int INSIDE = 0;
213 static const int BOTTOM = 4;
214 static const int TOP = 8;
220 OutCode code = INSIDE;
235 OutCode outcode0 = computeOutCode( x0, y0 );
236 OutCode outcode1 = computeOutCode( x1, y1 );
241 if ( !( outcode0 | outcode1 ) )
247 else if ( outcode0 & outcode1 )
259 OutCode outcodeOut = outcode0 ? outcode0 : outcode1;
263 if ( outcodeOut & TOP )
265 x = x0 + ( x1 - x0 ) * ( mRect.
yMaximum() - y0 ) / ( y1 - y0 );
268 else if ( outcodeOut & BOTTOM )
270 x = x0 + ( x1 - x0 ) * ( mRect.
yMinimum() - y0 ) / ( y1 - y0 );
273 else if ( outcodeOut & RIGHT )
275 y = y0 + ( y1 - y0 ) * ( mRect.
xMaximum() - x0 ) / ( x1 - x0 );
278 else if ( outcodeOut & LEFT )
280 y = y0 + ( y1 - y0 ) * ( mRect.
xMinimum() - x0 ) / ( x1 - x0 );
288 if ( outcodeOut == outcode0 )
292 outcode0 = computeOutCode( x0, y0 );
298 outcode1 = computeOutCode( x1, y1 );
313 unsigned char* wkb =
const_cast<unsigned char*
>( geom->
asWkb() );
324 bool hasZValue =
false;
345 double prevx = 0.0, prevy = 0.0;
349 wkbPtr >> thisx >> thisy;
351 wkbPtr +=
sizeof( double );
358 edgePoints[0].
set( prevx, prevy );
359 edgePoints[1].
set( thisx, thisy );
378 for (
int linenr = 0, pointIndex = 0; linenr < nLines; ++linenr )
384 double prevx = 0.0, prevy = 0.0;
385 for (
int pointnr = 0; pointnr < nPoints; ++pointnr )
388 wkbPtr >> thisx >> thisy;
390 wkbPtr +=
sizeof( double );
397 edgePoints[0].
set( prevx, prevy );
398 edgePoints[1].
set( thisx, thisy );
420 for (
int ringnr = 0, pointIndex = 0; ringnr < nRings; ++ringnr )
425 double prevx = 0.0, prevy = 0.0;
426 for (
int pointnr = 0; pointnr < nPoints; ++pointnr )
429 wkbPtr >> thisx >> thisy;
431 wkbPtr +=
sizeof( double );
438 edgePoints[0].
set( prevx, prevy );
439 edgePoints[1].
set( thisx, thisy );
460 for (
int polynr = 0, pointIndex = 0; polynr < nPolygons; ++polynr )
465 for (
int ringnr = 0; ringnr < nRings; ++ringnr )
470 double prevx = 0.0, prevy = 0.0;
471 for (
int pointnr = 0; pointnr < nPoints; ++pointnr )
474 wkbPtr >> thisx >> thisy;
476 wkbPtr +=
sizeof( double );
483 edgePoints[0].
set( prevx, prevy );
484 edgePoints[1].
set( thisx, thisy );
513 : mLocator( pl ), mList( lst ), mSrcRect( srcRect ), mFilter( filter ) {}
515 void visitNode(
const INode& n )
override { Q_UNUSED( n ); }
516 void visitData( std::vector<const IData*>& v )
override { Q_UNUSED( v ); }
526 if ( mFilter && !mFilter->acceptMatch( m ) )
555 void getNextEntry(
const IEntry& entry, id_type& nextEntry,
bool& hasNext )
override 557 const INode* n =
dynamic_cast<const INode*
>( &entry );
562 if ( n->getLevel() > 0 )
565 for ( uint32_t cChild = 0; cChild < n->getChildrenCount(); cChild++ )
568 ids.
push( n->getChildIdentifier( cChild ) );
574 for ( uint32_t cChild = 0; cChild < n->getChildrenCount(); cChild++ )
582 nextEntry = ids.back();
595 : mStorage( nullptr )
597 , mIsEmptyLayer( false )
598 , mTransform( nullptr )
609 mStorage = StorageManager::createNewMemoryStorageManager();
628 return mTransform ? &mTransform->
destCRS() :
nullptr;
650 return mRTree || mIsEmptyLayer;
679 QgsDebugMsg(
QString(
"could not transform bounding box to map, skipping the snap filter (%1)" ).arg( e.
what() ) );
685 int indexedCount = 0;
701 QgsDebugMsg(
QString(
"could not transform geometry to map, skipping the snap for it (%1)" ).arg( e.
what() ) );
707 dataList <<
new RTree::Data( 0,
nullptr, r, f.
id() );
710 delete mGeoms.
take( f.
id() );
714 if ( maxFeaturesToIndex != -1 && indexedCount > maxFeaturesToIndex )
716 qDeleteAll( dataList );
723 double fillFactor = 0.7;
724 unsigned long indexCapacity = 10;
725 unsigned long leafCapacity = 10;
726 unsigned long dimension = 2;
727 RTree::RTreeVariant variant = RTree::RV_RSTAR;
728 SpatialIndex::id_type indexId;
732 mIsEmptyLayer =
true;
737 mRTree = RTree::createAndBulkLoadNewRTree( RTree::BLM_STR, stream, *mStorage, fillFactor, indexCapacity,
738 leafCapacity, dimension, variant, indexId );
748 mIsEmptyLayer =
false;
750 qDeleteAll( mGeoms );
755 void QgsPointLocator::onFeatureAdded(
QgsFeatureId fid )
780 QgsDebugMsg(
QString(
"could not transform geometry to map, skipping the snap for it (%1)" ).arg( e.
what() ) );
789 mRTree->insertData( 0,
nullptr, r, f.
id() );
792 delete mGeoms.
take( f.
id() );
798 void QgsPointLocator::onFeatureDeleted(
QgsFeatureId fid )
805 mRTree->deleteData(
rect2region( mGeoms[fid]->boundingBox() ), fid );
806 delete mGeoms.
take( fid );
813 onFeatureDeleted( fid );
814 onFeatureAdded( fid );
829 QgsRectangle rect( point.
x() - tolerance, point.
y() - tolerance, point.
x() + tolerance, point.
y() + tolerance );
830 mRTree->intersectsWithQuery(
rect2region( rect ), visitor );
847 QgsRectangle rect( point.
x() - tolerance, point.
y() - tolerance, point.
x() + tolerance, point.
y() + tolerance );
848 mRTree->intersectsWithQuery(
rect2region( rect ), visitor );
865 mRTree->intersectsWithQuery(
rect2region( rect ), visitor );
872 QgsRectangle rect( point.
x() - tolerance, point.
y() - tolerance, point.
x() + tolerance, point.
y() + tolerance );
888 mRTree->intersectsWithQuery(
point2point( point ), visitor );
The class defines interface for querying point location:
Wrapper for iterator of features from vector data provider or vector layer.
void visitData(std::vector< const IData *> &v) override
A rectangle specified with double values.
QGis::WkbType wkbType() const
Returns type of the geometry as a WKB type (point / linestring / polygon etc.)
bool intersects(const QgsRectangle &r) const
Test for intersection with a rectangle (uses GEOS)
QgsPointLocator_VisitorNearestEdge(QgsPointLocator *pl, QgsPointLocator::Match &m, const QgsPoint &srcPoint, QgsPointLocator::MatchFilter *filter=nullptr)
static QgsPointLocator::MatchList _geometrySegmentsInRect(QgsGeometry *geom, const QgsRectangle &rect, QgsVectorLayer *vl, QgsFeatureId fid)
void visitData(const IData &d) override
bool hasIndex() const
Indicate whether the data have been already indexed.
QgsPointLocator_VisitorArea(QgsPointLocator *pl, const QgsPoint &origPt, QgsPointLocator::MatchList &list)
constructor
QgsFeatureIterator getFeatures(const QgsFeatureRequest &request=QgsFeatureRequest())
Query the provider for features specified in request.
const QgsCoordinateReferenceSystem & crs() const
Returns layer's spatial reference system.
~QgsPointLocator_VisitorArea()
QgsFeatureRequest & setSubsetOfAttributes(const QgsAttributeList &attrs)
Set a subset of attributes that will be fetched.
Helper class used when traversing the index looking for edges - builds a list of matches.
A geometry is the spatial representation of a feature.
WkbType
Used for symbology operations.
bool rebuildIndex(int maxFeaturesToIndex=-1)
const QgsGeometry * constGeometry() const
Gets a const pointer to the geometry object associated with this feature.
void visitNode(const INode &n) override
static SpatialIndex::Point point2point(const QgsPoint &point)
The feature class encapsulates a single feature including its id, geometry and a list of field/values...
Interface that allows rejection of some matches in intersection queries (e.g.
int wkbSize() const
Returns the size of the WKB in asWkb().
virtual uint32_t size() override
QgsPointLocator_Stream(const QLinkedList< RTree::Data *> &dataList)
double y() const
Get the y value of the point.
static SpatialIndex::Region rect2region(const QgsRectangle &rect)
virtual bool hasNext() override
QgsPointLocator_VisitorNearestVertex(QgsPointLocator *pl, QgsPointLocator::Match &m, const QgsPoint &srcPoint, QgsPointLocator::MatchFilter *filter=nullptr)
OutCode computeOutCode(double x, double y)
virtual IData * getNext() override
static const double POINT_LOC_EPSILON
Match nearestEdge(const QgsPoint &point, double tolerance, MatchFilter *filter=nullptr)
Find nearest edges to the specified point - up to distance specified by tolerance Optional filter may...
Helper class to dump the R-index nodes and their content.
This class wraps a request for features to a vector layer (or directly its vector data provider)...
bool isSegmentInRect(double x0, double y0, double x1, double y1)
QList< int > QgsAttributeList
const unsigned char * asWkb() const
Returns the buffer containing this geometry in WKB format.
void visitNode(const INode &n) override
void setExtent(const QgsRectangle *extent)
Configure extent - if not null, it will index only that area.
Helper class used when traversing the index with areas - builds a list of matches.
QGis::GeometryType geometryType() const
Returns point, line or polygon.
void set(double x, double y)
Sets the x and y value of the point.
void visitData(const IData &d) override
Helper class used when traversing the index looking for vertices - builds a list of matches...
class QList< Match > MatchList
A class to represent a point.
const QgsRectangle * extent() const
Get extent of the area point locator covers - if null then it caches the whole layer.
void visitData(std::vector< const IData *> &v) override
QgsFeatureId id() const
Get the feature ID for this feature.
void visitData(std::vector< const IData *> &v) override
double yMinimum() const
Get the y minimum value (bottom side of rectangle)
QgsGeometry * geometry()
Get the geometry object associated with this feature.
double xMaximum() const
Get the x maximum value (right side of rectangle)
~QgsPointLocator_Stream()
double closestSegmentWithContext(const QgsPoint &point, QgsPoint &minDistPoint, int &afterVertex, double *leftOf=nullptr, double epsilon=DEFAULT_SEGMENT_EPSILON) const
Searches for the closest segment of geometry to the given point.
QgsPoint vertexAt(int atVertex) const
Returns coordinates of a vertex.
void visitData(std::vector< const IData *> &v) override
Helper class for bulk loading of R-trees.
void visitData(const IData &d) override
void visitNode(const INode &n) override
QgsPointLocator(QgsVectorLayer *layer, const QgsCoordinateReferenceSystem *destCRS=nullptr, const QgsRectangle *extent=nullptr)
Construct point locator for a layer.
bool init(int maxFeaturesToIndex=-1)
Prepare the index for queries.
MatchList edgesInRect(const QgsRectangle &rect, MatchFilter *filter=nullptr)
Find edges within a specified recangle Optional filter may discard unwanted matches.
QgsRectangle boundingBox() const
Returns the bounding box of this feature.
Class for storing a coordinate reference system (CRS)
_CohenSutherland(const QgsRectangle &rect)
bool isNull() const
test if the rectangle is null (all coordinates zero or after call to setMinimal()).
const QgsCoordinateReferenceSystem * destCRS() const
Get destination CRS - may be null if not doing OTF reprojection.
void getNextEntry(const IEntry &entry, id_type &nextEntry, bool &hasNext) override
void visitData(const IData &d) override
double xMinimum() const
Get the x minimum value (left side of rectangle)
int transform(const QgsCoordinateTransform &ct)
Transform this geometry as described by CoordinateTransform ct.
double distance() const
for vertex / edge match units depending on what class returns it (geom.cache: layer units...
double yMaximum() const
Get the y maximum value (top side of rectangle)
Helper class used when traversing the index looking for edges - builds a list of matches.
void visitNode(const INode &n) override
MatchList pointInPolygon(const QgsPoint &point)
find out if the point is in any polygons
bool contains(const Key &key) const
virtual void rewind() override
QgsWKBTypes::Type readHeader() const
bool nextFeature(QgsFeature &f)
bool connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)
Represents a vector layer which manages a vector based data sets.
QgsPoint closestVertex(const QgsPoint &point, int &atVertex, int &beforeVertex, int &afterVertex, double &sqrDist) const
Returns the vertex closest to the given point, the corresponding vertex index, squared distance snap ...
Match nearestVertex(const QgsPoint &point, double tolerance, MatchFilter *filter=nullptr)
Find nearest vertex to the specified point - up to distance specified by tolerance Optional filter ma...
Defines a qgis exception class.
QgsPointLocator_VisitorEdgesInRect(QgsPointLocator *pl, QgsPointLocator::MatchList &lst, const QgsRectangle &srcRect, QgsPointLocator::MatchFilter *filter=nullptr)
QgsFeatureRequest & setFilterRect(const QgsRectangle &rect)
Set rectangle from which features will be taken.
double x() const
Get the x value of the point.