Если вы хотите представить данные вне класса, вы должны использовать сигналы, как показано ниже:
import sys
from PyQt4 import QtCore, QtGui
class rubberBandWidget(QtGui.QWidget):
rectChanged = QtCore.pyqtSignal(QtCore.QRect) # create signal
...
def mouseReleaseEvent(self, event):
self.tweaking = False
self.tweakingpart = ""
self.unsetCursor()
if not self.rubberBand.geometry().isNull():
self.rectChanged.emit(self.rubberBand.geometry()) # emit signal
if __name__ == '__main__':
app = QtGui.QApplication(sys.argv)
w = rubberBandWidget()
def on_rectChanged(rect):
# receiver
print(rect.x(), rect.y(), rect.width(), rect.height())
w.rectChanged.connect(on_rectChanged) # connect signal
w.show()
sys.exit(app.exec_())
С другой стороны, я вижу, что ваш код очень связан, потому что если вы хотитечтобы использовать ту же функциональность в другом виджете, вам придется скопировать весь код, а это нежелательно, поэтому я потрачу время на создание пользовательского QRubberband
, который обладает такими функциями. В следующей части я покажу пример.
import sys
from PyQt4 import QtCore, QtGui
class RubberBand(QtGui.QRubberBand):
rectChanged = QtCore.pyqtSignal(QtCore.QRect)
TopLeft, TopRight, BottomLeft, BottomRight, Top, Bottom, Left, Right, NonePos = range(9)
def __init__(self, parent=None):
super(RubberBand, self).__init__(QtGui.QRubberBand.Rectangle, parent)
self._widget = None
self.setWidget(parent)
self.tweakingpart = RubberBand.NonePos
self.cursors = [QtCore.Qt.SizeFDiagCursor,
QtCore.Qt.SizeBDiagCursor,
QtCore.Qt.SizeBDiagCursor,
QtCore.Qt.SizeFDiagCursor,
QtCore.Qt.SizeVerCursor,
QtCore.Qt.SizeVerCursor,
QtCore.Qt.SizeHorCursor,
QtCore.Qt.SizeHorCursor]
def setWidget(self, widget):
if widget is None:
return
if self._widget is not None:
self._widget.removeEventFilter(self)
self._widget = widget
self._widget.installEventFilter(self)
self.setParent(widget)
def eventFilter(self, obj, event):
if self._widget is obj:
if event.type() == QtCore.QEvent.MouseButtonPress:
self.handleMousePressEvent(event.pos())
return True
elif event.type() == QtCore.QEvent.MouseMove:
self.handleMouseMoveEvent(event.pos())
return True
elif event.type() == QtCore.QEvent.MouseButtonRelease:
self.handleMouseReleaseEvent(event.pos())
return True
return super(RubberBand, self).eventFilter(obj, event)
def handleMousePressEvent(self, pt):
rg = self.geometry()
if not rg.isValid():
return
off, offx, offy = QtCore.QPoint(3, 3), QtCore.QPoint(4, -3), QtCore.QPoint(-3, 4)
rect = QtCore.QRect(-off, off)
tl, tr, bl, br = rg.topLeft(), rg.topRight(), rg.bottomLeft(), rg.bottomRight()
for i, coord in enumerate([tl, tr, bl, br]):
rect.moveCenter(coord)
if rect.contains(pt):
self.tweakingpart = i
if QtCore.QRect(tl + offx, tr - offx).contains(pt):
self.tweakingpart = RubberBand.Top
elif QtCore.QRect(bl + offx, br - offx).contains(pt):
self.tweakingpart = RubberBand.Bottom
elif QtCore.QRect(tl + offy, bl - offy).contains(pt):
self.tweakingpart = RubberBand.Left
elif QtCore.QRect(tr + offy, br - offy).contains(pt):
self.tweakingpart = RubberBand.Right
if 0 <= self.tweakingpart < RubberBand.NonePos:
self._widget.setCursor(self.cursors[self.tweakingpart])
return
self.setGeometry(QtCore.QRect(pt, QtCore.QSize()))
self.show()
def handleMouseMoveEvent(self, pt):
rg = self.geometry()
if 0 <= self.tweakingpart < RubberBand.NonePos:
if self.tweakingpart == RubberBand.TopLeft:
rg.setTopLeft(pt)
elif self.tweakingpart == RubberBand.TopRight:
rg.setTopRight(pt)
elif self.tweakingpart == RubberBand.BottomLeft:
rg.setBottomLeft(pt)
elif self.tweakingpart == RubberBand.BottomRight:
rg.setBottomRight(pt)
elif self.tweakingpart == RubberBand.Top:
rg.setTop(pt.y())
elif self.tweakingpart == RubberBand.Bottom:
rg.setBottom(pt.y())
elif self.tweakingpart == RubberBand.Left:
rg.setLeft(pt.x())
elif self.tweakingpart == RubberBand.Right:
rg.setRight(pt.x())
else:
rg = QtCore.QRect(rg.topLeft(), pt).normalized()
self.setGeometry(rg)
def handleMouseReleaseEvent(self, pt):
self.tweakingpart = RubberBand.NonePos
self._widget.unsetCursor()
if not self.geometry().isNull():
self.rectChanged.emit(self.geometry())
class TestWidget(QtGui.QWidget):
pass
if __name__ == '__main__':
app = QtGui.QApplication(sys.argv)
w = TestWidget()
rubberBand = RubberBand(w)
def on_rectChanged(rect):
print(rect.x(), rect.y(), rect.width(), rect.height())
rubberBand.rectChanged.connect(on_rectChanged)
w.show()
sys.exit(app.exec_())