我无法理解 pyuic4 主要使用的 connectSlotsByName() 方法。到目前为止,该类在 PyQt 文件中是单个类,这是可以的,因为我们可以使用 self ,它将在整个过程中与单个对象关联。但是当我们尝试时要使用不同文件中的各种类,就会出现问题并需要使用 connectSlotsByName() 。这是我遇到的奇怪情况。
我创建了一个堆叠小部件..
我在上面放置了我的第一个小部件。它有一个名为“下一步 >”的按钮。
单击下一步时,它会隐藏当前小部件并添加另一个具有“单击我”按钮的小部件。
这里的问题是第二个“点击我”按钮的点击事件没有被捕获。这是我可以为我的原始问题给出的一个最小的例子。请帮助我。
这是文件 No.1..(它具有父级堆叠小部件及其第一页)。单击下一步时,它会添加第二页,其中 file2 中有“clickme”按钮。
from PyQt4 import QtCore, QtGui
import file2
class Ui_StackedWidget(QtGui.QStackedWidget):
def __init__(self,parent=None):
QtGui.QStackedWidget.__init__(self,parent)
self.setObjectName("self")
self.resize(484, 370)
self.setWindowTitle(QtGui.QApplication.translate("self", "stacked widget", None, QtGui.QApplication.UnicodeUTF8))
self.createWidget1()
def createWidget1(self):
self.page=QtGui.QWidget()
self.page.setObjectName("widget1")
self.pushButton=QtGui.QPushButton(self.page)
self.pushButton.setGeometry(QtCore.QRect(150, 230, 91, 31))
self.pushButton.setText(QtGui.QApplication.translate("self", "Next >", None, QtGui.QApplication.UnicodeUTF8))
self.addWidget(self.page)
QtCore.QMetaObject.connectSlotsByName(self.page)
QtCore.QObject.connect(self.pushButton,QtCore.SIGNAL('clicked()'),self.showWidget2)
def showWidget2(self):
self.page.hide()
obj=file2.widget2()
obj.createWidget2(self)
if __name__ == "__main__":
import sys
app = QtGui.QApplication(sys.argv)
ui = Ui_StackedWidget()
ui.show()
sys.exit(app.exec_())
Run Code Online (Sandbox Code Playgroud)
这是文件2
from PyQt4 import QtGui,QtCore
class widget2():
def createWidget2(self,parent):
self.page = QtGui.QWidget()
self.page.setObjectName("page")
self.parent=parent
self.groupBox = QtGui.QGroupBox(self.page)
self.groupBox.setGeometry(QtCore.QRect(30, 20, 421, 311))
self.groupBox.setObjectName("groupBox")
self.groupBox.setTitle(QtGui.QApplication.translate("self", "TestGroupBox", None, QtGui.QApplication.UnicodeUTF8))
self.pushButton = QtGui.QPushButton(self.groupBox)
self.pushButton.setGeometry(QtCore.QRect(150, 120, 92, 28))
self.pushButton.setObjectName("pushButton")
self.pushButton.setText(QtGui.QApplication.translate("self", "Click Me", None, QtGui.QApplication.UnicodeUTF8))
self.parent.addWidget(self.page)
self.parent.setCurrentWidget(self.page)
QtCore.QMetaObject.connectSlotsByName(self.page)
QtCore.QObject.connect(self.pushButton,QtCore.SIGNAL('clicked()'),self.printMessage)
def printMessage(self):
print("Hai")
Run Code Online (Sandbox Code Playgroud)
尽管在两个小部件中(我的意思是页面)
QtCore.QMetaObject.connectSlotsByName(self.page)
Run Code Online (Sandbox Code Playgroud)
第二个对话框中的点击信号未得到处理。预先感谢..可能是一个初学者的问题..
首先,这是最小的工作示例:
from sys import argv, exit
from PyQt4 import QtCore, QtGui
class widget2(QtGui.QWidget):
def __init__(self, args):
self.app = MainApp(args)
QtGui.QWidget.__init__(self)
self.setObjectName('I')
self._layout = QtGui.QVBoxLayout(self)
self.setLayout(self._layout)
self.pushButtoninWidget2 = QtGui.QPushButton(self)
self.pushButtoninWidget2.setObjectName("pushButtoninWidget2")
self.pushButtoninWidget2.setText('Click NOW!')
self._layout.addWidget(self.pushButtoninWidget2)
QtCore.QMetaObject.connectSlotsByName(self)
@QtCore.pyqtSlot()
def on_pushButtoninWidget2_clicked(self):
print("Hai")
class MainApp(QtGui.QApplication):
def __init__(self, args):
QtGui.QApplication.__init__(self, args)
if __name__ == "__main__":
main = widget2(argv)
main.show()
exit(main.app.exec_())
Run Code Online (Sandbox Code Playgroud)
当您尝试按名称连接插槽时,您必须为插槽提供正确的名称,然后某人(moc、uic 或您通过调用 connectSlotsByName)必须连接它们。此类插槽的正确名称是:“on_PyQtObjectName_PyQtSignalName”。
请注意,如果我在示例中省略了 @QtCore.pyqtSlot(),则每个适当的重载都会执行一次 slot (在本例中为两次)。
您确实需要直接调用 connectSlotsByNames,因为没有 moc,当您在 C++ 中使用 QT 时,它会为您完成此操作,并且您不使用 uic 和 .ui 文件。如果你想隐式连接插槽(我总是这样做,除了在.ui中直接连接的插槽),你最好使用更多的pytonish语法:button.clicked.connect(self._mySlot)。
看看https://riverbankcomputing.com/static/Docs/PyQt5/signals_slots.html#connecting-slots-by-name
您不需要致电connectSlotsByName(),只需删除这些线路即可。
在 中file2,调用QtCore.QMetaObject.connectSlotsByName(self.page)尝试执行此操作:
QtCore.QObject.connect(self.pushButton, QtCore.SIGNAL('clicked()'), self.on_pushButton_clicked())
Run Code Online (Sandbox Code Playgroud)
这对你不起作用,因为self.on_pushBotton_clicked()插槽没有定义。我发现在 PyQt 中创建自己的连接是最简单的...我建议删除对两个类的调用connectSlotsByName...您不需要它。
另外,你的wdiget1类应该设置它的pushButton 的名称(最好是“pushButton”以外的名称,以避免与 中的按钮混淆widget2)。