【发布时间】:2010-10-30 17:53:58
【问题描述】:
我有一个任务栏菜单,当单击它时,它会连接到获取触发事件的插槽。现在的问题是我想知道单击了哪个菜单项,但我不知道如何将该信息发送到连接的功能。这里是用来连接动作和函数的:
QtCore.QObject.connect(menuAction, 'triggered()', menuClickedFunc)
我知道有些事件会返回一个值,但trigger() 没有。那么我该如何实现呢?我必须自己发出信号吗?
【问题讨论】:
我有一个任务栏菜单,当单击它时,它会连接到获取触发事件的插槽。现在的问题是我想知道单击了哪个菜单项,但我不知道如何将该信息发送到连接的功能。这里是用来连接动作和函数的:
QtCore.QObject.connect(menuAction, 'triggered()', menuClickedFunc)
我知道有些事件会返回一个值,但trigger() 没有。那么我该如何实现呢?我必须自己发出信号吗?
【问题讨论】:
使用lambda
这是来自PyQt book 的示例:
self.connect(button3, SIGNAL("clicked()"),
lambda who="Three": self.anyButton(who))
顺便说一句,你也可以使用functools.partial,但我发现lambda的方法更简单明了。
【讨论】:
正如已经提到的here,您可以使用 lambda 函数将额外的参数传递给您要执行的方法。
在本例中,您可以将字符串 obj 传递给按下按钮时调用的函数 AddControl()。
# Create the build button with its caption
self.build_button = QPushButton('&Build Greeting', self)
# Connect the button's clicked signal to AddControl
self.build_button.clicked.connect(lambda: self.AddControl('fooData'))
def AddControl(self, name):
print name
来源:snip2code - Using Lambda Function To Pass Extra Argument in PyQt4
【讨论】:
使用 functools.partial
否则,如果您使用 lambda,您会发现在脚本运行时无法动态传递参数。
【讨论】:
def'ed 函数)是闭包,因此可以从其封闭范围中捕获绑定。 (是的,这也意味着作为第三种选择,您可以使用本地 def'ed 函数并动态地将参数传递给它。)此外,不要忘记您可以使用默认参数将动态值传递给 both。然而,话虽如此,我个人也更喜欢functools.partial,我自己的原因是它“感觉”比lambda 更轻量级(没有声称它确实如此)。
我还想补充一点,如果您只需要找出发送信号的小部件,您可以使用sender 方法。例如:
def menuClickedFunc(self):
# The sender object:
sender = self.sender()
# The sender object's name:
senderName = sender.objectName()
print senderName
【讨论】:
一般来说,您应该将每个菜单项连接到不同的插槽,并让每个插槽仅处理它自己的菜单项的功能。例如,如果您有“保存”、“关闭”、“打开”之类的菜单项,则应该为每个菜单项创建一个单独的插槽,而不是尝试在其中包含一个带有 case 语句的插槽。
如果您不想那样做,您可以使用QObject::sender() 函数来获取指向发送者的指针(即:发出信号的对象)。不过,我想听听更多关于您要完成的工作。
【讨论】: