void QgsOverlayAnalyzer::combineFieldLists( QgsFieldMap& fieldListA, QgsFieldMap fieldListB ) { QList<QString> names; QMap<int, QgsField>::const_iterator j = fieldListA.constBegin(); while ( j != fieldListA.constEnd() ) { names.append( j.value().name() ); ++j; } QMap<int, QgsField>::const_iterator i = fieldListB.constBegin(); int count = 0; int fcount = fieldListA.size(); QgsField field; while ( i != fieldListB.constEnd() ) { field = i.value(); while ( names.contains( field.name() ) ) { QString name = field.name(); name.append( "_" ).append( QString( count ) ); field = QgsField( name, field.type() ); ++count; } fieldListA.insert( fcount, field ); count = 0; ++fcount; ++i; } }
bool QgsGeometryAnalyzer::convexHull( QgsVectorLayer* layer, const QString& shapefileName, bool onlySelectedFeatures, int uniqueIdField, QProgressDialog* p ) { if ( !layer ) { return false; } QgsVectorDataProvider* dp = layer->dataProvider(); if ( !dp ) { return false; } bool useField = false; if ( uniqueIdField == -1 ) { uniqueIdField = 0; } else { useField = true; } QgsFieldMap fields; fields.insert( 0 , QgsField( QString( "UID" ), QVariant::String ) ); fields.insert( 1 , QgsField( QString( "AREA" ), QVariant::Double ) ); fields.insert( 2 , QgsField( QString( "PERIM" ), QVariant::Double ) ); QGis::WkbType outputType = QGis::WKBPolygon; const QgsCoordinateReferenceSystem crs = layer->crs(); QgsVectorFileWriter vWriter( shapefileName, dp->encoding(), fields, outputType, &crs ); QgsFeature currentFeature; QgsGeometry* dissolveGeometry = 0; //dissolve geometry QMultiMap<QString, QgsFeatureId> map; if ( onlySelectedFeatures ) { //use QgsVectorLayer::featureAtId const QgsFeatureIds selection = layer->selectedFeaturesIds(); QgsFeatureIds::const_iterator it = selection.constBegin(); for ( ; it != selection.constEnd(); ++it ) { #if 0 if ( p ) { p->setValue( processedFeatures ); } if ( p && p->wasCanceled() ) { // break; // it may be better to do something else here? return false; } #endif if ( !layer->featureAtId( *it, currentFeature, true, true ) ) { continue; } map.insert( currentFeature.attributeMap()[ uniqueIdField ].toString(), currentFeature.id() ); } } else { layer->select( layer->pendingAllAttributesList(), QgsRectangle(), true, false ); while ( layer->nextFeature( currentFeature ) ) { #if 0 if ( p ) { p->setValue( processedFeatures ); } if ( p && p->wasCanceled() ) { // break; // it may be better to do something else here? return false; } #endif map.insert( currentFeature.attributeMap()[ uniqueIdField ].toString(), currentFeature.id() ); } } QMultiMap<QString, QgsFeatureId>::const_iterator jt = map.constBegin(); while ( jt != map.constEnd() ) { QString currentKey = jt.key(); int processedFeatures = 0; //take only selection if ( onlySelectedFeatures ) { //use QgsVectorLayer::featureAtId const QgsFeatureIds selection = layer->selectedFeaturesIds(); if ( p ) { p->setMaximum( selection.size() ); } processedFeatures = 0; while ( jt != map.constEnd() && ( jt.key() == currentKey || !useField ) ) { if ( p && p->wasCanceled() ) { break; } if ( selection.contains( jt.value() ) ) { if ( p ) { p->setValue( processedFeatures ); } if ( !layer->featureAtId( jt.value(), currentFeature, true, true ) ) { continue; } convexFeature( currentFeature, processedFeatures, &dissolveGeometry ); ++processedFeatures; } ++jt; } QList<double> values; if ( !dissolveGeometry ) { QgsDebugMsg( "no dissolved geometry - should not happen" ); return false; } dissolveGeometry = dissolveGeometry->convexHull(); values = simpleMeasure( dissolveGeometry ); QgsAttributeMap attributeMap; attributeMap.insert( 0 , QVariant( currentKey ) ); attributeMap.insert( 1 , values[ 0 ] ); attributeMap.insert( 2 , values[ 1 ] ); QgsFeature dissolveFeature; dissolveFeature.setAttributeMap( attributeMap ); dissolveFeature.setGeometry( dissolveGeometry ); vWriter.addFeature( dissolveFeature ); } //take all features else { int featureCount = layer->featureCount(); if ( p ) { p->setMaximum( featureCount ); } processedFeatures = 0; while ( jt != map.constEnd() && ( jt.key() == currentKey || !useField ) ) { if ( p ) { p->setValue( processedFeatures ); } if ( p && p->wasCanceled() ) { break; } if ( !layer->featureAtId( jt.value(), currentFeature, true, true ) ) { continue; } convexFeature( currentFeature, processedFeatures, &dissolveGeometry ); ++processedFeatures; ++jt; } QList<double> values; // QgsGeometry* tmpGeometry = 0; if ( !dissolveGeometry ) { QgsDebugMsg( "no dissolved geometry - should not happen" ); return false; } dissolveGeometry = dissolveGeometry->convexHull(); // values = simpleMeasure( tmpGeometry ); values = simpleMeasure( dissolveGeometry ); QgsAttributeMap attributeMap; attributeMap.insert( 0 , QVariant( currentKey ) ); attributeMap.insert( 1 , QVariant( values[ 0 ] ) ); attributeMap.insert( 2 , QVariant( values[ 1 ] ) ); QgsFeature dissolveFeature; dissolveFeature.setAttributeMap( attributeMap ); dissolveFeature.setGeometry( dissolveGeometry ); vWriter.addFeature( dissolveFeature ); } } return true; }
bool QgsGeometryAnalyzer::extent( QgsVectorLayer* layer, const QString& shapefileName, bool onlySelectedFeatures, QProgressDialog * ) { if ( !layer ) { return false; } QgsVectorDataProvider* dp = layer->dataProvider(); if ( !dp ) { return false; } QGis::WkbType outputType = QGis::WKBPolygon; const QgsCoordinateReferenceSystem crs = layer->crs(); QgsFieldMap fields; fields.insert( 0 , QgsField( QString( "MINX" ), QVariant::Double ) ); fields.insert( 1 , QgsField( QString( "MINY" ), QVariant::Double ) ); fields.insert( 2 , QgsField( QString( "MAXX" ), QVariant::Double ) ); fields.insert( 3 , QgsField( QString( "MAXY" ), QVariant::Double ) ); fields.insert( 4 , QgsField( QString( "CNTX" ), QVariant::Double ) ); fields.insert( 5 , QgsField( QString( "CNTY" ), QVariant::Double ) ); fields.insert( 6 , QgsField( QString( "AREA" ), QVariant::Double ) ); fields.insert( 7 , QgsField( QString( "PERIM" ), QVariant::Double ) ); fields.insert( 8 , QgsField( QString( "HEIGHT" ), QVariant::Double ) ); fields.insert( 9 , QgsField( QString( "WIDTH" ), QVariant::Double ) ); QgsVectorFileWriter vWriter( shapefileName, dp->encoding(), fields, outputType, &crs ); QgsRectangle rect; if ( onlySelectedFeatures ) // take only selection { rect = layer->boundingBoxOfSelected(); } else { rect = layer->extent(); } double minx = rect.xMinimum(); double miny = rect.yMinimum(); double maxx = rect.xMaximum(); double maxy = rect.yMaximum(); double height = rect.height(); double width = rect.width(); double cntx = minx + ( width / 2.0 ); double cnty = miny + ( height / 2.0 ); double area = width * height; double perim = ( 2 * width ) + ( 2 * height ); QgsFeature feat; QgsAttributeMap map; map.insert( 0 , QVariant( minx ) ); map.insert( 1 , QVariant( miny ) ); map.insert( 2 , QVariant( maxx ) ); map.insert( 3 , QVariant( maxy ) ); map.insert( 4 , QVariant( cntx ) ); map.insert( 5 , QVariant( cnty ) ); map.insert( 6 , QVariant( area ) ); map.insert( 7 , QVariant( perim ) ); map.insert( 8 , QVariant( height ) ); map.insert( 9 , QVariant( width ) ); feat.setAttributeMap( map ); feat.setGeometry( QgsGeometry::fromRect( rect ) ); vWriter.addFeature( feat ); return true; }