Skip to content
Permalink
Browse files

Resume editing when saving layer with topology checks

Fixes #28592
  • Loading branch information
m-kuhn authored and nyalldawson committed Aug 20, 2020
1 parent 4563345 commit 05d632c1aff7aaed4a9760e8071067d0bc696d99
@@ -2045,7 +2045,7 @@ Deletes a set of features from the layer (but does not commit it)
changes can be discarded by calling :py:func:`~QgsVectorLayer.rollBack`.
%End

bool commitChanges();
bool commitChanges( bool stopEditing = true );
%Docstring
Attempts to commit to the underlying data provider any buffered changes made since the
last to call to :py:func:`~QgsVectorLayer.startEditing`.
@@ -2062,6 +2062,9 @@ so if a stage fails, it can be difficult to roll back cleanly.
Therefore any error message returned by :py:func:`~QgsVectorLayer.commitErrors` also includes which stage failed so
that the user has some chance of repairing the damage cleanly.

By setting ``stopEditing`` to ``False``, the layer will stay in editing mode.
Otherwise the layer editing mode will be disabled if the commit is successful.

.. seealso:: :py:func:`startEditing`

.. seealso:: :py:func:`commitErrors`
@@ -2693,9 +2696,11 @@ Emitted when editing on this layer has started.
Emitted when edited changes have been successfully written to the data provider.
%End

void beforeCommitChanges();
void beforeCommitChanges( bool stopEditing );
%Docstring
Emitted before changes are committed to the data provider.

The ``stopEditing`` flag specifies if the editing mode shall be left after this commit.
%End

