36 changes: 36 additions & 0 deletions src/core/qgscacheindexfeatureid.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
/***************************************************************************
qgscacheindexfeatureid.h
--------------------------------------
Date : 13.2.2013
Copyright : (C) 2013 Matthias Kuhn
Email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/

#ifndef QGSCACHEINDEXFEATUREID_H
#define QGSCACHEINDEXFEATUREID_H

#include "qgscacheindex.h"

class QgsCachedVectorLayer;

class QgsCacheIndexFeatureId : public QgsAbstractCacheIndex
{
public:
QgsCacheIndexFeatureId( QgsCachedVectorLayer* cachedVectorLayer );

signals:

public slots:

private:
QgsCachedVectorLayer* C;
};

#endif // QGSCACHEINDEXFEATUREID_H
1 change: 1 addition & 0 deletions src/core/qgsfeature.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ email : sherman at mrcc.com
#include <QList>
#include <QHash>
#include <QVector>
#include <QSet>

class QgsGeometry;
class QgsRectangle;
Expand Down
39 changes: 39 additions & 0 deletions src/core/qgsgeometrycache.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
#include "qgsgeometrycache.h"

#include "qgsvectorlayereditbuffer.h"

QgsGeometryCache::QgsGeometryCache(QgsVectorLayer* layer)
: L(layer)
{
}

QgsGeometryCache::~QgsGeometryCache()
{
// Destroy any cached geometries and clear the references to them
deleteCachedGeometries();
}

bool QgsGeometryCache::geometry(QgsFeatureId fid, QgsGeometry& geometry)
{
// no need to check changed geometries because all changed geometries are also cached

// first time this geometry has changed since last commit
if ( !mCachedGeometries.contains( fid ) )
return false;

geometry = mCachedGeometries[fid];
return true;
}

void QgsGeometryCache::cacheGeometry( QgsFeatureId fid, const QgsGeometry& geom )
{
mCachedGeometries[fid] = geom;
}


void QgsGeometryCache::deleteCachedGeometries()
{
// Destroy any cached geometries
mCachedGeometries.clear();
mCachedGeometriesRect = QgsRectangle();
}
46 changes: 46 additions & 0 deletions src/core/qgsgeometrycache.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
#ifndef QGSGEOMETRYCACHE_H
#define QGSGEOMETRYCACHE_H

#include "qgsfeature.h"

#include "qgsvectorlayer.h"

class QgsGeometryCache
{
public:
QgsGeometryCache(QgsVectorLayer* layer);
~QgsGeometryCache();

inline QgsGeometryMap& cachedGeometries() { return mCachedGeometries; }

//! fetch geometry from cache, return true if successful
bool geometry(QgsFeatureId fid, QgsGeometry& geometry);

//! store a geometry in the cache
void cacheGeometry( QgsFeatureId fid, const QgsGeometry& geom );

//! get rid of the cached geometry
void removeGeometry( QgsFeatureId fid ) { mCachedGeometries.remove(fid); }


/** Deletes the geometries in mCachedGeometries */
void deleteCachedGeometries();

void setCachedGeometriesRect( const QgsRectangle& extent ) { mCachedGeometriesRect = extent; }
const QgsRectangle& cachedGeometriesRect() { return mCachedGeometriesRect; }

protected:

inline QgsVectorLayerEditBuffer* editBuffer() { return L->editBuffer(); }

QgsVectorLayer* L;

/** cache of the committed geometries retrieved *for the current display* */
QgsGeometryMap mCachedGeometries;

/** extent for which there are cached geometries */
QgsRectangle mCachedGeometriesRect;

};

