[PyQt] Weird behaviour of destroyed() slots

Phil Thompson phil at riverbankcomputing.com
Sat Jul 26 17:10:28 BST 2008


On Wed, 23 Jul 2008 15:42:18 +0200, Giovanni Bajo <rasky at develer.com>
wrote:
> Hi Phil:
> 
>
=============================================================================
> import sip
> from PyQt4.Qt import *
> 
> called = []
> 
> class Core(QObject):
>      def __init__(self, parent=None):
>          QWidget.__init__(self, parent)
>          QObject.connect(self, SIGNAL("destroyed()"), self.callback)
>          QObject.connect(self, SIGNAL("destroyed()"), lambda: 
> self.callback())
>      def callback(self):
>          called.append("done")
> 
> app = QApplication([])
> core = Core(app)
> sip.delete(core)
> 
> assert len(called) == 2, called
>
=============================================================================
> Traceback (most recent call last):
>    File "bugpyqt.py", line 18, in <module>
>      assert len(called) == 2, called
> AssertionError: ['done']
> 
> The slot with "lambda" is called, but the other one is not.

The reason is that PyQt knows that self is being destroyed and
self.callback may be a wrapped C++ method (although it isn't in this case)
so it won't invoke it.

Obviously it doesn't know what the lambda is going to do and will always
invoke it.

I think the behaviour is pretty reasonable.

Phil



More information about the PyQt mailing list