Skip to content

Commit a6418d6

Browse files
committedOct 4, 2012
review Export geometry info tool, sync with master
1 parent 1a67b91 commit a6418d6

File tree

2 files changed

+129
-111
lines changed

2 files changed

+129
-111
lines changed
 
Lines changed: 126 additions & 108 deletions
Original file line numberDiff line numberDiff line change
@@ -1,133 +1,151 @@
1-
from sextante.core.GeoAlgorithm import GeoAlgorithm
21
import os.path
2+
33
from PyQt4 import QtGui
44
from PyQt4.QtCore import *
5-
from PyQt4.QtGui import *
5+
66
from qgis.core import *
7-
from sextante.parameters.ParameterVector import ParameterVector
7+
8+
from sextante.core.GeoAlgorithm import GeoAlgorithm
89
from sextante.core.QGisLayers import QGisLayers
10+
11+
from sextante.parameters.ParameterVector import ParameterVector
12+
from sextante.parameters.ParameterSelection import ParameterSelection
13+
914
from sextante.outputs.OutputVector import OutputVector
1015

16+
from sextante.ftools import FToolsUtils as utils
17+
1118
class ExportGeometryInfo(GeoAlgorithm):
1219

1320
INPUT = "INPUT"
21+
METHOD = "CALC_METHOD"
1422
OUTPUT = "OUTPUT"
1523

24+
CALC_METHODS = ["Layer CRS",
25+
"Project CRS",
26+
"Ellipsoidal"
27+
]
28+
1629
def getIcon(self):
1730
return QtGui.QIcon(os.path.dirname(__file__) + "/icons/export_geometry.png")
1831

32+
def defineCharacteristics(self):
33+
self.name = "Export/Add geometry columns"
34+
self.group = "Geometry tools"
35+
36+
self.addParameter(ParameterVector(self.INPUT, "Input layer", ParameterVector.VECTOR_TYPE_ANY))
37+
self.addParameter(ParameterSelection(self.METHOD, "Calculate using", self.CALC_METHODS, 0))
38+
39+
self.addOutput(OutputVector(self.OUTPUT, "Output layer"))
40+
41+
1942
def processAlgorithm(self, progress):
20-
vlayer = QGisLayers.getObjectFromUri(self.getParameterValue(ExportGeometryInfo.INPUT))
21-
vprovider = vlayer.dataProvider()
22-
allAttrs = vprovider.attributeIndexes()
23-
vprovider.select( allAttrs )
24-
( fields, index1, index2 ) = self.checkGeometryFields(vlayer)
25-
writer = self.getOutputFromName(ExportGeometryInfo.OUTPUT).getVectorWriter(fields, vprovider.geometryType(), vprovider.crs() )
43+
layer = QGisLayers.getObjectFromUri(self.getParameterValue(self.INPUT))
44+
method = self.getParameterValue(self.METHOD)
45+
46+
output = self.getOutputValue(self.OUTPUT)
47+
48+
provider = layer.dataProvider()
49+
geometryType = layer.geometryType()
50+
51+
layer.select(layer.pendingAllAttributesList())
52+
53+
idx1 = -1
54+
idx2 = -1
55+
fields = layer.pendingFields()
56+
57+
if geometryType == QGis.Polygon:
58+
idx1, fields = utils.findOrCreateField(layer, fields, "area", 21, 6)
59+
idx2, fields = utils.findOrCreateField(layer, fields, "perimeter", 21, 6)
60+
elif geometryType == QGis.Line:
61+
idx1, fields = utils.findOrCreateField(layer, fields, "length", 21, 6)
62+
idx2 = idx1
63+
else:
64+
idx1, fields = utils.findOrCreateField(layer, fields, "xcoord", 21, 6)
65+
idx2, fields = utils.findOrCreateField(layer, fields, "ycoord", 21, 6)
66+
67+
writer = self.getOutputFromName(self.OUTPUT).getVectorWriter(fields,
68+
provider.geometryType(), provider.crs())
69+
70+
ellips = None
71+
crs = None
72+
coordTransform = None
73+
74+
# calculate with:
75+
# 0 - layer CRS
76+
# 1 - project CRS
77+
# 2 - ellipsoidal
78+
if method == 2:
79+
settings = QSettings()
80+
ellips = settings.value("/qgis/measure/ellipsoid", "WGS84").toString()
81+
crs = layer.crs().srsid()
82+
elif method == 1:
83+
mapCRS = QGisLayers.iface.mapCanvas().mapRenderer().destinationCrs()
84+
layCRS = layer.crs()
85+
coordTransform = QgsCoordinateTransform(layCRS, mapCRS)
86+
2687
inFeat = QgsFeature()
2788
outFeat = QgsFeature()
2889
inGeom = QgsGeometry()
29-
nFeat = vprovider.featureCount()
30-
nElement = 0
31-
while vprovider.nextFeature(inFeat):
32-
progress.setPercentage(int(nElement/nFeat * 100))
33-
nElement += 1
34-
inGeom = inFeat.geometry()
35-
( attr1, attr2 ) = self.simpleMeasure( inGeom )
36-
outFeat.setGeometry( inGeom )
37-
atMap = inFeat.attributeMap()
38-
outFeat.setAttributeMap( atMap )
39-
outFeat.addAttribute( index1, QVariant( attr1 ) )
40-
outFeat.addAttribute( index2, QVariant( attr2 ) )
41-
writer.addFeature( outFeat )
42-
del writer
4390

