#python #qt #pyqt5 #qgraphicsscene #qpainter
#python #qt #pyqt5 #qgraphicsscene #qpainter
Вопрос:
Я пытаюсь повторно реализовать демонстрационное приложение scribble для нескольких слоев изображений. Я изо всех сил пытаюсь нарисовать растровое изображение внутри сцены, поскольку художник жалуется, что оно уничтожается слишком рано.
QPaintDevice: не удается уничтожить окрашиваемое устройство
Не могли бы вы, пожалуйста, помочь мне исправить мой код таким образом, чтобы вы могли рисовать на растровом изображении roilayer красным пером и чтобы этот слой начинался прозрачным.
#!/usr/bin/python3
import sys
import os
from PyQt5.QtWidgets import QApplication, QGraphicsView, QGraphicsScene, QGraphicsPixmapItem
from PyQt5.QtGui import QPixmap, QImage, QPainter, QPen
from PyQt5.QtCore import Qt, QRect
class Main(QGraphicsView):
def __init__(self):
super().__init__()
self.setWindowTitle("Scribble with layers")
self.scene = QGraphicsScene()
self.setScene(self.scene)
self.image = QImage('sample/test.bmp')
self.imlayer = QGraphicsPixmapItem(QPixmap.fromImage(self.image))
self.roilayer = QGraphicsPixmapItem(QPixmap(self.image.size()))
self.addlayer(self.imlayer)
self.addlayer(self.roilayer)
self.drawing = False
self.lastPoint = None
self.pencolour = Qt.red
self.penwidth = 2
self.show()
def addlayer(self, layer):
self.scene.addItem(layer)
self.updateviewer()
def updateviewer(self):
self.fitInView(self.sceneRect(), Qt.KeepAspectRatio)
def mousePressEvent(self, event):
# print(event.modifiers())
if event.button() == Qt.LeftButton:
self.lastPoint = event.pos()
self.drawing = True
def mouseMoveEvent(self, event):
if (event.buttons() amp; Qt.LeftButton) and self.drawing:
self.drawlineto(event.pos())
def mouseReleaseEvent(self, event):
if event.button() == Qt.LeftButton and self.drawing:
self.drawlineto(event.pos())
self.drawing = False
def drawlineto(self, position):
pixmap = self.roilayer.pixmap()
painter = QPainter(pixmap)
painter.setPen(QPen(self.pencolour, self.penwidth, Qt.SolidLine,
Qt.RoundCap, Qt.RoundJoin))
painter.drawLine(self.lastPoint, position)
self.imlayer.setPixmap(pixmap)
self.modified = True
rad = self.penwidth / 2 2
self.update(QRect(self.lastPoint, position).normalized().adjusted(-rad, -rad, rad, rad))
self.lastPoint = position
if __name__ == '__main__':
app = QApplication([])
main = Main()
sys.exit(app.exec_())
Комментарии:
1. Попробуйте добавить строку
painter.end()
непосредственно передself.imlayer.setPixmap(pixmap)
тем, как сообщить Qt, что вы закончили рисование.2. Спасибо. Я не могу поверить, что это так просто, я нахожу документы для Painter запутанными.
3. привет, Jbbiomed. Можете ли вы дать мне несколько указаний, как заставить этот код работать? Я создаю простое приложение для рисования. Я попытался добавить painter.end(), как сказал @G.M. ранее, но у меня это не сработало.
Ответ №1:
У меня была та же проблема. Решение состоит в том, чтобы выполнить следующие действия в этой части вашего кода:
def drawlineto(self, position):
pixmap = self.roilayer.pixmap()
painter = QPainter()
painter.begin(pixmap)
painter.setPen(QPen(self.pencolour, self.penwidth, Qt.SolidLine,
Qt.RoundCap, Qt.RoundJoin))
painter.drawLine(self.lastPoint, position)
painter.end()
self.imlayer.setPixmap(pixmap)
self.modified = True