8 #ifndef PXR_BASE_TF_MAKE_PY_CONSTRUCTOR_H
9 #define PXR_BASE_TF_MAKE_PY_CONSTRUCTOR_H
16 # define TF_MAX_ARITY 7
17 #endif // TF_MAX_ARITY
33 #include "pxr/external/boost/python/def_visitor.hpp"
34 #include "pxr/external/boost/python/dict.hpp"
35 #include "pxr/external/boost/python/errors.hpp"
36 #include "pxr/external/boost/python/list.hpp"
37 #include "pxr/external/boost/python/object/iterator.hpp"
38 #include "pxr/external/boost/python/raw_function.hpp"
39 #include "pxr/external/boost/python/tuple.hpp"
40 #include "pxr/external/boost/python/type_id.hpp"
44 #include <type_traits>
85 namespace Tf_MakePyConstructor {
87 namespace bp = pxr_boost::python;
89 template <
typename CTOR>
95 template <
typename CLS>
97 c.def(
"__init__", CTOR::template init_callable<CLS>(),
_doc.c_str());
100 template <
class CLS,
class Options>
101 void visit(CLS &
c,
char const*
name, Options& options)
const {
103 c.def(name, CTOR::template init_callable<CLS>(options),
_doc.c_str());
112 template <
typename CTOR>
118 template <
typename CLS>
132 if (PyObject_HasAttrString(c.ptr(),
"__new__"))
133 c.attr(
"__new__") = c.attr(
"__new__");
134 c.def(
"__new__", CTOR::template __new__<CLS>,
_doc.c_str());
135 c.staticmethod(
"__new__");
138 c.def(
"__init__", bp::raw_function(
_DummyInit));
141 template <
class CLS,
class Options>
142 void visit(CLS &
c,
char const*
name, Options& options)
const {
155 if (PyObject_HasAttrString(c.ptr(),
"__new__"))
156 c.attr(
"__new__") = c.attr(
"__new__");
157 c.def(
"__new__", CTOR::template __new__<CLS>,
163 c.staticmethod(
"__new__");
166 c.def(
"__init__", bp::raw_function(
_DummyInit));
174 template <
typename T>
181 template <
typename T>
184 "Type T must support refcount unique changed notification.");
186 const void *uniqueId) {
194 template <
typename CLS,
typename T>
198 typedef typename CLS::metadata::holder Holder;
199 typedef typename bp::objects::instance<Holder> instance_t;
201 typedef typename CLS::metadata::held_type HeldType;
206 allocate(
self.
ptr(), offsetof(instance_t,
storage),
sizeof(Holder));
209 Holder *holder = (
new (
memory) Holder(held));
212 bp::throw_error_already_set();
218 bp::detail::initialize_wrapper(
self.
ptr(), &(*(held.operator->())));
219 holder->install(
self.
ptr());
224 Policy::PostInstall(
self, t, held.GetUniqueIdentifier());
227 Holder::deallocate(
self.
ptr(), memory);
throw;
233 template <
typename WeakPtr,
typename P>
235 typedef std::remove_reference_t<P>
Ptr;
245 WeakPtr ptr(static_cast<typename WeakPtr::DataType *>
250 return bp::incref(Py_None);
255 Policy::PostInstall(result, p, ptr.GetUniqueIdentifier());
256 return bp::incref(result.ptr());
261 return pxr_boost::python::objects::registered_class_object(
262 pxr_boost::python::type_id<typename WeakPtr::DataType>()).get();
266 template <
typename WeakPtr =
void>
268 template <
typename FactoryResultPtr>
283 template <
typename SIG,
size_t EXTRA_ARITY = 0>
296 "Duplicate will be ignored.",
303 template <
typename SIG,
size_t EXTRA_ARITY>
304 SIG *CtorBase<SIG, EXTRA_ARITY>::_func =
nullptr;
315 template <
typename T>
325 template <
typename T>
335 template <
typename T>
345 template <
typename T>
355 template <
typename T>
366 template <
typename T =
void>
374 template <
typename T>
381 template <
typename T>
388 using namespace pxr_boost::python;
393 pxr_boost::python::list l;
394 for (
typename SeqType::const_iterator i = seq.begin();
395 i != seq.end(); ++i) {
396 l.append(
object(handle<>(RefPtrFactory()(*i))));
398 return pxr_boost::python::incref(l.ptr());
407 namespace Tf_MakePyConstructor {
409 template <
typename R,
typename... Args>
416 template <
typename CLS>
418 return bp::make_function(__init__<CLS>);
421 template <
typename CLS,
typename Options>
423 return bp::make_function(__init__<CLS>, o.policies(), o.keywords()) ;
426 template <
typename CLS>
429 Install<CLS>(
self, Base::_func(
args...), m);
433 template <
typename R,
typename... Args>
441 typedef typename CLS::metadata::held_type HeldType;
443 R r((Base::_func(
args...)));
446 bp::throw_error_already_set();
452 bp::detail::initialize_wrapper(ret.ptr(),
get_pointer(h));
454 bp::setattr(ret,
"__class__", cls);
461 template <
typename R,
typename... Args>
478 typename Base::Traits::template NthArg<(
Arity::value-2)>>) &&
481 typename Base::Traits::template NthArg<(
Arity::value-1)>>),
482 "InitCtorWithVarArgs requires a function of form "
483 "(..., const tuple&, const dict&)");
485 template <
typename CLS>
490 return bp::raw_function(__init__<CLS>, 1);
493 template <
typename CLS,
typename Options>
497 return bp::raw_function(
498 bp::make_function(__init__<CLS>, options.policies()),
502 template <
typename CLS,
size_t... I>
504 const bp::dict& kwargs,
505 std::index_sequence<I...>) {
510 const unsigned int expectedNamedArgs =
Arity::value - 2;
512 const unsigned int positionalArgs = bp::len(args) - 1;
513 if (positionalArgs < expectedNamedArgs) {
515 positionalArgTypes = {{
516 (bp::type_id<typename Base::Traits::template NthArg<I>>().
name())...
522 if (!joinedTypes.empty()) {
529 "Arguments to __init__ did not match C++ signature:\n"
530 "\t__init__(%s...)", joinedTypes.c_str()
542 typename Base::Traits::template NthArg<I>>>(args[I + 1])...,
543 bp::tuple(args.slice(expectedNamedArgs + 1, bp::len(args))), kwargs),
549 template <
typename CLS>
551 const bp::dict& kwargs) {
552 return __init__impl<CLS>(
563 template <
typename R,
typename SelfRef,
typename... Args>
570 template <
typename CLS>
572 return bp::make_function(__init__<CLS>);
575 template <
typename CLS,
typename Options>
577 return bp::make_function(__init__<CLS>, o.policies(), o.keywords());
580 template <
typename CLS>
583 Install<CLS>(
self, Base::_func(
self, args...), m);
587 template <
typename R,
typename ClsRef,
typename... Args>
596 typedef typename CLS::metadata::held_type HeldType;
598 R r(Base::_func(cls, args...));
601 bp::throw_error_already_set();
607 bp::detail::initialize_wrapper(ret.ptr(),
get_pointer(h));
609 bp::setattr(ret,
"__class__", cls);
619 #endif // PXR_BASE_TF_MAKE_PY_CONSTRUCTOR_H
GLsizei GLenum GLsizei GLsizei GLuint memory
Tf_MakePyConstructor::NewVisitor< typename Tf_MakePyConstructor::NewCtor< T > > TfMakePyNew(T *func, const std::string &doc=std::string())
TF_API std::string TfStringPrintf(const char *fmt,...)
Tf_MakePyConstructor::InitVisitor< typename Tf_MakePyConstructor::InitCtor< T > > TfMakePyConstructor(T *func, const std::string &doc=std::string())
CtorBase< R(SelfRef, Args...)> Base
friend class bp::def_visitor_access
static bp::object __new__(ClsRef cls, Args...args)
_RefPtrFactoryConverter< WeakPtrType, FactoryResultPtr > type
pxr_boost::python::object TfPyObject(T const &t, bool complainOnFailure=true)
getFileOption("OpenEXR:storage") storage
typename std::conditional< B, T, F >::type conditional_t
GLsizei const GLfloat * value
Tf_MakePyConstructor::InitVisitor< typename Tf_MakePyConstructor::InitCtorWithVarArgs< T > > TfMakePyConstructorWithVarArgs(T *func, const std::string &doc=std::string())
Tf_PySequenceToListConverterRefPtrFactory< T > type
PyObject * operator()(Ptr const &p) const
static bp::object __init__impl(const bp::tuple &args, const bp::dict &kwargs, std::index_sequence< I...>)
TfMetaLength< Args...> Arity
ARCH_API std::string ArchGetDemangled(const std::string &typeName)
static bp::object init_callable(Options &o)
static void SetFunc(Sig *func)
**But if you need a result
PyTypeObject const * get_pytype() const
PyTypeObject const * get_pytype() const
Tf_MakePyConstructor::InitVisitor< typename Tf_MakePyConstructor::InitCtorWithBackReference< T > > TfMakePyConstructorWithBackReference(T *func, const std::string &doc=std::string())
PXR_NAMESPACE_OPEN_SCOPE TF_API bool TfPyConvertTfErrorsToPythonException(TfErrorMark const &m)
Tf_MakePyConstructor::NewVisitor< typename Tf_MakePyConstructor::NewCtorWithClassReference< T > > TfMakePyNewWithClassReference(T *func, const std::string &doc=std::string())
Y * get_pointer(TfWeakPtrFacade< X, Y > const &p)
std::decay_t< decltype(make_index_sequence_impl< N >())> make_index_sequence
OIIO_FORCEINLINE bool extract(const vbool4 &a)
InitCtorWithBackReference(Sig *func)
friend class bp::def_visitor_access
InitCtorWithVarArgs(Sig *func)
std::weak_ptr< T > WeakPtr
NewVisitor(const std::string &doc=std::string())
TF_API bool TfPyIsNone(pxr_boost::python::object const &obj)
Return true iff obj is None.
static bp::object __new__(object &cls, Args...args)
InitVisitor(const std::string &doc=std::string())
PyObject * operator()(T seq) const
TF_API void TfPyThrowTypeError(const char *msg)
typename std::remove_reference< T >::type remove_reference_t
CtorBase< R(Args...)> Base
GLuint const GLchar * name
std::remove_reference_t< T > SeqType
static bp::object init_callable()
std::string TfStringJoin(ForwardIterator begin, ForwardIterator end, const char *separator=" ")
static void __init__(SelfRef self, Args...args)
static bp::object init_callable()
void visit(CLS &c, char const *name, Options &options) const
GLfloat GLfloat GLfloat GLfloat h
std::enable_if_t< Tf_PyIsRefPtr< Ptr >::value > Tf_PySetPythonIdentity(Ptr const &, PyObject *)
CtorBase< R(ClsRef, Args...)> Base
PXR_NAMESPACE_CLOSE_SCOPE PXR_NAMESPACE_OPEN_SCOPE
static void __init__(object &self, Args...args)
void Tf_PyAddPythonOwnership(Ptr const &t, const void *uniqueId, PyObject *obj)
TF_API bp::object _DummyInit(bp::tuple const &, bp::dict const &)
#define PXR_NAMESPACE_CLOSE_SCOPE
void Install(object const &self, T const &t, TfErrorMark const &m)
**If you just want to fire and args
OIIO_UTIL_API const char * c_str(string_view str)
std::conditional_t< std::is_same< WeakPtr, void >::value, TfWeakPtr< typename FactoryResultPtr::DataType >, WeakPtr > WeakPtrType
NewCtorWithClassReference(Sig *func)
static bp::object init_callable(Options &options)
TfFunctionTraits< R(SelfRef, Args...)* > Traits
CtorBase< R(Args...)> Base
static void PostInstall(object const &self, TfRefPtr< T > const &ptr, const void *uniqueId)
typename Tf_GetFuncSig< Fn >::Type TfFunctionTraits
static void PostInstall(object const &self, T const &t, const void *)
static bp::object init_callable()
TF_API void TfPyThrowRuntimeError(const char *msg)
static bp::object __init__(const bp::tuple &args, const bp::dict &kwargs)
CtorBase< R(Args...), 2 > Base
void visit(CLS &c, char const *name, Options &options) const
static bp::object init_callable(Options &o)
std::remove_reference_t< P > Ptr
PcpNodeRef_ChildrenIterator begin(const PcpNodeRef::child_const_range &r)
Support for range-based for loops for PcpNodeRef children ranges.