-
Notifications
You must be signed in to change notification settings - Fork 17
/
HumanoidModel.hpp
146 lines (126 loc) · 3.54 KB
/
HumanoidModel.hpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
#ifndef LEPH_HUMANOIDMODEL_HPP
#define LEPH_HUMANOIDMODEL_HPP
#include <Eigen/Dense>
#include "LegIK.hpp"
namespace Rhoban {
/**
* Leg motor result positions
*/
struct IKWalkOutputs {
double left_hip_yaw;
double left_hip_roll;
double left_hip_pitch;
double left_knee;
double left_ankle_pitch;
double left_ankle_roll;
double right_hip_yaw;
double right_hip_roll;
double right_hip_pitch;
double right_knee;
double right_ankle_pitch;
double right_ankle_roll;
};
}
namespace Leph {
/**
* All combinations
* of Euler angles types
* in same order as rotation application
*
* EulerYawPitchRoll is built as
* Roll * Pitch * Yaw.
*/
enum EulerType {
EulerYawPitchRoll,
EulerYawRollPitch,
EulerRollPitchYaw,
EulerRollYawPitch,
EulerPitchRollYaw,
EulerPitchYawRoll,
};
/**
* HumanoidModel
*/
class HumanoidModel
{
public:
/**
* Initialize the model with given
* typical leg length
*/
HumanoidModel(
double distHipToKnee,
double distKneeToAnkle,
double distAnkleToGround,
double distFeetLateral);
/**
* Run analytical inverse kinematics LegIK and
* assign outputs motor positions.
* Target footPos and angles are given in
* special frame when all leg motors are in zero position.
* Frame center is located on left or right foot tip.
* True is returned if angles are updated and inverse
* kinematics is sucessful, else false is returned.
*/
bool legIkLeft(
const Eigen::Vector3d& footPos,
const Eigen::Vector3d& angles,
EulerType eulerType,
Rhoban::IKWalkOutputs& outputs);
bool legIkRight(
const Eigen::Vector3d& footPos,
const Eigen::Vector3d& angles,
EulerType eulerType,
Rhoban::IKWalkOutputs& outputs);
/**
* Return the initial vertical distance
* from trunk frame to foot tip frame (Z)
*/
double legsLength() const;
/**
* Return the initial lateral distance
* between each feet
*/
double feetDistance() const;
private:
/**
* Leg segments lengths used by
* inverse kinematics
*/
double _legHipToKnee;
double _legKneeToAnkle;
double _legAnkleToGround;
double _legLateral;
/**
* Convert given euler angle of given
* convention type to rotation matrix
*/
Eigen::Matrix3d eulersToMatrix(
const Eigen::Vector3d angles, EulerType eulerType) const;
/**
* Compute and return the IK position reference
* vector and orientation reference matrix
* in LegIK specifics structures
*/
LegIK::Vector3D buildTargetPos(
const Eigen::Vector3d& footPos);
LegIK::Frame3D buildTargetOrientation(
const Eigen::Vector3d& angles,
EulerType eulerType);
/**
* Assign model leg DOF to given IK results
*/
void setIKResult(
const LegIK::Position& result, bool isLeftLeg,
Rhoban::IKWalkOutputs& outputs);
/**
* Check inverse kinematics computed value
* and throw an error in case of NaN
*/
void checkNaN(
const LegIK::Position& result,
const LegIK::Vector3D& pos,
const LegIK::Frame3D& orientation) const;
};
}
#endif