diff --git a/tests/test_classh_inheritance.cpp b/tests/test_classh_inheritance.cpp new file mode 100644 index 000000000..6dd1de59b --- /dev/null +++ b/tests/test_classh_inheritance.cpp @@ -0,0 +1,45 @@ +#include "pybind11_tests.h" + +#include + +namespace pybind11_tests { +namespace classh_inheritance { + +struct base { + base() : base_id(100) {} + virtual ~base() = default; + virtual int id() const { return base_id; } + int base_id; +}; + +struct drvd : base { + int id() const override { return 2 * base_id; } +}; + +inline drvd *make_drvd() { return new drvd; } +inline base *make_drvd_up_cast() { return new drvd; } + +inline int pass_base(const base *b) { return b->id(); } +inline int pass_drvd(const drvd *d) { return d->id(); } + +} // namespace classh_inheritance +} // namespace pybind11_tests + +PYBIND11_CLASSH_TYPE_CASTERS(pybind11_tests::classh_inheritance::base) +PYBIND11_CLASSH_TYPE_CASTERS(pybind11_tests::classh_inheritance::drvd) + +namespace pybind11_tests { +namespace classh_inheritance { + +TEST_SUBMODULE(classh_inheritance, m) { + py::classh(m, "base"); + py::classh(m, "drvd"); + + m.def("make_drvd", make_drvd, py::return_value_policy::take_ownership); + m.def("make_drvd_up_cast", make_drvd_up_cast, py::return_value_policy::take_ownership); + m.def("pass_base", pass_base); + m.def("pass_drvd", pass_drvd); +} + +} // namespace classh_inheritance +} // namespace pybind11_tests diff --git a/tests/test_classh_inheritance.py b/tests/test_classh_inheritance.py new file mode 100644 index 000000000..7784dd90f --- /dev/null +++ b/tests/test_classh_inheritance.py @@ -0,0 +1,17 @@ +# -*- coding: utf-8 -*- + +from pybind11_tests import classh_inheritance as m + + +def test_make_drvd_pass_base(): + d = m.make_drvd() + i = m.pass_base(d) + assert i == 200 + + +def test_make_drvd_up_cast_pass_drvd(): + b = m.make_drvd_up_cast() + # the base return is down-cast immediately. + assert b.__class__.__name__ == "drvd" + i = m.pass_drvd(b) + assert i == 200