15. 定时器控件

一、定时器控件

  在 PySide6 中,如果需要周期性地执行某项操作,就可以使用 QTimer 类实现。QTimer类表示计时器,它可以 定期发射 timeout 信号,执行与信号连接的槽函数,实现自动完成某些功能。时间间隔的长度 可以在 start() 方法中指定,以 毫秒 为单位。如果需要 停止定时器,则需要使用 stop() 方法。

  我们可以在终端中使用 pip 安装 PySide6 模块。默认是从国外的主站上下载,因此,我们可能会遇到网络不好的情况导致下载失败。我们可以在 pip 指令后通过 -i 指定国内镜像源下载

pip install pyside6 -i https://mirrors.aliyun.com/pypi/simple

  国内常用的 pip 下载源列表:

  用 QTimer 类创建实例对象的方法如下:

QTimer(parent:QWidget=Noone)

  其中,parent窗口 或者 容器 类控件。QTimer 是不可见的,当父类删除时,定时器也同时删除。

  定时器的常用方法如下:

# 实例方法
setInterval(msec:int) -> None                                                   # 设置信号发送的时间间隔,单位毫秒
interval() -> int                                                               # 获取信号发送的时间间隔,单位毫秒

isActive() -> bool                                                              # 判断信号是否激活

remainingTime() -> int                                                          # 获取据下次发送信号的时间,单位毫秒

setSingleShot(singleShot:bool) -> None                                          # 设置定时器是否为单次发送
isSingleShot() -> bool                                                          # 获取定时器是否为单次发送

setTimerType(atype:int) -> None                                                 # 设置定时器的类型
timerType() -> int                                                              # 获取定时器的类型

timerId() -> int                                                                # 获取定时器的ID

# 槽方法
start() -> None                                                                 # 启动定时器
start(msec:int) -> None                                                         # 经过msec毫秒后启动定时器
stop() -> None                                                                  # 停止定时器

# 静态方法
singleShot(msec:int, Callable) -> None                                                  # 经过msec毫米后,执行 调用Python的可执行函数Callable
singleShot(msec:int, receiver:QObject, member:bytes) -> None                            # 经过msec毫米后,执行 receiver的槽函数member
singleShot(msec:int, timerType:Qt.TimerType, receiver:QObject, member:bytes) -> None    # 经过msec毫米后,执行 receiver的槽函数member

  定时器只有一个信号 timeout()每经过固定的时间间隔发送一次信号,或者 只发送一次信号

timeout()                                                                       # 定时时间到发射信号

  使用定时器的步骤一般是先 创建定时器对象,用 setInterval(interval:int) 方法 设置定时器发送信号的时间间隔,然后将定时器的信号 timeout 与某个槽函数关联,最后用 start() 方法 启动定时器。如果定义了多个定时器,可以用 timeId() 方法获取定时器的编号。

  如果只需要定时器发送 1 次信号,可以设置 setSingleShot(enable:bool)True,否则将会 连续不断地发送信号,可以用 stop() 方法 停止定时器信号的发送。如果只是 1 次发送信号,也可以不用创建定时器对象,用定时器类的静态方法 singleShot() 直接连接某个控件的槽函数。

  定时器的精度与系统和硬件有关,用 setTimerType(type:Qt.TimerType) 方法可以 设置定时器的精度,其中参数 type Qt.TimerType 类型的枚举值,可以取值如下:

Qt.TimerType.PreciseTimer                                                       # 精确的定时器,保持1毫秒精度
Qt.TimerType.CoarseTimer                                                        # 精确度差的定时器,精度保持在时间间隔的5%范围内
Qt.TimerType.VeryCoarseTimer                                                    # 精度度非常差的定时器,精度是500毫秒

  我们新建一个 ui.py 文件,用来存放 UI 相关的代码。

from PySide6.QtWidgets import QWidget
from PySide6.QtWidgets import QLabel, QSpinBox, QPushButton, QRadioButton
from PySide6.QtWidgets import QGridLayout

class MyUi:
    def setupUi(self, window:QWidget):
        window.resize(300, 100)                                                 # 1.设置窗口对象大小

        layout = QGridLayout(window)                                            # 2.创建一个栅格布局
  
        time_interval_label = QLabel("定时时间(ms)", window)                    # 3.定时时间单行输入框,并添加到布局中
        layout.addWidget(time_interval_label, 0, 0,)

        self.time_interval_spinBox = QSpinBox(window)
        self.time_interval_spinBox.setRange(1, 99999)
        layout.addWidget(self.time_interval_spinBox, 0, 1, 1, 2)

        self.single_timing_radioButton = QRadioButton("单次定时", window)        # 4.创建是否单次定时按钮,并添加到布局中
        layout.addWidget(self.single_timing_radioButton, 1, 0, 1, 3)

        self.start_button = QPushButton("开始定时", window)                      # 5.创建开始定时和结束定时按钮,并添加到布局中
        self.stop_button = QPushButton("结束定时", window)
        layout.addWidget(self.start_button, 2, 0)
        layout.addWidget(self.stop_button, 2, 2)

        self.label = QLabel(window)                                             # 6.创建标签控件,并添加到布局中
        layout.addWidget(self.label, 3, 0, 1, 2)

  我们新建一个 widget.py 文件,用来存放业务逻辑相关的代码。

import sys

from PySide6.QtWidgets import QApplication, QWidget
from PySide6.QtCore import QTimer

from ui import MyUi

class MyWidget(QWidget):
    def __init__(self):
        super().__init__()                                                      # 1.调用父类Qwidget类的__init__()方法
      
        self.__ui = MyUi()
        self.__ui.setupUi(self)                                                 # 2.初始化页面

        self.timer = QTimer(self)                                               # 3.创建定时器
        self.number = 0

        self.__ui.start_button.clicked.connect(self.start_button_clicked)       # 4.关联按钮点击时触发信号
        self.__ui.stop_button.clicked.connect(self.stop_button_clicked)         # 5.关联按钮点击时触发信号

        self.timer.timeout.connect(self.timer_timeout)                          # 6.关联定时器定时时间到触发信号

    def start_button_clicked(self):
        self.number = 0

        interval = self.__ui.time_interval_spinBox.value()                      # 1.获取定时时间间隔

        if self.__ui.single_timing_radioButton.isChecked():                     # 2.判断是否单次定时
            self.timer.setSingleShot(True)
        else:
            self.timer.setSingleShot(False)

        self.timer.start(interval)                                              # 3.启动定时器

    def stop_button_clicked(self):
        self.timer.stop()                                                       # 1.停止定时器

    def timer_timeout(self):
        self.number += 1
        self.__ui.label.setText(f"number: {self.number}")

if __name__ == "__main__":
    app = QApplication(sys.argv)                                                # 1.创建一个QApplication类的实例
    window = MyWidget()                                                         # 2.创建一个窗口
    window.show()                                                               # 3.显示窗口
    sys.exit(app.exec())                                                        # 4.进入程序的主循环,并通过exit函数确保主循环安全结束
posted @ 2025-01-03 19:51  星光映梦  阅读(172)  评论(0)    收藏  举报