Skip to content

Commit 74e76f9

Browse files
author
cfarmer
committed
commit missing files for new simplify implementation by alexbruy
git-svn-id: http://svn.osgeo.org/qgis/trunk/qgis@14678 c8812cc2-4d05-0410-92ff-de0c093fc19c
1 parent 67aa08e commit 74e76f9

File tree

2 files changed

+435
-0
lines changed

2 files changed

+435
-0
lines changed
+272
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,272 @@
1+
# -*- coding: utf-8 -*-
2+
3+
from PyQt4.QtCore import *
4+
from PyQt4.QtGui import *
5+
6+
from qgis.core import *
7+
from qgis.gui import *
8+
9+
import ftools_utils
10+
11+
from ui_frmSimplify import Ui_Dialog
12+
13+
class Dialog( QDialog, Ui_Dialog ):
14+
def __init__( self, iface ):
15+
QDialog.__init__( self )
16+
self.setupUi( self )
17+
self.iface = iface
18+
19+
self.simplifyThread = None
20+
21+
self.okButton = self.buttonBox.button( QDialogButtonBox.Ok )
22+
self.closeButton = self.buttonBox.button( QDialogButtonBox.Close )
23+
24+
QObject.connect( self.writeShapefileCheck, SIGNAL( "stateChanged( int )" ), self.updateGui )
25+
QObject.connect( self.btnSelectOutputFile, SIGNAL( "clicked()" ), self.selectOutputFile )
26+
27+
self.manageGui()
28+
29+
def manageGui( self ):
30+
layers = ftools_utils.getLayerNames( [ QGis.Polygon, QGis.Line ] )
31+
self.cmbInputLayer.addItems( layers )
32+
33+
def updateGui( self ):
34+
if self.writeShapefileCheck.isChecked():
35+
self.outputFileEdit.setEnabled( True )
36+
self.btnSelectOutputFile.setEnabled( True )
37+
self.addToCanvasCheck.setEnabled( True )
38+
else:
39+
self.outputFileEdit.setEnabled( False )
40+
self.btnSelectOutputFile.setEnabled( False )
41+
self.addToCanvasCheck.setEnabled( False )
42+
self.encoding = None
43+
44+
def selectOutputFile( self ):
45+
self.outputFileEdit.clear()
46+
(self.shapefileName, self.encoding) = ftools_utils.saveDialog(self)
47+
if self.shapefileName is None or self.encoding is None:
48+
return
49+
self.outputFileEdit.setText(QString(self.shapefileName))
50+
51+
def accept( self ):
52+
vLayer = ftools_utils.getVectorLayerByName( self.cmbInputLayer.currentText() )
53+
54+
QApplication.setOverrideCursor( Qt.WaitCursor )
55+
self.okButton.setEnabled( False )
56+
57+
if self.writeShapefileCheck.isChecked():
58+
outFileName = self.outputFileEdit.text()
59+
outFile = QFile( outFileName )
60+
if outFile.exists():
61+
if not QgsVectorFileWriter.deleteShapeFile( outFileName ):
62+
QmessageBox.warning( self, self.tr( "Delete error" ), self.tr( "Can't delete file %1" ).arg( outFileName ) )
63+
return
64+
self.simplifyThread = GeneralizationThread( vLayer, self.useSelectionCheck.isChecked(), self.toleranceSpin.value(), True, outFileName, self.encoding )
65+
else:
66+
self.simplifyThread = GeneralizationThread( vLayer, self.useSelectionCheck.isChecked(), self.toleranceSpin.value(), False, None, None )
67+
QObject.connect( self.simplifyThread, SIGNAL( "rangeCalculated( PyQt_PyObject )" ), self.setProgressRange )
68+
QObject.connect( self.simplifyThread, SIGNAL( "featureProcessed()" ), self.featureProcessed )
69+
QObject.connect( self.simplifyThread, SIGNAL( "generalizationFinished( PyQt_PyObject )" ), self.generalizationFinished )
70+
QObject.connect( self.simplifyThread, SIGNAL( "generalizationInterrupted()" ), self.generalizationInterrupted )
71+
72+
self.closeButton.setText( self.tr( "Cancel" ) )
73+
QObject.disconnect( self.buttonBox, SIGNAL( "rejected()" ), self.reject )
74+
QObject.connect( self.closeButton, SIGNAL( "clicked()" ), self.stopProcessing )
75+
76+
self.simplifyThread.start()
77+
78+
def setProgressRange( self, max ):
79+
self.progressBar.setRange( 0, max )
80+
81+
def featureProcessed( self ):
82+
self.progressBar.setValue( self.progressBar.value() + 1 )
83+
84+
def generalizationFinished( self, pointsCount ):
85+
self.stopProcessing()
86+
87+
QMessageBox.information( self,
88+
self.tr( "Simplify results" ),
89+
self.tr( "There were %1 vertices in original dataset which\nwere reduced to %2 vertices after simplification" )
90+
.arg( pointsCount[ 0 ] )
91+
.arg( pointsCount[ 1 ] ) )
92+
93+
self.restoreGui()
94+
if self.addToCanvasCheck.isEnabled() and self.addToCanvasCheck.isChecked():
95+
if not ftools_utils.addShapeToCanvas( unicode( self.shapefileName ) ):
96+
QMessageBox.warning( self, self.tr( "Merging" ),
97+
self.tr( "Error loading output shapefile:\n%1" )
98+
.arg( unicode( self.shapefileName ) ) )
99+
100+
self.iface.mapCanvas().refresh()
101+
#self.restoreGui()
102+
103+
def generalizationInterrupted( self ):
104+
self.restoreGui()
105+
106+
def stopProcessing( self ):
107+
if self.simplifyThread != None:
108+
self.simplifyThread.stop()
109+
self.simplifyThread = None
110+
111+
def restoreGui( self ):
112+
self.progressBar.setValue( 0 )
113+
QApplication.restoreOverrideCursor()
114+
QObject.connect( self.buttonBox, SIGNAL( "rejected()" ), self.reject )
115+
self.closeButton.setText( self.tr( "Close" ) )
116+
self.okButton.setEnabled( True )
117+
118+
def geomVertexCount( geometry ):
119+
geomType = geometry.type()
120+
if geomType == 1: # line
121+
points = geometry.asPolyline()
122+
return len( points )
123+
elif geomType == 2: # polygon
124+
polylines = geometry.asPolygon()
125+
points = []
126+
for l in polylines:
127+
points.extend( l )
128+
return len( points )
129+
else:
130+
return None
131+
132+
class GeneralizationThread( QThread ):
133+
def __init__( self, inputLayer, useSelection, tolerance, writeShape, shapePath, shapeEncoding ):
134+
QThread.__init__( self, QThread.currentThread() )
135+
self.inputLayer = inputLayer
136+
self.useSelection = useSelection
137+
self.tolerance = tolerance
138+
self.writeShape = writeShape
139+
self.outputFileName = shapePath
140+
self.outputEncoding = shapeEncoding
141+
142+
self.shapeFileWriter = None
143+
self.pointsBefore = 0
144+
self.pointsAfter = 0
145+
146+
self.mutex = QMutex()
147+
self.stopMe = 0
148+
149+
def run( self ):
150+
self.mutex.lock()
151+
self.stopMe = 0
152+
self.mutex.unlock()
153+
154+
interrupted = False
155+
156+
shapeFileWriter = None
157+
158+
if self.writeShape:
159+
vProvider = self.inputLayer.dataProvider()
160+
allAttrs = vProvider.attributeIndexes()
161+
vProvider.select( allAttrs )
162+
shapeFields = vProvider.fields()
163+
crs = vProvider.crs()
164+
wkbType = self.inputLayer.wkbType()
165+
if not crs.isValid():
166+
crs = None
167+
shapeFileWriter = QgsVectorFileWriter( self.outputFileName, self.outputEncoding, shapeFields, wkbType, crs )
168+
featureId = 0
169+
if self.useSelection:
170+
selection = self.inputLayer.selectedFeatures()
171+
self.emit( SIGNAL( "rangeCalculated( PyQt_PyObject )" ), len( selection ) )
172+
for f in selection:
173+
featGeometry = QgsGeometry( f.geometry() )
174+
attrMap = f.attributeMap()
175+
self.pointsBefore += geomVertexCount( featGeometry )
176+
newGeometry = featGeometry.simplify( self.tolerance )
177+
self.pointsAfter += geomVertexCount( newGeometry )
178+
feature = QgsFeature()
179+
feature.setGeometry( newGeometry )
180+
feature.setAttributeMap( attrMap )
181+
shapeFileWriter.addFeature( feature )
182+
featureId += 1
183+
self.emit( SIGNAL( "featureProcessed()" ) )
184+
185+
self.mutex.lock()
186+
s = self.stopMe
187+
self.mutex.unlock()
188+
if s == 1:
189+
interrupted = True
190+
break
191+
else:
192+
self.emit( SIGNAL( "rangeCalculated( PyQt_PyObject )" ), vProvider.featureCount() )
193+
f = QgsFeature()
194+
while vProvider.nextFeature( f ):
195+
featGeometry = QgsGeometry( f.geometry() )
196+
attrMap = f.attributeMap()
197+
self.pointsBefore += geomVertexCount( featGeometry )
198+
newGeometry = featGeometry.simplify( self.tolerance )
199+
self.pointsAfter += geomVertexCount( newGeometry )
200+
feature = QgsFeature()
201+
feature.setGeometry( newGeometry )
202+
feature.setAttributeMap( attrMap )
203+
shapeFileWriter.addFeature( feature )
204+
featureId += 1
205+
self.emit( SIGNAL( "featureProcessed()" ) )
206+
207+
self.mutex.lock()
208+
s = self.stopMe
209+
self.mutex.unlock()
210+
if s == 1:
211+
interrupted = True
212+
break
213+
else: # modify existing shapefile
214+
if not self.inputLayer.isEditable():
215+
self.inputLayer.startEditing()
216+
self.inputLayer.beginEditCommand( QString( "Simplify line(s)" ) )
217+
if self.useSelection:
218+
selection = self.inputLayer.selectedFeatures()
219+
self.emit( SIGNAL( "rangeCalculated( PyQt_PyObject )" ), len( selection ) )
220+
for f in selection:
221+
featureId = f.id()
222+
featGeometry = QgsGeometry( f.geometry() )
223+
self.pointsBefore += geomVertexCount( featGeometry )
224+
newGeometry = featGeometry.simplify( self.tolerance )
225+
self.pointsAfter += geomVertexCount( newGeometry )
226+
self.inputLayer.changeGeometry( featureId, newGeometry )
227+
self.emit( SIGNAL( "featureProcessed()" ) )
228+
229+
self.mutex.lock()
230+
s = self.stopMe
231+
self.mutex.unlock()
232+
if s == 1:
233+
interrupted = True
234+
break
235+
else:
236+
vProvider = self.inputLayer.dataProvider()
237+
self.emit( SIGNAL( "rangeCalculated( PyQt_PyObject )" ), vProvider.featureCount() )
238+
f = QgsFeature()
239+
while vProvider.nextFeature( f ):
240+
featureId = f.id()
241+
featGeometry = QgsGeometry( f.geometry() )
242+
self.pointsBefore += geomVertexCount( featGeometry )
243+
newGeometry = featGeometry.simplify( self.tolerance )
244+
self.pointsAfter += geomVertexCount( newGeometry )
245+
self.inputLayer.changeGeometry( featureId, newGeometry )
246+
self.emit( SIGNAL( "featureProcessed()" ) )
247+
248+
self.mutex.lock()
249+
s = self.stopMe
250+
self.mutex.unlock()
251+
if s == 1:
252+
interrupted = True
253+
break
254+
255+
# cleanup
256+
if self.inputLayer.isEditable():
257+
self.inputLayer.endEditCommand()
258+
259+
if shapeFileWriter != None:
260+
del shapeFileWriter
261+
262+
if not interrupted:
263+
self.emit( SIGNAL( "generalizationFinished( PyQt_PyObject )" ), ( self.pointsBefore, self.pointsAfter ) )
264+
else:
265+
self.emit( SIGNAL( "generalizationInterrupted()" ) )
266+
267+
def stop( self ):
268+
self.mutex.lock()
269+
self.stopMe = 1
270+
self.mutex.unlock()
271+
272+
QThread.wait( self )

0 commit comments

Comments
 (0)