#endif // QGSGEOMETRYCACHE_H
13 changes: 6 additions & 7 deletions src/core/qgsvectorlayer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@
#include "qgsrendercontext.h"
#include "qgscoordinatereferencesystem.h"
#include "qgsvectordataprovider.h"
#include "qgsvectorlayercache.h"
#include "qgsgeometrycache.h"
#include "qgsvectorlayereditbuffer.h"
#include "qgsvectorlayereditutils.h"
#include "qgsvectorlayerfeatureiterator.h"
Expand Down Expand Up @@ -100,8 +100,7 @@ QgsVectorLayer::QgsVectorLayer( QString vectorLayerPath,
, mLabel( 0 )
, mLabelOn( false )
, mVertexMarkerOnlyForSelection( false )
, mEditorLayout( GeneratedLayout )
, mCache( new QgsVectorLayerCache( this ) )
, mCache( new QgsGeometryCache( this ) )
, mEditBuffer( 0 )
, mJoinBuffer( 0 )
, mDiagramRenderer( 0 )
Expand Down Expand Up @@ -1256,7 +1255,7 @@ void QgsVectorLayer::invertSelection()
emit selectionChanged();
}

void QgsVectorLayer::invertSelectionInRectangle( QgsRectangle &rect )
void QgsVectorLayer::invertSelectionInRectangle( QgsRectangle & rect )
{
// normalize the rectangle
rect.normalize();
Expand Down Expand Up @@ -3091,8 +3090,8 @@ bool QgsVectorLayer::rollBack( bool deleteBuffer )

if ( deleteBuffer )
{
delete mEditBuffer;
mEditBuffer = 0;
delete mEditBuffer;
mEditBuffer = 0;
undoStack()->clear();
}
emit editingStopped();
Expand Down Expand Up @@ -4144,7 +4143,7 @@ QString QgsVectorLayer::metadata()
{
myMetadata += "<tr><td>";
myMetadata += tr( "Primary key attributes: " );
foreach ( int idx, pkAttrList )
foreach( int idx, pkAttrList )
{
myMetadata += pendingFields()[ idx ].name() + " ";
}
Expand Down
6 changes: 3 additions & 3 deletions src/core/qgsvectorlayer.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ class QgsVectorLayerJoinBuffer;
class QgsFeatureRendererV2;
class QgsDiagramRendererV2;
class QgsDiagramLayerSettings;
class QgsVectorLayerCache;
class QgsGeometryCache;
class QgsVectorLayerEditBuffer;
class QgsSymbolV2;

Expand Down Expand Up @@ -855,7 +855,7 @@ class CORE_EXPORT QgsVectorLayer : public QgsMapLayer

QString metadata();

inline QgsVectorLayerCache* cache() { return mCache; }
inline QgsGeometryCache* cache() { return mCache; }

signals:

Expand Down Expand Up @@ -1066,7 +1066,7 @@ class CORE_EXPORT QgsVectorLayer : public QgsMapLayer
QString mAnnotationForm;

//! cache for some vector layer data - currently only geometries for faster editing
QgsVectorLayerCache* mCache;
QgsGeometryCache* mCache;

//! stores information about uncommitted changes to layer
QgsVectorLayerEditBuffer* mEditBuffer;
Expand Down
293 changes: 269 additions & 24 deletions src/core/qgsvectorlayercache.cpp
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
/***************************************************************************
qgsvectorlayercache.cpp
---------------------
begin : Dezember 2012
copyright : (C) 2012 by Martin Dobias
email : wonder dot sk at gmail dot com
qgsvectorlayercache.cpp
Cache features of a vector layer
-------------------
begin : January 2013
copyright : (C) Matthias Kuhn
email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
Expand All @@ -12,42 +14,285 @@
* (at your option) any later version. *
* *
***************************************************************************/

#include "qgsvectorlayercache.h"
#include "qgscacheindex.h"
#include "qgscachedfeatureiterator.h"

QgsVectorLayerCache::QgsVectorLayerCache( QgsVectorLayer* layer, int cacheSize, QObject* parent ) :
QObject( parent ),
mLayer( layer )
{
mCache.setMaxCost( cacheSize );

connect( mLayer, SIGNAL( featureDeleted( QgsFeatureId ) ), SLOT( featureDeleted( QgsFeatureId ) ) );
connect( mLayer, SIGNAL( featureAdded( QgsFeatureId ) ), SLOT( featureAdded( QgsFeatureId ) ) );

#include "qgsvectorlayereditbuffer.h"
setCacheGeometry( true );
setCacheSubsetOfAttributes( mLayer->pendingAllAttributesList() );
setCacheAddedAttributes( true );

QgsVectorLayerCache::QgsVectorLayerCache( QgsVectorLayer* layer )
: L( layer )
connect( mLayer, SIGNAL( attributeDeleted( int ) ), SLOT( attributeDeleted( int ) ) );
connect( mLayer, SIGNAL( attributeValueChanged( QgsFeatureId, int, const QVariant& ) ), SLOT( attributeValueChanged( QgsFeatureId, int, const QVariant& ) ) );
}

void QgsVectorLayerCache::setCacheSize( int cacheSize )
{
mCache.setMaxCost( cacheSize );
}

QgsVectorLayerCache::~QgsVectorLayerCache()
int QgsVectorLayerCache::cacheSize()
{
// Destroy any cached geometries and clear the references to them
deleteCachedGeometries();
return mCache.maxCost();
}

bool QgsVectorLayerCache::geometry( QgsFeatureId fid, QgsGeometry& geometry )
void QgsVectorLayerCache::setCacheGeometry( bool cacheGeometry )
{
// no need to check changed geometries because all changed geometries are also cached
mCacheGeometry = cacheGeometry;
if ( cacheGeometry )
{
connect( mLayer, SIGNAL( geometryChanged( QgsFeatureId, QgsGeometry& ) ), SLOT( geometryChanged( QgsFeatureId, QgsGeometry& ) ) );
}
else
{
disconnect( mLayer, SIGNAL( geometryChanged( QgsFeatureId, QgsGeometry& ) ), this, SLOT( geometryChanged( QgsFeatureId, QgsGeometry& ) ) );
}
}

// first time this geometry has changed since last commit
if ( !mCachedGeometries.contains( fid ) )
return false;
void QgsVectorLayerCache::setCacheSubsetOfAttributes( const QgsAttributeList& attributes )
{
mCachedAttributes = attributes;
}

geometry = mCachedGeometries[fid];
return true;
void QgsVectorLayerCache::setFullCache( bool fullCache )
{
mFullCache = fullCache;

if ( mFullCache )
{
// Add a little more than necessary...
setCacheSize( mLayer->featureCount() + 100 );

// Initialize the cache...
QgsFeatureIterator it = getFeatures( QgsFeatureRequest()
.setSubsetOfAttributes( mCachedAttributes )
.setFlags( !mCacheGeometry ? QgsFeatureRequest::NoGeometry : QgsFeatureRequest::Flags( 0 ) ) );

int i = 0;

QTime t;
t.start();

QgsFeature f;
while ( it.nextFeature( f ) )
{
++i;

if ( t.elapsed() > 1000 )
{
bool cancel = false;
emit progress( i, cancel );
if ( cancel )
break;

t.restart();
}
}

it.close();
}
}

void QgsVectorLayerCache::setCacheAddedAttributes( bool cacheAddedAttributes )
{
if ( cacheAddedAttributes )
{
connect( mLayer, SIGNAL( attributeAdded( int ) ), SLOT( attributeAdded( int ) ) );
}
else
{
disconnect( mLayer, SIGNAL( attributeAdded( int ) ), this, SLOT( attributeAdded( int ) ) );
}
}

bool QgsVectorLayerCache::featureAtId( QgsFeatureId featureId, QgsFeature& feature, bool skipCache )
{
bool featureFound = false;

QgsCachedFeature* cachedFeature = NULL;

if ( !skipCache )
{
cachedFeature = mCache[ featureId ];
}

if ( cachedFeature != NULL )
{
feature = QgsFeature( *cachedFeature->feature() );
featureFound = true;
}
else if ( mLayer->getFeatures( QgsFeatureRequest()
.setFilterFid( featureId )
.setSubsetOfAttributes( mCachedAttributes )
.setFlags( !mCacheGeometry ? QgsFeatureRequest::NoGeometry : QgsFeatureRequest::Flags( 0 ) ) )
.nextFeature( feature ) )
{
cacheFeature( feature );
featureFound = true;
}

return featureFound;
}

void QgsVectorLayerCache::cacheGeometry( QgsFeatureId fid, const QgsGeometry& geom )
bool QgsVectorLayerCache::removeCachedFeature( QgsFeatureId fid )
{
mCachedGeometries[fid] = geom;
return mCache.remove( fid );
}

QgsVectorLayer* QgsVectorLayerCache::layer()
{
return mLayer;
}

void QgsVectorLayerCache::deleteCachedGeometries()
void QgsVectorLayerCache::requestCompleted( QgsFeatureRequest featureRequest, QgsFeatureIds fids )
{
// Destroy any cached geometries
mCachedGeometries.clear();
mCachedGeometriesRect = QgsRectangle();
// If a request is too large for the cache don't notify to prevent from indexing incomplete requests
if ( fids.count() < mCache.size() )
{
foreach( QgsAbstractCacheIndex* idx, mCacheIndices )
{
idx->requestCompleted( featureRequest, fids );
}
}
}

void QgsVectorLayerCache::featureRemoved( QgsFeatureId fid )
{
foreach( QgsAbstractCacheIndex* idx, mCacheIndices )
{
idx->flushFeature( fid );
}
}

void QgsVectorLayerCache::attributeValueChanged( QgsFeatureId fid, int field, const QVariant& value )
{
QgsCachedFeature* cachedFeat = mCache[ fid ];

if ( NULL != cachedFeat )
{
cachedFeat->mFeature->setAttribute( field, value );
}
}

void QgsVectorLayerCache::featureDeleted( QgsFeatureId fid )
{
mCache.remove( fid );
}

void QgsVectorLayerCache::featureAdded( QgsFeatureId fid )
{
if ( mFullCache )
{
if ( cacheSize() <= mLayer->featureCount() )
{
setCacheSize( mLayer->featureCount() + 100 );
}

QgsFeature feat;
featureAtId( fid, feat );
}
}

void QgsVectorLayerCache::attributeAdded( int field )
{
Q_UNUSED( field )
mCachedAttributes.append( field );
mCache.clear();
}

void QgsVectorLayerCache::attributeDeleted( int field )
{
foreach ( QgsFeatureId fid, mCache.keys() )
{
mCache[ fid ]->mFeature->deleteAttribute( field );
}
}

void QgsVectorLayerCache::geometryChanged( QgsFeatureId fid, QgsGeometry& geom )
{
QgsCachedFeature* cachedFeat = mCache[ fid ];

if ( cachedFeat != NULL )
{
cachedFeat->mFeature->setGeometry( geom );
}
}

QgsFeatureIterator QgsVectorLayerCache::getFeatures( const QgsFeatureRequest &featureRequest )
{
QgsFeatureIterator it;
bool requiresWriterIt = true; // If a not yet cached, but cachable request is made, this stays true.

if ( checkInformationCovered( featureRequest ) )
{
// Check if an index is able to deliver the requested features
foreach( QgsAbstractCacheIndex *idx, mCacheIndices )
{
QgsFeatureIds featureIds;

if ( idx->getCachedIds( featureIds, featureRequest ) )
{
it = QgsFeatureIterator( new QgsCachedFeatureIterator( this, featureRequest, featureIds ) );
requiresWriterIt = false;
break;
}
}
}
else
{
// Let the layer answer the request, so no caching of requests
// we don't want to cache is done
requiresWriterIt = false;
it = mLayer->getFeatures( featureRequest );
}

if ( requiresWriterIt )
{
// No index was able to satisfy the request
it = QgsFeatureIterator( new QgsCachedFeatureWriterIterator( this, featureRequest ) );
}

return it;
}

bool QgsVectorLayerCache::checkInformationCovered( const QgsFeatureRequest& featureRequest )
{
QgsAttributeList requestedAttributes;

if ( false == featureRequest.flags().testFlag( QgsFeatureRequest::SubsetOfAttributes ) )
{
requestedAttributes = mLayer->pendingAllAttributesList();
}
else
{
requestedAttributes = featureRequest.subsetOfAttributes();
}

// Check if we even cache the information requested
foreach ( int attr, requestedAttributes )
{
if ( !mCachedAttributes.contains( attr ) )
{
return false;
}
}

// If the request needs geometry but we don't cache this...
if ( false == featureRequest.flags().testFlag( QgsFeatureRequest::NoGeometry )
&& false == mCacheGeometry )
{
return false;
}

return true;
}
261 changes: 221 additions & 40 deletions src/core/qgsvectorlayercache.h
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
/***************************************************************************
qgsvectorlayercache.h
---------------------
begin : Dezember 2012
copyright : (C) 2012 by Martin Dobias
email : wonder dot sk at gmail dot com
qgsvectorlayercache.h
Cache features of a vector layer
-------------------
begin : January 2013
copyright : (C) Matthias Kuhn
email : matthias dot kuhn at gmx dot ch
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
Expand All @@ -12,49 +14,228 @@
* (at your option) any later version. *
* *
***************************************************************************/
#ifndef QGSVECTORLAYERCACHE_H
#define QGSVECTORLAYERCACHE_H

#include "qgsfeature.h"

#include "qgsvectorlayer.h"

class QgsVectorLayerCache
{
public:
QgsVectorLayerCache( QgsVectorLayer* layer );
~QgsVectorLayerCache();

inline QgsGeometryMap& cachedGeometries() { return mCachedGeometries; }
#ifndef QgsVectorLayerCache_H
#define QgsVectorLayerCache_H

//! fetch geometry from cache, return true if successful
bool geometry( QgsFeatureId fid, QgsGeometry& geometry );
#include <QCache>

//! store a geometry in the cache
void cacheGeometry( QgsFeatureId fid, const QgsGeometry& geom );
#include "qgsvectorlayer.h"

//! get rid of the cached geometry
void removeGeometry( QgsFeatureId fid ) { mCachedGeometries.remove( fid ); }
class QgsCachedFeatureIterator;
class QgsAbstractCacheIndex;

/**
* This class caches features of a given QgsVectorLayer.
*
* @brief
* The cached features can be indexed by @link {QgsAbstractCacheIndex}.
*
* Proper indexing for a given use-case may speed up performance substantially.
*/

/** Deletes the geometries in mCachedGeometries */
void deleteCachedGeometries();
class CORE_EXPORT QgsVectorLayerCache : public QObject
{
Q_OBJECT

private:
/**
* This is a wrapper class around a cached @link {QgsFeature}, which will inform
* the cache, when it has been deleted, so indexes can be updated that the wrapped
* feature needs to be fetched again if needed.
*/
class QgsCachedFeature
{
public:
/**
* Will create a new cached feature.
*
* @param feat The feature to cache. A copy will be made.
* @param vlCache The cache to inform when the feature has been removed from the cache.
*/
QgsCachedFeature( const QgsFeature& feat, QgsVectorLayerCache* vlCache ) :
mCache( vlCache )
{
mFeature = new QgsFeature( feat );
}

~QgsCachedFeature()
{
// That's the reason we need this wrapper:
// Inform the cache that this feature has been removed
mCache->featureRemoved( mFeature->id() );
delete( mFeature );
}

inline const QgsFeature* feature() { return mFeature; }

private:
QgsFeature* mFeature;
QgsVectorLayerCache* mCache;

friend class QgsVectorLayerCache;
};

void setCachedGeometriesRect( const QgsRectangle& extent ) { mCachedGeometriesRect = extent; }
const QgsRectangle& cachedGeometriesRect() { return mCachedGeometriesRect; }
public:
QgsVectorLayerCache( QgsVectorLayer* layer, int cacheSize, QObject* parent = NULL );

/**
* Sets the maximum number of features to keep in the cache. Some features will be removed from
* the cache if the number is smaller than the previous size of the cache.
*
* @param cacheSize indicates the maximum number of features to keep in the cache
*/

void setCacheSize( int cacheSize );

/**
* @brief
* Returns the maximum number of features this cache will hold.
* In case full caching is enabled, this number can change, as new features get added.
*
* @return int
*/
int cacheSize();

/**
* Enable or disable the caching of geometries
*
* @param cacheGeometry Enable or disable the caching of geometries
*/
void setCacheGeometry( bool cacheGeometry );


/**
* Set the subset of attributes to be cached
*
* @param attributes The attributes to be cached
*/
void setCacheSubsetOfAttributes( const QgsAttributeList& attributes );

/**
* If this is enabled, the subset of cached attributes will automatically be extended
* to also include newly added attributes.
*
* @param cacheAddedAttributes Automatically cache new attributes
*/
void setCacheAddedAttributes( bool cacheAddedAttributes );

/**
* @brief
* This enables or disables full caching.
* If enabled, all features will be held in the cache. The cache size will incrementally
* be increased to offer space for all features.
* When enabled, all features will be read into cache. As this feature will most likely
* be used for slow data sources, be aware, that the call to this method might take a long time.
*
* @param fullCache True: enable full caching, False: disable full caching
*/
void setFullCache( bool fullCache );

/**
* @brief
* Adds a {@link QgsAbstractCacheIndex} to this cache. Cache indices know about features present
* in this cache and decide, if enough information is present in the cache to respond to a {@link QgsFeatureRequest}.
*
* @param cacheIndex The cache index to add.
*/
void addCacheIndex( const QgsAbstractCacheIndex& cacheIndex );

QgsFeatureIterator getFeatures( const QgsFeatureRequest& featureRequest );

/**
* Gets the feature at the given feature id. Considers the changed, added, deleted and permanent features
* @param featureId The id of the feature to query
* @param feature The result of the operation will be written to this feature
* @param skipCache Will query the layer regardless if the feature is in the cache already
* @return true in case of success
*/
bool featureAtId( QgsFeatureId featureId, QgsFeature &feature, bool skipCache = false );

/**
* Removes the feature identified by fid from the cache if present.
* @param fid The id of the feature to delete
* @return true if the feature was removed, false if the feature id was not found in the cache
*/
bool removeCachedFeature( QgsFeatureId fid );

/**
* Returns the layer to which this cache belongs
*/
QgsVectorLayer* layer();

protected:

inline QgsVectorLayerEditBuffer* editBuffer() { return L->editBuffer(); }

QgsVectorLayer* L;

/** cache of the committed geometries retrieved *for the current display* */
QgsGeometryMap mCachedGeometries;

/** extent for which there are cached geometries */
QgsRectangle mCachedGeometriesRect;

/**
* @brief
* Gets called, whenever the full list of feature ids for a certain request is known.
* Broadcasts this information to indices, so they can update their tables.
*
* @param featureRequest The feature request that was answered
* @param fids The feature ids that have been returned
*/
void requestCompleted( QgsFeatureRequest featureRequest, QgsFeatureIds fids );

/**
* @brief
* Gets called, whenever a feature has been removed.
* Broadcasts this information to indices, so they can invalidate their cache if required.
*
* @param fid The feature id of the removed feature.
*/
void featureRemoved( QgsFeatureId fid );

/**
* @brief
* Checks if the information required to complete the request is cached.
* i.e. If all attributes required and the geometry is held in the cache.
* Please note, that this does not check, if the requested features are cached.
*
*
* @param featureRequest The {@link QgsFeatureRequest} to be answered
* @return True if the information is being cached, false if not
*/
bool checkInformationCovered( const QgsFeatureRequest& featureRequest );


signals:

/**
* When filling the cache, this signal gets emited periodically to notify about the progress
* and to be able to cancel an operation.
*
* @param i The number of already fetched features
* @param cancel A reference to a boolean variable. Set to true and the operation will be canceled.
*/
void progress( int i, bool& cancel );

public slots:
void attributeValueChanged( QgsFeatureId fid, int field, const QVariant& value );
void featureDeleted( QgsFeatureId fid );
void featureAdded( QgsFeatureId fid );
void attributeAdded( int field );
void attributeDeleted( int field );
void geometryChanged( QgsFeatureId fid, QgsGeometry& geom );

private:

inline void cacheFeature( QgsFeature& feat )
{
QgsCachedFeature* cachedFeature = new QgsCachedFeature( feat, this );
mCache.insert( feat.id(), cachedFeature );
}

QgsVectorLayer* mLayer;
QCache< QgsFeatureId, QgsCachedFeature > mCache;

bool mCacheGeometry;
bool mFullCache;
QList<QgsAbstractCacheIndex*> mCacheIndices;

QgsAttributeList mCachedAttributes;

friend class QgsCachedFeatureIterator;
friend class QgsCachedFeatureWriterIterator;
friend class QgsCachedFeature;
};

#endif // QGSVECTORLAYERCACHE_H
#endif // QgsVectorLayerCache_H
2 changes: 1 addition & 1 deletion src/core/qgsvectorlayereditutils.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
#include "qgsvectorlayereditutils.h"

#include "qgsvectordataprovider.h"
#include "qgsvectorlayercache.h"
#include "qgsgeometrycache.h"
#include "qgsvectorlayereditbuffer.h"

#include <limits>
Expand Down
3 changes: 2 additions & 1 deletion src/core/qgsvectorlayereditutils.h
Original file line number Diff line number Diff line change
Expand Up @@ -20,13 +20,14 @@

#include "qgsvectorlayer.h"

class QgsGeometryCache;

class CORE_EXPORT QgsVectorLayerEditUtils
{
public:
QgsVectorLayerEditUtils( QgsVectorLayer* layer );

inline QgsVectorLayerCache* cache() { return L->cache(); }
inline QgsGeometryCache* cache() { return L->cache(); }


/** Insert a new vertex before the given vertex number,
Expand Down
2 changes: 1 addition & 1 deletion src/core/qgsvectorlayerundocommand.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
#include "qgsgeometry.h"
#include "qgsfeature.h"
#include "qgsvectorlayer.h"
#include "qgsvectorlayercache.h"
#include "qgsgeometrycache.h"
#include "qgsvectorlayereditbuffer.h"

#include "qgslogger.h"
Expand Down
3 changes: 2 additions & 1 deletion src/core/qgsvectorlayerundocommand.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
#include "qgsfeature.h"

class QgsGeometry;
class QgsGeometryCache;

#include "qgsvectorlayer.h"
#include "qgsvectorlayereditbuffer.h"
Expand All @@ -36,7 +37,7 @@ class QgsVectorLayerUndoCommand : public QUndoCommand
public:
QgsVectorLayerUndoCommand( QgsVectorLayerEditBuffer* buffer ) : mBuffer( buffer ) {}
inline QgsVectorLayer* layer() { return mBuffer->L; }
inline QgsVectorLayerCache* cache() { return mBuffer->L->cache(); }
inline QgsGeometryCache* cache() { return mBuffer->L->cache(); }

protected:
QgsVectorLayerEditBuffer* mBuffer;
Expand Down