3

I'm trying to paint something on a QPixmap, but it throws an error during cleanup.

from PySide2.QtGui import QPixmap, QPainter
from PySide2.QtWidgets import QApplication

app = QApplication()
width = 200
height = 100
pixmap = QPixmap(width, height)
painter = QPainter(pixmap)
painter.drawLine(0, 0, 100, 100)
print('Done.')

When I run that, I see the 'Done' message, and then an error.

Done.
QPaintDevice: Cannot destroy paint device that is being painted

Process finished with exit code 139 (interrupted by signal 11: SIGSEGV)

I've seen some similar questions with the same error, but it's not clear what's causing the error or how to avoid it.

Don Kirkby
  • 53,582
  • 27
  • 205
  • 286

1 Answers1

8

After experimenting, it seems that the painter has to clean up before the pixmap does, otherwise you get the error. For example, this works without error.

from PySide2.QtGui import QPixmap, QPainter
from PySide2.QtWidgets import QApplication

app = QApplication()
width = 200
height = 100
pixmap = QPixmap(width, height)
painter = QPainter(pixmap)
painter.drawLine(0, 0, 100, 100)
print('Done.')

del painter
del pixmap

You can also tell the painter to clean up without destroying it. Just tell it that you've finished painting by calling end().

from PySide2.QtGui import QPixmap, QPainter
from PySide2.QtWidgets import QApplication

app = QApplication()
width = 200
height = 100
pixmap = QPixmap(width, height)
painter = QPainter(pixmap)
painter.drawLine(0, 0, 100, 100)
print('Done.')

painter.end()

There are some other things that avoid the error for mysterious reasons. For example, this avoids the error.

from PySide2.QtGui import QPixmap, QPainter
from PySide2.QtWidgets import QApplication

app = QApplication()
width = 200
height = 100
pixmap = QPixmap(width, height)
painter = QPainter(pixmap)
painter.device()  # <-- No idea why this helps!
painter.drawLine(0, 0, 100, 100)
print('Done.')

In summary, just make sure that the painter cleans up before the pixmap does. I would recommend either using the painter in a smaller scope than the pixmap or explicitly calling painter.end().

Don Kirkby
  • 53,582
  • 27
  • 205
  • 286