31
31
from qgis .PyQt .QtGui import QIcon
32
32
from qgis .PyQt .QtCore import QVariant
33
33
34
- from qgis .core import QgsField , QgsFeature , QgsGeometry , QgsPointXY , QgsWkbTypes , QgsProcessingUtils , QgsFeatureSink , QgsFields
34
+ from qgis .core import (QgsField ,
35
+ QgsFeature ,
36
+ QgsGeometry ,
37
+ QgsPointXY ,
38
+ QgsWkbTypes ,
39
+ QgsFeatureRequest ,
40
+ QgsFeatureSink ,
41
+ QgsFields ,
42
+ QgsProcessing ,
43
+ QgsProcessingParameterFeatureSink ,
44
+ QgsProcessingParameterField ,
45
+ QgsProcessingParameterFeatureSource ,
46
+ QgsProcessingException )
35
47
36
48
from processing .algs .qgis .QgisAlgorithm import QgisAlgorithm
37
- from processing .core .GeoAlgorithmExecutionException import GeoAlgorithmExecutionException
38
- from processing .core .parameters import ParameterTableField
39
- from processing .core .parameters import ParameterVector
40
- from processing .core .outputs import OutputVector
41
- from processing .tools import dataobjects , vector
49
+ from processing .tools import vector
42
50
43
51
pluginPath = os .path .split (os .path .split (os .path .dirname (__file__ ))[0 ])[0 ]
44
52
45
53
46
54
class MeanCoords (QgisAlgorithm ):
47
-
48
- POINTS = 'POINTS'
55
+ INPUT = 'INPUT'
49
56
WEIGHT = 'WEIGHT'
50
57
OUTPUT = 'OUTPUT'
51
58
UID = 'UID'
@@ -61,19 +68,19 @@ def __init__(self):
61
68
super ().__init__ ()
62
69
63
70
def initAlgorithm (self , config = None ):
64
- self .addParameter (ParameterVector (self .POINTS ,
65
- self .tr ('Input layer' )))
66
- self .addParameter (ParameterTableField (self .WEIGHT ,
67
- self . tr ( 'Weight field' ) ,
68
- MeanCoords . POINTS ,
69
- ParameterTableField . DATA_TYPE_NUMBER ,
70
- optional = True ))
71
- self .addParameter ( ParameterTableField ( self . UID ,
72
- self . tr ( 'Unique ID field' ) ,
73
- MeanCoords . POINTS ,
74
- optional = True ))
75
-
76
- self . addOutput ( OutputVector ( MeanCoords . OUTPUT , self . tr ( 'Mean coordinates' ), datatype = [ dataobjects . TYPE_VECTOR_POINT ] ))
71
+ self .addParameter (QgsProcessingParameterFeatureSource (self .INPUT ,
72
+ self .tr ('Input layer' )))
73
+ self .addParameter (QgsProcessingParameterField (self .WEIGHT , self . tr ( 'Weight field' ) ,
74
+ parentLayerParameterName = MeanCoords . INPUT ,
75
+ type = QgsProcessingParameterField . Numeric ,
76
+ optional = True ))
77
+ self . addParameter ( QgsProcessingParameterField ( self . UID ,
78
+ self .tr ( 'Unique ID field' ) ,
79
+ parentLayerParameterName = MeanCoords . INPUT ,
80
+ optional = True ))
81
+
82
+ self . addParameter ( QgsProcessingParameterFeatureSink ( MeanCoords . OUTPUT , self . tr ( 'Mean coordinates' ),
83
+ QgsProcessing . TypeVectorPoint ))
77
84
78
85
def name (self ):
79
86
return 'meancoordinates'
@@ -82,46 +89,58 @@ def displayName(self):
82
89
return self .tr ('Mean coordinate(s)' )
83
90
84
91
def processAlgorithm (self , parameters , context , feedback ):
85
- layer = QgsProcessingUtils .mapLayerFromString (self .getParameterValue (self .POINTS ), context )
86
- weightField = self .getParameterValue (self .WEIGHT )
87
- uniqueField = self .getParameterValue (self .UID )
92
+ source = self .parameterAsSource (parameters , self .INPUT , context )
93
+
94
+ weight_field = self .parameterAsString (parameters , self .WEIGHT , context )
95
+ unique_field = self .parameterAsString (parameters , self .UID , context )
88
96
89
- if weightField is None :
90
- weightIndex = - 1
97
+ attributes = []
98
+ if not weight_field :
99
+ weight_index = - 1
91
100
else :
92
- weightIndex = layer .fields ().lookupField (weightField )
101
+ weight_index = source .fields ().lookupField (weight_field )
102
+ if weight_index >= 0 :
103
+ attributes .append (weight_index )
93
104
94
- if uniqueField is None :
95
- uniqueIndex = - 1
105
+ if not unique_field :
106
+ unique_index = - 1
96
107
else :
97
- uniqueIndex = layer .fields ().lookupField (uniqueField )
108
+ unique_index = source .fields ().lookupField (unique_field )
109
+ if unique_index >= 0 :
110
+ attributes .append (unique_index )
98
111
99
- fieldList = QgsFields ()
100
- fieldList .append (QgsField ('MEAN_X' , QVariant .Double , '' , 24 , 15 ))
101
- fieldList .append (QgsField ('MEAN_Y' , QVariant .Double , '' , 24 , 15 ))
102
- fieldList .append (QgsField ('UID' , QVariant .String , '' , 255 ))
112
+ field_list = QgsFields ()
113
+ field_list .append (QgsField ('MEAN_X' , QVariant .Double , '' , 24 , 15 ))
114
+ field_list .append (QgsField ('MEAN_Y' , QVariant .Double , '' , 24 , 15 ))
115
+ if unique_index >= 0 :
116
+ field_list .append (QgsField ('UID' , QVariant .String , '' , 255 ))
103
117
104
- writer = self .getOutputFromName (self .OUTPUT ).getVectorWriter (fieldList , QgsWkbTypes .Point , layer .crs (), context )
118
+ (sink , dest_id ) = self .parameterAsSink (parameters , self .OUTPUT , context ,
119
+ field_list , QgsWkbTypes .Point , source .sourceCrs ())
105
120
106
- features = QgsProcessingUtils .getFeatures (layer , context )
107
- total = 100.0 / layer .featureCount () if layer .featureCount () else 0
121
+ features = source .getFeatures (QgsFeatureRequest (). setSubsetOfAttributes ( attributes ) )
122
+ total = 100.0 / source .featureCount () if source .featureCount () else 0
108
123
means = {}
109
124
for current , feat in enumerate (features ):
125
+ if feedback .isCanceled ():
126
+ break
127
+
110
128
feedback .setProgress (int (current * total ))
111
- if uniqueIndex == - 1 :
129
+ if unique_index == - 1 :
112
130
clazz = "Single class"
113
131
else :
114
- clazz = str (feat .attributes ()[uniqueIndex ]).strip ()
115
- if weightIndex == - 1 :
132
+ clazz = str (feat .attributes ()[unique_index ]).strip ()
133
+ if weight_index == - 1 :
116
134
weight = 1.00
117
135
else :
118
136
try :
119
- weight = float (feat .attributes ()[weightIndex ])
137
+ weight = float (feat .attributes ()[weight_index ])
120
138
except :
121
139
weight = 1.00
122
140
123
141
if weight < 0 :
124
- raise GeoAlgorithmExecutionException (self .tr ('Negative weight value found. Please fix your data and try again.' ))
142
+ raise QgsProcessingException (
143
+ self .tr ('Negative weight value found. Please fix your data and try again.' ))
125
144
126
145
if clazz not in means :
127
146
means [clazz ] = (0 , 0 , 0 )
@@ -138,15 +157,21 @@ def processAlgorithm(self, parameters, context, feedback):
138
157
current = 0
139
158
total = 100.0 / len (means ) if means else 1
140
159
for (clazz , values ) in list (means .items ()):
160
+ if feedback .isCanceled ():
161
+ break
162
+
141
163
outFeat = QgsFeature ()
142
164
cx = values [0 ] / values [2 ]
143
165
cy = values [1 ] / values [2 ]
144
166
meanPoint = QgsPointXY (cx , cy )
145
167
146
168
outFeat .setGeometry (QgsGeometry .fromPoint (meanPoint ))
147
- outFeat .setAttributes ([cx , cy , clazz ])
148
- writer .addFeature (outFeat , QgsFeatureSink .FastInsert )
169
+ attributes = [cx , cy ]
170
+ if unique_index >= 0 :
171
+ attributes .append (clazz )
172
+ outFeat .setAttributes (attributes )
173
+ sink .addFeature (outFeat , QgsFeatureSink .FastInsert )
149
174
current += 1
150
175
feedback .setProgress (int (current * total ))
151
176
152
- del writer
177
+ return { self . OUTPUT : dest_id }
0 commit comments