I am developing a plugin in QGIS3QGIS 3.14 to customize editing. I am drawing a line by clicking on map canvas. It is showing points with mouse click and creating a line with right click. I want to trace mouse by showing dotted line while generating points. Just like existing 'Add Line Feature' function of 'Toggle Editing' in QGIS. Following is the code which I am using now.
class StraightLine(QgsMapToolEmitPoint):
points=[]
def __init__(self, canvas):
# call the parent constructor
QgsMapToolEmitPoint.__init__(self, canvas)
# store the passed canvas
self.canvas = canvas
# flag to know whether the tool is performing a drawing operation
self.isDrawing = False
self.dlg = CurveToolDialog()
# create and setup the rubber band to display the line
self.rubberBand = QgsRubberBand(iface.mapCanvas(), QgsWkbTypes.LineGeometry)
self.rubberBand.setColor( Qt.red )
self.rubberBand.setWidth( 1 )
self.dlg.setFocusPolicy(Qt.StrongFocus)
def clear(self):
self.rubberBand.reset( False ) # False = not a polygon = a line
def delete(self):
self.canvas.scene().removeItem( self.rubberBand )
def canvasPressEvent(self, e):
# which the mouse button?
if e.button() == Qt.LeftButton:
# left click
# if it's the first left click, clear the rubberband
if not self.isDrawing:
self.clear()
self.points=[]
# we are drawing now
self.isDrawing = True
point = self.toMapCoordinates( e.pos() )
# add a new point to the rubber band
self.rubberBand.addPoint( point, True ) # True = display updates on the canvas
self.points.append(QgsPoint(point))
polyline = QgsGeometry.fromPolyline(self.points)
feat = QgsFeature()
feat.setGeometry(polyline)
self.rubberBand.setToGeometry(polyline)
self.rubberBand.movePoint( point )
self.rubberBand.show()
# and finally show the rubber band
self.rubberBand.show()
if e.button() == Qt.RightButton:
# right click, stop drawing
self.isDrawing = False
# emit a signal
polyline = QgsGeometry.fromPolyline(self.points)
feat = QgsFeature()
feat.setGeometry(polyline)
self.rubberBand.setToGeometry(polyline)
self.rubberBand.show()
layer=iface.activeLayer()
f=layer.getFeature(0)
prov1 = layer.dataProvider()
layer.startEditing()
prov1.addFeatures([feat])
feat.setAttributes(f.attributes())
layer.commitChanges()
layer.updateExtents()
iface.mapCanvas().refresh()
self.dlg.open()
def geometry(self):
return self.rubberBand.asGeometry()
class StraightLine(QgsMapToolEmitPoint):
points = []
def __init__(self, canvas):
# call the parent constructor
QgsMapToolEmitPoint.__init__(self, canvas)
# store the passed canvas
self.canvas = canvas
# flag to know whether the tool is performing a drawing operation
self.isDrawing = False
self.dlg = CurveToolDialog()
# create and setup the rubber band to display the line
self.rubberBand = QgsRubberBand(iface.mapCanvas(), QgsWkbTypes.LineGeometry)
self.rubberBand.setColor(Qt.red)
self.rubberBand.setWidth(1)
self.dlg.setFocusPolicy(Qt.StrongFocus)
def clear(self):
self.rubberBand.reset(False) # False = not a polygon = a line
def delete(self):
self.canvas.scene().removeItem(self.rubberBand)
def canvasPressEvent(self, e):
# which the mouse button?
if e.button() == Qt.LeftButton:
# left click
# if it's the first left click, clear the rubberband
if not self.isDrawing:
self.clear()
self.points = []
# we are drawing now
self.isDrawing = True
point = self.toMapCoordinates(e.pos())
# add a new point to the rubber band
self.rubberBand.addPoint(point, True) # True = display updates on the canvas
self.points.append(QgsPoint(point))
polyline = QgsGeometry.fromPolyline(self.points)
feat = QgsFeature()
feat.setGeometry(polyline)
self.rubberBand.setToGeometry(polyline)
self.rubberBand.movePoint(point)
self.rubberBand.show()
# and finally show the rubber band
self.rubberBand.show()
if e.button() == Qt.RightButton:
# right click, stop drawing
self.isDrawing = False
# emit a signal
polyline = QgsGeometry.fromPolyline(self.points)
feat = QgsFeature()
feat.setGeometry(polyline)
self.rubberBand.setToGeometry(polyline)
self.rubberBand.show()
layer = iface.activeLayer()
f = layer.getFeature(0)
prov1 = layer.dataProvider()
layer.startEditing()
prov1.addFeatures([feat])
feat.setAttributes(f.attributes())
layer.commitChanges()
layer.updateExtents()
iface.mapCanvas().refresh()
self.dlg.open()
def geometry(self):
return self.rubberBand.asGeometry()
def mouseMoveEvent(self, event):
if self.last:
self.painter.drawLine(self.last, event.pos())
self.last = event.pos()
self.update()
def mouseMoveEvent(self, event):
if self.last:
self.painter.drawLine(self.last, event.pos())
self.last = event.pos()
self.update()