我在下面提出了一个简单的信号/插槽机制。当通过QSlider :: valueChanged()更改值时,QSlider将调用该信号。并通过QLCDNumber :: display()方法调用插槽。
令我感到困惑的是,为什么PyQt5的文档很少,而且大多数文档都会导致Qt5的链接。我对代码的具体问题是:
1)如果QSlider::valueChanged()(signal)期望一个整数作为参数,为什么我们只传入QLCDNumber::display()(slot)这是一个void函数。因此,没有任何内容可以传递。
2)在下面注释掉的代码中,我无法拨打第二个插槽。您可以为1个信号调用的插槽数量是否有限制?如果我如何在PyQt5中调用多个插槽。
编辑:我相信因为printLabel()不是一个定义的插槽,这就是我遇到问题的原因。我可以在:: connect()参数中包含任意数量的插槽吗?或者我是以一种黑客的方式接近这个。
import sys
from PyQt5.QtCore import (Qt)
from PyQt5.QtWidgets import (QWidget, QLCDNumber, QSlider,
QVBoxLayout, QApplication)
class Example(QWidget):
def __init__(self):
super().__init__()
self.initUI()
def printLabel(self, str):
print(str)
def initUI(self):
lcd = QLCDNumber(self)
sld = QSlider(Qt.Horizontal, self)
vbox = QVBoxLayout()
vbox.addWidget(lcd)
vbox.addWidget(sld)
self.setLayout(vbox)
#This line works
sld.valueChanged.connect(lcd.display)
#This line does not work
#sld.valueChanged.connect(lcd.display, self.printLabel("hi"))
self.setGeometry(300, 300, 250, 150)
self.setWindowTitle('Signal & slot')
self.show()
if __name__ == '__main__':
app = QApplication(sys.argv)
ex = Example()
sys.exit(app.exec_())
答案 0 :(得分:5)
按顺序记下你的观点:
Qt5文档包含至少90%的需要知道的内容,因此在PyQt5文档中重复这一点并不重要,而后者主要集中在PyQt特有的功能上。 (例如,参见Signals and Slots文章)。 Qt5是一个C ++库。你不需要了解C ++就可以使用PyQt(或者阅读Qt的优秀文档),但你很难完全避免使用它。
QSlider.valueChanged
信号向所有与其连接的插槽发送一个int值。 QLCDNUmber.display
槽接收字符串,int或float对象(即它有三个重载)。对于内置Qt插槽,必须存在与信号发送匹配的过载。但是PyQt中的用户定义的插槽可以是任何 python可调用对象,如果签名不匹配则不重要(任何额外的参数都将被丢弃)。话虽如此,可以使用pyqtSlot
装饰器(因此允许在PyQt中指定多个重载)为用户定义的槽定义显式签名。
正如上面提到的PyQt文章的第一部分所述,信号和插槽都可以有多个连接。本文还详细介绍了PyQt特定的API(包括pyqtSlot
),并提供了如何使用它们的示例。
以下是如何连接多个插槽的示例:
class Example(QWidget):
...
def initUI(self):
...
#connect to a built-in slot
sld.valueChanged.connect(lcd.display)
#connect to a user-defined lot
sld.valueChanged.connect(self.printLabel)
#any python callable will do
sld.valueChanged.connect(lambda x: print('lambda:', x))
...
def printLabel(self, value):
print('printLabel:', value)