[PyKDE] SIP automatically casting up to a QWidget
Phil Thompson
phil at riverbankcomputing.co.uk
Fri Feb 23 00:58:18 GMT 2007
On Thursday 22 February 2007 6:49 pm, Paul Giannaros wrote:
> On Thursday 22 February 2007 17:10, Giovanni Bajo wrote:
> > On 2/22/2007 5:32 PM, Paul Giannaros wrote:
> > >>> I have a class A that i'm wrapping with SIP. The class inherits from
> > >>> a bunch of other classes. One of the classes it inherits from also in
> > >>> turn inherits from QWidget. When I import the created module,
> > >>> whenever I call a method that is meant to return an instance of class
> > >>> A I get a QWidget instead. I can use sip.cast to get the QWidget back
> > >>> to an A instance, but that's not a very friendly solution.
> > >>> Can someone suggest why this is happening, or how to fix it?
> > >>
> > >> SIP needs to know the correct run-time type of your class: otherwise
> > >> when it receives a QWidget* it cannot know what type the class really
> > >> is.
> > >>
> > >> Have a look at how %ConvertToSubClassCode is implemented in
> > >> QtCore/qobject.sip and QtGui/qapplication.sip (assuming you're using
> > >> Qt4). Within your a.sip, you must add your own %ConvertToSubClassCode
> > >> that verifies if a generic QObject* is an instance of your type (class
> > >> A). SIP then knows how to "chain" all the other %ConvertToSubClassCode
> > >> in the object hierarchy, so your code needs only to verify your own
> > >> class.
> > >
> > > But I don't see why it's receiving a QWidget* -- the return type of the
> > > functions i'm calling are explicitly A*.
> >
> > Because elsewhere, in a point of your code that you are probably
> > ignoring, the instance is being returned as QWidget*. SIP executes the
> > %ConvertToSubClassCode *once* and create a Python object of type
> > QWidget; it register this Python an object within a hash table. After
> > that, every time the instance is returned by *any* method, it's looked
> > up in the hash table, and the Python wrapper (already constructed) is
> > found.
That can happen, but only if the object is first returned before the module
defining the more specific class is imported (ie. before the convertor code
handling the more specific class is loaded).
> > > Nevertheless, I implemented %ConvertToSubClassCode in class A (and
> > > class B which inherits QWidget) using
> > > sipMapStringToClass/sipStringTypeClassMap, and a QWidget is still being
> > > returned.
The convertor code fragments are invoked in the reverse order that the modules
were imported (or implicitly imported as a module will import the modules it
depends on before registering itself with the sip module). In other words, an
object will be given a class of QWidget if no other more specific modules
have identified it as a more specific class. If you think your (more
specific) module does identify it as a more specific class, then
your %ConvertToSubClassCode is probably buggy.
Phil
More information about the PyQt
mailing list