PySide核心概念

内容分享1个月前发布
0 1 0

核心概念

PySide作为Qt官方Python绑定的GUI工具包,其强劲功能建立在几个核心概念之上。

如果你之前有Qt的开发经验信任很好理解,但是如果你没有那么理解起来可能有些困难,不用担心,仔细阅读我的描述和分析例程代码,就能完全掌握。

第一我们讲几个核心概念用表格的方式总结出来方便记忆。

核心概念

核心类/机制

主要功能与特点

应用与事件循环

QApplication

管理应用程序的生命周期、主事件循环和系统级设置。每个GUI应用必须有且只有一个实例。

窗口与控件基础

QWidget

所有用户界面对象的基类,提供坐标几何、绘制、事件处理等基础功能。

界面布局管理

QLayout及其子类 (如 QVBoxLayout)

自动排列和调整控件位置与大小,确保界面布局整洁且适应窗口尺寸变化。

对象间通信

信号与槽 (Signals & Slots)

Qt的核心机制,用于对象间松散耦合的通信。当事件发生时(如按钮被点击),控件发出信号,与之连接的槽函数(一般是你写的处理逻辑)会自动执行。

数据与显示分离

Model-View 架构

将数据(Model)的管理和数据的显示(View)分离,使数据变更可以自动同步到视图,且一个模型可为多个视图提供数据。

QApplication 与事件循环

任何PySide图形界面应用程序的起点都是创建**QApplication**实例,它负责管理应用程序的控制流、主事件循环和全局设置。

  • 关键角色:处理来自窗口系统和其他来源的所有事件(如鼠标点击、键盘输入),并将它们分派给相应的窗口部件。它还负责应用程序的初始化和清理工作。
  • 事件循环:通过调用 app.exec()启动事件循环。这是一个“无限”循环,不断检查是否有事件发生并处理,直到收到退出指令(如主窗口关闭)。没有它,界面会一闪而过,程序立即退出。

一个典型的程序入口代码如下:

import sys
from PySide6.QtWidgets import QApplication, QWidget

app = QApplication(sys.argv)# 创建应用实例,可处理命令行参数

# ... (创建窗口和其他控件)

window.show()# 显示窗口

sys.exit(app.exec())# 进入事件循环,并将退出代码传递给系统

QWidget 与窗口部件

QWidget 类是所有用户界面对象的基类。按钮、标签、对话框、主窗口——几乎所有你在屏幕上看到的界面元素都是QWidget或其子类。

  • 窗口与部件:一个没有父部件的 QWidget一般是一个窗口(带有系统边框和标题栏)。有父部件的 QWidget则作为容器或其他窗口内部的子控件存在。
  • 几何管理:QWidget提供了管理自身位置和大小的方法,如 resize(), move(), 和 setGeometry()。
  • 常用窗口类QMainWindow:为典型的主应用程序窗口提供了预定义的布局结构,包括菜单栏、工具栏、状态栏和一个可放置中心部件的区域。 QDialog:主要用于创建短期存在的对话框窗口,例如“打开文件”或“设置偏好”对话框。

布局管理器

手动为每个控件设置绝对坐标 (move(x, y)) 既繁琐又难以维护,尤其在窗口大小改变时界面会变得混乱。布局管理器 解决了这个问题,它能自动安排控件的位置和大小。

  • 工作原理:你将控件添加到布局管理器(如 QVBoxLayout垂直排列,QHBoxLayout水平排列,QGridLayout网格排列),然后将该布局管理器设置给一个父 QWidget。布局管理器会负责控件的排列和当父窗口调整大小时的重绘。
  • 优势:保证界面元素排列整齐,自适应窗口尺寸变化,支持布局嵌套以构建复杂界面。

这里我总结四种核心布局管理器的特点和典型用途:

布局类型

核心类

排列方式

适用场景

水平布局

QHBoxLayout

从左到右水平排列控件

工具栏、一行按钮、水平排列的表单

垂直布局

QVBoxLayout

从上到下垂直排列控件

设置对话框、侧边栏、垂直排列的列表

网格布局

QGridLayout

在行和列组成的网格中排列控件

数据表格、计算器界面、复杂的仪表盘

表单布局

QFormLayout

两列布局(一般左标签右输入)

用户注册、设置、数据录入等表单界面

后面我们会专门学习使用布局管理器,这里就不提供代码了。

信号与槽机制

这是Qt框架最突出的特性之一,实现了对象之间的高效、松散耦合的通信。

  • 信号:当某个特定事件发生在对象上时(例如按钮被点击 clicked,滑块值改变 valueChanged),该对象会发射一个信号。信号本身不执行任何操作。
  • :槽是一个可以被调用的函数(或方法)。你负责编写槽函数来定义当特定信号发出时应发生什么。
  • 连接:使用 信号发射者.信号名.connect(槽函数)将信号与槽关联起来。一旦连接建立,当信号发射时,对应的槽函数便会自动执行。

这里我提供一个代码示例,通过点击按钮弹出消息框的简单程序,可以体验信号和槽机制。

from PySide6.QtWidgets import QApplication, QPushButton, QMessageBox

def on_button_clicked():
    QMessageBox.information(window, "提示", "按钮被点击了!")

app = QApplication([])
button = QPushButton("点击我")
button.clicked.connect(on_button_clicked)  # 连接信号与槽
button.show()
app.exec()

Model-View 架构

