@@ -11,6 +11,15 @@ using namespace XBot;
1111namespace py = pybind11;
1212using rvp = py::return_value_policy;
1313
14+ template <typename _Matrix_Type_>
15+ _Matrix_Type_ pinv_SVD (const _Matrix_Type_& a, double epsilon = std::numeric_limits<double >::epsilon())
16+ {
17+ Eigen::JacobiSVD<_Matrix_Type_> svd (a, Eigen::ComputeThinU | Eigen::ComputeThinV);
18+ double tolerance = epsilon * std::max (a.cols (), a.rows ()) * svd.singularValues ().array ().abs ()(0 );
19+ return svd.matrixV () * (svd.singularValues ().array ().abs () > tolerance).select (
20+ svd.singularValues ().array ().inverse (), 0 ).matrix ().asDiagonal () * svd.matrixU ().adjoint ();
21+ }
22+
1423PYBIND11_MODULE (pyxbot2_interface, m) {
1524
1625 py::class_<ControlMode> controlMode (m, " ControlMode" );
@@ -141,7 +150,7 @@ PYBIND11_MODULE(pyxbot2_interface, m) {
141150 .def (" getPose" ,
142151 py::overload_cast<string_const_ref>(&XBotInterface::getPose, py::const_))
143152 .def (" getPose" ,
144- py::overload_cast<string_const_ref,string_const_ref>(&XBotInterface::getPose, py::const_))
153+ py::overload_cast<string_const_ref, string_const_ref>(&XBotInterface::getPose, py::const_))
145154 .def (" getAccelerationTwist" ,
146155 py::overload_cast<string_const_ref>(&XBotInterface::getAccelerationTwist, py::const_))
147156 .def (" getVelocityTwist" ,
@@ -266,6 +275,8 @@ PYBIND11_MODULE(pyxbot2_interface, m) {
266275 .def_property (" tau" ,
267276 py::overload_cast<>(&ModelInterface::getJointEffort, py::const_),
268277 py::overload_cast<VecConstRef>(&ModelInterface::setJointEffort))
278+ .def (" getInverseJacobian" ,
279+ [](const ModelInterface& self, const std::string& link_id) { return pinv_SVD (self.getJacobian (link_id)); })
269280 ;
270281
271282 py::class_<RobotInterface, XBotInterface, RobotInterface::Ptr>(m, " RobotInterface2" )
0 commit comments