On Sat, 2 Jan 2010 13:15:52 +0300, z <[email protected]> wrote:
> Hello everybody, and happy new year!
> to the point:
> In python it is possible to override some method of an instance,
> assigning to a "instance.methodname" a new value (which must be
> callabe with the same number of arguments, to be useful)
> For example i'd like to intercept events, coming to some widget,
> having this widget instance. It is easy to achieve, if i define this
> widget's class myself, and therefore can redefine event() method in
> class definiion. But suppose, that i just providing an interface for
> using by other parties. One, who using it only give me an instance,
> which class definition i can not control.
> This is an example program, which defines a hook function, and
> replaces instance's original event() method with it (for the start we
> will see how it works for QGraphicsWidget):
> ###########################
> from PyQt4 import QtGui, QtCore
> 
> app = QtGui.QApplication(sys.argv)
> 
> # suppose this class is defined somewhere else
> class Target(QtGui.QGraphicsWidget):
>     def __init__(self):
>         QtGui.QGraphicsWidget.__init__(self)
> 
> target = Target()
> target.show()
> 
> eventOrig = target.event
> 
> # intercept function, which just prints incoming event type, and
> passes further processing to original event()
> def eventHook(ev):
>     print 'HOOK', ev.type()
>     return eventOrig(ev)
> 
> target.event = eventHook
> 
> # Let's trigger an event()
> QtGui.QApplication.postEvent(target,
> QtCore.QEvent(QtCore.QEvent.LayoutRequest))
> target.resize(200,200)
> 
> sys.exit(app.exec_())
> ############################
> 
> Of course, it is not fully complete and sane code, but it
> demonstrates, that this approach works fine. This is console output of
> this program:
> ###########
> HOOK 181
> HOOK 76
> ############
> (181 is QEvent.GraphicsSceneResize, and 76 is layoutrequest ) So it
> works for QGraphicsWidget.
> But it does not work for QWidget. i.e. if the class is defined as:
> ############
> class Target(QtGui.QWidget):
>    def __init__(self):
>        QtGui.QWidget.__init__(self)
> #############
> Nothing appears on output at all. But the program runs flawlessly,
> (and shows main window, containing this widget)
> 
> So the question is: what's the difference? Why it works for
> QGraphicsWidget, but not QWidget? Is it some peculiarities of Qt event
> processing? Or is it PyQt? Or is it my system config or installed
> software gone wrong?
> 
> P.S: running system config:
> - linux x86_64
> - python 2.6
> - PyQt 4.6.2
> - Qt 4.6

PyQt caches lookups for Python reimplementations of methods. Monkey
patching will only work if you patch a method before it is looked up for
the first time. Your example will work for QWidget if you move the call to
show() after you patch it.

Phil
_______________________________________________
PyQt mailing list    [email protected]
http://www.riverbankcomputing.com/mailman/listinfo/pyqt

Reply via email to