Я не могу изменить размер окна при скрытии виджета - PullRequest
1 голос
/ 02 марта 2020

Я нашел здесь некоторый код, который показывает пример того, как вы можете изменить размер окна, когда виджет скрыт, и он работает для меня. Вот код:

from PyQt4 import QtCore, QtGui
import sys

class MainWindow(QtGui.QWidget):
    def __init__(self):
        self.app = QtGui.QApplication(sys.argv)
        super(MainWindow, self).__init__()

        self.button = QtGui.QPushButton('Show/Hide')
        self.button.setCheckable(True)
        self.frame = QtGui.QFrame()
        self.frame.setFixedHeight(100)
        self.layout = layout = QtGui.QVBoxLayout()
        layout2 = QtGui.QVBoxLayout()
        self.setLayout(layout)
        self.frame.setLayout(layout2)

        layout.addWidget(self.button)
        layout.addWidget(self.frame)
        layout.addStretch(1)
        layout2.addWidget(QtGui.QLabel('Yoyoyo'))

        self.button.toggled.connect(self.clickAction)

    def startup(self):
        self.show()
        sys.exit(self.app.exec_())

    def clickAction(self):
        checked = self.button.isChecked()
        if checked:
            self.frame.show()
        else:
            self.frame.hide()
        QtCore.QTimer.singleShot(0, self.resizeMe)

    def resizeMe(self):
        self.resize(self.minimumSizeHint())
if __name__ == "__main__":
    myApp = MainWindow()
    myApp.startup()

Затем я попытался изменить это в соответствии с моим существующим кодом, разделив класс mainWindow и класс виджетов. Вот код, который делает это.

from PySide import QtGui,QtCore
import sys



class MainWindow(QtGui.QMainWindow):
    def __init__(self):
        super(MainWindow, self).__init__()
        self.w = testW(self)
        self.setCentralWidget(self.w)
        self.show()



class testW(QtGui.QWidget):
    def __init__(self,parent):
        super(testW,self).__init__()
        self.parent = parent
        self.button = QtGui.QPushButton('Show/Hide')
        self.button.setCheckable(True)
        self.button.setChecked(True);
        self.frame = QtGui.QFrame()
        self.frame.setFixedHeight(100)
        self.layout = layout = QtGui.QVBoxLayout()
        layout2 = QtGui.QVBoxLayout()
        self.setLayout(layout)
        self.frame.setLayout(layout2)

        layout.addWidget(self.button)
        layout.addWidget(self.frame)
        layout.addStretch(1)
        layout2.addWidget(QtGui.QLabel('Yoyoyo'))

        self.button.toggled.connect(self.clickAction)

    def clickAction(self):
        checked = self.button.isChecked()
        if checked:
            self.frame.show()
        else:
            self.frame.hide()
        QtCore.QTimer.singleShot(0, self.resizeMe)

    def resizeMe(self):
        self.resize(self.minimumSizeHint())

if __name__ == "__main__":
    app = QtGui.QApplication(sys.argv)
    myApp = MainWindow()
    sys.exit(app.exec_())
    #time.sleep(1)

Запуск первого кода делает то, что я хочу. После того, как я скрываю виджет, размер окна изменяется до правильного размера. Вторая реализация кода не сжимает и не расширяет окно, когда я скрываю и показываю виджет. Это потому, что MainWindow находится в отдельном классе?

1 Ответ

2 голосов
/ 05 марта 2020
  1. Используйте политики размера для ваших виджетов. Для вашего примера вы можете изменить код создания пользовательского интерфейса следующим образом:
class MainWindow(QtWidgets.QMainWindow):
    def __init__(self):
        super(MainWindow, self).__init__()
        self.w = testW(self)
        self.w.setSizePolicy(
            QtWidgets.QSizePolicy.MinimumExpanding,
            QtWidgets.QSizePolicy.MinimumExpanding
        )
        self.setCentralWidget(self.w)
        self.show()

Обратите внимание на новый вызов setSizePolicy, который говорит Qt layout engine , как изменить размер вашего виджета в соответствии с его содержание.

К сожалению, QMainWindow не учитывает sizeHint автоматически, но рассчитывается правильно, поэтому вы можете AdjustSize вручную:
    def clickAction(self):
        checked = self.button.isChecked()
        if checked:
            self.frame.show()
        else:
            self.frame.hide()
        QtCore.QTimer.singleShot(0, self.parent.adjustSize)

Вы не необходимо изменить размер самого виджета, потому что он будет изменен в соответствии с политикой. Даже sizeHint будет вычислен автоматически, поэтому вам нужно только вызвать AdjustSize QMainWindow.

PS: я использовал PySide2 вместо PySide, поэтому импорт немного отличается:

from PySide2 import QtWidgets, QtCore
...