QgsAttributeTableModel::QgsAttributeTableModel( QgsVectorLayerCache *layerCache, QObject *parent ) : QAbstractTableModel( parent ) , mLayerCache( layerCache ) , mCachedField( -1 ) { QgsDebugMsg( "entered." ); if ( layerCache->layer()->geometryType() == QGis::NoGeometry ) { mFeatureRequest.setFlags( QgsFeatureRequest::NoGeometry ); } mFeat.setFeatureId( std::numeric_limits<int>::min() ); if ( !layer()->hasGeometryType() ) mFeatureRequest.setFlags( QgsFeatureRequest::NoGeometry ); loadAttributes(); connect( mLayerCache, SIGNAL( attributeValueChanged( QgsFeatureId, int, const QVariant& ) ), this, SLOT( attributeValueChanged( QgsFeatureId, int, const QVariant& ) ) ); connect( layer(), SIGNAL( featureDeleted( QgsFeatureId ) ), this, SLOT( featureDeleted( QgsFeatureId ) ) ); connect( layer(), SIGNAL( attributeDeleted( int ) ), this, SLOT( attributeDeleted( int ) ) ); connect( layer(), SIGNAL( updatedFields() ), this, SLOT( updatedFields() ) ); connect( layer(), SIGNAL( editCommandEnded() ), this, SLOT( editCommandEnded() ) ); connect( mLayerCache, SIGNAL( featureAdded( QgsFeatureId ) ), this, SLOT( featureAdded( QgsFeatureId ) ) ); connect( mLayerCache, SIGNAL( cachedLayerDeleted() ), this, SLOT( layerDeleted() ) ); }
void QgsSelectedFeature::setSelectedFeature( QgsFeatureId featureId, QgsVectorLayer* vlayer, QgsMapCanvas* canvas ) { mFeatureId = featureId; mVlayer = vlayer; mCanvas = canvas; delete mRubberBand; mRubberBand = 0; delete mGeometry; mGeometry = 0; // signal changing of current layer connect( QgisApp::instance()->legend(), SIGNAL( currentLayerChanged( QgsMapLayer* ) ), this, SLOT( currentLayerChanged( QgsMapLayer* ) ) ); // feature was deleted connect( mVlayer, SIGNAL( featureDeleted( QgsFeatureId ) ), this, SLOT( featureDeleted( QgsFeatureId ) ) ); // projection or extents changed connect( canvas->mapRenderer(), SIGNAL( destinationSrsChanged() ), this, SLOT( updateVertexMarkersPosition() ) ); connect( canvas, SIGNAL( extentsChanged() ), this, SLOT( updateVertexMarkersPosition() ) ); // geometry was changed connect( mVlayer, SIGNAL( geometryChanged( QgsFeatureId, QgsGeometry & ) ), this, SLOT( geometryChanged( QgsFeatureId, QgsGeometry & ) ) ); replaceVertexMap(); }
void QgsSelectedFeature::setSelectedFeature( QgsFeatureId featureId, QgsVectorLayer* vlayer, QgsMapCanvas* canvas ) { mFeatureId = featureId; mVlayer = vlayer; mCanvas = canvas; delete mGeometry; mGeometry = nullptr; // signal changing of current layer connect( QgisApp::instance()->layerTreeView(), SIGNAL( currentLayerChanged( QgsMapLayer* ) ), this, SLOT( currentLayerChanged( QgsMapLayer* ) ) ); // feature was deleted connect( mVlayer, SIGNAL( featureDeleted( QgsFeatureId ) ), this, SLOT( featureDeleted( QgsFeatureId ) ) ); // rolling back connect( mVlayer, SIGNAL( beforeRollBack() ), this, SLOT( beforeRollBack() ) ); // projection or extents changed connect( canvas, SIGNAL( destinationCrsChanged() ), this, SLOT( updateVertexMarkersPosition() ) ); connect( canvas, SIGNAL( extentsChanged() ), this, SLOT( updateVertexMarkersPosition() ) ); // geometry was changed connect( mVlayer, SIGNAL( geometryChanged( QgsFeatureId, QgsGeometry & ) ), this, SLOT( geometryChanged( QgsFeatureId, QgsGeometry & ) ) ); replaceVertexMap(); }
bool QgsVirtualLayerProvider::loadSourceLayers() { Q_FOREACH ( const QgsVirtualLayerDefinition::SourceLayer &layer, mDefinition.sourceLayers() ) { if ( layer.isReferenced() ) { QgsMapLayer *l = QgsMapLayerRegistry::instance()->mapLayer( layer.reference() ); if ( !l ) { PROVIDER_ERROR( QString( "Cannot find layer %1" ).arg( layer.reference() ) ); return false; } if ( l->type() != QgsMapLayer::VectorLayer ) { PROVIDER_ERROR( QString( "Layer %1 is not a vector layer" ).arg( layer.reference() ) ); return false; } // add the layer to the list QgsVectorLayer* vl = static_cast<QgsVectorLayer*>( l ); mLayers << SourceLayer( vl, layer.name() ); // connect to modification signals to invalidate statistics connect( vl, SIGNAL( featureAdded( QgsFeatureId ) ), this, SLOT( invalidateStatistics() ) ); connect( vl, SIGNAL( featureDeleted( QgsFeatureId ) ), this, SLOT( invalidateStatistics() ) ); connect( vl, SIGNAL( geometryChanged( QgsFeatureId, const QgsGeometry& ) ), this, SLOT( invalidateStatistics() ) ); } else {
void FeatureListModel::setFeatures( const QList<QgsMapToolIdentify::IdentifyResult>& results ) { beginResetModel(); qDeleteAll( mFeatures ); mFeatures.clear(); disconnect( this, SLOT( layerDeleted() ) ); Q_FOREACH( const QgsMapToolIdentify::IdentifyResult& res, results ) { Feature* f = new Feature( res.mFeature, qobject_cast<QgsVectorLayer*>( res.mLayer ) ); mFeatures.append( f ); connect( f->layer(), SIGNAL( layerDeleted() ), this, SLOT( layerDeleted() ), Qt::UniqueConnection ); connect( f->layer(), SIGNAL( featureDeleted( QgsFeatureId ) ), this, SLOT( featureDeleted( QgsFeatureId ) ), Qt::UniqueConnection ); }
void QgsIdentifyResultsDialog::addFeature( QgsVectorLayer *vlayer, const QgsFeature &f, const QMap<QString, QString> &derivedAttributes ) { QTreeWidgetItem *layItem = layerItem( vlayer ); if ( layItem == 0 ) { layItem = new QTreeWidgetItem( QStringList() << QString::number( lstResults->topLevelItemCount() ) << vlayer->name() ); layItem->setData( 0, Qt::UserRole, QVariant::fromValue( qobject_cast<QObject *>( vlayer ) ) ); lstResults->addTopLevelItem( layItem ); connect( vlayer, SIGNAL( layerDeleted() ), this, SLOT( layerDestroyed() ) ); connect( vlayer, SIGNAL( layerCrsChanged() ), this, SLOT( layerDestroyed() ) ); connect( vlayer, SIGNAL( featureDeleted( QgsFeatureId ) ), this, SLOT( featureDeleted( QgsFeatureId ) ) ); connect( vlayer, SIGNAL( attributeValueChanged( QgsFeatureId, int, const QVariant & ) ), this, SLOT( attributeValueChanged( QgsFeatureId, int, const QVariant & ) ) ); connect( vlayer, SIGNAL( editingStarted() ), this, SLOT( editingToggled() ) ); connect( vlayer, SIGNAL( editingStopped() ), this, SLOT( editingToggled() ) ); }
void QgsAttributeTableModel::attributeValueChanged( QgsFeatureId fid, int idx, const QVariant &value ) { QgsDebugMsgLevel( QString( "(%4) fid: %1, idx: %2, value: %3" ).arg( fid ).arg( idx ).arg( value.toString() ).arg( mFeatureRequest.filterType() ), 3 ); // No filter request: skip all possibly heavy checks if ( mFeatureRequest.filterType() == QgsFeatureRequest::FilterNone ) { setData( index( idToRow( fid ), fieldCol( idx ) ), value, Qt::EditRole ); } else { if ( loadFeatureAtId( fid ) ) { if ( mFeatureRequest.acceptFeature( mFeat ) ) { if ( !mIdRowMap.contains( fid ) ) { // Feature changed in such a way, it will be shown now featureAdded( fid ); } else { if ( idx == mCachedField ) mFieldCache[ fid ] = value; // Update representation setData( index( idToRow( fid ), fieldCol( idx ) ), value, Qt::EditRole ); } } else { if ( mIdRowMap.contains( fid ) ) { // Feature changed such, that it is no longer shown featureDeleted( fid ); } // else: we don't care } } } }
bool QgsVectorLayerEditBuffer::commitChanges( QStringList& commitErrors ) { QgsVectorDataProvider* provider = L->dataProvider(); commitErrors.clear(); int cap = provider->capabilities(); bool success = true; QgsFields oldFields = L->pendingFields(); // // delete attributes // bool attributesChanged = false; if ( !mDeletedAttributeIds.isEmpty() ) { if (( cap & QgsVectorDataProvider::DeleteAttributes ) && provider->deleteAttributes( mDeletedAttributeIds.toSet() ) ) { commitErrors << tr( "SUCCESS: %n attribute(s) deleted.", "deleted attributes count", mDeletedAttributeIds.size() ); emit committedAttributesDeleted( L->id(), mDeletedAttributeIds ); mDeletedAttributeIds.clear(); attributesChanged = true; } else { commitErrors << tr( "ERROR: %n attribute(s) not deleted.", "not deleted attributes count", mDeletedAttributeIds.size() ); success = false; } } // // add attributes // if ( !mAddedAttributes.isEmpty() ) { if (( cap & QgsVectorDataProvider::AddAttributes ) && provider->addAttributes( mAddedAttributes ) ) { commitErrors << tr( "SUCCESS: %n attribute(s) added.", "added attributes count", mAddedAttributes.size() ); emit committedAttributesAdded( L->id(), mAddedAttributes ); mAddedAttributes.clear(); attributesChanged = true; } else { commitErrors << tr( "ERROR: %n new attribute(s) not added", "not added attributes count", mAddedAttributes.size() ); success = false; } } // // check that addition/removal went as expected // bool attributeChangesOk = true; if ( attributesChanged ) { L->updateFields(); QgsFields newFields = L->pendingFields(); if ( oldFields.count() != newFields.count() ) { commitErrors << tr( "ERROR: the count of fields is incorrect after addition/removal of fields!" ); attributeChangesOk = false; // don't try attribute updates - they'll fail. } for ( int i = 0; i < oldFields.count(); ++i ) { const QgsField& oldField = oldFields[i]; const QgsField& newField = newFields[i]; if ( attributeChangesOk && oldField != newField ) { commitErrors << tr( "ERROR: field with index %1 is not the same!" ).arg( i ); attributeChangesOk = false; // don't try attribute updates - they'll fail. } } } if ( attributeChangesOk ) { // // change attributes // if ( !mChangedAttributeValues.isEmpty() ) { if (( cap & QgsVectorDataProvider::ChangeAttributeValues ) && provider->changeAttributeValues( mChangedAttributeValues ) ) { commitErrors << tr( "SUCCESS: %n attribute value(s) changed.", "changed attribute values count", mChangedAttributeValues.size() ); emit committedAttributeValuesChanges( L->id(), mChangedAttributeValues ); mChangedAttributeValues.clear(); } else { commitErrors << tr( "ERROR: %n attribute value change(s) not applied.", "not changed attribute values count", mChangedAttributeValues.size() ); success = false; } } // // delete features // if ( !mDeletedFeatureIds.isEmpty() ) { if (( cap & QgsVectorDataProvider::DeleteFeatures ) && provider->deleteFeatures( mDeletedFeatureIds ) ) { commitErrors << tr( "SUCCESS: %n feature(s) deleted.", "deleted features count", mDeletedFeatureIds.size() ); // TODO[MD]: we should not need this here for ( QgsFeatureIds::const_iterator it = mDeletedFeatureIds.begin(); it != mDeletedFeatureIds.end(); it++ ) { mChangedAttributeValues.remove( *it ); mChangedGeometries.remove( *it ); } emit committedFeaturesRemoved( L->id(), mDeletedFeatureIds ); mDeletedFeatureIds.clear(); } else { commitErrors << tr( "ERROR: %n feature(s) not deleted.", "not deleted features count", mDeletedFeatureIds.size() ); success = false; } } // // add features // if ( !mAddedFeatures.isEmpty() ) { if ( cap & QgsVectorDataProvider::AddFeatures ) { QList<QgsFeatureId> ids = mAddedFeatures.keys(); QgsFeatureList featuresToAdd = mAddedFeatures.values(); if ( provider->addFeatures( featuresToAdd ) ) { commitErrors << tr( "SUCCESS: %n feature(s) added.", "added features count", featuresToAdd.size() ); emit committedFeaturesAdded( L->id(), featuresToAdd ); // notify everyone that the features with temporary ids were updated with permanent ids for ( int i = 0; i < featuresToAdd.count(); ++i ) { if ( featuresToAdd[i].id() != ids[i] ) { emit featureDeleted( ids[i] ); emit featureAdded( featuresToAdd[i].id() ); } } mAddedFeatures.clear(); } else { commitErrors << tr( "ERROR: %n feature(s) not added.", "not added features count", mAddedFeatures.size() ); success = false; } } else { commitErrors << tr( "ERROR: %n feature(s) not added - provider doesn't support adding features.", "not added features count", mAddedFeatures.size() ); success = false; } } } // // update geometries // if ( !mChangedGeometries.isEmpty() ) { if (( cap & QgsVectorDataProvider::ChangeGeometries ) && provider->changeGeometryValues( mChangedGeometries ) ) { commitErrors << tr( "SUCCESS: %n geometries were changed.", "changed geometries count", mChangedGeometries.size() ); emit committedGeometriesChanges( L->id(), mChangedGeometries ); mChangedGeometries.clear(); } else { commitErrors << tr( "ERROR: %n geometries not changed.", "not changed geometries count", mChangedGeometries.size() ); success = false; } } if ( !success ) { if ( provider->hasErrors() ) { commitErrors << tr( "\n Provider errors:" ) << provider->errors(); provider->clearErrors(); } } return success; }