diff options
author | Marcelo Lira <marcelo.lira@openbossa.org> | 2010-03-02 17:10:32 -0300 |
---|---|---|
committer | Marcelo Lira <marcelo.lira@openbossa.org> | 2010-03-02 17:10:32 -0300 |
commit | cff48628063b8cf145c01a0f84c19fabd75682db (patch) | |
tree | 163131831d13fd56e3c46bc2c3c1c138772d9139 /libshiboken/conversions.h | |
parent | ddc5bef058932584f5da644b606fad74707a63c7 (diff) |
Adds support for extensible converters for value type classes.
Value type classes without implicit conversions use the default
implementation provided by ValueTypeConverter. This commit updates
ValueTypeConverter to check for extended conversions, since even a
class without implicit conversions in one module could get some
conversion operators in another.
CppGenerator now writes 'isConvertible' calls to all object and
value types checks leaving the door open to extended conversions.
Diffstat (limited to 'libshiboken/conversions.h')
-rw-r--r-- | libshiboken/conversions.h | 28 |
1 files changed, 24 insertions, 4 deletions
diff --git a/libshiboken/conversions.h b/libshiboken/conversions.h index 3c14df321..48f28048a 100644 --- a/libshiboken/conversions.h +++ b/libshiboken/conversions.h @@ -37,6 +37,7 @@ #include <Python.h> #include <limits> +#include <memory> #include "pyenum.h" #include "basewrapper.h" @@ -190,7 +191,14 @@ template <> struct Converter<const void*> : Converter<void*> {}; template <typename T> struct ValueTypeConverter { - static inline bool isConvertible(PyObject* pyobj) { return false; } + // The basic version of this method also tries to use the extended 'isConvertible' method. + static inline bool isConvertible(PyObject* pyobj) + { + SbkBaseWrapperType* shiboType = reinterpret_cast<SbkBaseWrapperType*>(SbkType<T>()); + if (shiboType->ext_isconvertible) + return shiboType->ext_isconvertible(pyobj); + return false; + } static inline PyObject* toPython(void* cppobj) { return toPython(*reinterpret_cast<T*>(cppobj)); } static inline PyObject* toPython(const T& cppobj) { @@ -198,9 +206,21 @@ struct ValueTypeConverter SbkBaseWrapper_setContainsCppWrapper(obj, SbkTypeInfo<T>::isCppWrapper); return obj; } - // Classes with implicit conversions are expected to reimplement - // this to build T from its various implicit constructors. - static inline T toCpp(PyObject* pyobj) { return *Converter<T*>::toCpp(pyobj); } + // Classes with implicit conversions are expected to reimplement 'toCpp' to build T from + // its various implicit constructors. Even classes without implicit conversions could + // get some of those via other modules defining conversion operator for them, thus + // the basic Converter for value types checks for extended conversion and tries to + // use them if it is the case. + static inline T toCpp(PyObject* pyobj) + { + if (isConvertible(pyobj)) { + SbkBaseWrapperType* shiboType = reinterpret_cast<SbkBaseWrapperType*>(SbkType<T>()); + T* cptr = reinterpret_cast<T*>(shiboType->ext_tocpp(pyobj)); + std::auto_ptr<T> cptr_auto_ptr(cptr); + return *cptr; + } + return *reinterpret_cast<T*>(reinterpret_cast<Shiboken::SbkBaseWrapper*>(pyobj)->cptr); + } }; // Base converter meant to be inherited by converters for abstract classes and object types |