Skip to content

Commit 29714dc

Browse files
committed
feat(ik): added pinocchio ik
1 parent 293d720 commit 29714dc

File tree

6 files changed

+95
-8
lines changed

6 files changed

+95
-8
lines changed

python/rcsss/_core/common.pyi

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ __all__ = [
1919
"IdentityRotQuartVec",
2020
"IdentityTranslation",
2121
"NRobotsWithGripper",
22+
"Pin",
2223
"Pose",
2324
"RConfig",
2425
"RL",
@@ -69,6 +70,9 @@ class NRobotsWithGripper:
6970
) -> None: ...
7071
def shut(self, idxs: list[int]) -> None: ...
7172

73+
class Pin(IK):
74+
def __init__(self, urdf_path: str) -> None: ...
75+
7276
class Pose:
7377
def __getstate__(self) -> typing.Annotated[list[float], pybind11_stubgen.typing_ext.FixedSize(16)]: ...
7478
@typing.overload

src/common/CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
add_library(common)
22
target_sources(common PRIVATE Pose.cpp NRobotsWithGripper.cpp Robot.cpp IK.cpp)
3-
target_link_libraries(common PUBLIC Eigen3::Eigen mdl)
3+
target_link_libraries(common PUBLIC Eigen3::Eigen mdl pinocchio::pinocchio)

src/common/IK.cpp

Lines changed: 59 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,12 @@
1212
#include <rl/mdl/Kinematic.h>
1313
#include <rl/mdl/UrdfFactory.h>
1414

15+
#include <pinocchio/parsers/urdf.hpp>
16+
17+
#include "pinocchio/algorithm/jacobian.hpp"
18+
#include "pinocchio/algorithm/joint-configuration.hpp"
19+
#include "pinocchio/algorithm/kinematics.hpp"
20+
1521
namespace rcs {
1622
namespace common {
1723

@@ -21,8 +27,8 @@ RL::RL(const std::string& urdf_path, size_t max_duration_ms) : rl_data() {
2127
std::dynamic_pointer_cast<rl::mdl::Kinematic>(this->rl_data.mdl);
2228
this->rl_data.ik = std::make_shared<rl::mdl::JacobianInverseKinematics>(
2329
this->rl_data.kin.get());
24-
this->rl_data.ik->setRandomRestarts(0);
25-
this->rl_data.ik->setEpsilon(1e-3);
30+
this->rl_data.ik->setRandomRestarts(this->random_restarts);
31+
this->rl_data.ik->setEpsilon(this->eps);
2632
this->rl_data.ik->setDuration(std::chrono::milliseconds(max_duration_ms));
2733
}
2834

@@ -45,5 +51,56 @@ std::optional<Vector7d> RL::ik(const Pose& pose, const Vector7d& q0,
4551
}
4652
}
4753

54+
Pin::Pin(const std::string& urdf_path) : model() {
55+
pinocchio::urdf::buildModel(urdf_path, this->model);
56+
this->data = pinocchio::Data(this->model);
57+
}
58+
59+
std::optional<Vector7d> Pin::ik(const Pose& pose, const Vector7d& q0,
60+
const Pose& tcp_offset) {
61+
rcs::common::Pose new_pose = pose * tcp_offset.inverse();
62+
Vector7d q(q0);
63+
const pinocchio::SE3 oMdes(new_pose.rotation_m(), new_pose.translation());
64+
pinocchio::Data::Matrix6x J(6, model.nv);
65+
J.setZero();
66+
bool success = false;
67+
Vector6d err;
68+
Eigen::VectorXd v(model.nv);
69+
for (int i = 0;; i++) {
70+
pinocchio::forwardKinematics(model, data, q);
71+
const pinocchio::SE3 iMd = data.oMi[this->JOINT_ID].actInv(oMdes);
72+
err = pinocchio::log6(iMd).toVector(); // in joint frame
73+
if (err.norm() < this->eps) {
74+
success = true;
75+
break;
76+
}
77+
if (i >= this->IT_MAX) {
78+
success = false;
79+
break;
80+
}
81+
pinocchio::computeJointJacobian(model, data, q, this->JOINT_ID,
82+
J); // J in joint frame
83+
pinocchio::Data::Matrix6 Jlog;
84+
pinocchio::Jlog6(iMd.inverse(), Jlog);
85+
J = -Jlog * J;
86+
pinocchio::Data::Matrix6 JJt;
87+
JJt.noalias() = J * J.transpose();
88+
JJt.diagonal().array() += this->damp;
89+
v.noalias() = -J.transpose() * JJt.ldlt().solve(err);
90+
q = pinocchio::integrate(model, q, v * this->DT);
91+
if (!(i % 10))
92+
std::cout << i << ": error = " << err.transpose() << std::endl;
93+
}
94+
if (success) {
95+
// print amount of iterations
96+
std::cout << "IK success after " << std::to_string(IT_MAX) << " iterations"
97+
<< std::endl;
98+
return q;
99+
} else {
100+
std::cout << "IK failed" << std::endl;
101+
return std::nullopt;
102+
}
103+
}
104+
48105
} // namespace common
49106
} // namespace rcs

