Skip to content

Commit

Permalink
Added select() variant with QgsFeatureRequest for simpler constructio…
Browse files Browse the repository at this point in the history
…n of requests
  • Loading branch information
wonder-sk committed Oct 8, 2012
1 parent 13a6fd9 commit 70ff8ef
Show file tree
Hide file tree
Showing 11 changed files with 352 additions and 0 deletions.
1 change: 1 addition & 0 deletions python/core/core.sip
Expand Up @@ -26,6 +26,7 @@
%Include qgsdistancearea.sip
%Include qgsexpression.sip
%Include qgsfeature.sip
%Include qgsfeaturerequest.sip
%Include qgsfield.sip
%Include qgsgeometry.sip
%Include qgsgeometryvalidator.sip
Expand Down
32 changes: 32 additions & 0 deletions python/core/qgsfeaturerequest.sip
@@ -0,0 +1,32 @@

class QgsFeatureRequest
{
%TypeHeaderCode
#include <qgsfeaturerequest.h>
%End

public:
enum Flag {
NoGeometry = 0x01, //!< Do not fetch geometry
NoAttributes = 0x02, //!< Do not fetch any attributes
ExactIntersect = 0x04 //!< Use exact geometry intersection (slower) instead of bounding boxes
};
typedef QFlags<QgsFeatureRequest::Flag> Flags;

//! construct a default request: for all features get attributes and geometries
QgsFeatureRequest();

//! Set rectangle from which features will be taken. Empty rectangle removes the filter.
QgsFeatureRequest& setExtent(const QgsRectangle& rect);
const QgsRectangle& extent() const;

//! Set flags that affect how features will be fetched
QgsFeatureRequest& setFlags(Flags flags);
const Flags& flags() const;

//! Set a subset of attributes that will be fetched. Empty list means that all attributes are used.
//! To disable fetching attributes, reset the FetchAttributes flag (which is set by default)
QgsFeatureRequest& setAttributes(const QgsAttributeList& attrs);
const QgsAttributeList& attributes() const;

};
2 changes: 2 additions & 0 deletions src/core/CMakeLists.txt
Expand Up @@ -65,6 +65,7 @@ SET(QGIS_CORE_SRCS
qgsdistancearea.cpp
qgsexpression.cpp
qgsfeature.cpp
qgsfeaturerequest.cpp
qgsfield.cpp
qgsgeometry.cpp
qgsgeometryvalidator.cpp
Expand Down Expand Up @@ -352,6 +353,7 @@ SET(QGIS_CORE_HDRS
qgsexception.h
qgsexpression.h
qgsfeature.h
qgsfeaturerequest.h
qgsfield.h
qgsgeometry.h
qgshttptransaction.h
Expand Down
6 changes: 6 additions & 0 deletions src/core/qgsfeaturerequest.cpp
@@ -0,0 +1,6 @@
#include "qgsfeaturerequest.h"

QgsFeatureRequest::QgsFeatureRequest()
: mFlags( 0 )
{
}
59 changes: 59 additions & 0 deletions src/core/qgsfeaturerequest.h
@@ -0,0 +1,59 @@
#ifndef QGSFEATUREREQUEST_H
#define QGSFEATUREREQUEST_H

#include <QFlags>

#include "qgsrectangle.h"

#include <QList>
typedef QList<int> QgsAttributeList;

/**
* This class wraps a request for features to a vector layer (or directly its vector data provider).
*
* The options may be chained, e.g.:
* QgsFeatureRequest().setExtent(QgsRectangle(0,0,1,1)).setFlags(QgsFeatureRequest::ExactIntersect)
*/
class QgsFeatureRequest
{
public:
enum Flag
{
NoGeometry = 0x01, //!< Do not fetch geometry
NoAttributes = 0x02, //!< Do not fetch any attributes
ExactIntersect = 0x04 //!< Use exact geometry intersection (slower) instead of bounding boxes
};
Q_DECLARE_FLAGS( Flags, Flag )

//! construct a default request: for all features get attributes and geometries
QgsFeatureRequest();

//! Set rectangle from which features will be taken. Empty rectangle removes the filter.
QgsFeatureRequest& setExtent( const QgsRectangle& rect ) { mRect = rect; return *this; }
const QgsRectangle& extent() const { return mRect; }

//! Set flags that affect how features will be fetched
QgsFeatureRequest& setFlags( Flags flags ) { mFlags = flags; return *this; }
const Flags& flags() const { return mFlags; }

//! Set a subset of attributes that will be fetched. Empty list means that all attributes are used.
//! To disable fetching attributes, reset the FetchAttributes flag (which is set by default)
QgsFeatureRequest& setAttributes( const QgsAttributeList& attrs ) { mAttrs = attrs; return *this; }
const QgsAttributeList& attributes() const { return mAttrs; }

// TODO: maybe set attributes as a list of strings?

// TODO: in future
// void setExpression(const QString& expression);
// void setLimit(int limit);

protected:
QgsRectangle mRect;
Flags mFlags;
QgsAttributeList mAttrs;
};

Q_DECLARE_OPERATORS_FOR_FLAGS( QgsFeatureRequest::Flags )


#endif // QGSFEATUREREQUEST_H
17 changes: 17 additions & 0 deletions src/core/qgsvectordataprovider.cpp
Expand Up @@ -21,6 +21,7 @@

#include "qgsvectordataprovider.h"
#include "qgsfeature.h"
#include "qgsfeaturerequest.h"
#include "qgsfield.h"
#include "qgslogger.h"
#include "qgsmessagelog.h"
Expand All @@ -44,6 +45,22 @@ QString QgsVectorDataProvider::storageType() const
return "Generic vector file";
}


void QgsVectorDataProvider::select( const QgsFeatureRequest& request )
{
QgsAttributeList attrs;
if ( !( request.flags() & QgsFeatureRequest::NoAttributes ) )
{
attrs = request.attributes();
if ( attrs.isEmpty() ) // empty list = fetch all attributes
attrs = attributeIndexes();
}
bool fetchGeom = !( request.flags() & QgsFeatureRequest::NoGeometry );
bool exactIntersect = ( request.flags() & QgsFeatureRequest::ExactIntersect );
select( attrs, request.extent(), fetchGeom, exactIntersect );
}


long QgsVectorDataProvider::updateFeatureCount()
{
return -1;
Expand Down
7 changes: 7 additions & 0 deletions src/core/qgsvectordataprovider.h
Expand Up @@ -31,6 +31,8 @@ class QTextCodec;
typedef QList<int> QgsAttributeList;
typedef QSet<int> QgsAttributeIds;

class QgsFeatureRequest;

/** \ingroup core
* This is the base class for vector data providers.
*
Expand Down Expand Up @@ -114,6 +116,11 @@ class CORE_EXPORT QgsVectorDataProvider : public QgsDataProvider
bool fetchGeometry = true,
bool useIntersect = false ) = 0;

/** Select features based on criteria specified in the request
* @note added in 2.0
*/
virtual void select( const QgsFeatureRequest& request );

/**
* This function does nothing useful, it's kept only for compatibility.
* @todo to be removed
Expand Down
17 changes: 17 additions & 0 deletions src/core/qgsvectorlayer.cpp
Expand Up @@ -46,6 +46,7 @@
#include "qgsapplication.h"
#include "qgscoordinatetransform.h"
#include "qgsfeature.h"
#include "qgsfeaturerequest.h"
#include "qgsfield.h"
#include "qgsgeometry.h"
#include "qgslabel.h"
Expand Down Expand Up @@ -1743,6 +1744,22 @@ void QgsVectorLayer::select( QgsAttributeList attributes, QgsRectangle rect, boo
}
}


void QgsVectorLayer::select( const QgsFeatureRequest& request )
{
QgsAttributeList attrs;
if ( !( request.flags() & QgsFeatureRequest::NoAttributes ) )
{
attrs = request.attributes();
if ( attrs.isEmpty() ) // empty list = fetch all attributes
attrs = pendingAllAttributesList();
}
bool fetchGeom = !( request.flags() & QgsFeatureRequest::NoGeometry );
bool exactIntersect = ( request.flags() & QgsFeatureRequest::ExactIntersect );
select( attrs, request.extent(), fetchGeom, exactIntersect );
}


bool QgsVectorLayer::nextFeature( QgsFeature &f )
{
if ( !mFetching )
Expand Down
6 changes: 6 additions & 0 deletions src/core/qgsvectorlayer.h
Expand Up @@ -34,6 +34,7 @@ class QImage;

class QgsAttributeAction;
class QgsCoordinateTransform;
class QgsFeatureRequest;
class QgsGeometry;
class QgsGeometryVertexIndex;
class QgsMapToPixel;
Expand Down Expand Up @@ -355,6 +356,11 @@ class CORE_EXPORT QgsVectorLayer : public QgsMapLayer
bool fetchGeometry = true,
bool useIntersect = false );

/** Select features based on criteria specified in the request
* @note added in 2.0
*/
void select( const QgsFeatureRequest& request );

/**
* fetch a feature (after select)
* @param feature buffer to read the feature into
Expand Down
1 change: 1 addition & 0 deletions tests/src/core/CMakeLists.txt
Expand Up @@ -96,6 +96,7 @@ ADD_QGIS_TEST(geometrytest testqgsgeometry.cpp)
ADD_QGIS_TEST(coordinatereferencesystemtest testqgscoordinatereferencesystem.cpp)
ADD_DEPENDENCIES(qgis_coordinatereferencesystemtest synccrsdb)
ADD_QGIS_TEST(pointtest testqgspoint.cpp)
ADD_QGIS_TEST(vectordataprovidertest testqgsvectordataprovider.cpp)
ADD_QGIS_TEST(vectorlayertest testqgsvectorlayer.cpp)
ADD_QGIS_TEST(rulebasedrenderertest testqgsrulebasedrenderer.cpp)
ADD_QGIS_TEST(ziplayertest testziplayer.cpp)
Expand Down

0 comments on commit 70ff8ef

Please sign in to comment.