1
+ #include " inria_wbc/behaviors/humanoid/move_feet.hpp"
2
+
3
+ namespace inria_wbc {
4
+ namespace behaviors {
5
+ namespace generic {
6
+ static Register<MoveFeet> __talos_move_feet (" humanoid::move-feet" );
7
+
8
+ MoveFeet::MoveFeet (const controller_ptr_t & controller, const YAML::Node& config) : Behavior(controller, config),
9
+ traj_selector_ (0 )
10
+ {
11
+
12
+ auto c = IWBC_CHECK (config[" BEHAVIOR" ]);
13
+ trajectory_duration_ = IWBC_CHECK (c[" trajectory_duration" ].as <float >());
14
+ behavior_type_ = this ->behavior_type ();
15
+ controller_->set_behavior_type (behavior_type_);
16
+
17
+ loop_ = IWBC_CHECK (c[" loop" ].as <bool >());
18
+ task_names_ = IWBC_CHECK (c[" task_names" ].as <std::vector<std::string>>());
19
+ contact_names_ = IWBC_CHECK (c[" contact_names" ].as <std::vector<std::string>>());
20
+
21
+ for (auto & task_name : task_names_) {
22
+ IWBC_ASSERT (std::static_pointer_cast<inria_wbc::controllers::PosTracker>(controller_)->has_task (task_name), " active_walk: a " + task_name + " task is required" );
23
+ }
24
+
25
+ for (auto & contact_name : contact_names_) {
26
+ IWBC_ASSERT (std::static_pointer_cast<inria_wbc::controllers::PosTracker>(controller_)->has_contact (contact_name), " active_walk: a " + contact_name + " task is required" );
27
+ }
28
+
29
+ auto ts = IWBC_CHECK (c[" relative_targets_pos" ].as <std::vector<std::vector<double >>>());
30
+ auto to = IWBC_CHECK (c[" relative_targets_rpy" ].as <std::vector<std::vector<double >>>());
31
+
32
+ if (task_names_.size () != ts.size ())
33
+ IWBC_ERROR (" MoveFeet behavior needs the same number of tasks and targets" );
34
+
35
+ for (uint i = 0 ; i < task_names_.size (); i++) {
36
+
37
+ auto task_init = std::static_pointer_cast<inria_wbc::controllers::PosTracker>(controller_)->get_se3_ref (task_names_[i]);
38
+ auto task_final = task_init;
39
+
40
+ if (ts[i].size () == 3 )
41
+ task_final.translation () = Eigen::Vector3d::Map (ts[i].data ()) + task_init.translation ();
42
+
43
+ if (to[i].size () == 3 ) {
44
+ Eigen::Matrix3d rot = (Eigen::AngleAxisd (to[i][2 ], Eigen::Vector3d::UnitZ ())
45
+ * Eigen::AngleAxisd (to[i][1 ], Eigen::Vector3d::UnitY ())
46
+ * Eigen::AngleAxisd (to[i][0 ], Eigen::Vector3d::UnitX ()))
47
+ .toRotationMatrix ();
48
+
49
+ task_final.rotation () = rot * task_init.rotation ();
50
+ }
51
+
52
+ std::vector<std::vector<pinocchio::SE3>> trajectory;
53
+ std::vector<std::vector<Eigen::VectorXd>> trajectory_d;
54
+ std::vector<std::vector<Eigen::VectorXd>> trajectory_dd;
55
+
56
+ trajectory.push_back (trajs::min_jerk_trajectory (task_init, task_final, controller_->dt (), trajectory_duration_));
57
+ trajectory_d.push_back (trajs::min_jerk_trajectory<trajs::d_order::FIRST>(task_init, task_final, controller_->dt (), trajectory_duration_));
58
+ trajectory_dd.push_back (trajs::min_jerk_trajectory<trajs::d_order::SECOND>(task_init, task_final, controller_->dt (), trajectory_duration_));
59
+
60
+ if (loop_) {
61
+ trajectory.push_back (trajs::min_jerk_trajectory (task_final, task_init, controller_->dt (), trajectory_duration_));
62
+ trajectory_d.push_back (trajs::min_jerk_trajectory<trajs::d_order::FIRST>(task_final, task_init, controller_->dt (), trajectory_duration_));
63
+ trajectory_dd.push_back (trajs::min_jerk_trajectory<trajs::d_order::SECOND>(task_final, task_init, controller_->dt (), trajectory_duration_));
64
+ }
65
+
66
+ trajectories_.push_back (trajectory);
67
+ trajectories_d_.push_back (trajectory_d);
68
+ trajectories_dd_.push_back (trajectory_dd);
69
+ }
70
+ }
71
+
72
+ void MoveFeet::update (const controllers::SensorData& sensor_data)
73
+ {
74
+
75
+ for (uint i = 0 ; i < task_names_.size (); i++) {
76
+ if (traj_selector_ < trajectories_[i].size ()) {
77
+
78
+ auto ref = trajectories_[i][traj_selector_][time_];
79
+ Eigen::VectorXd ref_vec (12 );
80
+ tsid::math::SE3ToVector (ref, ref_vec);
81
+
82
+ tsid::trajectories::TrajectorySample sample_ref (12 , 6 );
83
+ sample_ref.setValue (ref_vec);
84
+ sample_ref.setDerivative (trajectories_d_[i][traj_selector_][time_]);
85
+ sample_ref.setSecondDerivative (trajectories_dd_[i][traj_selector_][time_]);
86
+
87
+ std::static_pointer_cast<inria_wbc::controllers::PosTracker>(controller_)->set_se3_ref (sample_ref, task_names_[i]);
88
+ std::static_pointer_cast<inria_wbc::controllers::PosTracker>(controller_)->set_contact_se3_ref (sample_ref, contact_names_[i]);
89
+ }
90
+ }
91
+
92
+ controller_->update (sensor_data);
93
+ ++time_;
94
+ if (trajectories_.size () > 0 ) {
95
+ if (time_ == trajectories_[0 ][traj_selector_].size ()) {
96
+ time_ = 0 ;
97
+ traj_selector_ = ++traj_selector_;
98
+ if (loop_)
99
+ traj_selector_ = traj_selector_ % trajectories_[0 ].size ();
100
+ }
101
+ }
102
+ }
103
+ } // namespace generic
104
+ } // namespace behaviors
105
+ } // namespace inria_wbc
0 commit comments