src/common/IK.h

Lines changed: 26 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,8 +8,12 @@
88
#include <eigen3/Eigen/Geometry>
99
#include <memory>
1010
#include <optional>
11+
#include <pinocchio/parsers/urdf.hpp>
1112

1213
#include "Pose.h"
14+
#include "pinocchio/algorithm/jacobian.hpp"
15+
#include "pinocchio/algorithm/joint-configuration.hpp"
16+
#include "pinocchio/algorithm/kinematics.hpp"
1317
#include "utils.h"
1418

1519
namespace rcs {
@@ -25,16 +29,34 @@ class IK {
2529

2630
class RL : public IK {
2731
private:
28-
struct RLData {
32+
const int random_restarts = 0;
33+
const double eps = 1e-3;
34+
struct {
2935
std::shared_ptr<rl::mdl::Model> mdl;
3036
std::shared_ptr<rl::mdl::Kinematic> kin;
3137
std::shared_ptr<rl::mdl::JacobianInverseKinematics> ik;
32-
};
33-
RLData rl_data;
38+
} rl_data;
3439

3540
public:
3641
RL(const std::string& urdf_path, size_t max_duration_ms = 300);
37-
~RL() override = default;
42+
std::optional<Vector7d> ik(
43+
const Pose& pose, const Vector7d& q0,
44+
const Pose& tcp_offset = Pose::Identity()) override;
45+
};
46+
47+
class Pin : public IK {
48+
private:
49+
const double eps = 1e-4;
50+
const int IT_MAX = 1000;
51+
const double DT = 1e-1;
52+
const double damp = 1e-6;
53+
const int JOINT_ID = 7;
54+
55+
pinocchio::Model model;
56+
pinocchio::Data data;
57+
58+
public:
59+
Pin(const std::string& urdf_path);
3860
std::optional<Vector7d> ik(
3961
const Pose& pose, const Vector7d& q0,
4062
const Pose& tcp_offset = Pose::Identity()) override;

src/pybind/CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ target_link_libraries(_core PRIVATE hw sim common)
33
target_compile_definitions(_core PRIVATE VERSION_INFO=${PROJECT_VERSION})
44

55
set_target_properties(_core PROPERTIES
6-
INSTALL_RPATH "$ORIGIN;$ORIGIN/../mujoco"
6+
INSTALL_RPATH "$ORIGIN;$ORIGIN/../mujoco;$ORIGIN/../cmeel.prefix/lib"
77
INTERPROCEDURAL_OPTIMIZATION TRUE
88
)
99
set_target_properties(franka PROPERTIES

src/pybind/rcsss.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -220,6 +220,10 @@ PYBIND11_MODULE(_core, m) {
220220
.def(py::init<const std::string &, size_t>(), py::arg("urdf_path"),
221221
py::arg("max_duration_ms") = 300);
222222

223+
py::class_<rcs::common::Pin, rcs::common::IK,
224+
std::shared_ptr<rcs::common::Pin>>(common, "Pin")
225+
.def(py::init<const std::string &>(), py::arg("urdf_path"));
226+
223227
py::class_<rcs::common::RConfig>(common, "RConfig");
224228
py::class_<rcs::common::RState>(common, "RState");
225229
py::class_<rcs::common::GConfig>(common, "GConfig");

0 commit comments

Comments
 (0)