对于显示列表、表格或树形等结构化数据,Qt推荐使用Model-View架构。这种架构将数据本身(Model)和数据的可视化呈现(View)分离开来。

  • Model:负责数据的存储、访问和底层逻辑。Qt提供了如 QStandardItemModel等标准模型,你也可以自定义模型。
  • View:负责将模型中的数据以某种形式(如列表、表格)显示给用户,并处理用户的显示交互。
  • 优势分离关注点:数据逻辑和显示逻辑独立,便于维护和扩展。 一致性:同一个数据模型可以同时用于多个不同的视图(例如,一份数据既用表格显示,又用图表显示)。 高效处理大数据:对于大型数据集,Qt的视图部件经过优化,可以只渲染可见部分,性能更好。

Model-View 是超级重大的GUI开发思想,虽然我们才刚开始学习GUI开发,但是也需要超级了解,这里为了便于大家理解,我提供一个简单的例子,用来说明Model-View 架构。

import sys
from PySide6.QtCore import Qt
from PySide6.QtGui import QStandardItemModel, QStandardItem, QIcon
from PySide6.QtWidgets import (QApplication, QMainWindow, QListView,
                              QVBoxLayout, QHBoxLayout, QLineEdit,
                              QPushButton, QWidget, QAbstractItemView)

class TodoModel(QStandardItemModel):
    """自定义模型,管理待办事项数据"""
    def add_item(self, text):
        """向模型添加一个新的待办事项"""
        if not text.strip():
            return
        item = QStandardItem(text)
        item.setCheckable(True)  # 让项目可以被勾选
        item.setEditable(False) # 禁止直接编辑
        # 初始状态为未完成(未勾选)
        item.setCheckState(Qt.Unchecked)
        self.appendRow(item)

    def remove_selected_item(self, index):
        """从模型中移除选定的项目"""
        if index.isValid():
            self.removeRow(index.row())

    def toggle_completion(self, index):
        """切换项目的完成状态(可选扩展功能)"""
        if index.isValid():
            item = self.itemFromIndex(index)
            # 这里可以根据需要添加更复杂的完成状态逻辑
            current_state = item.checkState()
            new_state = Qt.Checked if current_state == Qt.Unchecked else Qt.Unchecked
            item.setCheckState(new_state)

class TodoView(QListView):
    """自定义视图,显示待办事项列表"""
    def __init__(self, model):
        super().__init__()
        self.setModel(model)  # 设置模型
        self.setSelectionMode(QAbstractItemView.SingleSelection)  # 设置为单选模式

class MainWindow(QMainWindow):
    """主窗口,充当控制器的角色"""
    def __init__(self):
        super().__init__()
        self.setWindowTitle("简易待办事项列表 - PySide6 MVC示例")
        self.resize(400, 500)

        # 初始化模型和视图
        self.model = TodoModel()
        self.view = TodoView(self.model)

        # 创建UI控件
        self.input_field = QLineEdit()
        self.input_field.setPlaceholderText("输入新的待办事项...")
        self.input_field.returnPressed.connect(self.add_item)  # 按回车键添加

        self.add_button = QPushButton("添加")
        self.add_button.clicked.connect(self.add_item)

        self.delete_button = QPushButton("删除选中")
        self.delete_button.clicked.connect(self.delete_item)

        # 设置布局
        input_layout = QHBoxLayout()
        input_layout.addWidget(self.input_field)
        input_layout.addWidget(self.add_button)

        button_layout = QHBoxLayout()
        button_layout.addWidget(self.delete_button)

        main_layout = QVBoxLayout()
        main_layout.addWidget(self.view)
        main_layout.addLayout(input_layout)
        main_layout.addLayout(button_layout)

        container = QWidget()
        container.setLayout(main_layout)
        self.setCentralWidget(container)

    def add_item(self):
        """处理添加新待办事项的逻辑"""
        text = self.input_field.text()
        self.model.add_item(text)
        self.input_field.clear()  # 清空输入框

    def delete_item(self):
        """处理删除选中待办事项的逻辑"""
        current_index = self.view.currentIndex()
        self.model.remove_selected_item(current_index)

if __name__ == "__main__":
    app = QApplication(sys.argv)
    window = MainWindow()
    window.show()
    sys.exit(app.exec())

这个示例清晰地展示了MVC架构的三个核心部分:

  1. 模型 (Model – TodoModel): 继承自 QStandardItemModel,负责管理应用程序的数据。 提供了 add_item, remove_selected_item等方法来操作数据。 数据变化会自动通知视图更新。
  2. 视图 (View – TodoView): 继承自 QListView,负责将模型中的数据呈现给用户。 通过 setModel()方法与模型关联。 处理用户的界面交互,如选择项目。
  3. 控制器 (Controller – MainWindow): 协调模型和视图之间的交互。 包含UI控件(按钮、输入框)并连接它们的信号(如 clicked, returnPressed)到相应的槽函数(如 add_item, delete_item)。 当用户执行操作时,控制器调用模型的方法来更新数据,视图会自动更新以反映这些变化。

总结

QApplication驱动整个应用的生命周期和事件处理;QWidget及其子类构成界面的基本元素;布局管理器 负责这些元素的优雅排列;信号与槽 机制让这些元素能够响应用户交互并进行通信;Model-View 架构则为复杂数据的展示提供了清晰、高效的解决方案。

© 版权声明

相关文章

1 条评论

您必须登录才能参与评论!
立即登录
  • 头像
    椰子树花_ 投稿者

    收藏了,感谢分享

    无记录