I'm trying to pass an object from python to C++. I want C++ to take control of
the object.
The object I'm trying to change ownership on is defined in it's module as
follows (superfluous code removed):
BOOST_PYTHON_MODULE(ComponentModule) {
class_<Components::Component,
std::auto_ptr<Components::Component> >("Component")
.def(init<>()) .def(init<bool,
boost::python::optional<const int> >()) .def(init<const
std::string&, int, boost::python::optional<bool, const int> >())
.def(init<const std::string&, const std::string&,
boost::python::optional<bool, const int> >()) ;
class_<Components::UseComponent,
std::auto_ptr<UseComponentWrap>, bases<Components::Component> >("UseComponent")
.def(init<>())
.def(init<const std::string&,bool, bool>())
.def(init<const Components::UseComponent&>()) ;
} }
And The object I want to take control is:
BOOST_PYTHON_MODULE(ItemModule) {
class_<Items::Item, bases<Entity> >("Item")
.def(init<Items::Item&>()) .def(init<const
std::string&>())
.def("RegisterComponent",&Items::Item::RegisterComponent )
; }
Register Component is the function that takes control of the component. It's
full definition is:
void Item::RegisterComponent(const std::string& indexName,
Components::Component* component) { auto it =
ComponentCollection.find(indexName); if (it !=
ComponentCollection.end()) {
delete it->second;
ComponentCollection.erase(it);
ComponentCollection[indexName] = component; }
The item posses the component until destroyed/overwritten.
A sample piece of python code would be:
healer = UseComponent("HealUseModule", True, True)print "Adding Healing
Component"CurrentItem.RegisterComponent("Healing Component", healer)
where CurrentItem is an item. The problem here is that when the component goes
out of scope in the python file, it get's deleted adn invalidated since C++
hasn't taken ownership of it. I tried following the advice here
http://www.boost.org/doc/libs/1_36_0/libs/python/doc/v2/faq.html#ownership
which is why I wrapped Component/UseComponent in an auto_ptr. Additionally fro,
this advice, I changed to RegisterComponent wrap to
.def("RegisterComponent", &RegisterComp)
where RegisterComp is
void RegisterComp(Items::Item& item, const std::string& compName,
std::auto_ptr<Components::UseComponent> comp)//, void* comp) {
item.RegisterComponent(compName, comp.get());
comp.release(); }
this fails, saying the Python argument types did not match the C++ signature.
I'm certain it's the std::auto_ptr<Components::UseComponent> comp argument that
is invalid because the call succeeds when that argument is removed but item and
name are left.
Am I doing something wrong? base on that snippet it should work. Is there
another way to do this? I know I should probably switch to smart_ptrs and I'm
considering it, but Id like to be able to know how to do this, even if its just
for future reference. Any help would be appreciated.
Thanks _______________________________________________
Cplusplus-sig mailing list
[email protected]
http://mail.python.org/mailman/listinfo/cplusplus-sig