Skip to content

Commit 94156de

Browse files
committed
QgsVectorLayer: delete before adding/changing features (fixes #6422)
1 parent 522bbcd commit 94156de

File tree

1 file changed

+49
-36
lines changed

1 file changed

+49
-36
lines changed

src/core/qgsvectorlayer.cpp

+49-36
Original file line numberDiff line numberDiff line change
@@ -3970,14 +3970,31 @@ bool QgsVectorLayer::commitChanges()
39703970
}
39713971
}
39723972

3973+
// collect new feature ids that weren't deleted again and forget still
3974+
// pending updates for deleted features
3975+
QHash<QgsFeatureId, int> addedFeaturesIdx;
3976+
for ( int i = 0; i < mAddedFeatures.size(); i++ )
3977+
{
3978+
const QgsFeature &f = mAddedFeatures.at( i );
3979+
if ( !mDeletedFeatureIds.remove( f.id() ) )
3980+
{
3981+
addedFeaturesIdx.insert( f.id(), i );
3982+
}
3983+
else
3984+
{
3985+
mChangedAttributeValues.remove( f.id() );
3986+
mChangedGeometries.remove( f.id() );
3987+
}
3988+
}
3989+
39733990
//
39743991
// remap changed and attributes of added features
39753992
//
39763993
bool attributeChangesOk = true;
39773994
if ( attributesChanged )
39783995
{
39793996
// map updates field indexes to names
3980-
QMap<int, QString> src;
3997+
QHash<int, QString> src;
39813998
for ( QgsFieldMap::const_iterator it = mUpdatedFields.begin(); it != mUpdatedFields.end(); it++ )
39823999
{
39834000
src[ it.key()] = it.value().name();
@@ -3987,7 +4004,7 @@ bool QgsVectorLayer::commitChanges()
39874004
const QgsFieldMap &pFields = mDataProvider->fields();
39884005

39894006
// map provider table names to field indexes
3990-
QMap<QString, int> dst;
4007+
QHash<QString, int> dst;
39914008
for ( QgsFieldMap::const_iterator it = pFields.begin(); it != pFields.end(); it++ )
39924009
{
39934010
dst[ it.value().name()] = it.key();
@@ -4019,8 +4036,8 @@ bool QgsVectorLayer::commitChanges()
40194036
}
40204037

40214038
// map updated fields to provider fields
4022-
QMap<int, int> remap;
4023-
for ( QMap<int, QString>::const_iterator it = src.begin(); it != src.end(); it++ )
4039+
QHash<int, int> remap;
4040+
for ( QHash<int, QString>::const_iterator it = src.begin(); it != src.end(); it++ )
40244041
{
40254042
if ( dst.contains( it.value() ) )
40264043
{
@@ -4060,7 +4077,7 @@ bool QgsVectorLayer::commitChanges()
40604077
QgsFieldMap attributes;
40614078

40624079
// update private field map
4063-
for ( QMap<int, int>::iterator it = remap.begin(); it != remap.end(); it++ )
4080+
for ( QHash<int, int>::iterator it = remap.begin(); it != remap.end(); it++ )
40644081
attributes[ it.value()] = mUpdatedFields[ it.key()];
40654082

40664083
mUpdatedFields = attributes;
@@ -4088,21 +4105,42 @@ bool QgsVectorLayer::commitChanges()
40884105
}
40894106
}
40904107

4108+
//
4109+
// delete features
4110+
//
4111+
if ( mDeletedFeatureIds.size() > 0 )
4112+
{
4113+
if (( cap & QgsVectorDataProvider::DeleteFeatures ) && mDataProvider->deleteFeatures( mDeletedFeatureIds ) )
4114+
{
4115+
mCommitErrors << tr( "SUCCESS: %n feature(s) deleted.", "deleted features count", mDeletedFeatureIds.size() );
4116+
foreach ( const QgsFeatureId &id, mDeletedFeatureIds )
4117+
{
4118+
mChangedAttributeValues.remove( id );
4119+
mChangedGeometries.remove( id );
4120+
}
4121+
4122+
emit committedFeaturesRemoved( id(), mDeletedFeatureIds );
4123+
4124+
mDeletedFeatureIds.clear();
4125+
}
4126+
else
4127+
{
4128+
mCommitErrors << tr( "ERROR: %n feature(s) not deleted.", "not deleted features count", mDeletedFeatureIds.size() );
4129+
success = false;
4130+
}
4131+
}
4132+
40914133
//
40924134
// add features
40934135
//
40944136
if ( mAddedFeatures.size() > 0 )
40954137
{
4096-
for ( int i = 0; i < mAddedFeatures.size(); i++ )
4138+
foreach ( int i, addedFeaturesIdx.values() )
40974139
{
40984140
QgsFeature &f = mAddedFeatures[i];
40994141

4100-
if ( mDeletedFeatureIds.contains( f.id() ) )
4142+
if ( mDeletedFeatureIds.remove( f.id() ) )
41014143
{
4102-
mDeletedFeatureIds.remove( f.id() );
4103-
4104-
if ( mChangedGeometries.contains( f.id() ) )
4105-
mChangedGeometries.remove( f.id() );
41064144

41074145
mAddedFeatures.removeAt( i-- );
41084146
continue;
@@ -4174,31 +4212,6 @@ bool QgsVectorLayer::commitChanges()
41744212
}
41754213
}
41764214

4177-
//
4178-
// delete features
4179-
//
4180-
if ( mDeletedFeatureIds.size() > 0 )
4181-
{
4182-
if (( cap & QgsVectorDataProvider::DeleteFeatures ) && mDataProvider->deleteFeatures( mDeletedFeatureIds ) )
4183-
{
4184-
mCommitErrors << tr( "SUCCESS: %n feature(s) deleted.", "deleted features count", mDeletedFeatureIds.size() );
4185-
for ( QgsFeatureIds::const_iterator it = mDeletedFeatureIds.begin(); it != mDeletedFeatureIds.end(); it++ )
4186-
{
4187-
mChangedAttributeValues.remove( *it );
4188-
mChangedGeometries.remove( *it );
4189-
}
4190-
4191-
emit committedFeaturesRemoved( id(), mDeletedFeatureIds );
4192-
4193-
mDeletedFeatureIds.clear();
4194-
}
4195-
else
4196-
{
4197-
mCommitErrors << tr( "ERROR: %n feature(s) not deleted.", "not deleted features count", mDeletedFeatureIds.size() );
4198-
success = false;
4199-
}
4200-
}
4201-
42024215
if ( !success )
42034216
{
42044217
if ( mDataProvider->hasErrors() )

0 commit comments

Comments
 (0)