26#include "moc_qgsfeaturelistview.cpp"
37 setSelectionMode( QAbstractItemView::ExtendedSelection );
39 mUpdateEditSelectionTimerWithSelection.setSingleShot(
true );
40 connect( &mUpdateEditSelectionTimerWithSelection, &QTimer::timeout,
this, [
this]() {
41 updateEditSelection(
true );
44 mUpdateEditSelectionTimerWithSelection.setInterval( 0 );
46 mUpdateEditSelectionTimerWithoutSelection.setSingleShot(
true );
47 connect( &mUpdateEditSelectionTimerWithoutSelection, &QTimer::timeout,
this, [
this]() {
48 updateEditSelection(
false );
51 mUpdateEditSelectionTimerWithoutSelection.setInterval( 0 );
64 delete mFeatureSelectionModel;
65 delete mCurrentEditSelectionModel;
67 mCurrentEditSelectionModel =
new QItemSelectionModel( mModel->
masterModel(),
this );
68 if ( !mFeatureSelectionManager )
71 mFeatureSelectionManager = mOwnedFeatureSelectionManager;
75 setSelectionModel( mFeatureSelectionModel );
77 ensureEditSelection( true );
80 if ( mItemDelegate && mItemDelegate->parent() ==
this )
87 setItemDelegate( mItemDelegate );
92 connect( mCurrentEditSelectionModel, &QItemSelectionModel::selectionChanged,
this, &QgsFeatureListView::editSelectionChanged );
94 connect(
featureListModel, &QgsFeatureListModel::rowsRemoved,
this, [
this]() { ensureEditSelection(); } );
95 connect(
featureListModel, &QgsFeatureListModel::rowsInserted,
this, [
this]() { ensureEditSelection(); } );
96 connect(
featureListModel, &QgsFeatureListModel::modelReset,
this, [
this]() { ensureEditSelection(); } );
125 const QModelIndexList selectedIndexes = mCurrentEditSelectionModel->selectedIndexes();
126 for (
const QModelIndex &idx : selectedIndexes )
136 viewport()->update( visualRegionForSelection( mCurrentEditSelectionModel->selection() ) );
141 if ( event->button() != Qt::LeftButton )
143 QListView::mousePressEvent( event );
149 const QPoint pos =
event->pos();
151 const QModelIndex index = indexAt( pos );
155 mDragMode = DragMode::MoveSelection;
156 if ( index.isValid() )
161 mDragMode = DragMode::ExpandSelection;
163 selectRow( index,
true );
169 QgsDebugError( QStringLiteral(
"No model assigned to this view" ) );
173void QgsFeatureListView::editSelectionChanged(
const QItemSelection &selected,
const QItemSelection &deselected )
175 if ( isVisible() && updatesEnabled() )
179 viewport()->update( visualRegionForSelection( localDeselected ) | visualRegionForSelection( localSelected ) );
183 if ( !selected.isEmpty() )
185 const QModelIndexList indexList = selected.indexes();
186 if ( !indexList.isEmpty() )
190 mLastEditSelectionFid = selectedFeature.
id();
194 const QItemSelection currentSelection = mCurrentEditSelectionModel->selection();
195 if ( currentSelection.size() == 1 )
197 QModelIndexList indexList = currentSelection.indexes();
198 if ( !indexList.isEmpty() )
215 QItemSelection selection;
216 selection.append( QItemSelectionRange( mModel->index( 0, 0 ), mModel->index( mModel->
rowCount() - 1, 0 ) ) );
218 mFeatureSelectionModel->
selectFeatures( selection, QItemSelectionModel::ClearAndSelect | QItemSelectionModel::Rows );
223 QItemSelection selection;
224 QModelIndex firstModelIdx;
226 const auto constFids = fids;
229 const QModelIndex modelIdx = mModel->
fidToIdx( fid );
231 if ( !firstModelIdx.isValid() )
232 firstModelIdx = modelIdx;
234 selection.append( QItemSelectionRange( mModel->
mapToMaster( modelIdx ) ) );
242 mCurrentEditSelectionModel->select( selection, QItemSelectionModel::ClearAndSelect );
243 scrollTo( firstModelIdx );
253 Q_ASSERT( index.model() == mModel->
masterModel() || !index.isValid() );
257 mCurrentEditSelectionModel->select( index, command );
264 const auto constIndexes = indexes;
265 for (
const QModelIndex &index : constIndexes )
273 setDirtyRegion( viewport()->rect() );
280 const QPoint pos =
event->pos();
281 const QModelIndex index = indexAt( pos );
285 case QgsFeatureListView::DragMode::Inactive:
288 case QgsFeatureListView::DragMode::ExpandSelection:
290 selectRow( index,
false );
294 case QgsFeatureListView::DragMode::MoveSelection:
296 if ( index.isValid() )
304 QgsDebugError( QStringLiteral(
"No model assigned to this view" ) );
310 if ( event->button() != Qt::LeftButton )
312 QListView::mouseReleaseEvent( event );
318 case QgsFeatureListView::DragMode::ExpandSelection:
319 if ( mFeatureSelectionModel )
322 case QgsFeatureListView::DragMode::Inactive:
323 case QgsFeatureListView::DragMode::MoveSelection:
327 mDragMode = DragMode::Inactive;
332 switch ( event->key() )
335 editOtherFeature( Previous );
339 editOtherFeature( Next );
343 QListView::keyPressEvent( event );
347void QgsFeatureListView::editOtherFeature( QgsFeatureListView::PositionInList positionInList )
350 if ( 0 != mCurrentEditSelectionModel->selectedIndexes().count() )
352 const QModelIndex localIndex = mModel->
mapFromMaster( mCurrentEditSelectionModel->selectedIndexes().first() );
353 currentRow = localIndex.row();
356 QModelIndex newLocalIndex;
357 QModelIndex newIndex;
359 switch ( positionInList )
362 newLocalIndex = mModel->index( 0, 0 );
366 newLocalIndex = mModel->index( currentRow - 1, 0 );
370 newLocalIndex = mModel->index( currentRow + 1, 0 );
374 newLocalIndex = mModel->index( mModel->
rowCount() - 1, 0 );
379 if ( newIndex.isValid() )
382 scrollTo( newLocalIndex );
388 const QModelIndex index = indexAt( event->pos() );
390 if ( index.isValid() )
402 menu->exec( event->globalPos() );
406void QgsFeatureListView::selectRow(
const QModelIndex &index,
bool anchor )
408 QItemSelectionModel::SelectionFlags command = selectionCommand( index );
409 const int row = index.row();
414 if ( selectionMode() != QListView::SingleSelection
415 && command.testFlag( QItemSelectionModel::Toggle ) )
418 mCtrlDragSelectionFlag = mFeatureSelectionModel->
isSelected( index )
419 ? QItemSelectionModel::Deselect
420 : QItemSelectionModel::Select;
421 command &= ~QItemSelectionModel::Toggle;
422 command |= mCtrlDragSelectionFlag;
424 command |= QItemSelectionModel::Current;
427 const QModelIndex tl = model()->index( std::min( mRowAnchor, row ), 0 );
428 const QModelIndex br = model()->index( std::max( mRowAnchor, row ), model()->columnCount() - 1 );
430 mFeatureSelectionModel->
selectFeatures( QItemSelection( tl, br ), command );
433void QgsFeatureListView::ensureEditSelection(
bool inSelection )
437 mUpdateEditSelectionTimerWithSelection.start();
441 mUpdateEditSelectionTimerWithoutSelection.start();
445void QgsFeatureListView::updateEditSelection(
bool inSelection )
455 const QModelIndexList selectedIndexes = mCurrentEditSelectionModel->selectedIndexes();
461 bool editSelectionUpdateRequested =
false;
464 bool validEditSelectionAvailable =
false;
466 if ( selectedIndexes.isEmpty() || !selectedIndexes.first().isValid() || mModel->
mapFromMaster( selectedIndexes.first() ).row() == -1 )
468 validEditSelectionAvailable =
false;
472 validEditSelectionAvailable =
true;
480 if ( !validEditSelectionAvailable )
482 editSelectionUpdateRequested =
true;
489 if ( !selectedFids.contains( mModel->
idxToFid( mModel->
mapFromMaster( selectedIndexes.first() ) ) ) )
491 editSelectionUpdateRequested =
true;
499 if ( !validEditSelectionAvailable )
500 editSelectionUpdateRequested =
true;
503 if ( editSelectionUpdateRequested )
510 int rowToSelect = -1;
520 if ( selectedFids.isEmpty() )
526 const int rowCount = mModel->
rowCount();
527 for (
int i = 0; i < rowCount; i++ )
529 if ( selectedFids.contains( mModel->
idxToFid( mModel->index( i, 0 ) ) ) )
536 if ( rowToSelect == -1 && !validEditSelectionAvailable )
542 if ( rowToSelect != -1 )
551 mFeatureSelectionManager = featureSelectionManager;
553 if ( mFeatureSelectionModel )
557 if ( mOwnedFeatureSelectionManager )
559 mOwnedFeatureSelectionManager->deleteLater();
560 mOwnedFeatureSelectionManager =
nullptr;
@ FeatureId
Get the feature id of the feature in this row.
QgsFeatureId idxToFid(const QModelIndex &index) const
Returns the feature ID corresponding to an index from the model.
int rowCount(const QModelIndex &parent=QModelIndex()) const override
bool featureByIndex(const QModelIndex &index, QgsFeature &feat)
virtual QModelIndex mapToMaster(const QModelIndex &proxyIndex) const
QModelIndex fidToIdx(QgsFeatureId fid) const
Returns the model index corresponding to a feature ID.
QString parserErrorString()
Returns a detailed message about errors while parsing a QgsExpression.
QVariant data(const QModelIndex &index, int role) const override
bool setDisplayExpression(const QString &expression)
virtual QModelIndex mapFromMaster(const QModelIndex &sourceIndex) const
QString displayExpression() const
QgsVectorLayerCache * layerCache()
Returns the vector layer cache which is being used to populate the model.
QModelIndex mapToSource(const QModelIndex &proxyIndex) const override
virtual QItemSelection mapSelectionFromMaster(const QItemSelection &selection) const
QgsAttributeTableModel * masterModel()
void setEditSelectionModel(QItemSelectionModel *editSelectionModel)
void setCurrentFeatureEdited(bool state)
void setFeatureSelectionModel(QgsFeatureSelectionModel *featureSelectionModel)
Element positionToElement(QPoint pos)
Shows a list of features and renders a edit button next to each feature.
void currentEditSelectionProgressChanged(int progress, int count)
Emitted whenever the current edit selection has been changed.
const QString displayExpression() const
Returns the expression which is currently used to render the features.
void keyPressEvent(QKeyEvent *event) override
void contextMenuEvent(QContextMenuEvent *event) override
void setCurrentFeatureEdited(bool state)
Sets if the currently shown form has received any edit events so far.
void displayExpressionChanged(const QString &expression)
Emitted whenever the display expression is successfully changed.
void mouseMoveEvent(QMouseEvent *event) override
void setEditSelection(const QgsFeatureIds &fids)
Set the feature(s) to be edited.
void setFeatureSelectionManager(QgsIFeatureSelectionManager *featureSelectionManager)
setFeatureSelectionManager
QgsFeatureIds currentEditSelection()
Gets the currentEditSelection.
void mousePressEvent(QMouseEvent *event) override
bool setDisplayExpression(const QString &displayExpression)
The display expression is an expression used to render the fields into a single string which is displ...
void selectAll() override
Select all currently visible features.
QgsVectorLayerCache * layerCache()
Returns the layer cache.
QString parserErrorString()
Returns a detailed message about errors while parsing a QgsExpression.
void mouseReleaseEvent(QMouseEvent *event) override
void willShowContextMenu(QgsActionMenu *menu, const QModelIndex &atIndex)
Emitted when the context menu is created to add the specific actions to it.
QgsFeatureListModel * featureListModel()
Gets the featureListModel used by this view.
QgsFeatureListView(QWidget *parent=nullptr)
Creates a feature list view.
virtual void setModel(QgsFeatureListModel *featureListModel)
Set the QgsFeatureListModel which is used to retrieve information.
void currentEditSelectionChanged(QgsFeature &feat)
Emitted whenever the current edit selection has been changed.
void aboutToChangeEditSelection(bool &ok)
void enableSync(bool enable)
Enables or disables synchronisation to the QgsVectorLayer When synchronisation is disabled,...
virtual void selectFeatures(const QItemSelection &selection, QItemSelectionModel::SelectionFlags command)
Select features on this table.
virtual bool isSelected(QgsFeatureId fid)
Returns the selection status of a given feature id.
virtual void setFeatureSelectionManager(QgsIFeatureSelectionManager *featureSelectionManager)
void requestRepaint()
Request a repaint of the visible items of connected views.
The feature class encapsulates a single feature including its unique ID, geometry and a list of field...
Is an interface class to abstract feature selection handling.
This class caches features of a given QgsVectorLayer.
QgsVectorLayer * layer()
Returns the layer to which this cache belongs.
Q_INVOKABLE const QgsFeatureIds & selectedFeatureIds() const
Returns a list of the selected features IDs in this layer.
void attributeValueChanged(QgsFeatureId fid, int idx, const QVariant &value)
Emitted whenever an attribute value change is done in the edit buffer.
void selectionChanged(const QgsFeatureIds &selected, const QgsFeatureIds &deselected, bool clearAndSelect)
Emitted when selection was changed.
QSet< QgsFeatureId > QgsFeatureIds
qint64 QgsFeatureId
64 bit feature ids negative numbers are used for uncommitted/newly added features
#define QgsDebugError(str)