PyQt GUI编程——信号与槽

PyQt中使用信号与槽的机制实现对象之间的通信。

信号

当对象改变其状态时,信号就由该对象发射出去,并且对象只负责发送信号,它不知道另一端是谁在接收这个信号。这样就做到了真正的信息封装,能确保对象被当作一个真正的软件组件来使用。

用于接收信号,并且槽只是普通的对象成员函数。一个槽并不知道是否有其他信号自己相连接,而且对象并不了解具体的通信机制。

信号和槽的绑定

 通过调用QObject对象的connect()函数将某个对象的信号与另外一个对象的槽函数相关联。这样当发射者发射信号时,接受者的槽函数将被调用。

一个信号可以连接到多个槽,当信号发出后,槽函数都会被调用,但是调用的顺序是随机的,不确定的。

多个信号可以连接到同一个槽,其中任何一个信号发出,槽函数都会被执行。

信号和槽的连接可以被移除,PyQt5提供了disconnect()成员函数来进行解绑。

信号可以和另外一个信号进行关联;第一个信号发出后,第二个信号也同时发送。

一个演示信号和槽的关系的样例

# -*- coding: utf-8 -*-

import sys
from PyQt5.QtGui import *
from PyQt5.QtCore import *
from PyQt5.QtWidgets import *


class SignalSlot(QWidget):
   def __init__(self):
      super(SignalSlot, self).__init__()
      self.initUI()

   def initUI(self):
      self.controlsGroup = QGroupBox('信号和槽')
      self.lcdNumber = QLCDNumber(self)  # 创建lcdNumber控件
      self.slider = QSlider(Qt.Horizontal, self)   # 创建slider控件
      self.pBar = QProgressBar(self)  # 创建ProgressBar控件
      vbox = QVBoxLayout()  # 创建垂直布局
      vbox.addWidget(self.pBar)  # 将pBar 控件加入布局中
      vbox.addWidget(self.lcdNumber)
      vbox.addWidget(self.slider)
      self.controlsGroup.setLayout(vbox)
      controlsLayout = QGridLayout()  # 常见网格布局
      self.label1 = QLabel('保存状态:')  # 添加标签
      self.saveLabel = QLabel()
      self.label2 = QLabel('运行状态:')
      self.runLabel = QLabel()
      self.buttonSave = QPushButton('保存')  # 添加按钮
      self.buttonRun = QPushButton('运行')
      self.buttonStop = QPushButton('停止')
      self.buttonDisconnect = QPushButton('解除关联')
      self.buttonConnect = QPushButton('绑定关联')
      controlsLayout.addWidget(self.label1, 0, 0)  # 在网格布局中1行1列添加控件
      controlsLayout.addWidget(self.saveLabel, 0, 1)
      controlsLayout.addWidget(self.label2, 1, 0)
      controlsLayout.addWidget(self.runLabel, 1, 1)
      controlsLayout.addWidget(self.buttonSave, 2, 0)
      controlsLayout.addWidget(self.buttonRun, 2, 1)
      controlsLayout.addWidget(self.buttonStop, 2, 2)
      controlsLayout.addWidget(self.buttonDisconnect, 3, 0)
      controlsLayout.addWidget(self.buttonConnect, 3, 1)
      layout = QHBoxLayout()
      layout.addWidget(self.controlsGroup)
      layout.addLayout(controlsLayout)
      self.setLayout(layout)
      self.slider.valueChanged.connect(self.pBar.setValue)
      self.slider.valueChanged.connect(self.lcdNumber.display)
      self.buttonRun.clicked.connect(self.buttonSave.clicked)
      self.buttonSave.clicked.connect(self.showMessage)
      self.buttonRun.clicked.connect(self.showMessage)
      self.buttonDisconnect.clicked.connect(self.unbindConnection)
      self.buttonConnect.clicked.connect(self.bindConnection)
      self.buttonStop.clicked.connect(self.stop)
      self.setGeometry(300, 500, 500, 180)
      self.setWindowTitle('信号和槽')

   def showMessage(self):
      if self.sender().text() == "保存":
         self.saveLabel.setText("Saved")
      elif self.sender().text() == "运行":
         self.saveLabel.setText("Saved")
         self.runLabel.setText("Running")

   def unbindConnection(self):
      self.slider.valueChanged.disconnect()

   def bindConnection(self):
      self.slider.valueChanged.connect(self.pBar.setValue)
      self.slider.valueChanged.connect(self.lcdNumber.display)

   def stop(self):
      self.saveLabel.setText('')
      self.runLabel.setText('')


if __name__ == '__main__':
   app = QApplication(sys.argv)
   ex = SignalSlot()
   ex.show()
   sys.exit(app.exec_())
-------------------------------------------------------------代码分割线--------------------------------------------

1-47行生成用户界面

47-54行连接了信号与槽。

self.slider.valueChanged.connect(self.pBar.setValue)   

连接滑动条的改变(信号) 到进度条显示(槽)

self.slider.valueChanged.connect(self.lcdNumber.display)

连接滑动条的改变(信号) 到LCD面板显示(槽)

self.buttonRun.clicked.connect(self.buttonSave.clicked)

连接运行按钮点击操作(信号) 到保存按钮点击操作(信号)

self.buttonSave.clicked.connect(self.showMessage)

连接保存按钮点击操作(信号) 到标签内容显示(槽)

self.buttonRun.clicked.connect(self.showMessage)

连接运行按钮点击操作(信号) 到标签内容显示(槽)

self.buttonDisconnect.clicked.connect(self.unbindConnection)

连接解除关联按钮点击操作(信号) 到解除绑定操作(槽)

self.buttonConnect.clicked.connect(self.bindConnection) 

连接绑定关联按钮点击操作(信号) 到绑定操作(槽)

self.buttonStop.clicked.connect(self.stop)

连接停止按钮点击操作(信号)到停止操作(槽)

66-67行解除了信号和槽的关联

def unbindConnection(self): self.slider.valueChanged.disconnect()

解除滑动条的改变(信号)的一切关联。

--------------------------------------------------------------------------------------

本文实例来源:《Python程序设计》人民邮电出版社 王学军 胡畅霞 韩艳峰 主编

That's All .Thankyou!

猜你喜欢

转载自blog.csdn.net/qq_41377419/article/details/82417951