void beforeRollBack();
@@ -10853,16 +10853,12 @@ void QgisApp::saveEdits( QgsMapLayer *layer, bool leaveEditable, bool triggerRep
if ( vlayer == activeLayer() )
mSaveRollbackInProgress = true;

if ( !vlayer->commitChanges() )
if ( !vlayer->commitChanges( !leaveEditable ) )
{
mSaveRollbackInProgress = false;
commitError( vlayer );
}

if ( leaveEditable )
{
vlayer->startEditing();
}
if ( triggerRepaint )
{
vlayer->triggerRepaint();
@@ -147,7 +147,7 @@ void QgsGeometryValidationService::onFeatureDeleted( QgsVectorLayer *layer, QgsF
emit geometryCheckCompleted( layer, fid, QList<std::shared_ptr<QgsSingleGeometryCheckError>>() );
}

void QgsGeometryValidationService::onBeforeCommitChanges( QgsVectorLayer *layer )
void QgsGeometryValidationService::onBeforeCommitChanges( QgsVectorLayer *layer, bool stopEditing )
{
if ( mLayerChecks[layer].topologyChecks.empty() && !layer->allowCommit() )
{
@@ -162,7 +162,7 @@ void QgsGeometryValidationService::onBeforeCommitChanges( QgsVectorLayer *layer

mLayerChecks[layer].commitPending = true;

triggerTopologyChecks( layer );
triggerTopologyChecks( layer, stopEditing );
}
}

@@ -315,9 +315,9 @@ void QgsGeometryValidationService::enableLayerChecks( QgsVectorLayer *layer )
onFeatureDeleted( layer, fid );
} );
checkInformation.connections
<< connect( layer, &QgsVectorLayer::beforeCommitChanges, this, [this, layer]()
<< connect( layer, &QgsVectorLayer::beforeCommitChanges, this, [this, layer]( bool stopEditing )
{
onBeforeCommitChanges( layer );
onBeforeCommitChanges( layer, stopEditing );
} );
checkInformation.connections
<< connect( layer, &QgsVectorLayer::editingStopped, this, [this, layer]()
@@ -405,7 +405,7 @@ void QgsGeometryValidationService::setMessageBar( QgsMessageBar *messageBar )
mMessageBar = messageBar;
}

void QgsGeometryValidationService::triggerTopologyChecks( QgsVectorLayer *layer )
void QgsGeometryValidationService::triggerTopologyChecks( QgsVectorLayer *layer, bool stopEditing )
{
cancelTopologyCheck( layer );
clearTopologyChecks( layer );
@@ -504,7 +504,7 @@ void QgsGeometryValidationService::triggerTopologyChecks( QgsVectorLayer *layer
QFutureWatcher<void> *futureWatcher = new QFutureWatcher<void>();
futureWatcher->setFuture( future );

connect( futureWatcher, &QFutureWatcherBase::finished, this, [&allErrors, layer, feedbacks, futureWatcher, this]()
connect( futureWatcher, &QFutureWatcherBase::finished, this, [&allErrors, layer, feedbacks, futureWatcher, stopEditing, this]()
{
QgsReadWriteLocker errorLocker( mTopologyCheckLock, QgsReadWriteLocker::Read );
layer->setAllowCommit( allErrors.empty() && mLayerChecks[layer].singleFeatureCheckErrors.empty() );
@@ -524,7 +524,7 @@ void QgsGeometryValidationService::triggerTopologyChecks( QgsVectorLayer *layer
if ( allErrors.empty() && mLayerChecks[layer].singleFeatureCheckErrors.empty() && mLayerChecks[layer].commitPending )
{
mBypassChecks = true;
layer->commitChanges();
layer->commitChanges( stopEditing );
mBypassChecks = false;
mMessageBar->popWidget( mMessageBarItem );
mMessageBarItem = nullptr;
@@ -66,7 +66,7 @@ class QgsGeometryValidationService : public QObject

void fixError( QgsGeometryCheckError *error, int method );

void triggerTopologyChecks( QgsVectorLayer *layer );
void triggerTopologyChecks( QgsVectorLayer *layer, bool stopEditing );

void setMessageBar( QgsMessageBar *messageBar );

@@ -92,7 +92,7 @@ class QgsGeometryValidationService : public QObject
void onFeatureAdded( QgsVectorLayer *layer, QgsFeatureId fid );
void onGeometryChanged( QgsVectorLayer *layer, QgsFeatureId fid, const QgsGeometry &geometry );
void onFeatureDeleted( QgsVectorLayer *layer, QgsFeatureId fid );
void onBeforeCommitChanges( QgsVectorLayer *layer );
void onBeforeCommitChanges( QgsVectorLayer *layer, bool stopEditing );
void onEditingStopped( QgsVectorLayer *layer );

private:
@@ -3345,7 +3345,7 @@ QgsFeatureSource::FeatureAvailability QgsVectorLayer::hasFeatures() const
return QgsFeatureSource::FeatureAvailability::FeaturesAvailable;
}

bool QgsVectorLayer::commitChanges()
bool QgsVectorLayer::commitChanges( bool stopEditing )
{
mCommitErrors.clear();

@@ -3361,7 +3361,7 @@ bool QgsVectorLayer::commitChanges()
return false;
}

emit beforeCommitChanges();
emit beforeCommitChanges( stopEditing );

if ( !mAllowCommit )
return false;
@@ -3370,11 +3370,15 @@ bool QgsVectorLayer::commitChanges()

if ( success )
{
delete mEditBuffer;
mEditBuffer = nullptr;
if ( stopEditing )
{
delete mEditBuffer;
mEditBuffer = nullptr;
}
undoStack()->clear();
emit afterCommitChanges();
emit editingStopped();
if ( stopEditing )
emit editingStopped();
}
else
{
@@ -1921,11 +1921,14 @@ class CORE_EXPORT QgsVectorLayer : public QgsMapLayer, public QgsExpressionConte
* Therefore any error message returned by commitErrors() also includes which stage failed so
* that the user has some chance of repairing the damage cleanly.
*
* By setting \a stopEditing to FALSE, the layer will stay in editing mode.
* Otherwise the layer editing mode will be disabled if the commit is successful.
*
* \see startEditing()
* \see commitErrors()
* \see rollBack()
*/
Q_INVOKABLE bool commitChanges();
Q_INVOKABLE bool commitChanges( bool stopEditing = true );

/**
* Returns a list containing any error messages generated when attempting
@@ -2500,8 +2503,12 @@ class CORE_EXPORT QgsVectorLayer : public QgsMapLayer, public QgsExpressionConte
//! Emitted when edited changes have been successfully written to the data provider.
void editingStopped();

//! Emitted before changes are committed to the data provider.
void beforeCommitChanges();
/**
* Emitted before changes are committed to the data provider.
*
* The \a stopEditing flag specifies if the editing mode shall be left after this commit.
*/
void beforeCommitChanges( bool stopEditing );

//! Emitted before changes are rolled back.
void beforeRollBack();

0 comments on commit 05d632c

Please sign in to comment.
You can’t perform that action at this time.