PyQt/lesson1/动态layout.py

363 lines
13 KiB
Python
Raw Permalink Normal View History

2024-10-04 12:37:45 +08:00
# -*- coding: utf-8 -*-
import os
import sys
from PyQt5.QtCore import pyqtSlot, Qt
# from PyQt5.QtGui import Q
from PyQt5.QtWidgets import QHBoxLayout, QDockWidget, QMainWindow, QListWidget, QTextEdit, QPushButton, QApplication, \
QWidget, QToolBar, QAction, QVBoxLayout, QMenu, QLineEdit, QLabel
from PyQt5.QtCore import Qt, QSettings
from PyQt5.QtCore import QByteArray
class MainWindow(QMainWindow):
def __init__(self, parent=None):
super(MainWindow, self).__init__(parent)
self.dock_widgets = {} # 存储QDockWidget的字典
self.object = []
self.initUI()
def initUI(self):
self.setWindowTitle("DockWidget Example")
self.setGeometry(100, 100, 800, 600)
self.setDockNestingEnabled(True)
# 加载布局
self.loadLayout()
def add(self, text):
# 创建三个QDockWidget
dock1 = QDockWidget(text, self)
# 设置QDockWidget的特性
dock1.setFeatures(
QDockWidget.DockWidgetMovable | QDockWidget.DockWidgetFloatable | QDockWidget.DockWidgetClosable)
# 创建QTextEdit作为QDockWidget的内容
text_edit = QWidget()
text_edit1 = QLabel()
text_edit1.setText('sdfdsfdsafdsfdsa')
text_edit11 = QVBoxLayout()
text_edit11.addWidget(text_edit1)
text_edit.setLayout(text_edit11)
# 将QTextEdit添加到QDockWidget中
dock1.setWidget(text_edit1)
# 将QDockWidget添加到主窗口中
self.addDockWidget(Qt.LeftDockWidgetArea, dock1)
if self.object:
# 设置QDockWidget的叠加摆放
self.tabifyDockWidget(self.object[-1], dock1)
else:
self.object.append(dock1)
print(self.object)
self.dock_widgets[text] = dock1
def save_layout(self):
try:
p = 'layout1.ini'
with open(p, 'wb') as f:
s = self.saveState()
f.write(s)
# 创建QSettings对象用于保存布局设置
settings = QSettings("layout.ini", QSettings.IniFormat)
# 保存当前的布局设置
settings.setValue("mainWindow/geometry", self.saveGeometry())
settings.setValue("mainWindow/state", self.saveState())
# 保存QDockWidget的信息
settings.beginGroup("dockWidgets")
for name, dock in self.dock_widgets.items():
settings.setValue(name + "/geometry", dock.saveGeometry())
settings.endGroup()
except Exception as e:
print("保存布局时出错:", e)
def createDockWidget(self, name):
# 创建一个QDockWidget
dock = QDockWidget(name, self)
dock.setObjectName(name)
# 设置QDockWidget的特性
dock.setFeatures(QDockWidget.DockWidgetMovable | QDockWidget.DockWidgetFloatable | QDockWidget.DockWidgetClosable)
# 创建QTextEdit作为QDockWidget的内容
text_edit = QTextEdit()
dock.setWidget(text_edit)
# 将QDockWidget添加到字典中
self.dock_widgets[name] = dock
def loadLayout(self):
# 创建QSettings对象用于加载布局设置
settings = QSettings("layout.ini", QSettings.IniFormat)
# 加载之前保存的布局设置
self.restoreGeometry(settings.value("mainWindow/geometry", self.saveGeometry()))
self.restoreState(settings.value("mainWindow/state", self.saveState()))
# 加载QDockWidget的信息
settings.beginGroup("dockWidgets")
dock_names = settings.childGroups()
for s, name in enumerate(dock_names):
self.createDockWidget(name)
dock = self.dock_widgets[name]
dock.restoreGeometry(settings.value(name + "/geometry", dock.saveGeometry()))
self.addDockWidget(Qt.LeftDockWidgetArea, dock) # 将QDockWidget添加到主窗口中
self.restoreState(self.saveState())
settings.endGroup()
p = 'layout1.ini'
if os.path.exists(p):
with open(p, 'rb') as f:
s = f.read()
self.restoreState(s)
class widget(QWidget):
def __init__(self):
super(widget, self).__init__()
self.L = QHBoxLayout()
self.setLayout(self.L)
self.A = MainWindow()
self.P = QPushButton('add')
self.Ps = QPushButton('save')
self.Lo = QPushButton('lo')
self.name = QLineEdit()
self.L.addWidget(self.name)
self.L.addWidget(self.A)
self.L.addWidget(self.P)
self.L.addWidget(self.Ps)
self.L.addWidget(self.Lo)
self.P.clicked.connect(self.add)
self.Ps.clicked.connect(self.adds)
self.Lo.clicked.connect(self.addss)
def add(self):
self.A.add(self.name.text())
def adds(self):
self.A.save_layout()
def addss(self):
self.A.sss()
if __name__ == "__main__":
import sys
import qtmodern.styles
app = QApplication(sys.argv)
qtmodern.styles.dark(app)
mainWindow = widget()
mainWindow.show()
sys.exit(app.exec_())
from .import_qt import *
import os
from .MyDockWidget import MyDockWidget
from .util.form_class_registration import FormCalss
from util.func import quantity_recursion
import re
class InitUI(QMainWindow):
def __init__(self, parent=None):
super(InitUI, self).__init__(parent)
self.dock_widgets = {} # 存储QDockWidget的字典
self.initUI()
# self.setStyleSheet_func()
# 创建一个动作,用于保存布局设置
save_layout_action = QAction("Save Layout", self)
save_layout_action.triggered.connect(self.save_layout)
# 创建一个动作,用于加载布局设置
load_layout_action = QAction("Load Layout", self)
load_layout_action.triggered.connect(self.load_layout)
# 创建一个动作,用于加载布局设置
create_action = QAction("create", self)
create_action.triggered.connect(self.create_action_func)
# 将动作添加到菜单栏
file_menu = self.menuBar().addMenu("File")
file_menu.addAction(save_layout_action)
file_menu.addAction(load_layout_action)
file_menu.addAction(create_action)
# 将动作添加到菜单栏
self.tool_menu = self.menuBar().addMenu("tool")
self.init_tool()
def init_tool(self):
import functools
for i in FormCalss.FormDict:
create_action = QAction(i, self)
self.tool_menu.addAction(create_action)
create_action.triggered.connect(functools.partial(self.create_action_func, i))
def create_action_func(self, name):
widget = {'type': name, 'text': ''}
try:
FormCalss.form_class_dict[widget['type']]
except:
FormCalss.form_class_dict[widget['type']] = []
if FormCalss.form_class_dict[widget['type']] != []:
widgetList = FormCalss.form_class_dict[widget['type']]
widgetNameList = [i.objectName() for i in widgetList]
widget['text'] = quantity_recursion(1, widgetNameList)
else:
widget = {'type': name, 'text': '%s1' % name}
widgets = FormCalss.FormDict[widget['type']]()
widgets.setObjectName(widget['text'])
self.addTest(widgets, text=widget['text'])
FormCalss.add_form_class(widgets, widget['type'])
print(FormCalss.form_class_dict)
def addTest(self, widget, text):
# 创建三个QDockWidget
result = re.sub(r'\d+', '', text)
dock1 = MyDockWidget(text, self, type=result)
# 将QTextEdit添加到QDockWidget中
dock1.setWidget(widget)
# 将QDockWidget添加到主窗口中
self.addDockWidget(Qt.LeftDockWidgetArea, dock1)
self.dock_widgets[text] = dock1
def setStyleSheet_func(self):
StyleSheet = """
background-color: rgb(50, 50, 50);
"""
self.setStyleSheet(StyleSheet)
def initUI(self):
self.setWindowTitle("DockWidget Example")
self.setGeometry(100, 100, 800, 600)
self.setDockNestingEnabled(True)
# 加载布局
self.load_layout()
# def add(self, text):
# # 创建三个QDockWidget
# dock1 = QDockWidget(text, self)
# # 设置QDockWidget的特性
# dock1.setFeatures(
# QDockWidget.DockWidgetMovable | QDockWidget.DockWidgetFloatable | QDockWidget.DockWidgetClosable)
# # 创建QTextEdit作为QDockWidget的内容
# text_edit = QWidget()
# text_edit1 = QLabel()
# text_edit1.setText('sdfdsfdsafdsfdsa')
# text_edit11 = QVBoxLayout()
# text_edit11.addWidget(text_edit1)
# text_edit.setLayout(text_edit11)
# # 将QTextEdit添加到QDockWidget中
# dock1.setWidget(text_edit1)
#
# # 将QDockWidget添加到主窗口中
# self.addDockWidget(Qt.LeftDockWidgetArea, dock1)
#
# if self.object:
# # 设置QDockWidget的叠加摆放
# self.tabifyDockWidget(self.object[-1], dock1)
# else:
# self.object.append(dock1)
# self.dock_widgets[text] = dock1
def save_layout(self):
try:
try:
os.remove('layout1.ini')
except:
try:
os.remove('layout.ini')
except Exception as e:
print(e, 'save')
pass
p = 'layout1.ini'
with open(p, 'wb') as f:
s = self.saveState()
f.write(s)
# 创建QSettings对象用于保存布局设置
settings = QSettings("layout.ini", QSettings.IniFormat)
# 保存当前的布局设置
settings.setValue("mainWindow/geometry", self.saveGeometry())
settings.setValue("mainWindow/state", self.saveState())
# 保存QDockWidget的信息
settings.beginGroup("dockWidgets")
for name, dock in self.dock_widgets.items():
settings.setValue(name + "/geometry", dock.saveGeometry())
settings.endGroup()
except Exception as e:
print("保存布局时出错:", e)
self.w = QWidget()
self.w.setWindowFlags(Qt.WindowStaysOnTopHint)
reply = QMessageBox.question(self.w, '信息', '保存预设成功', QMessageBox.Cancel)
if reply == QMessageBox.Cancel:
return
def createDockWidget(self, name):
result = re.sub(r'\d+', '', name)
widget_object = FormCalss.FormDict[result]()
widget_object.setObjectName(name)
# 创建一个QDockWidget
dock = MyDockWidget(name, self, type=result)
# 创建QTextEdit作为QDockWidget的内容
dock.setWidget(widget_object)
widget = {'type': result, 'text': ''}
try:
FormCalss.form_class_dict[widget['type']]
except:
FormCalss.form_class_dict[widget['type']] = []
if FormCalss.form_class_dict[widget['type']] != []:
widgetList = FormCalss.form_class_dict[widget['type']]
widgetNameList = [i.objectName() for i in widgetList]
widget['text'] = quantity_recursion(1, widgetNameList)
else:
widget = {'type': result, 'text': '%s1' % result}
FormCalss.add_form_class(widget_object, widget['type'])
print(FormCalss.form_class_dict)
# 将QDockWidget添加到字典中
self.dock_widgets[name] = dock
def load_layout(self):
# 创建QSettings对象用于加载布局设置
settings = QSettings("layout.ini", QSettings.IniFormat)
# 加载之前保存的布局设置
self.restoreGeometry(settings.value("mainWindow/geometry", self.saveGeometry()))
self.restoreState(settings.value("mainWindow/state", self.saveState()))
# 加载QDockWidget的信息
settings.beginGroup("dockWidgets")
dock_names = settings.childGroups()
for s, name in enumerate(dock_names):
self.createDockWidget(name)
dock = self.dock_widgets[name]
dock.restoreGeometry(settings.value(name + "/geometry", dock.saveGeometry()))
self.addDockWidget(Qt.LeftDockWidgetArea, dock) # 将QDockWidget添加到主窗口中
self.restoreState(self.saveState())
settings.endGroup()
p = 'layout1.ini'
if os.path.exists(p):
with open(p, 'rb') as f:
s = f.read()
self.restoreState(s)
for i in self.findChildren(QDockWidget):
if i.isHidden():
settings = QSettings("layout.ini", QSettings.IniFormat)
settings.remove("dockWidgets/" + i.objectName() + "/geometry")