bindings/python/spatial/inertia.hpp
Go to the documentation of this file.
1 //
2 // Copyright (c) 2015-2020 CNRS INRIA
3 // Copyright (c) 2016 Wandercraft, 86 rue de Paris 91400 Orsay, France.
4 //
5 
6 #ifndef __pinocchio_python_spatial_inertia_hpp__
7 #define __pinocchio_python_spatial_inertia_hpp__
8 
9 #include <eigenpy/exception.hpp>
10 #include <eigenpy/memory.hpp>
12 #include <boost/python/tuple.hpp>
13 
14 #include "pinocchio/spatial/inertia.hpp"
17 
19 
20 namespace pinocchio
21 {
22  namespace python
23  {
24  namespace bp = boost::python;
25 
26  template<typename T> struct call;
27 
28  template<typename Scalar, int Options>
30  {
32 
33  static bool isApprox(const Inertia & self, const Inertia & other,
34  const Scalar & prec = Eigen::NumTraits<Scalar>::dummy_precision())
35  {
36  return self.isApprox(other,prec);
37  }
38 
39  static bool isZero(const Inertia & self,
40  const Scalar & prec = Eigen::NumTraits<Scalar>::dummy_precision())
41  {
42  return self.isZero(prec);
43  }
44  };
45 
46  BOOST_PYTHON_FUNCTION_OVERLOADS(isApproxInertia_overload,call<Inertia>::isApprox,2,3)
48 
49  template<typename Inertia>
51  : public boost::python::def_visitor< InertiaPythonVisitor<Inertia> >
52  {
53 
54  typedef typename Inertia::Scalar Scalar;
55  typedef typename Inertia::Vector3 Vector3;
56  typedef typename Inertia::Matrix3 Matrix3;
57  typedef typename Inertia::Vector6 Vector6;
58  typedef typename Inertia::Matrix6 Matrix6;
59 
60  public:
61 
62  template<class PyClass>
63  void visit(PyClass& cl) const
64  {
65  cl
66  .def("__init__",
67  bp::make_constructor(&InertiaPythonVisitor::makeFromMCI,
68  bp::default_call_policies(),
69  (bp::arg("mass"),bp::arg("lever"),bp::arg("inertia"))),
70  "Initialize from mass, lever and 3d inertia.")
71  .def(bp::init<Inertia>((bp::arg("self"),bp::arg("other")),"Copy constructor."))
72 
73  .add_property("mass",
74  &InertiaPythonVisitor::getMass,
75  &InertiaPythonVisitor::setMass,
76  "Mass of the Spatial Inertia.")
77  .add_property("lever",
78  bp::make_function((typename Inertia::Vector3 & (Inertia::*)())&Inertia::lever,
79  bp::return_internal_reference<>()),
80  &InertiaPythonVisitor::setLever,
81  "Center of mass location of the Spatial Inertia. It corresponds to the location of the center of mass regarding to the frame where the Spatial Inertia is expressed.")
82  .add_property("inertia",
83  &InertiaPythonVisitor::getInertia,
84  &InertiaPythonVisitor::setInertia,
85  "Rotational part of the Spatial Inertia, i.e. a symmetric matrix representing the rotational inertia around the center of mass.")
86 
87  .def("matrix",&Inertia::matrix,bp::arg("self"))
88  .def("se3Action",&Inertia::se3Action,
89  bp::args("self","M"),"Returns the result of the action of M on *this.")
90  .def("se3ActionInverse",&Inertia::se3ActionInverse,
91  bp::args("self","M"),"Returns the result of the action of the inverse of M on *this.")
92 
93  .def("setIdentity",&Inertia::setIdentity,bp::arg("self"),
94  "Set *this to be the Identity inertia.")
95  .def("setZero",&Inertia::setZero,bp::arg("self"),
96  "Set all the components of *this to zero.")
97  .def("setRandom",&Inertia::setRandom,bp::arg("self"),
98  "Set all the components of *this to random values.")
99 
100  .def(bp::self + bp::self)
101  .def(bp::self * bp::other<Motion>() )
102  .add_property("np",&Inertia::matrix)
103  .def("vxiv",&Inertia::vxiv,bp::args("self","v"),"Returns the result of v x Iv.")
104  .def("vtiv",&Inertia::vtiv,bp::args("self","v"),"Returns the result of v.T * Iv.")
105  .def("vxi",(Matrix6 (Inertia::*)(const Motion &) const)&Inertia::vxi,
106  bp::args("self","v"),
107  "Returns the result of v x* I, a 6x6 matrix.")
108  .def("ivx",(Matrix6 (Inertia::*)(const Motion &) const)&Inertia::ivx,
109  bp::args("self","v"),
110  "Returns the result of I vx, a 6x6 matrix.")
111  .def("variation",(Matrix6 (Inertia::*)(const Motion &) const)&Inertia::variation,
112  bp::args("self","v"),
113  "Returns the time derivative of the inertia.")
114 
115  .def(bp::self == bp::self)
116  .def(bp::self != bp::self)
117 
118  .def("isApprox",
120  isApproxInertia_overload(bp::args("self","other","prec"),
121  "Returns true if *this is approximately equal to other, within the precision given by prec."))
122 
123  .def("isZero",
125  isZero_overload(bp::args("self","prec"),
126  "Returns true if *this is approximately equal to the zero Inertia, within the precision given by prec."))
127 
128  .def("Identity",&Inertia::Identity,"Returns the identity Inertia.")
129  .staticmethod("Identity")
130  .def("Zero",&Inertia::Zero,"Returns the null Inertia.")
131  .staticmethod("Zero")
132  .def("Random",&Inertia::Random,"Returns a random Inertia.")
133  .staticmethod("Random")
134 
135  .def("toDynamicParameters",&InertiaPythonVisitor::toDynamicParameters_proxy,bp::arg("self"),
136  "Returns the representation of the matrix as a vector of dynamic parameters."
137  "\nThe parameters are given as v = [m, mc_x, mc_y, mc_z, I_{xx}, I_{xy}, I_{yy}, I_{xz}, I_{yz}, I_{zz}]^T "
138  "where I = I_C + mS^T(c)S(c) and I_C has its origin at the barycenter"
139  )
140  .def("FromDynamicParameters",&Inertia::template FromDynamicParameters<Eigen::VectorXd>,
141  bp::args("dynamic_parameters"),
142  "Builds and inertia matrix from a vector of dynamic parameters."
143  "\nThe parameters are given as dynamic_parameters = [m, mc_x, mc_y, mc_z, I_{xx}, I_{xy}, I_{yy}, I_{xz}, I_{yz}, I_{zz}]^T "
144  "where I = I_C + mS^T(c)S(c) and I_C has its origin at the barycenter."
145  )
146  .staticmethod("FromDynamicParameters")
147 
148  .def("FromSphere", &Inertia::FromSphere,
149  bp::args("mass","radius"),
150  "Returns the Inertia of a sphere defined by a given mass and radius.")
151  .staticmethod("FromSphere")
152  .def("FromEllipsoid", &Inertia::FromEllipsoid,
153  bp::args("mass","length_x","length_y","length_z"),
154  "Returns the Inertia of an ellipsoid shape defined by a mass and given dimensions the semi-axis of values length_{x,y,z}.")
155  .staticmethod("FromEllipsoid")
156  .def("FromCylinder", &Inertia::FromCylinder,
157  bp::args("mass","radius","length"),
158  "Returns the Inertia of a cylinder defined by its mass, radius and length along the Z axis.")
159  .staticmethod("FromCylinder")
160  .def("FromBox", &Inertia::FromBox,
161  bp::args("mass","length_x","length_y","length_z"),
162  "Returns the Inertia of a box shape with a mass and of dimension the semi axis of length_{x,y,z}.")
163  .staticmethod("FromBox")
164 
165  .def("__array__",&Inertia::matrix)
166 
167  .def_pickle(Pickle())
168  ;
169  }
170 
171  static Scalar getMass( const Inertia & self ) { return self.mass(); }
172  static void setMass( Inertia & self, Scalar mass ) { self.mass() = mass; }
173 
174  static void setLever( Inertia & self, const Vector3 & lever ) { self.lever() = lever; }
175 
176  static Matrix3 getInertia( const Inertia & self ) { return self.inertia().matrix(); }
177 // static void setInertia(Inertia & self, const Vector6 & minimal_inertia) { self.inertia().data() = minimal_inertia; }
178  static void setInertia(Inertia & self, const Matrix3 & symmetric_inertia)
179  {
180  assert(symmetric_inertia.isApprox(symmetric_inertia.transpose()));
181  self.inertia().data() <<
182  symmetric_inertia(0,0),
183  symmetric_inertia(1,0),
184  symmetric_inertia(1,1),
185  symmetric_inertia(0,2),
186  symmetric_inertia(1,2),
187  symmetric_inertia(2,2);
188  }
189 
190  static Eigen::VectorXd toDynamicParameters_proxy(const Inertia & self)
191  {
192  return self.toDynamicParameters();
193  }
194 
195  static Inertia* makeFromMCI(const double & mass,
196  const Vector3 & lever,
197  const Matrix3 & inertia)
198  {
199  if(! inertia.isApprox(inertia.transpose()) )
200  throw eigenpy::Exception("The 3d inertia should be symmetric.");
201  if( (Eigen::Vector3d::UnitX().transpose()*inertia*Eigen::Vector3d::UnitX()<0)
202  || (Eigen::Vector3d::UnitY().transpose()*inertia*Eigen::Vector3d::UnitY()<0)
203  || (Eigen::Vector3d::UnitZ().transpose()*inertia*Eigen::Vector3d::UnitZ()<0) )
204  throw eigenpy::Exception("The 3d inertia should be positive.");
205  return new Inertia(mass,lever,inertia);
206  }
207 
208  static void expose()
209  {
210  bp::class_<Inertia>("Inertia",
211  "This class represenses a sparse version of a Spatial Inertia and its is defined by its mass, its center of mass location and the rotational inertia expressed around this center of mass.\n\n"
212  "Supported operations ...",
213  bp::init<>(bp::arg("self"),"Default constructor."))
217  ;
218 
219  }
220 
221  private:
222 
223  struct Pickle : bp::pickle_suite
224  {
225  static
226  boost::python::tuple
227  getinitargs(const Inertia & I)
228  { return bp::make_tuple(I.mass(),(Vector3)I.lever(),I.inertia().matrix()); }
229  };
230 
231 
232  }; // struct InertiaPythonVisitor
233 
234  } // namespace python
235 } // namespace pinocchio
236 
237 #endif // ifndef __pinocchio_python_spatial_inertia_hpp__
InertiaTpl< double, 0 > Inertia
static void setInertia(Inertia &self, const Matrix3 &symmetric_inertia)
static void setLever(Inertia &self, const Vector3 &lever)
static Eigen::VectorXd toDynamicParameters_proxy(const Inertia &self)
static bool isApprox(const Inertia &self, const Inertia &other, const Scalar &prec=Eigen::NumTraits< Scalar >::dummy_precision())
Set the Python method str and repr to use the overloading operator<<.
Definition: printable.hpp:21
BOOST_PYTHON_FUNCTION_OVERLOADS(computeKKTContactDynamicMatrixInverse_overload, computeKKTContactDynamicMatrixInverse_proxy, 4, 5) static const Eigen
static void se3ActionInverse(const SE3Tpl< Scalar, Options > &m, const Eigen::MatrixBase< Mat > &iF, Eigen::MatrixBase< MatRet > const &jF)
Inverse SE3 action on a set of forces, represented by a 6xN matrix whose each column represent a spat...
SE3::Scalar Scalar
Definition: conversions.cpp:13
const Symmetric3 & inertia() const
const Vector3 & lever() const
static void se3Action(const SE3Tpl< Scalar, Options > &m, const Eigen::MatrixBase< Mat > &iF, Eigen::MatrixBase< MatRet > const &jF)
SE3 action on a set of forces, represented by a 6xN matrix whose each column represent a spatial forc...
static boost::python::tuple getinitargs(const Inertia &I)
Add the Python method copy to allow a copy of this by calling the copy constructor.
Definition: copyable.hpp:21
static void setMass(Inertia &self, Scalar mass)
Main pinocchio namespace.
Definition: timings.cpp:30
static Inertia * makeFromMCI(const double &mass, const Vector3 &lever, const Matrix3 &inertia)
#define EIGENPY_DEFINE_STRUCT_ALLOCATOR_SPECIALIZATION(...)
Eigen::Matrix< Scalar, Eigen::Dynamic, 1 > VectorXd
Definition: conversions.cpp:14
static bool isZero(const Inertia &self, const Scalar &prec=Eigen::NumTraits< Scalar >::dummy_precision())


pinocchio
Author(s):
autogenerated on Tue Jun 1 2021 02:45:03