Не работает setGeometry для QDockWidget при размещении его в QMainWindow PyQt6
Надо установить положение и размер для QDockWidget, который находиться в QMainWindow.
В QMainWindow, 7 QDockWidget.
Создание QDock:
self.dock = QDockWidget('Фильтр')
self.dock.setAllowedAreas(Qt.DockWidgetArea.AllDockWidgetAreas)
_window.addDockWidget(Qt.DockWidgetArea.RightDockWidgetArea, self.dock)
self.dock.setWidget(self.Table_filter)
self.dock = QDockWidget('История изменений выделенной накладной')
self.dock.setAllowedAreas(Qt.DockWidgetArea.AllDockWidgetAreas)
_window.addDockWidget(Qt.DockWidgetArea.RightDockWidgetArea, self.dock)
self.dock.setWidget(self.Table_history__select_Nacl_history_Orders)
При активации приложения применение размеров:
sql_file_settings._cursor.execute("SELECT x, y, width, height, state FROM dock_data WHERE dock_name = ?", (name,))
data = sql_file_settings._cursor.fetchone()
if data:
x, y, width, height, state = data
self.dock.setGeometry(x, y, width, height)
_window = QMainWindow
self.dock.setGeometry(0,0,200,260)
не работает, размер и положение не изменяются.
Вообще мне надо сделать сохранение положения и размеров нескольких QDockWidget (расположенных в одном QMainWindow) при закрытии приложения.
Для того чтобы при следующей активации приложения они были такими какими их настроил пользователь.
Ответы (1 шт):
Пожалуйста, ВСЕГДА предоставьте минимальный воспроизводимый пример, который демонстрирует проблему.
Sorry, у меня PyQt5.
Класс QSettings обеспечивает постоянные, независимые от платформы настройки приложения.
А выглядеть, то что вы хотите сделать, примерно так:
from PyQt5.Qt import *
class DockWidget(QDockWidget):
def __init__(self, title, parent):
super(DockWidget, self).__init__(title, parent)
self.win_name = title
self.parent = parent
self.setObjectName(self.win_name)
self.can_close = False
def restore_window(self) -> bool:
try:
settings = QSettings("MySoftExamples", "DockWidgets")
self.restoreGeometry(settings.value(f'{self.win_name} Geometry'))
self.restoreState(settings.value(f'{self.win_name} State'))
return True
except:
return False
def closeEvent(self, event):
if not self.can_close:
event.ignore()
else:
settings = QSettings("MySoftExamples", "DockWidgets")
settings.setValue(f'{self.win_name} Geometry', self.saveGeometry())
settings.setValue(f'{self.win_name} State', self.parent.saveState())
QDockWidget.closeEvent(self, event)
class RememberWin(QMainWindow):
def __init__(self, win_name: str):
super(RememberWin, self).__init__()
self.win_name = win_name
self.setObjectName(win_name)
self.setWindowTitle(win_name)
self.can_close = False
def restore_window(self) -> bool:
try:
settings = QSettings("MySoftExamples", "DockWidgets")
self.restoreGeometry(settings.value(f'{self.win_name} Geometry'))
self.restoreState(settings.value(f'{self.win_name} State'))
return True
except:
return False
def closeEvent(self, event: QCloseEvent):
if not self.can_close:
event.ignore()
else:
settings = QSettings("MySoftExamples", "DockWidgets")
settings.setValue(f'{self.win_name} Geometry', self.saveGeometry())
settings.setValue(f'{self.win_name} State', self.saveState())
super().closeEvent(event)
class ControlWindow(RememberWin):
def __init__(self, win_name: str="ControlWindow"):
super(ControlWindow, self).__init__(win_name=win_name)
self.can_close = True
self.textEdit = QTextEdit('Вы можете закрыть только это окно.')
self.setCentralWidget(self.textEdit)
self.dockAble()
if not self.restore_window():
self.setGeometry(200, 290, 600, 300)
if not self.dock1.restore_window():
self.dock1.setGeometry(700, 100, 200, 200)
if not self.dock2.restore_window():
self.dock2.setGeometry(950, 100, 200, 200)
self.dock1.show()
self.dock2.show()
self.settings = QSettings("MySoftExamples", "DockWidgets")
self.zOrder = []
QApplication.instance().focusObjectChanged.connect(self.focusChanged)
windowOrder = self.settings.value('windowOrder', type='QStringList')
topLevelWindows = QApplication.topLevelWidgets()
if windowOrder:
for objName in windowOrder:
for win in topLevelWindows:
if win.objectName() == objName:
win.show()
else:
self.dock1.show()
self.dock2.show()
def focusChanged(self, obj):
if not obj or obj.window() == self.window():
return
if obj.window() in self.zOrder[:-1]:
self.zOrder.remove(obj.window())
self.zOrder.append(obj.window())
def closeEvent(self, event: QCloseEvent):
for win in (self.dock1, self.dock2):
win.can_close = True
win.close()
self.settings.setValue('windowOrder',
[w.window().objectName() for w in self.zOrder])
super(ControlWindow, self).closeEvent(event)
def dockAble(self):
self.dock1 = DockWidget("Fruits", self)
self.dock1.setAllowedAreas(Qt.DockWidgetArea.AllDockWidgetAreas)
self.myfruit = ["Груша", "Айва", "Персик", "Яблоко"]
self.listwidget1 = QListWidget(self.dock1)
self.listwidget1.addItems(self.myfruit)
self.listwidget1.itemClicked.connect(self.clickedItemListwidget1)
self.dock1.setWidget(self.listwidget1)
self.addDockWidget(Qt.DockWidgetArea.RightDockWidgetArea, self.dock1)
self.dock2 = DockWidget("Vegetables", self)
self.dock2.setAllowedAreas(Qt.DockWidgetArea.AllDockWidgetAreas)
self.myvegetables = ["Капуста", "Лук", "Морковь", "Огкрец"]
self.listwidget2 = QListWidget(self.dock2)
self.listwidget2.addItems(self.myvegetables)
self.listwidget2.itemClicked.connect(self.clickedItemListwidget1)
self.dock2.setWidget(self.listwidget2)
self.addDockWidget(Qt.DockWidgetArea.RightDockWidgetArea, self.dock2)
def clickedItemListwidget1(self, item):
self.textEdit.append(item.text())
if __name__ == '__main__':
import sys
app = QApplication(sys.argv)
w = ControlWindow(win_name='ControlWindow')
w.show()
sys.exit(app.exec())

