pinocchio  3.7.0
A fast and flexible implementation of Rigid Body Dynamics algorithms and their analytical derivatives
 
Loading...
Searching...
No Matches
force.hpp
1//
2// Copyright (c) 2015-2023 CNRS INRIA
3// Copyright (c) 2016 Wandercraft, 86 rue de Paris 91400 Orsay, France.
4//
5
6#ifndef __pinocchio_python_spatial_force_hpp__
7#define __pinocchio_python_spatial_force_hpp__
8
9#include <eigenpy/eigenpy.hpp>
10#include <eigenpy/memory.hpp>
11#include <boost/python/tuple.hpp>
12
13#include "pinocchio/spatial/se3.hpp"
14#include "pinocchio/spatial/force.hpp"
15
16#include "pinocchio/bindings/python/utils/cast.hpp"
17#include "pinocchio/bindings/python/utils/copyable.hpp"
18#include "pinocchio/bindings/python/utils/printable.hpp"
19
20#if EIGENPY_VERSION_AT_MOST(2, 8, 1)
21EIGENPY_DEFINE_STRUCT_ALLOCATOR_SPECIALIZATION(pinocchio::Force)
22#endif
23
24namespace pinocchio
25{
26 namespace python
27 {
28 namespace bp = boost::python;
29
30 template<typename T>
31 struct call;
32
33 template<typename Scalar, int Options>
34 struct call<ForceTpl<Scalar, Options>>
35 {
37
38 static bool isApprox(
39 const Force & self,
40 const Force & other,
41 const Scalar & prec = Eigen::NumTraits<Scalar>::dummy_precision())
42 {
43 return self.isApprox(other, prec);
44 }
45
46 static bool
47 isZero(const Force & self, const Scalar & prec = Eigen::NumTraits<Scalar>::dummy_precision())
48 {
49 return self.isZero(prec);
50 }
51 };
52
53 template<typename Force>
54 struct ForcePythonVisitor : public boost::python::def_visitor<ForcePythonVisitor<Force>>
55 {
56 enum
57 {
59 };
60
61 typedef typename Force::Vector6 Vector6;
62 typedef typename Force::Vector3 Vector3;
63 typedef typename Force::Scalar Scalar;
64
65 typedef typename Eigen::Map<Vector3> MapVector3;
66 typedef typename Eigen::Ref<Vector3> RefVector3;
67
68 template<class PyClass>
69 void visit(PyClass & cl) const
70 {
71 static const Scalar dummy_precision = Eigen::NumTraits<Scalar>::dummy_precision();
72 PINOCCHIO_COMPILER_DIAGNOSTIC_PUSH
73 PINOCCHIO_COMPILER_DIAGNOSTIC_IGNORED_SELF_ASSIGN_OVERLOADED
74 cl.def(bp::init<>(bp::arg("self"), "Default constructor"))
75 .def(bp::init<const Vector3 &, const Vector3 &>(
76 (bp::arg("self"), bp::arg("linear"), bp::arg("angular")),
77 "Initialize from linear and angular components of a Wrench vector (don't mix the "
78 "order)."))
79 .def(bp::init<const Vector6 &>(
80 (bp::args("self", "array")), "Init from a vector 6 [force,torque]"))
81 .def(bp::init<const Force &>((bp::arg("self"), bp::arg("clone")), "Copy constructor"))
82
83 .add_property(
84 "linear",
85 bp::make_function(
86 &ForcePythonVisitor::getLinear, bp::with_custodian_and_ward_postcall<0, 1>()),
87 &ForcePythonVisitor::setLinear,
88 "Linear part of a *this, corresponding to the linear velocity in case of a "
89 "Spatial velocity.")
90 .add_property(
91 "angular",
92 bp::make_function(
93 &ForcePythonVisitor::getAngular, bp::with_custodian_and_ward_postcall<0, 1>()),
94 &ForcePythonVisitor::setAngular,
95 "Angular part of a *this, corresponding to the angular velocity in case of "
96 "a Spatial velocity.")
97 .add_property(
98 "vector",
99 bp::make_function(
100 (typename Force::ToVectorReturnType(Force::*)()) & Force::toVector,
102 &ForcePythonVisitor::setVector, "Returns the components of *this as a 6d vector.")
104 "np", bp::make_function(
105 (typename Force::ToVectorReturnType(Force::*)()) & Force::toVector,
107
108 .def(
109 "se3Action", &Force::template se3Action<Scalar, Options>, bp::args("self", "M"),
110 "Returns the result of the dual action of M on *this.")
111 .def(
112 "se3ActionInverse", &Force::template se3ActionInverse<Scalar, Options>,
113 bp::args("self", "M"),
114 "Returns the result of the dual action of the inverse of M on *this.")
115
116 .def(
117 "setZero", &ForcePythonVisitor::setZero, bp::arg("self"),
118 "Set the linear and angular components of *this to zero.")
119 .def(
120 "setRandom", &ForcePythonVisitor::setRandom, bp::arg("self"),
121 "Set the linear and angular components of *this to random values.")
122
123 .def(
124 "dot", (Scalar(Force::*)(const MotionDense<context::Motion> &) const)&Force::dot,
125 bp::args("self", "m"), "Dot product between *this and a Motion m.")
126
127 .def(bp::self + bp::self)
128 .def(bp::self += bp::self)
129 .def(bp::self - bp::self)
130 .def(bp::self -= bp::self)
131 .def(-bp::self)
132
133#ifndef PINOCCHIO_PYTHON_SKIP_COMPARISON_OPERATIONS
134 .def(bp::self == bp::self)
135 .def(bp::self != bp::self)
136#endif
137
138 .def(bp::self * Scalar())
139 .def(Scalar() * bp::self)
140 .def(bp::self / Scalar())
141
142#ifndef PINOCCHIO_PYTHON_SKIP_COMPARISON_OPERATIONS
143 .def(
144 "isApprox", &call<Force>::isApprox,
145 (bp::arg("self"), bp::arg("other"), bp::arg("prec") = dummy_precision),
146 "Returns true if *this is approximately equal to other, within the precision given "
147 "by prec.")
148
149 .def(
150 "isZero", &call<Force>::isZero, (bp::arg("self"), bp::arg("prec") = dummy_precision),
151 "Returns true if *this is approximately equal to the zero Force, within the "
152 "precision given by prec.")
153#endif
154
155 .def("Random", &Force::Random, "Returns a random Force.")
156 .staticmethod("Random")
157 .def("Zero", &Force::Zero, "Returns a zero Force.")
158 .staticmethod("Zero")
159
160 .def(
161 "__array__", bp::make_function(
162 (typename Force::ToVectorReturnType(Force::*)()) & Force::toVector,
164 .def(
165 "__array__", &__array__,
166 (bp::arg("self"), bp::arg("dtype") = bp::object(), bp::arg("copy") = bp::object()),
168#ifndef PINOCCHIO_PYTHON_NO_SERIALIZATION
169 .def_pickle(Pickle())
170#endif
171 ;
172 PINOCCHIO_COMPILER_DIAGNOSTIC_POP
173 }
174
175 static void expose()
176 {
177 typedef pinocchio::ForceBase<Force> ForceBase;
178 bp::objects::register_dynamic_id<ForceBase>();
179 bp::objects::register_conversion<Force, ForceBase>(false);
180
181 typedef pinocchio::ForceDense<Force> ForceDense;
182 bp::objects::register_dynamic_id<ForceBase>();
183 bp::objects::register_conversion<Force, ForceDense>(false);
184
185#if PY_MAJOR_VERSION == 3 && PY_MINOR_VERSION == 6 && EIGENPY_VERSION_AT_LEAST(2, 9, 0)
186 typedef PINOCCHIO_SHARED_PTR_HOLDER_TYPE(Force) HolderType;
187#else
188 typedef ::boost::python::detail::not_specified HolderType;
189#endif
190 bp::class_<Force, HolderType>(
191 "Force",
192 "Force vectors, in se3* == F^6.\n\n"
193 "Supported operations ...",
194 bp::no_init)
195 .def(ForcePythonVisitor<Force>())
196 .def(CastVisitor<Force>())
197 .def(ExposeConstructorByCastVisitor<Force, ::pinocchio::Force>())
198 .def(CopyableVisitor<Force>())
199 .def(PrintableVisitor<Force>());
200 }
201
202 private:
203 static typename Force::ToVectorConstReturnType
204 __array__(const Force & self, bp::object, bp::object)
205 {
206 return self.toVector();
207 }
208
209 struct Pickle : bp::pickle_suite
210 {
211 static boost::python::tuple getinitargs(const Force & f)
212 {
213 return bp::make_tuple((Vector3)f.linear(), (Vector3)f.angular());
214 }
215
216 static bool getstate_manages_dict()
217 {
218 return true;
219 }
220 };
221
222 static RefVector3 getLinear(Force & self)
223 {
224 return self.linear();
225 }
226 static void setLinear(Force & self, const Vector3 & f)
227 {
228 self.linear(f);
229 }
230 static RefVector3 getAngular(Force & self)
231 {
232 return self.angular();
233 }
234 static void setAngular(Force & self, const Vector3 & n)
235 {
236 self.angular(n);
237 }
238
239 static void setZero(Force & self)
240 {
241 self.setZero();
242 }
243 static void setRandom(Force & self)
244 {
245 self.setRandom();
246 }
247
248 static void setVector(Force & self, const Vector6 & f)
249 {
250 self = f;
251 }
252 };
253
254 } // namespace python
255} // namespace pinocchio
256
257#endif // ifndef __pinocchio_python_spatial_force_hpp__
bool isZero(const Scalar &prec=Eigen::NumTraits< Scalar >::dummy_precision()) const
Main pinocchio namespace.
Definition treeview.dox:11
Common traits structure to fully define base classes for CRTP.
Definition fwd.hpp:72