91+
current = 0
92+
total = 100.0 / float(provider.featureCount())
4493

45-
def simpleMeasure( self, inGeom ):
46-
if inGeom.wkbType() in (QGis.WKBPoint, QGis.WKBPoint25D):
47-
pt = QgsPoint()
48-
pt = inGeom.asPoint()
49-
attr1 = pt.x()
50-
attr2 = pt.y()
51-
elif inGeom.wkbType() in (QGis.WKBMultiPoint, QGis.WKBMultiPoint25D):
52-
pt = inGeom.asMultiPoint()
53-
attr1 = pt[ 0 ].x()
54-
attr2 = pt[ 0 ].y()
55-
else:
56-
measure = QgsDistanceArea()
57-
attr1 = measure.measure(inGeom)
58-
if inGeom.type() == QGis.Polygon:
59-
attr2 = self.perimMeasure( inGeom, measure )
60-
else:
61-
attr2 = attr1
62-
return ( attr1, attr2 )
63-
64-
def perimMeasure( self, inGeom, measure ):
65-
value = 0.00
66-
if inGeom.isMultipart():
67-
poly = inGeom.asMultiPolygon()
68-
for k in poly:
69-
for j in k:
70-
value = value + measure.measureLine( j )
71-
else:
72-
poly = inGeom.asPolygon()
73-
for k in poly:
74-
value = value + measure.measureLine( k )
75-
return value
94+
while layer.nextFeature(inFeat):
95+
inGeom = inFeat.geometry()
96+
97+
if method == 1:
98+
inGeom.transform(coordTransform)
99+
100+
(attr1, attr2) = self.simpleMeasure(inGeom, method, ellips, crs)
101+
102+
outFeat.setGeometry(inGeom)
103+
atMap = inFeat.attributeMap()
104+
outFeat.setAttributeMap(atMap)
105+
outFeat.addAttribute(idx1, QVariant(attr1))
106+
outFeat.addAttribute(idx2, QVariant(attr2))
107+
writer.addFeature( outFeat )
76108

