QGIS API Documentation  3.26.3-Buenos Aires (65e4edfdad)
qgsalgorithmextractbylocation.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsalgorithmextractbylocation.cpp
3  ---------------------
4  begin : April 2017
5  copyright : (C) 2017 by Nyall Dawson
6  email : nyall dot dawson at gmail dot com
7  ***************************************************************************/
8 
9 /***************************************************************************
10  * *
11  * This program is free software; you can redistribute it and/or modify *
12  * it under the terms of the GNU General Public License as published by *
13  * the Free Software Foundation; either version 2 of the License, or *
14  * (at your option) any later version. *
15  * *
16  ***************************************************************************/
17 
19 #include "qgsgeometryengine.h"
20 #include "qgsvectorlayer.h"
22 
24 
25 void QgsLocationBasedAlgorithm::addPredicateParameter()
26 {
27  std::unique_ptr< QgsProcessingParameterEnum > predicateParam( new QgsProcessingParameterEnum( QStringLiteral( "PREDICATE" ),
28  QObject::tr( "Where the features (geometric predicate)" ),
29  predicateOptionsList(), true, QVariant::fromValue( QList< int >() << 0 ) ) );
30 
31  QVariantMap predicateMetadata;
32  QVariantMap widgetMetadata;
33  widgetMetadata.insert( QStringLiteral( "useCheckBoxes" ), true );
34  widgetMetadata.insert( QStringLiteral( "columns" ), 2 );
35  predicateMetadata.insert( QStringLiteral( "widget_wrapper" ), widgetMetadata );
36  predicateParam->setMetadata( predicateMetadata );
37 
38  addParameter( predicateParam.release() );
39 }
40 
41 QgsLocationBasedAlgorithm::Predicate QgsLocationBasedAlgorithm::reversePredicate( QgsLocationBasedAlgorithm::Predicate predicate ) const
42 {
43  switch ( predicate )
44  {
45  case Intersects:
46  return Intersects;
47  case Contains:
48  return Within;
49  case Disjoint:
50  return Disjoint;
51  case IsEqual:
52  return IsEqual;
53  case Touches:
54  return Touches;
55  case Overlaps:
56  return Overlaps;
57  case Within:
58  return Contains;
59  case Crosses:
60  return Crosses;
61  }
62  // no warnings
63  return Intersects;
64 }
65 
66 QStringList QgsLocationBasedAlgorithm::predicateOptionsList() const
67 {
68  return QStringList() << QObject::tr( "intersect" )
69  << QObject::tr( "contain" )
70  << QObject::tr( "disjoint" )
71  << QObject::tr( "equal" )
72  << QObject::tr( "touch" )
73  << QObject::tr( "overlap" )
74  << QObject::tr( "are within" )
75  << QObject::tr( "cross" );
76 }
77 
78 void QgsLocationBasedAlgorithm::process( const QgsProcessingContext &context, QgsFeatureSource *targetSource,
79  QgsFeatureSource *intersectSource,
80  const QList< int > &selectedPredicates,
81  const std::function < void( const QgsFeature & ) > &handleFeatureFunction,
82  bool onlyRequireTargetIds,
83  QgsProcessingFeedback *feedback,
84  const QgsFeatureIds &skipTargetFeatureIds )
85 {
86  // skip if there are no features to select from!
87  if ( targetSource->featureCount() == 0 )
88  return;
89 
90  // skip if intersect layer is empty, unless we are looking for disjoints
91  if ( intersectSource->featureCount() == 0 &&
92  !selectedPredicates.contains( Disjoint ) )
93  return;
94 
95  if ( targetSource->featureCount() > 0 && intersectSource->featureCount() > 0 &&
96  targetSource->featureCount() < intersectSource->featureCount() )
97  {
98  // joining FEWER features to a layer with MORE features. So we iterate over the FEW features and find matches from the MANY
99  processByIteratingOverTargetSource( context, targetSource, intersectSource,
100  selectedPredicates, handleFeatureFunction,
101  onlyRequireTargetIds, feedback, skipTargetFeatureIds );
102  }
103  else
104  {
105  // default -- iterate over the intersect source and match back to the target source. We do this on the assumption that the most common
106  // use case is joining a points layer to a polygon layer (e.g. findings points within a polygon), so by iterating
107  // over the polygons we can take advantage of prepared geometries for the spatial relationship test.
108 
109  // TODO - consider using more heuristics to determine whether it's always best to iterate over the intersect
110  // source.
111  processByIteratingOverIntersectSource( context, targetSource, intersectSource,
112  selectedPredicates, handleFeatureFunction,
113  onlyRequireTargetIds, feedback, skipTargetFeatureIds );
114  }
115 }
116 
117 void QgsLocationBasedAlgorithm::processByIteratingOverTargetSource( const QgsProcessingContext &context, QgsFeatureSource *targetSource,
118  QgsFeatureSource *intersectSource,
119  const QList< int > &selectedPredicates,
120  const std::function < void( const QgsFeature & ) > &handleFeatureFunction,
121  bool onlyRequireTargetIds,
122  QgsProcessingFeedback *feedback,
123  const QgsFeatureIds &skipTargetFeatureIds )
124 {
125  if ( intersectSource->hasSpatialIndex() == QgsFeatureSource::SpatialIndexNotPresent )
126  feedback->pushWarning( QObject::tr( "No spatial index exists for intersect layer, performance will be severely degraded" ) );
127 
128  QgsFeatureIds foundSet;
130  if ( onlyRequireTargetIds )
131  request.setNoAttributes();
132 
133  QgsFeatureIterator fIt = targetSource->getFeatures( request );
134  double step = targetSource->featureCount() > 0 ? 100.0 / targetSource->featureCount() : 1;
135  int current = 0;
136  QgsFeature f;
137  std::unique_ptr< QgsGeometryEngine > engine;
138  while ( fIt.nextFeature( f ) )
139  {
140  if ( feedback->isCanceled() )
141  break;
142 
143  // don't check features in skipTargetFeatureIds
144  if ( skipTargetFeatureIds.contains( f.id() ) )
145  continue;
146  if ( !f.hasGeometry() )
147  continue;
148 
149  engine.reset();
150 
151  QgsRectangle bbox = f.geometry().boundingBox();
152  request = QgsFeatureRequest().setFilterRect( bbox ).setNoAttributes().setDestinationCrs( targetSource->sourceCrs(), context.transformContext() );
153 
154  QgsFeatureIterator testFeatureIt = intersectSource->getFeatures( request );
155  QgsFeature testFeature;
156  bool isMatch = false;
157  bool isDisjoint = true;
158  while ( testFeatureIt.nextFeature( testFeature ) )
159  {
160  if ( feedback->isCanceled() )
161  break;
162 
163  if ( !engine )
164  {
165  engine.reset( QgsGeometry::createGeometryEngine( f.geometry().constGet() ) );
166  engine->prepareGeometry();
167  }
168 
169  for ( int predicate : selectedPredicates )
170  {
171  switch ( static_cast< Predicate>( predicate ) )
172  {
173  case Intersects:
174  isMatch = engine->intersects( testFeature.geometry().constGet() );
175  break;
176  case Contains:
177  isMatch = engine->contains( testFeature.geometry().constGet() );
178  break;
179  case Disjoint:
180  if ( engine->intersects( testFeature.geometry().constGet() ) )
181  {
182  isDisjoint = false;
183  }
184  break;
185  case IsEqual:
186  isMatch = engine->isEqual( testFeature.geometry().constGet() );
187  break;
188  case Touches:
189  isMatch = engine->touches( testFeature.geometry().constGet() );
190  break;
191  case Overlaps:
192  isMatch = engine->overlaps( testFeature.geometry().constGet() );
193  break;
194  case Within:
195  isMatch = engine->within( testFeature.geometry().constGet() );
196  break;
197  case Crosses:
198  isMatch = engine->crosses( testFeature.geometry().constGet() );
199  break;
200  }
201 
202  if ( isMatch )
203  break;
204  }
205 
206  if ( isMatch )
207  {
208  foundSet.insert( f.id() );
209  handleFeatureFunction( f );
210  break;
211  }
212  }
213  if ( isDisjoint && selectedPredicates.contains( Disjoint ) )
214  {
215  foundSet.insert( f.id() );
216  handleFeatureFunction( f );
217  }
218 
219  current += 1;
220  feedback->setProgress( current * step );
221  }
222 }
223 
224 void QgsLocationBasedAlgorithm::processByIteratingOverIntersectSource( const QgsProcessingContext &context, QgsFeatureSource *targetSource,
225  QgsFeatureSource *intersectSource,
226  const QList< int > &selectedPredicates,
227  const std::function < void( const QgsFeature & ) > &handleFeatureFunction,
228  bool onlyRequireTargetIds,
229  QgsProcessingFeedback *feedback,
230  const QgsFeatureIds &skipTargetFeatureIds )
231 {
233  feedback->pushWarning( QObject::tr( "No spatial index exists for input layer, performance will be severely degraded" ) );
234 
235  // build a list of 'reversed' predicates, because in this function
236  // we actually test the reverse of what the user wants (allowing us
237  // to prepare geometries and optimise the algorithm)
238  QList< Predicate > predicates;
239  predicates.reserve( selectedPredicates.count() );
240  for ( int i : selectedPredicates )
241  {
242  predicates << reversePredicate( static_cast< Predicate >( i ) );
243  }
244 
245  QgsFeatureIds disjointSet;
246  if ( predicates.contains( Disjoint ) )
247  disjointSet = targetSource->allFeatureIds();
248 
249  QgsFeatureIds foundSet;
251  QgsFeatureIterator fIt = intersectSource->getFeatures( request );
252  double step = intersectSource->featureCount() > 0 ? 100.0 / intersectSource->featureCount() : 1;
253  int current = 0;
254  QgsFeature f;
255  std::unique_ptr< QgsGeometryEngine > engine;
256  while ( fIt.nextFeature( f ) )
257  {
258  if ( feedback->isCanceled() )
259  break;
260 
261  if ( !f.hasGeometry() )
262  continue;
263 
264  engine.reset();
265 
266  QgsRectangle bbox = f.geometry().boundingBox();
267  request = QgsFeatureRequest().setFilterRect( bbox );
268  if ( onlyRequireTargetIds )
269  request.setNoAttributes();
270 
271  QgsFeatureIterator testFeatureIt = targetSource->getFeatures( request );
272  QgsFeature testFeature;
273  while ( testFeatureIt.nextFeature( testFeature ) )
274  {
275  if ( feedback->isCanceled() )
276  break;
277 
278  if ( skipTargetFeatureIds.contains( testFeature.id() ) )
279  {
280  // don't check features in skipTargetFeatureIds
281  continue;
282  }
283  if ( foundSet.contains( testFeature.id() ) )
284  {
285  // already added this one, no need for further tests
286  continue;
287  }
288  if ( predicates.count() == 1 && predicates.at( 0 ) == Disjoint && !disjointSet.contains( testFeature.id() ) )
289  {
290  // calculating only the disjoint set, and we've already eliminated this feature so no need for further tests
291  continue;
292  }
293 
294  if ( !engine )
295  {
296  engine.reset( QgsGeometry::createGeometryEngine( f.geometry().constGet() ) );
297  engine->prepareGeometry();
298  }
299 
300  bool isMatch = false;
301 
302  for ( Predicate predicate : std::as_const( predicates ) )
303  {
304  switch ( predicate )
305  {
306  case Intersects:
307  isMatch = engine->intersects( testFeature.geometry().constGet() );
308  break;
309  case Contains:
310  isMatch = engine->contains( testFeature.geometry().constGet() );
311  break;
312  case Disjoint:
313  if ( engine->intersects( testFeature.geometry().constGet() ) )
314  {
315  disjointSet.remove( testFeature.id() );
316  }
317  break;
318  case IsEqual:
319  isMatch = engine->isEqual( testFeature.geometry().constGet() );
320  break;
321  case Touches:
322  isMatch = engine->touches( testFeature.geometry().constGet() );
323  break;
324  case Overlaps:
325  isMatch = engine->overlaps( testFeature.geometry().constGet() );
326  break;
327  case Within:
328  isMatch = engine->within( testFeature.geometry().constGet() );
329  break;
330  case Crosses:
331  isMatch = engine->crosses( testFeature.geometry().constGet() );
332  break;
333  }
334  if ( isMatch )
335  break;
336  }
337 
338  if ( isMatch )
339  {
340  foundSet.insert( testFeature.id() );
341  handleFeatureFunction( testFeature );
342  }
343 
344  }
345 
346  current += 1;
347  feedback->setProgress( current * step );
348  }
349 
350  if ( predicates.contains( Disjoint ) )
351  {
352  disjointSet = disjointSet.subtract( foundSet );
353  QgsFeatureRequest disjointReq = QgsFeatureRequest().setFilterFids( disjointSet );
354  if ( onlyRequireTargetIds )
356  QgsFeatureIterator disjointIt = targetSource->getFeatures( disjointReq );
357  QgsFeature f;
358  while ( disjointIt.nextFeature( f ) )
359  {
360  handleFeatureFunction( f );
361  }
362  }
363 }
364 
365 
366 //
367 // QgsSelectByLocationAlgorithm
368 //
369 
370 void QgsSelectByLocationAlgorithm::initAlgorithm( const QVariantMap & )
371 {
372  QStringList methods = QStringList() << QObject::tr( "creating new selection" )
373  << QObject::tr( "adding to current selection" )
374  << QObject::tr( "selecting within current selection" )
375  << QObject::tr( "removing from current selection" );
376 
377  addParameter( new QgsProcessingParameterVectorLayer( QStringLiteral( "INPUT" ), QObject::tr( "Select features from" ),
378  QList< int >() << QgsProcessing::TypeVectorAnyGeometry ) );
379  addPredicateParameter();
380  addParameter( new QgsProcessingParameterFeatureSource( QStringLiteral( "INTERSECT" ),
381  QObject::tr( "By comparing to the features from" ),
382  QList< int >() << QgsProcessing::TypeVectorAnyGeometry ) );
383 
384  addParameter( new QgsProcessingParameterEnum( QStringLiteral( "METHOD" ),
385  QObject::tr( "Modify current selection by" ),
386  methods, false, 0 ) );
387 }
388 
389 QString QgsSelectByLocationAlgorithm::name() const
390 {
391  return QStringLiteral( "selectbylocation" );
392 }
393 
394 QgsProcessingAlgorithm::Flags QgsSelectByLocationAlgorithm::flags() const
395 {
397 }
398 
399 QString QgsSelectByLocationAlgorithm::displayName() const
400 {
401  return QObject::tr( "Select by location" );
402 }
403 
404 QStringList QgsSelectByLocationAlgorithm::tags() const
405 {
406  return QObject::tr( "select,intersects,intersecting,disjoint,touching,within,contains,overlaps,relation" ).split( ',' );
407 }
408 
409 QString QgsSelectByLocationAlgorithm::group() const
410 {
411  return QObject::tr( "Vector selection" );
412 }
413 
414 QString QgsSelectByLocationAlgorithm::groupId() const
415 {
416  return QStringLiteral( "vectorselection" );
417 }
418 
419 QString QgsSelectByLocationAlgorithm::shortHelpString() const
420 {
421  return QObject::tr( "This algorithm creates a selection in a vector layer. The criteria for selecting "
422  "features is based on the spatial relationship between each feature and the features in an additional layer." );
423 }
424 
425 QgsSelectByLocationAlgorithm *QgsSelectByLocationAlgorithm::createInstance() const
426 {
427  return new QgsSelectByLocationAlgorithm();
428 }
429 
430 QVariantMap QgsSelectByLocationAlgorithm::processAlgorithm( const QVariantMap &parameters, QgsProcessingContext &context, QgsProcessingFeedback *feedback )
431 {
432  QgsVectorLayer *selectLayer = parameterAsVectorLayer( parameters, QStringLiteral( "INPUT" ), context );
433  if ( !selectLayer )
434  throw QgsProcessingException( QObject::tr( "Could not load source layer for INPUT" ) );
435 
436  Qgis::SelectBehavior method = static_cast< Qgis::SelectBehavior >( parameterAsEnum( parameters, QStringLiteral( "METHOD" ), context ) );
437  std::unique_ptr< QgsFeatureSource > intersectSource( parameterAsSource( parameters, QStringLiteral( "INTERSECT" ), context ) );
438  if ( !intersectSource )
439  throw QgsProcessingException( invalidSourceError( parameters, QStringLiteral( "INTERSECT" ) ) );
440 
441  const QList< int > selectedPredicates = parameterAsEnums( parameters, QStringLiteral( "PREDICATE" ), context );
442 
443  QgsFeatureIds selectedIds;
444  auto addToSelection = [&]( const QgsFeature & feature )
445  {
446  selectedIds.insert( feature.id() );
447  };
448  switch ( method )
449  {
452  {
453  // When subsetting or removing we only need to check already selected features
454  std::unique_ptr< QgsVectorLayerSelectedFeatureSource > selectLayerSelected( new QgsVectorLayerSelectedFeatureSource( selectLayer ) );
455  process( context, selectLayerSelected.get(), intersectSource.get(), selectedPredicates, addToSelection, true, feedback );
456  break;
457  }
459  // When adding we can skip checking already selected features
460  process( context, selectLayer, intersectSource.get(), selectedPredicates, addToSelection, true, feedback, selectLayer->selectedFeatureIds() );
461  break;
463  process( context, selectLayer, intersectSource.get(), selectedPredicates, addToSelection, true, feedback );
464  break;
465  }
466 
467  selectLayer->selectByIds( selectedIds, method );
468  QVariantMap results;
469  results.insert( QStringLiteral( "OUTPUT" ), parameters.value( QStringLiteral( "INPUT" ) ) );
470  return results;
471 }
472 
473 
474 //
475 // QgsExtractByLocationAlgorithm
476 //
477 
478 void QgsExtractByLocationAlgorithm::initAlgorithm( const QVariantMap & )
479 {
480  addParameter( new QgsProcessingParameterFeatureSource( QStringLiteral( "INPUT" ),
481  QObject::tr( "Extract features from" ),
482  QList< int >() << QgsProcessing::TypeVectorAnyGeometry ) );
483  addPredicateParameter();
484  addParameter( new QgsProcessingParameterFeatureSource( QStringLiteral( "INTERSECT" ),
485  QObject::tr( "By comparing to the features from" ),
486  QList< int >() << QgsProcessing::TypeVectorAnyGeometry ) );
487 
488  addParameter( new QgsProcessingParameterFeatureSink( QStringLiteral( "OUTPUT" ), QObject::tr( "Extracted (location)" ) ) );
489 }
490 
491 QString QgsExtractByLocationAlgorithm::name() const
492 {
493  return QStringLiteral( "extractbylocation" );
494 }
495 
496 QString QgsExtractByLocationAlgorithm::displayName() const
497 {
498  return QObject::tr( "Extract by location" );
499 }
500 
501 QStringList QgsExtractByLocationAlgorithm::tags() const
502 {
503  return QObject::tr( "extract,filter,intersects,intersecting,disjoint,touching,within,contains,overlaps,relation" ).split( ',' );
504 }
505 
506 QString QgsExtractByLocationAlgorithm::group() const
507 {
508  return QObject::tr( "Vector selection" );
509 }
510 
511 QString QgsExtractByLocationAlgorithm::groupId() const
512 {
513  return QStringLiteral( "vectorselection" );
514 }
515 
516 QString QgsExtractByLocationAlgorithm::shortHelpString() const
517 {
518  return QObject::tr( "This algorithm creates a new vector layer that only contains matching features from an "
519  "input layer. The criteria for adding features to the resulting layer is defined "
520  "based on the spatial relationship between each feature and the features in an additional layer." );
521 }
522 
523 QgsExtractByLocationAlgorithm *QgsExtractByLocationAlgorithm::createInstance() const
524 {
525  return new QgsExtractByLocationAlgorithm();
526 }
527 
528 QVariantMap QgsExtractByLocationAlgorithm::processAlgorithm( const QVariantMap &parameters, QgsProcessingContext &context, QgsProcessingFeedback *feedback )
529 {
530  std::unique_ptr< QgsFeatureSource > input( parameterAsSource( parameters, QStringLiteral( "INPUT" ), context ) );
531  if ( !input )
532  throw QgsProcessingException( invalidSourceError( parameters, QStringLiteral( "INPUT" ) ) );
533  std::unique_ptr< QgsFeatureSource > intersectSource( parameterAsSource( parameters, QStringLiteral( "INTERSECT" ), context ) );
534  if ( !intersectSource )
535  throw QgsProcessingException( invalidSourceError( parameters, QStringLiteral( "INTERSECT" ) ) );
536 
537  const QList< int > selectedPredicates = parameterAsEnums( parameters, QStringLiteral( "PREDICATE" ), context );
538  QString dest;
539  std::unique_ptr< QgsFeatureSink > sink( parameterAsSink( parameters, QStringLiteral( "OUTPUT" ), context, dest, input->fields(), input->wkbType(), input->sourceCrs() ) );
540 
541  if ( !sink )
542  throw QgsProcessingException( invalidSinkError( parameters, QStringLiteral( "OUTPUT" ) ) );
543 
544  auto addToSink = [&]( const QgsFeature & feature )
545  {
546  QgsFeature f = feature;
547  if ( !sink->addFeature( f, QgsFeatureSink::FastInsert ) )
548  throw QgsProcessingException( writeFeatureError( sink.get(), parameters, QStringLiteral( "OUTPUT" ) ) );
549  };
550  process( context, input.get(), intersectSource.get(), selectedPredicates, addToSink, false, feedback );
551 
552  QVariantMap results;
553  results.insert( QStringLiteral( "OUTPUT" ), dest );
554  return results;
555 }
556 
558 
559 
QgsFeatureRequest::NoGeometry
@ NoGeometry
Geometry is not required. It may still be returned if e.g. required for a filter condition.
Definition: qgsfeaturerequest.h:115
QgsFeedback::setProgress
void setProgress(double progress)
Sets the current progress for the feedback object.
Definition: qgsfeedback.h:76
QgsVectorLayer::selectByIds
Q_INVOKABLE void selectByIds(const QgsFeatureIds &ids, Qgis::SelectBehavior behavior=Qgis::SelectBehavior::SetSelection)
Selects matching features using a list of feature IDs.
Definition: qgsvectorlayer.cpp:572
QgsFeatureSource::hasSpatialIndex
virtual SpatialIndexPresence hasSpatialIndex() const
Returns an enum value representing the presence of a valid spatial index on the source,...
Definition: qgsfeaturesource.cpp:190
QgsFeatureSource::sourceCrs
virtual QgsCoordinateReferenceSystem sourceCrs() const =0
Returns the coordinate reference system for features in the source.
QgsProcessingFeedback
Base class for providing feedback from a processing algorithm.
Definition: qgsprocessingfeedback.h:37
QgsFeatureSource::SpatialIndexNotPresent
@ SpatialIndexNotPresent
No spatial index exists for the source.
Definition: qgsfeaturesource.h:190
QgsFeature::geometry
QgsGeometry geometry
Definition: qgsfeature.h:71
QgsFeedback::isCanceled
bool isCanceled() const SIP_HOLDGIL
Tells whether the operation has been canceled already.
Definition: qgsfeedback.h:67
QgsFeatureSource
An interface for objects which provide features via a getFeatures method.
Definition: qgsfeaturesource.h:37
Qgis::SelectBehavior::AddToSelection
@ AddToSelection
Add selection to current selection.
QgsProcessingParameterFeatureSource
An input feature source (such as vector layers) parameter for processing algorithms.
Definition: qgsprocessingparameters.h:3057
Qgis::SelectBehavior::IntersectSelection
@ IntersectSelection
Modify current selection to include only select features which match.
QgsRectangle
A rectangle specified with double values.
Definition: qgsrectangle.h:41
QgsProcessingParameterFeatureSink
A feature sink output for processing algorithms.
Definition: qgsprocessingparameters.h:3219
QgsFeatureSource::allFeatureIds
virtual QgsFeatureIds allFeatureIds() const
Returns a list of all feature IDs for features present in the source.
Definition: qgsfeaturesource.cpp:115
QgsFeatureRequest::setFilterRect
QgsFeatureRequest & setFilterRect(const QgsRectangle &rectangle)
Sets the rectangle from which features will be taken.
Definition: qgsfeaturerequest.cpp:101
QgsFeature::id
QgsFeatureId id
Definition: qgsfeature.h:68
QgsFeatureRequest
This class wraps a request for features to a vector layer (or directly its vector data provider).
Definition: qgsfeaturerequest.h:83
qgsgeometryengine.h
QgsVectorLayerSelectedFeatureSource
QgsFeatureSource subclass for the selected features from a QgsVectorLayer.
Definition: qgsvectorlayerfeatureiterator.h:345
QgsProcessingContext
Contains information about the context in which a processing algorithm is executed.
Definition: qgsprocessingcontext.h:46
QgsVectorLayer::selectedFeatureIds
const Q_INVOKABLE QgsFeatureIds & selectedFeatureIds() const
Returns a list of the selected features IDs in this layer.
Definition: qgsvectorlayer.cpp:3621
QgsProcessing::TypeVectorAnyGeometry
@ TypeVectorAnyGeometry
Any vector layer with geometry.
Definition: qgsprocessing.h:48
QgsFeatureSource::getFeatures
virtual QgsFeatureIterator getFeatures(const QgsFeatureRequest &request=QgsFeatureRequest()) const =0
Returns an iterator for the features in the source.
QgsFeatureSource::featureCount
virtual long long featureCount() const =0
Returns the number of features contained in the source, or -1 if the feature count is unknown.
QgsFeatureRequest::setFilterFids
QgsFeatureRequest & setFilterFids(const QgsFeatureIds &fids)
Sets the feature IDs that should be fetched.
Definition: qgsfeaturerequest.cpp:148
qgsvectorlayerfeatureiterator.h
QgsProcessingContext::transformContext
QgsCoordinateTransformContext transformContext() const
Returns the coordinate transform context.
Definition: qgsprocessingcontext.h:165
QgsProcessingParameterVectorLayer
A vector layer (with or without geometry) parameter for processing algorithms. Consider using the mor...
Definition: qgsprocessingparameters.h:2827
QgsFeatureRequest::setNoAttributes
QgsFeatureRequest & setNoAttributes()
Set that no attributes will be fetched.
Definition: qgsfeaturerequest.cpp:235
QgsGeometry::constGet
const QgsAbstractGeometry * constGet() const SIP_HOLDGIL
Returns a non-modifiable (const) reference to the underlying abstract geometry primitive.
Definition: qgsgeometry.cpp:136
QgsFeatureIds
QSet< QgsFeatureId > QgsFeatureIds
Definition: qgsfeatureid.h:37
qgsvectorlayer.h
Qgis::SelectBehavior
SelectBehavior
Specifies how a selection should be applied.
Definition: qgis.h:777
QgsGeometry::createGeometryEngine
static QgsGeometryEngine * createGeometryEngine(const QgsAbstractGeometry *geometry)
Creates and returns a new geometry engine representing the specified geometry.
Definition: qgsgeometry.cpp:3972
QgsProcessingAlgorithm::FlagNoThreading
@ FlagNoThreading
Algorithm is not thread safe and cannot be run in a background thread, e.g. for algorithms which mani...
Definition: qgsprocessingalgorithm.h:76
QgsFeatureIterator::nextFeature
bool nextFeature(QgsFeature &f)
Definition: qgsfeatureiterator.h:399
QgsVectorLayer
Represents a vector layer which manages a vector based data sets.
Definition: qgsvectorlayer.h:391
QgsFeature::hasGeometry
bool hasGeometry() const
Returns true if the feature has an associated geometry.
Definition: qgsfeature.cpp:230
qgsalgorithmextractbylocation.h
QgsProcessingAlgorithm::FlagNotAvailableInStandaloneTool
@ FlagNotAvailableInStandaloneTool
Algorithm should not be available from the standalone "qgis_process" tool. Used to flag algorithms wh...
Definition: qgsprocessingalgorithm.h:83
QgsGeometry::boundingBox
QgsRectangle boundingBox() const
Returns the bounding box of the geometry.
Definition: qgsgeometry.cpp:1080
Qgis::SelectBehavior::SetSelection
@ SetSelection
Set selection, removing any existing selection.
QgsFeature
The feature class encapsulates a single feature including its unique ID, geometry and a list of field...
Definition: qgsfeature.h:55
QgsFeatureRequest::setDestinationCrs
QgsFeatureRequest & setDestinationCrs(const QgsCoordinateReferenceSystem &crs, const QgsCoordinateTransformContext &context)
Sets the destination crs for feature's geometries.
Definition: qgsfeaturerequest.cpp:301
QgsProcessingParameterEnum
An enum based parameter for processing algorithms, allowing for selection from predefined values.
Definition: qgsprocessingparameters.h:2540
QgsProcessingAlgorithm::flags
virtual Flags flags() const
Returns the flags indicating how and when the algorithm operates and should be exposed to users.
Definition: qgsprocessingalgorithm.cpp:90
Qgis::SelectBehavior::RemoveFromSelection
@ RemoveFromSelection
Remove from current selection.
QgsFeatureIterator
Wrapper for iterator of features from vector data provider or vector layer.
Definition: qgsfeatureiterator.h:289
QgsFeatureRequest::setFlags
QgsFeatureRequest & setFlags(QgsFeatureRequest::Flags flags)
Sets flags that affect how features will be fetched.
Definition: qgsfeaturerequest.cpp:222
QgsProcessingException
Custom exception class for processing related exceptions.
Definition: qgsexception.h:82
QgsProcessingFeedback::pushWarning
virtual void pushWarning(const QString &warning)
Pushes a warning informational message from the algorithm.
Definition: qgsprocessingfeedback.cpp:68
QgsFeatureSink::FastInsert
@ FastInsert
Use faster inserts, at the cost of updating the passed features to reflect changes made at the provid...
Definition: qgsfeaturesink.h:70