|
1 | 1 | #include <memory>
|
| 2 | +#include <stdexcept> |
2 | 3 |
|
3 | 4 | #include <pybind11/pybind11.h>
|
4 | 5 | #include <pybind11/gil.h>
|
@@ -43,6 +44,46 @@ class Py_SyncActionNode : public SyncActionNode
|
43 | 44 | }
|
44 | 45 | };
|
45 | 46 |
|
| 47 | +class Py_StatefulActionNode final : public StatefulActionNode |
| 48 | +{ |
| 49 | +public: |
| 50 | + Py_StatefulActionNode(const std::string& name, const NodeConfig& config) : |
| 51 | + StatefulActionNode(name, config) |
| 52 | + {} |
| 53 | + |
| 54 | + NodeStatus onStart() override |
| 55 | + { |
| 56 | + py::gil_scoped_acquire gil; |
| 57 | + return py::get_overload(this, "on_start")().cast<NodeStatus>(); |
| 58 | + } |
| 59 | + |
| 60 | + NodeStatus onRunning() override |
| 61 | + { |
| 62 | + py::gil_scoped_acquire gil; |
| 63 | + return py::get_overload(this, "on_running")().cast<NodeStatus>(); |
| 64 | + } |
| 65 | + |
| 66 | + void onHalted() override |
| 67 | + { |
| 68 | + py::gil_scoped_acquire gil; |
| 69 | + py::get_overload(this, "on_halted")(); |
| 70 | + } |
| 71 | + |
| 72 | + // TODO: Share these duplicated methods with other node types. |
| 73 | + py::object Py_getInput(const std::string& name) |
| 74 | + { |
| 75 | + py::object obj; |
| 76 | + getInput(name, obj); |
| 77 | + return obj; |
| 78 | + } |
| 79 | + |
| 80 | + // TODO: Share these duplicated methods with other node types. |
| 81 | + void Py_setOutput(const std::string& name, const py::object& value) |
| 82 | + { |
| 83 | + setOutput(name, value); |
| 84 | + } |
| 85 | +}; |
| 86 | + |
46 | 87 | // Add a conversion specialization from string values into general py::objects
|
47 | 88 | // by evaluating as a Python expression.
|
48 | 89 | template <>
|
@@ -112,8 +153,18 @@ PYBIND11_MODULE(btpy_cpp, m)
|
112 | 153 | // is destroyed, then the object will live forever.
|
113 | 154 | obj.inc_ref();
|
114 | 155 |
|
115 |
| - return std::unique_ptr<Py_SyncActionNode>( |
116 |
| - obj.cast<Py_SyncActionNode*>()); |
| 156 | + if (py::isinstance<Py_SyncActionNode>(obj)) |
| 157 | + { |
| 158 | + return std::unique_ptr<TreeNode>(obj.cast<Py_SyncActionNode*>()); |
| 159 | + } |
| 160 | + else if (py::isinstance<Py_StatefulActionNode>(obj)) |
| 161 | + { |
| 162 | + return std::unique_ptr<TreeNode>(obj.cast<Py_StatefulActionNode*>()); |
| 163 | + } |
| 164 | + else |
| 165 | + { |
| 166 | + throw std::runtime_error("invalid node type of " + name); |
| 167 | + } |
117 | 168 | });
|
118 | 169 | })
|
119 | 170 | .def("create_tree_from_text",
|
@@ -142,6 +193,14 @@ PYBIND11_MODULE(btpy_cpp, m)
|
142 | 193 | .def("tick", &Py_SyncActionNode::tick)
|
143 | 194 | .def("get_input", &Py_SyncActionNode::Py_getInput)
|
144 | 195 | .def("set_output", &Py_SyncActionNode::Py_setOutput);
|
| 196 | + |
| 197 | + py::class_<Py_StatefulActionNode>(m, "StatefulActionNode") |
| 198 | + .def(py::init<const std::string&, const NodeConfig&>()) |
| 199 | + .def("on_start", &Py_StatefulActionNode::onStart) |
| 200 | + .def("on_running", &Py_StatefulActionNode::onRunning) |
| 201 | + .def("on_halted", &Py_StatefulActionNode::onHalted) |
| 202 | + .def("get_input", &Py_StatefulActionNode::Py_getInput) |
| 203 | + .def("set_output", &Py_StatefulActionNode::Py_setOutput); |
145 | 204 | }
|
146 | 205 |
|
147 | 206 | } // namespace BT
|
0 commit comments