77-
def checkForField( self, L, e ):
78-
e = QString( e ).toLower()
79-
fieldRange = range( 0,len( L ) )
80-
for item in fieldRange:
81-
if L[ item ].toLower() == e:
82-
return True, item
83-
return False, len( L )
84-
85-
def checkGeometryFields( self, vlayer ):
86-
vprovider = vlayer.dataProvider()
87-
nameList = []
88-
fieldList = vprovider.fields()
89-
geomType = vlayer.geometryType()
90-
for i in fieldList.keys():
91-
nameList.append( fieldList[ i ].name().toLower() )
92-
if geomType == QGis.Polygon:
93-
plp = "Poly"
94-
( found, index1 ) = self.checkForField( nameList, "AREA" )
95-
if not found:
96-
field = QgsField( "AREA", QVariant.Double, "double", 21, 6, "Polygon area" )
97-
index1 = len( fieldList.keys() )
98-
fieldList[ index1 ] = field
99-
( found, index2 ) = self.checkForField( nameList, "PERIMETER" )
100-
101-
if not found:
102-
field = QgsField( "PERIMETER", QVariant.Double, "double", 21, 6, "Polygon perimeter" )
103-
index2 = len( fieldList.keys() )
104-
fieldList[ index2 ] = field
105-
elif geomType == QGis.Line:
106-
plp = "Line"
107-
(found, index1) = self.checkForField(nameList, "LENGTH")
108-
if not found:
109-
field = QgsField("LENGTH", QVariant.Double, "double", 21, 6, "Line length" )
110-
index1 = len(fieldList.keys())
111-
fieldList[index1] = field
112-
index2 = index1
109+
current += 1
110+
progress.setPercentage(int(current * total))
111+
112+
del writer
113+
114+
def simpleMeasure(self, geom, method, ellips, crs):
115+
if geom.wkbType() in [QGis.WKBPoint, QGis.WKBPoint25D]:
116+
pt = geom.asPoint()
117+
attr1 = pt.x()
118+
attr2 = pt.y()
119+
elif geom.wkbType() in [QGis.WKBMultiPoint, QGis.WKBMultiPoint25D]:
120+
pt = inGeom.asMultiPoint()
121+
attr1 = pt[0].x()
122+
attr2 = pt[0].y()
113123
else:
114-
plp = "Point"
115-
(found, index1) = self.checkForField(nameList, "XCOORD")
116-
if not found:
117-
field = QgsField("XCOORD", QVariant.Double, "double", 21, 6, "Point x coordinate" )
118-
index1 = len(fieldList.keys())
119-
fieldList[index1] = field
120-
(found, index2) = self.checkForField(nameList, "YCOORD")
121-
if not found:
122-
field = QgsField("YCOORD", QVariant.Double, "double", 21, 6, "Point y coordinate" )
123-
index2 = len(fieldList.keys())
124-
fieldList[index2] = field
125-
return (fieldList, index1, index2)
124+
measure = QgsDistanceArea()
126125

126+
if method == 2:
127+
measure.setSourceCrs(crs)
128+
measure.setEllipsoid(ellips)
129+
measure.setProjectionsEnabled(True)
127130

128-
def defineCharacteristics(self):
129-
self.name = "Export/Add geometry columns"
130-
self.group = "Geometry tools"
131-
self.addParameter(ParameterVector(ExportGeometryInfo.INPUT, "Input layer", ParameterVector.VECTOR_TYPE_ANY))
132-
self.addOutput(OutputVector(ExportGeometryInfo.OUTPUT, "Output layer"))
133-
#=========================================================
131+
attr1 = measure.measure(geom)
132+
if geom.type() == QGis.Polygon:
133+
attr2 = self.perimMeasure(geom, measure)
134+
else:
135+
attr2 = attr1
136+
137+
return (attr1, attr2)
138+
139+
def perimMeasure(self, geom, measure):
140+
value = 0.0
141+
if geom.isMultipart():
142+
polygons = geom.asMultiPolygon()
143+
for p in polygons:
144+
for line in p:
145+
value += measure.measureLine(line)
146+
else:
147+
poly = geom.asPolygon()
148+
for r in poly:
149+
value += measure.measureLine(r)
150+
151+
return value

‎python/plugins/sextante/ftools/FToolsUtils.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,8 @@ def createSpatialIndex(provider):
77
idx = QgsSpatialIndex()
88
provider.rewind()
99
provider.select()
10-
while provider.nextFeature( ft ):
11-
idx.insertFeature( ft )
10+
while provider.nextFeature(ft):
11+
idx.insertFeature(ft)
1212
return idx
1313

1414
def createUniqueFieldName(fieldName, fieldList):
@@ -37,7 +37,7 @@ def createUniqueFieldName(fieldName, fieldList):
3737

3838
return shortName
3939

40-
def findOrCreateField(layer, fieldList, fieldName, fieldLen = 24, fieldPrec = 15):
40+
def findOrCreateField(layer, fieldList, fieldName, fieldLen=24, fieldPrec=15):
4141
idx = layer.fieldNameIndex(fieldName)
4242
if idx == -1:
4343
idx = len(fieldList)

0 commit comments

Comments
 (0)
Please sign in to comment.