cfi*_*cfi 5 super signals-slots pyside python-3.x
是否可以从基类继承信号,并在派生类中将连接方法连接到它们?如果是,怎么办?
实例化MyObject的MyWidget,并在微件起反应要由物体发射的信号。
from PySide.QtGui import QApplication, QMainWindow
from PySide.QtCore import QObject, QTimer, Signal
from PySide.QtGui import QLabel
class MyObject(QObject):
sig = Signal()
def __init__(self, parent=None):
super().__init__(parent)
QTimer.singleShot(3000, self.alert)
QTimer.singleShot(5000, self.exit)
def alert(self):
self.sig.emit()
def exit(self):
print('All done')
exit(0)
class MyWidget(QLabel):
def __init__(self, parent=None):
super().__init__(parent)
self.monitor = MyObject(self)
self.monitor.sig.connect(self.update)
def update(self):
print(2)
app = QApplication([])
w = MyWidget()
w.show()
app.exec_()
Run Code Online (Sandbox Code Playgroud)
这是一个小巧但有效的示例,它打开了一个最小的空白窗口,self.monitor由小部件实例化的对象在3秒和5秒后发出计时器信号。第一个提示窗口小部件只在控制台上打印一个数字,第二个提示导致应用程序退出。
为了继承,仅将小部件类更改为:
class MyWidget(MyObject, QLabel):
def __init__(self, parent=None):
super().__init__(parent)
self.sig.connect(self.update)
def update(self):
print(2)
Run Code Online (Sandbox Code Playgroud)
如果在控制台中运行此命令,则不会打印任何内容,但会发生分段错误。为什么?可以挽救吗?
super()有趣的是,如果两个类都更改为不使用super(),则该示例再次起作用:
class MyObject(QObject):
sig = Signal()
def __init__(self, parent=None):
QObject.__init__(self, parent)
QTimer.singleShot(3000, self.alert)
QTimer.singleShot(5000, self.exit)
def alert(self):
self.sig.emit()
def exit(self):
print('All done')
exit(0)
class MyWidget(MyObject, QLabel):
def __init__(self, parent=None):
MyObject.__init__(self, parent)
QLabel.__init__(self, parent)
self.sig.connect(self.update)
def update(self):
print(2)
Run Code Online (Sandbox Code Playgroud)
通常,我更喜欢使用super(),但也许我需要重新考虑?我有意链接到有关super()Python 用法的两篇有争议的文章。现在,您将对如何super()正确使用pyside感兴趣,或者对为什么在pyside中根本不起作用的解释感兴趣。
较小的更新:
使用继承并super()删除所有与信号相关的代码时,此示例可以打开窗口且不会出现段错误。因此似乎有迹象表明super()初始化和信号的组合会导致问题。
次要update2:
..并在注释掉时self.sig.connect启动窗口,并且仅在触发5秒信号退出应用程序时才会出现段错误。
(这是带有CPython 3.3.1解释器的Ubuntu 13.04系统上的Qt 4.8.4,Pyside 1.1.2)
到目前为止,我能想到的满足标准(a)继承和(b)使用的唯一解决方案 - 或者更确切地说是解决方法 -super()是防止钻石关系,正如用户 tcaswell 的评论所启发的那样。
对于我的用例来说,保留任何消费者类的继承(对于自定义小部件)至关重要。另一方面,目前保证所有使用类都将(间接)从QObject. 因此,无需从 派生MyObject,QObject尽管这实际上创建了一个真正的抽象 MixIn 类:它不能独立使用,并且对使用类有接口要求。我不确定我是否喜欢它。
这是工作代码:
from PySide.QtGui import QApplication, QMainWindow
from PySide.QtCore import QObject, QTimer, Signal
from PySide.QtGui import QLabel
class MyObject:
sig = Signal()
def __init__(self, parent=None):
super().__init__(parent)
QTimer.singleShot(3000, self.alert)
QTimer.singleShot(5000, self.exit)
def alert(self):
self.sig.emit()
def exit(self):
print('All done')
exit(0)
class MyWidget(MyObject, QLabel):
def __init__(self, parent=None):
super().__init__(parent)
self.sig.connect(self.update)
def update(self):
print(2)
app = QApplication([])
w = MyWidget()
w.show()
app.exec_()
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1083 次 |
| 最近记录: |