通过拖动调整小部件的大小

2024-06-30 15:00:50 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个自定义小部件。我想通过拖动小部件的一角来调整大小。当前,当光标靠近小部件的一角时,它会自动调整大小

下面是示例代码。我想通过拖动右下角的红色三角形来调整小部件的大小。我能知道怎么做吗

from PyQt5.QtCore import Qt, QPoint, QPointF, QEvent
from PyQt5.QtGui import QPainter, QIcon, QColor, QPolygon
from PyQt5.QtWidgets import *
import sys


class Stack(QWidget):
    def __init__(self, parent=None):

        super(Stack, self).__init__(parent)
        self._triangle = QPolygon()
        self.setMouseTracking(True)
        self.old_x_pos = 0
        self.old_y_pos = 0

    def _recalculate_triangle(self):
        p = QPoint(self.width() - 20, self.height() - 10)
        q = QPoint(self.width() - 10, self.height() - 20)
        r = QPoint(self.width() - 10, self.height() - 10)
        self._triangle = QPolygon([p, q, r])
        self.update()

    def resizeEvent(self, event):
        self._recalculate_triangle()

    def paintEvent(self, event):
        super(Stack, self).paintEvent(event)
        qp = QPainter(self)

        qp.setPen(Qt.white)

        qp.setBrush(Qt.white)
        qp.drawRect(10, 10, 150, 150)

        qp.setPen(Qt.white)
        qp.setBrush(Qt.red)
        qp.drawPolygon(self._triangle)

    def mousePressEvent(self, event):
        if event.button() == Qt.LeftButton and self._triangle.containsPoint(
            event.pos(), Qt.OddEvenFill
        ):
            self.setCursor(Qt.SizeFDiagCursor)

        else:
            self.unsetCursor()
        
        super(Stack, self).mousePressEvent(event)
        
    def mouseMoveEvent(self, event):
        if self._triangle.containsPoint(event.pos(), Qt.OddEvenFill):
            self.setCursor(Qt.SizeFDiagCursor)

            self.setCursor(Qt.SizeFDiagCursor)

            if event.x() > self.old_x_pos and event.y() > self.old_y_pos:
                self.resize(self.width() + (self.width() - event.x()), self.height() + (self.height() - event.y()))

            elif event.x() < self.old_x_pos and event.y() < self.old_y_pos:
                self.resize(self.width() - (self.width() - event.x()), self.height() - (self.height() - event.y()))

        else:
            self.unsetCursor()

        print(self.old_y_pos)
        self.old_x_pos = event.x()
        self.old_y_pos = event.y()


if __name__ == "__main__":
    app = QApplication(sys.argv)
    win = Stack()
    win.show()
    sys.exit(app.exec_())

Tags: posimportselfeventifstack部件def
1条回答
网友
1楼 · 发布于 2024-06-30 15:00:50

好的,我知道了。对于其他人,这里是问题中修改过的代码。使用此代码,您可以调整小部件的大小,以及在主窗口或框架中移动自定义小部件。要应用于代码,只需复制粘贴__init__()下的代码和鼠标事件下的代码即可

import sys

from PyQt5.QtCore import Qt, QPoint
from PyQt5.QtGui import QPainter, QPolygon
from PyQt5.QtWidgets import *


class Stack(QWidget):
    def __init__(self, parent=None):

        super(Stack, self).__init__(parent)


        self.__mouseMovePos = None
        self.setMouseTracking(True)
        self._triangle = QPolygon()
        self.start_pos = None

    def _recalculate_triangle(self):
        p = QPoint(self.width() - 20, self.height() - 10)
        q = QPoint(self.width() - 10, self.height() - 20)
        r = QPoint(self.width() - 10, self.height() - 10)
        self._triangle = QPolygon([p, q, r])
        self.update()

    def resizeEvent(self, event):
        self._recalculate_triangle()

    def paintEvent(self, event):
        super(Stack, self).paintEvent(event)
        qp = QPainter(self)

        qp.setPen(Qt.white)

        qp.setBrush(Qt.white)
        qp.drawRect(10, 10, 150, 150)

        qp.setPen(Qt.white)
        qp.setBrush(Qt.red)
        qp.drawPolygon(self._triangle)

    def mousePressEvent(self, event):
        self.__mousePressPos = None
        self.__mouseMovePos = None
        if event.button() == Qt.LeftButton:

            if event.button() == Qt.LeftButton and self._triangle.containsPoint(
                    event.pos(), Qt.OddEvenFill
            ):
                self.setCursor(Qt.SizeFDiagCursor)
                self.start_pos = event.pos()

            else:
                self.__mousePressPos = event.globalPos()
                self.__mouseMovePos = event.globalPos()
                self.start_pos = None
                self.unsetCursor()

        super().mousePressEvent(event)
        
    def mouseMoveEvent(self, event):
        if self._triangle.containsPoint(event.pos(), Qt.OddEvenFill):
            self.setCursor(Qt.SizeFDiagCursor)

        else:
            self.unsetCursor()

        if event.buttons() == Qt.LeftButton:

            if event.buttons() == Qt.LeftButton and self.start_pos is not None:

                self.setCursor(Qt.SizeFDiagCursor)

                delta = event.pos() - self.start_pos

                self.resize(self.width() + delta.x(), self.height() + delta.y())
                self.start_pos = event.pos()

            elif not self._triangle.containsPoint(event.pos(), Qt.OddEvenFill):
                currPos = self.mapToGlobal(self.pos())
                globalPos = event.globalPos()
                diff = globalPos - self.__mouseMovePos
                newPos = self.mapFromGlobal(currPos + diff)

                self.move(newPos)
                self.__mouseMovePos = globalPos

                self.start_pos = None
                self.unsetCursor()

        super().mouseMoveEvent(event)

    def mouseReleaseEvent(self, event):
        if self.__mousePressPos is not None:
            moved = event.globalPos() - self.__mousePressPos
            if moved.manhattanLength() > 3:
                event.ignore()
                return

        self.start_pos = None
        super().mouseReleaseEvent(event)


if __name__ == "__main__":
    app = QApplication(sys.argv)
    win = Stack()
    win.show()
    sys.exit(app.exec_())

相关问题 更多 >