I save the state of one of my QSplitter like that:
self.options.setValue("Window/final_splitter", self.splitter2.saveState())
And I restore it like that:
self.splitter2.restoreState(self.options.value("Window/final_splitter"))
When I save the splitter, splitter2.sizes() indicates: [321, 818, 769]
When I restore the splitter, it has visually the same dimensions as when I closed it, but splitter2.sizes() indicates: [224, 572, 537]
And I can't perform more actions on the splitter because I can't get its size right.
Do you have any idea about how to solve this bug ?
EDIT: even more odd:
saving:
self.options.setValue("Window/final_splitter", self.splitter2.sizes())
-> self.splitter2.sizes(): [321, 844, 743]
Restoring:
sizes_splitter2 = [int(nbr) for nbr in self.options.value("Window/final_splitter", [])]
self.splitter2.setSizes(sizes_splitter2)
EDIT 2: When I save the splitter, I also do (self is a QMainWIndow):
self.options.setValue("window_geometry", self.saveGeometry())
self.options.setValue("window_state", self.saveState())
If I comment those lines, the splitter.sizes() returns the good values. But those 2 lines do their job, the window is restored to the right size with them !
I'm guessing that you're trying to query the splitter sizes before the window is fully shown.
One way to work around this is to use a single shot timer to perform further actions after the event loop has started.
Hopefully this demo script should show what's going on:
from PyQt4 import QtCore, QtGui
class Window(QtGui.QMainWindow):
def __init__(self):
super(Window, self).__init__()
widget = QtGui.QWidget(self)
layout = QtGui.QVBoxLayout(widget)
self.setCentralWidget(widget)
self.splitter = QtGui.QSplitter(self)
self.splitter.addWidget(QtGui.QTextEdit(self))
self.splitter.addWidget(QtGui.QTextEdit(self))
self.splitter.addWidget(QtGui.QTextEdit(self))
self.button = QtGui.QPushButton('Test', self)
self.button.clicked.connect(lambda: self.printSizes('Test'))
layout.addWidget(self.splitter)
layout.addWidget(self.button)
self.printSizes('Show Before')
settings = self.settings()
value = settings.value('splitter')
if value is not None:
self.splitter.restoreState(value)
value = settings.value('layout')
if value is not None:
self.restoreState(value)
value = settings.value('geometry')
if value is not None:
self.restoreGeometry(value)
self.printSizes('Show After')
QtCore.QTimer.singleShot(
20, lambda: self.printSizes('Timer'))
def closeEvent(self, event):
self.printSizes('Close')
settings = self.settings()
settings.setValue("splitter", self.splitter.saveState())
settings.setValue("geometry", self.saveGeometry())
settings.setValue("layout", self.saveState())
def settings(self):
return QtCore.QSettings(
QtCore.QSettings.IniFormat,
QtCore.QSettings.UserScope, 'test', 'test')
def printSizes(self, message):
print('%s:' % message)
print(' window geometry:', (
self.width(), self.height(), self.x(), self.y()))
print(' splitter sizes:', self.splitter.sizes())
print()
if __name__ == '__main__':
import sys
app = QtGui.QApplication(sys.argv)
window = Window()
window.show()
sys.exit(app.exec_())