ocra-recipes
Doxygen documentation for the ocra-recipes repository
controlUtils.cpp
Go to the documentation of this file.
2 
3 namespace ocra
4 {
5  namespace utils
6  {
7  Vector6d cartesianPCoupling(const Vector6d& kp, const Eigen::Displacementd& Hdes, const Eigen::Displacementd& H)
8  {
9  Vector6d ret;
10  Eigen::Displacementd delta = H.inverse()*Hdes;
11  ret.tail<3>() = delta.getTranslation();
12  ret.head<3>() = delta.getRotation().log();
13  ret.array() *= kp.array();
14  return ret;
15  }
16 
17  Vector6d cartesianDCoupling(const Vector6d& kv, const Eigen::Twistd& Tdes, const Eigen::Twistd& T)
18  {
19  Eigen::Twistd deltav = Tdes-T;
20  return kv.asDiagonal() * deltav.get();
21  }
22 
23  Vector6d cartesianPDCoupling(const Vector6d& kp, const Eigen::Displacementd& Hdes, const Eigen::Displacementd& H,
24  const Vector6d& kv, const Eigen::Twistd& Tdes, const Eigen::Twistd& T)
25  {
26  return cartesianPCoupling(kp, Hdes, H) + cartesianDCoupling(kv, Tdes, T);
27  }
28 
29  VectorXd adaptKToInertia(const VectorXd& K, const Model& model, double scale)
30  {
31  VectorXd k(model.nbInternalDofs());
32  const MatrixXd& inertiaMatrix = model.getInertiaMatrix();
33 
34  k = inertiaMatrix.diagonal().tail(model.nbInternalDofs()).asDiagonal() * K;
35  k *= scale;
36 
37  return k;
38  }
39 
40  Eigen::Displacementd compute_H_2_in_1(const Eigen::Displacementd& H_1_in_ref, const Eigen::Displacementd& H_2_in_ref)
41  {
42  return H_1_in_ref.inverse() * H_2_in_ref;
43  }
44 
45  Eigen::Displacementd computeEgoFrame(Model& model, const Vector3d& fwdDirection_in_phantom)
46  {
47  Matrix3d R;
48  R.col(0) = model.getFreeFlyerPosition().getRotation() * fwdDirection_in_phantom;
49  R.col(0).z() = 0.;
50  R.col(0).normalize();
51  R.col(2) = Vector3d::UnitZ();
52  R.col(1) = R.col(2).cross(R.col(0));
53  return Eigen::Displacementd(model.getCoMPosition(), Quaterniond(R));
54  }
55 
56  Eigen::Displacementd interpolate(const Eigen::Displacementd& Hstart, const Eigen::Displacementd& Hend, double t)
57  {
58  SE3CubicInterpolator<double>::StdVectorDisplacement displ;
59  SE3CubicInterpolator<double>::StdVectorTwist twist;
60  std::vector<double> times;
61  SE3CubicInterpolator<double> spline;
62 
63  displ.push_back(Hstart);
64  displ.push_back(Hend);
65  Eigen::Twistd td(0,0,0,0,0,0);
66  twist.push_back(td);
67  twist.push_back(td);
68  times.push_back(0);
69  times.push_back(1);
70  spline.setControlPoint(displ, twist, times);
71 
72  Eigen::Displacementd H;
73  Eigen::Twistd T;
74 
75  spline.Interpolate(H, T, t);
76  return H;
77  }
78 
79  Eigen::Displacementd projectRotation(const Eigen::Displacementd& H, const Vector3d& n, double& theta)
80  {
81  Eigen::Displacementd result = H;
82 
83  const Matrix3d& R = H.getRotation().adjoint();
84  //tr(R^t*[n])
85  double tr1 = (R(2,1)-R(1,2))*n[0] + (R(0,2)-R(2,0))*n[1] + (R(1,0)-R(0,1))*n[2];
86  //tr(R^t*[n]^2) = tr(R^t*n*n^t) - tr(R^t) since n^2 = 1
87  double tr2 = n[0] * (R(0,0)*n[0]+R(1,0)*n[1]+R(2,0)*n[2])
88  + n[1] * (R(0,1)*n[0]+R(1,1)*n[1]+R(2,1)*n[2])
89  + n[2] * (R(0,2)*n[0]+R(1,2)*n[1]+R(2,2)*n[2])
90  - R(0,0) - R(1,1) - R(2,2);
91 
92  double alpha = atan2(tr1, tr2);
93  theta = M_PI - alpha;
94  double s = sin(theta);
95  double c = cos(theta);
96  double ic = 1-c;
97  Matrix3d Rp;
98  Rp(0,0) = + ic*n[0]*n[0] + c;
99  Rp(0,1) = -s*n[2] + ic*n[0]*n[1];
100  Rp(0,2) = s*n[1] + ic*n[0]*n[2];
101  Rp(1,0) = s*n[2] + ic*n[1]*n[0];
102  Rp(1,1) = + ic*n[1]*n[1] + c;
103  Rp(1,2) = -s*n[0] + ic*n[1]*n[2];
104  Rp(2,0) = -s*n[1] + ic*n[2]*n[0];
105  Rp(2,1) = s*n[0] + ic*n[2]*n[1];
106  Rp(2,2) = + ic*n[2]*n[2] + c;
107 
108  result.getRotation() = Eigen::Displacementd::Rotation3D(Quaterniond(Rp));
109  return result;
110  }
111  }
112 }
113 
114 // cmake:sourcegroup=Api
Eigen::Displacementd compute_H_2_in_1(const Eigen::Displacementd &H_1_in_ref, const Eigen::Displacementd &H_2_in_ref)
int nbInternalDofs() const
Definition: Model.cpp:59
#define M_PI
Definition: MathTypes.h:43
virtual const Eigen::Displacementd & getFreeFlyerPosition() const =0
Eigen::Displacementd interpolate(const Eigen::Displacementd &Hstart, const Eigen::Displacementd &Hend, double t)
Eigen::Matrix< double, 6, 1 > cartesianPCoupling(const Eigen::Matrix< double, 6, 1 > &kp, const Eigen::Displacementd &Hdes, const Eigen::Displacementd &H)
Definition: controlUtils.cpp:7
Model class.
Definition: Model.h:38
Optimization-based Robot Controller namespace. a library of classes to write and solve optimization p...
virtual const Eigen::Vector3d & getCoMPosition() const =0
Eigen::Matrix< double, 6, 1 > cartesianDCoupling(const Eigen::Matrix< double, 6, 1 > &kv, const Eigen::Twistd &Tdes, const Eigen::Twistd &T)
Eigen::Displacementd projectRotation(const Eigen::Displacementd &H, const Eigen::Vector3d &n, double &theta)
Eigen::Matrix< double, 6, 1 > Vector6d
Definition: MathTypes.h:36
Eigen::Matrix< double, 6, 1 > cartesianPDCoupling(const Eigen::Matrix< double, 6, 1 > &kp, const Eigen::Displacementd &Hdes, const Eigen::Displacementd &H, const Eigen::Matrix< double, 6, 1 > &kv, const Eigen::Twistd &Tdes, const Eigen::Twistd &T)
virtual const Eigen::MatrixXd & getInertiaMatrix() const =0
Control utility functions.
Eigen::Displacementd computeEgoFrame(Model &model, const Eigen::Vector3d &fwdDirection_in_phantom)
Eigen::VectorXd adaptKToInertia(const Eigen::VectorXd &K, const Model &model, double scale=1.)