cartpole.py
Go to the documentation of this file.
1 import sys
2 
3 import casadi
4 import hppfcl as fcl
5 import numpy as np
6 import pinocchio as pin
7 import pinocchio.casadi as cpin
8 from pinocchio.visualize import MeshcatVisualizer
9 
10 
11 def make_cartpole(ub=True):
12  model = pin.Model()
13 
14  m1 = 1.0
15  m2 = 0.1
16  length = 0.5
17  base_sizes = (0.4, 0.2, 0.05)
18 
19  base = pin.JointModelPX()
20  base_id = model.addJoint(0, base, pin.SE3.Identity(), "base")
21 
22  if ub:
23  pole = pin.JointModelRUBY()
24  else:
25  pole = pin.JointModelRY()
26  pole_id = model.addJoint(1, pole, pin.SE3.Identity(), "pole")
27 
28  base_inertia = pin.Inertia.FromBox(m1, *base_sizes)
29  pole_inertia = pin.Inertia(
30  m2,
31  np.array([0.0, 0.0, length / 2]),
32  m2 / 5 * np.diagflat([1e-2, length**2, 1e-2]),
33  )
34 
35  base_body_pl = pin.SE3.Identity()
36  pole_body_pl = pin.SE3.Identity()
37  pole_body_pl.translation = np.array([0.0, 0.0, length / 2])
38 
39  model.appendBodyToJoint(base_id, base_inertia, base_body_pl)
40  model.appendBodyToJoint(pole_id, pole_inertia, pole_body_pl)
41 
42  # make visual/collision models
43  collision_model = pin.GeometryModel()
44  shape_base = fcl.Box(*base_sizes)
45  radius = 0.01
46  shape_pole = fcl.Capsule(radius, length)
47  RED_COLOR = np.array([1, 0.0, 0.0, 1.0])
48  WHITE_COLOR = np.array([1, 1.0, 1.0, 1.0])
49  geom_base = pin.GeometryObject("link_base", base_id, shape_base, base_body_pl)
50  geom_base.meshColor = WHITE_COLOR
51  geom_pole = pin.GeometryObject("link_pole", pole_id, shape_pole, pole_body_pl)
52  geom_pole.meshColor = RED_COLOR
53 
54  collision_model.addGeometryObject(geom_base)
55  collision_model.addGeometryObject(geom_pole)
56  visual_model = collision_model
57  return model, collision_model, visual_model
58 
59 
61  """Take a Pinocchio model, turn it into a Casadi model
62  and define the appropriate graphs.
63  """
64 
65  def __init__(self, model: pin.Model, timestep=0.05):
66  self.model = model
67  self.cmodel = cpin.Model(model) # cast to CasADi model
68  self.cdata = self.cmodel.createData()
69  self.timestep = timestep
70  self.create_dynamics()
72 
73  def create_dynamics(self):
74  """Create the acceleration expression and acceleration function."""
75  nq = self.model.nq
76  nu = 1
77  nv = self.model.nv
78  q = casadi.SX.sym("q", nq)
79  v = casadi.SX.sym("v", nv)
80  u = casadi.SX.sym("u", nu)
81  dq_ = casadi.SX.sym("dq_", nv)
82  self.u_node = u
83  self.q_node = q
84  self.v_node = v
85  self.dq_ = dq_
86 
87  B = np.array([1, 0])
88  tau = B @ u
89  a = cpin.aba(self.cmodel, self.cdata, q, v, tau)
90  self.acc = a
91  self.acc_func = casadi.Function("acc", [q, v, u], [a], ["q", "v", "u"], ["a"])
92 
94  """
95  Create the map `(q,v) -> (qnext, vnext)` using semi-implicit Euler integration.
96  """
97  q = self.q_node
98  v = self.v_node
99  u = self.u_node
100  dq_ = self.dq_
101  # q' = q + dq
102  q_dq = cpin.integrate(self.cmodel, q, dq_)
103  self.q_dq = q_dq
104  # express acceleration using q' = q + dq
105  a = self.acc_func(q_dq, v, u)
106 
107  dt = self.timestep
108  vnext = v + a * dt
109  qnext = cpin.integrate(self.cmodel, self.q_dq, dt * vnext)
110 
111  self.dyn_qv_fn_ = casadi.Function(
112  "discrete_dyn",
113  [q, dq_, v, u],
114  [qnext, vnext],
115  ["q", "dq_", "v", "u"],
116  ["qnext", "vnext"],
117  )
118 
119  def forward(self, x, u):
120  nq = self.model.nq
121  nv = self.model.nv
122  q = x[:nq]
123  v = x[nq:]
124  dq_ = np.zeros(nv)
125  qnext, vnext = self.dyn_qv_fn_(q, dq_, v, u)
126  xnext = np.concatenate((qnext, vnext))
127  return xnext
128 
129  def residual_fwd(self, x, u, xnext):
130  nv = self.model.nv
131  dq = np.zeros(nv)
132  dqn = dq
133  res = self.dyn_residual(x, u, xnext, dq, dqn)
134  return res
135 
136 
138  def __init__(self, timestep=0.05):
139  model, collision_model, visual_model = make_cartpole()
140  self.collision_model = collision_model
141  self.visual_model = visual_model
142  super().__init__(model=model, timestep=timestep)
143 
144 
145 dt = 0.02
146 cartpole = CartpoleDynamics(timestep=dt)
147 model = cartpole.model
148 
149 print(model)
150 
151 q0 = np.array([0.0, 0.95, 0.01])
152 q0 = pin.normalize(model, q0)
153 v = np.zeros(model.nv)
154 u = np.zeros(1)
155 a0 = cartpole.acc_func(q0, v, u)
156 
157 print("a0:", a0)
158 
159 x0 = np.append(q0, v)
160 xnext = cartpole.forward(x0, u)
161 
162 
163 def integrate_no_control(x0, nsteps):
164  states_ = [x0.copy()]
165  for t in range(nsteps):
166  u = np.zeros(1)
167  xnext = cartpole.forward(states_[t], u).ravel()
168  states_.append(xnext)
169  return states_
170 
171 
172 states_ = integrate_no_control(x0, nsteps=400)
173 states_ = np.stack(states_).T
174 
175 try:
177  model=model,
178  collision_model=cartpole.collision_model,
179  visual_model=cartpole.visual_model,
180  )
181 
182  viz.initViewer()
183  viz.loadViewerModel("pinocchio")
184 
185  qs_ = states_[: model.nq, :].T
186  viz.play(q_trajectory=qs_, dt=dt)
187 except ImportError as err:
188  print(
189  "Error while initializing the viewer. "
190  "It seems you should install Python meshcat"
191  )
192  print(err)
193  sys.exit(0)
cartpole.PinocchioCasadi.residual_fwd
def residual_fwd(self, x, u, xnext)
Definition: cartpole.py:129
cartpole.integrate_no_control
def integrate_no_control(x0, nsteps)
Definition: cartpole.py:163
cartpole.PinocchioCasadi.dyn_qv_fn_
dyn_qv_fn_
Definition: cartpole.py:111
pinocchio.visualize
Definition: bindings/python/pinocchio/visualize/__init__.py:1
cartpole.PinocchioCasadi.q_node
q_node
Definition: cartpole.py:83
cartpole.PinocchioCasadi.__init__
def __init__(self, pin.Model model, timestep=0.05)
Definition: cartpole.py:65
cartpole.PinocchioCasadi.cdata
cdata
Definition: cartpole.py:68
cartpole.PinocchioCasadi.v_node
v_node
Definition: cartpole.py:84
cartpole.PinocchioCasadi.create_dynamics
def create_dynamics(self)
Definition: cartpole.py:73
pinocchio.casadi
Definition: bindings/python/pinocchio/casadi/__init__.py:1
cartpole.PinocchioCasadi.u_node
u_node
Definition: cartpole.py:82
cartpole.PinocchioCasadi.cmodel
cmodel
Definition: cartpole.py:67
cartpole.PinocchioCasadi.timestep
timestep
Definition: cartpole.py:69
pinocchio::createData
ConstraintDataTpl< Scalar, Options, ConstraintCollectionTpl > createData(const ConstraintModelTpl< Scalar, Options, ConstraintCollectionTpl > &cmodel)
Definition: constraint-model-visitor.hpp:248
cartpole.CartpoleDynamics
Definition: cartpole.py:137
cartpole.PinocchioCasadi
Definition: cartpole.py:60
cartpole.CartpoleDynamics.visual_model
visual_model
Definition: cartpole.py:141
cartpole.PinocchioCasadi.forward
def forward(self, x, u)
Definition: cartpole.py:119
cartpole.PinocchioCasadi.acc
acc
Definition: cartpole.py:90
pinocchio.visualize.meshcat_visualizer.MeshcatVisualizer
Definition: meshcat_visualizer.py:537
cartpole.PinocchioCasadi.acc_func
acc_func
Definition: cartpole.py:91
cartpole.PinocchioCasadi.create_discrete_dynamics
def create_discrete_dynamics(self)
Definition: cartpole.py:93
cartpole.PinocchioCasadi.dq_
dq_
Definition: cartpole.py:85
cartpole.PinocchioCasadi.q_dq
q_dq
Definition: cartpole.py:103
cartpole.CartpoleDynamics.collision_model
collision_model
Definition: cartpole.py:140
cartpole.CartpoleDynamics.__init__
def __init__(self, timestep=0.05)
Definition: cartpole.py:138
cartpole.make_cartpole
def make_cartpole(ub=True)
Definition: cartpole.py:11
cartpole.PinocchioCasadi.model
model
Definition: cartpole.py:66


pinocchio
Author(s):
autogenerated on Wed Sep 25 2024 02:42:20