Skip to content

Commit f360332

Browse files
committed
Fix script to simulate pneumatically actuated planar pcs by specfiying xi_eq in actuation_mapping_fn
1 parent 7b6590b commit f360332

File tree

1 file changed

+14
-6
lines changed

1 file changed

+14
-6
lines changed

examples/simulate_pneumatically_actuated_planar_pcs.py

Lines changed: 14 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -43,13 +43,21 @@
4343
) * params["l"][:, None]).flatten()
4444
)
4545

46+
# specify the rest strain
47+
xi_eq = jnp.zeros((3 * num_segments,))
48+
# by default, set the axial rest strain (local y-axis) along the entire rod to 1.0
49+
rest_strain_reshaped = xi_eq.reshape((-1, 3))
50+
rest_strain_reshaped = rest_strain_reshaped.at[:, -1].set(1.0)
51+
xi_eq = rest_strain_reshaped.flatten()
52+
print("xi_eq:\n", xi_eq)
53+
4654
# activate all strains (i.e. bending, shear, and axial)
4755
# strain_selector = jnp.ones((3 * num_segments,), dtype=bool)
4856
strain_selector = jnp.array([True, False, True])[None, :].repeat(num_segments, axis=0).flatten()
4957

5058
B_xi, forward_kinematics_fn, dynamical_matrices_fn, auxiliary_fns = (
5159
pneumatically_actuated_planar_pcs.factory(
52-
num_segments, sym_exp_filepath, strain_selector, # simplified_actuation_mapping=True
60+
num_segments, sym_exp_filepath, strain_selector=strain_selector, xi_eq=xi_eq, # simplified_actuation_mapping=True
5361
)
5462
)
5563
# jit the functions
@@ -59,19 +67,19 @@
5967
forward_kinematics_fn,
6068
auxiliary_fns["jacobian_fn"],
6169
)
62-
print("A=", actuation_mapping_fn(params, B_xi, jnp.zeros((2 * num_segments,))))
70+
print("A=", actuation_mapping_fn(params, B_xi, xi_eq, jnp.zeros((2 * num_segments,))))
6371

6472

6573
def sweep_actuation_mapping():
6674
# evaluate the actuation matrix for a straight backbone
6775
q = jnp.zeros((2 * num_segments,))
68-
A = actuation_mapping_fn(params, B_xi, q)
76+
A = actuation_mapping_fn(params, B_xi, xi_eq, q)
6977
print("Evaluating actuation matrix for straight backbone: A =\n", A)
7078

7179
kappa_be_pts = jnp.linspace(-3*jnp.pi, 3*jnp.pi, 500)
7280
sigma_ax_pts = jnp.zeros_like(kappa_be_pts)
7381
q_pts = jnp.stack([kappa_be_pts, sigma_ax_pts], axis=-1)
74-
A_pts = vmap(actuation_mapping_fn, in_axes=(None, None, 0))(params, B_xi, q_pts)
82+
A_pts = vmap(actuation_mapping_fn, in_axes=(None, None, None, 0))(params, B_xi, xi_eq, q_pts)
7583
# mark the points that are not controllable as the u1 and u2 terms share the same sign
7684
non_controllable_selector = A_pts[..., 0, 0] * A_pts[..., 0, 1] >= 0.0
7785
non_controllable_indices = jnp.where(non_controllable_selector)[0]
@@ -100,7 +108,7 @@ def sweep_actuation_mapping():
100108
_params = params.copy()
101109
_params["r"] = r * jnp.ones((num_segments,))
102110
_params["r_cham_out"] = r_cham_out * jnp.ones((num_segments,))
103-
A_pts = vmap(actuation_mapping_fn, in_axes=(None, None, 0))(_params, B_xi, q_pts)
111+
A_pts = vmap(actuation_mapping_fn, in_axes=(None, None, None, 0))(_params, B_xi, xi_eq, q_pts)
104112
ax.plot(kappa_be_pts, A_pts[:, 0, 0], label=r"$R = " + str(r) + "$")
105113
ax.set_xlabel(r"$\kappa_\mathrm{be}$ [rad/m]")
106114
ax.set_ylabel(r"$\frac{\partial \tau_\mathrm{be}}{\partial u_1}$")
@@ -117,7 +125,7 @@ def sweep_actuation_mapping():
117125
q_pts = jnp.stack([kappa_be_grid.flatten(), sigma_ax_grid.flatten()], axis=-1)
118126

119127
# evaluate the actuation mapping on the grid
120-
A_pts = vmap(actuation_mapping_fn, in_axes=(None, None, 0))(params, B_xi, q_pts)
128+
A_pts = vmap(actuation_mapping_fn, in_axes=(None, None, None, 0))(params, B_xi, xi_eq, q_pts)
121129
# reshape A_pts to match the grid shape
122130
A_grid = A_pts.reshape(kappa_be_grid.shape[:2] + A_pts.shape[-2:])
123131

0 commit comments

Comments
 (0)