[SOLVED] How to fill a QRect and remove a smaller QRect out of it?
-
I am trying to draw a mask around a selection made on a document with a QRubberband.
I created a QWidget and reimplemented the paintEvent() so that, whenever the mask ought to be visible, it is first painted with a semi-transparent black using QPainter().fillRect(), then the selected QRect (QRubberband.geometry()) should be removed from this freshly painted mask. I hoped a simple QPainter().eraseRect() would work, but it remove everything below that selection, i.e. not only the mask, but also the other widget below (the document). Then I bumped into the composition modes, but that didn't work out either. All I've been able to come up with so far is:
@
surface = self.parent().geometry()
self.setGeometry(surface)
self.painter.begin(self)
self.painter.setCompositionMode(QtGui.QPainter.CompositionMode_SourceOver)
self.painter.fillRect(surface, QtGui.QColor(100, 100, 100, 70))
self.painter.setCompositionMode(QtGui.QPainter.CompositionMode_Clear)
self.painter.fillRect(self.parent().rubberband.geometry(), QtGui.QColor(100, 100, 100, 100,))
self.painter.end()@I tried other composition modes (xor, destination out, etc.) but no matter what I do, the second Painter().fillRect() adds colour to the previous layour or removes everything to leave pitch black only.
I feel I am on the right track, but I could just be fooling myself into believing that. Can you save me?
-
OK it seems I found the solution:
@ surface = self.parent().geometry()
self.setGeometry(surface)
path = QtGui.QPainterPath()
path.setFillRule(QtCore.Qt.OddEvenFill)
path.addRect(QtCore.QRectF(surface))
path.addRect(QtCore.QRectF(self.parent().rubberband.geometry()))
self.painter.begin(self)
self.painter.setBrush(QtGui.QBrush(QtGui.QColor(100, 100, 100, 70)))
self.painter.setPen(QtGui.QPen(QtGui.QColor(0, 0, 0, 80)))
self.painter.drawPath(path)
self.painter.end()@Although I wonder whether this is the simplest solution? I'm surprised QPainter does not has a fill mode that allows to invert or exclude an area.