I can't figure out why this program is failing.
#!/usr/bin/env python
from __future__ import division, print_function
from future_builtins import *
import types
import libui as ui
from PyQt4 import QtCore
import sip
p = ui.QPoint()
q = QtCore.QPoint()
def _q_getattr(self, attr):
print("get %s" % attr)
value = getattr(sip.wrapinstance(self.myself(), QtCore.QPoint), attr)
print("get2 %s returned %s" % (attr, value))
return value
p.__getattr__ = types.MethodType(_q_getattr, p)
print(p.__getattr__('x')()) # Works! Prints "0"
print(p.x()) # AttributeError: 'QPoint' object has no attribute 'x'
I used Boost.Python to create libui, which exposes the class QPoint. I aso included PyQt4, which has a sip-exposed QPoint. I'm trying to accomplish a mapping between the two types.
I checked that p
is a new-style class, so why isn't __getattr__
being called for p.x()
?
I suggest that you not attempt to expose QPoint in boost python. You should be able to register converters to/from python with boost that will use the SIP api functions to convert QPoint from/to python as the sip objects.
I've done it, but not recently enough to give more details.
This is an example how to integrate PyQt4 and boost::python
first of all we must define wrap/unwrap function to deal with bare pointers
after that we must register all classes we want integrate to
and for example we have class that works with.. QLabel:
we must expose this class to python too:
now we a ready to interaction, on C++-size do something like this
python:
In other case if you wan't send you own Q-object to PyQt4 :
python:
And this is my real little helper:
This is somewhat similar to the issue someone else has encountered just yesterday. In short, it seems like special methods (like
__getattr__
,__str__
,__repr__
,__call__
and so on) aren't overridable in new-style class instance, i.e. you can only define them in its type.And here's an adaptation of my solution for that problem which should hopefully work for yours: