4

我有一个带有主要“显示”小部件和几个小部件的 QMainWindow。我希望能够在鼠标进入或离开窗口时打开/关闭小部件。

我可以通过实现enterEventleaveEvent调用显示/隐藏不必要的小部件来实现这个基本功能。然而,Qt4 的默认行为是保持 QMainWindow 几何形状固定,并调整重要的小部件的大小。我宁愿维护这个小部件的几何形状,并根据需要移动/调整 QMainWindow 的大小。这可能吗?

这是 PyQt4 中的一个简化示例

from PyQt4.QtGui import *
from PyQt4.QtCore import *

app = QApplication([''])

class MyWidget(QWidget):
    def __init__(self, parent=None):
        super(MyWidget, self).__init__(parent)

        layout = QVBoxLayout()
        self.setLayout(layout)
        self.main = QPushButton("major")
        self.main.setSizePolicy(QSizePolicy.Expanding, QSizePolicy.Expanding)
        self.minor = QPushButton("minor")
        layout.addWidget(self.main)
        layout.addWidget(self.minor)

    def enterEvent(self, event):
        self.minor.show()

    def leaveEvent(self, event):
        self.minor.hide()

mw = QMainWindow()
mw.setCentralWidget(MyWidget())
mw.show()

app.exec_()

我希望 MyWidget 的边界改变为环绕此按钮,而不是“主要”按钮的增长/缩小。

4

2 回答 2

1

我用 PySide 在 Mac OS X 上破解了你的例子。经过一段时间的尝试,我找到了以下解决方案:

from PySide.QtGui import *
from PySide.QtCore import *

app = QApplication([''])

class MyWidget(QWidget):
    def __init__(self, parent=None):
        super(MyWidget, self).__init__(parent)

        layout = QVBoxLayout()
        self.setLayout(layout)
        self.main = QPushButton("major")
        self.main.setSizePolicy(QSizePolicy.Expanding, QSizePolicy.Expanding)
        self.minor = QPushButton("minor")
        layout.addWidget(self.main)
        layout.addWidget(self.minor)

    def resizeEvent(self, event):
        self.appendix = self.minor.frameGeometry().height() + 2
        if self.minor.isVisible():
            self.varheight = mw.height() - self.appendix
        else:
            self.varheight = mw.height()

    def enterEvent(self, event):
        self.minor.show()
        mw.resize(mw.width(), self.varheight + self.appendix)

    def leaveEvent(self, event):
        self.minor.hide()
        mw.resize(mw.width(), self.varheight)

mw = QMainWindow()
mw.setCentralWidget(MyWidget())
mw.show()

app.exec_()

这并不完美,因为初始状态不检查鼠标位置。此外,魔术“+ 2”应该可以从小部件几何的其他一些指标中计算出来。但是对于这个例子应该没​​问题。

这个实现需要几个小时才能正确完成。确保所有计算都处于固定状态至关重要。否则布局引擎会产生难以理解的结果,甚至是无限循环。

resizeEvent从小部件大小中获取正确的值,但仅此而已。然后使用这些值并调整大小enterEventleaveEvent

我的变量没有初始化。您可以这样做,但第一次调整大小要早于我们的其他事件。

于 2012-12-15T03:01:04.790 回答
0

你可以试试这段代码。你可以直接继承 QMainWindow,而不是继承 QWidget。

from PyQt4.QtGui import *
from PyQt4.QtCore import *

class MyWindow( QMainWindow ):
    def __init__( self, parent = None ):
        QMainWindow.__init__( self, parent )

        self.widget = QWidget( self )
        lyt = QVBoxLayout()

        self.main = QPushButton( "major" )
        self.minor = QPushButton( "minor" )

        if not self.underMouse() :
            self.minor.hide()
            self.setMaximumHeight( self.main.sizeHint().height() )

        else :
            self.setMaximumHeight( self.minor.sizeHint().height() + self.main.sizeHint().height() )

        lyt.addWidget( self.main )
        lyt.addWidget( self.minor )

        self.widget.setLayout( lyt )
        self.setCentralWidget( self.widget )

    def enterEvent( self, event ) :

        self.minor.show()
        self.setMaximumHeight( self.minor.sizeHint().height() + self.main.sizeHint().height() )
        self.adjustSize()

        event.accept()

    def leaveEvent( self, event ):

        self.minor.hide()
        self.setMaximumHeight( self.main.sizeHint().height() )
        self.adjustSize()

        event.accept()

if __name__ == '__main__' :

    app = QApplication( [] )

    Gui = MyWindow()
    Gui.show()

    app.exec_()
于 2013-09-05T11:16:24.130 回答