trusty.affine¶
Affine (articulated) bodies.
VelocityPenaltyMode
¶
MuscleModel
¶
add_affine_body
¶
add_affine_body(
world: World,
V: ndarray[float64, (N, 3)],
F: ndarray[int32, (N, M)],
density: float = 1000.0,
stiffness: float = 100000000.0,
*,
friction_mu: float = 0.0,
) -> int
Add a near-rigid affine body from a closed, outward-wound triangle surface mesh (V: (n,3), F: (m,3)). stiffness (Pa) is the orthogonality rigidity -- large values are effectively rigid. friction_mu is the body's surface Coulomb coefficient (>= 0); 0 is frictionless.
add_spherical_joint
¶
add_spherical_joint(
world: World,
body_i: int,
anchor: tuple[float, float, float],
body_j: int | None = None,
stiffness: float = 100000000.0,
) -> int
Spherical (ball) joint: pin anchor (rest world coords) on body_i to body_j, or to its fixed rest position if body_j is omitted. Free relative rotation.
add_revolute_joint
¶
add_revolute_joint(
world: World,
body_i: int,
axis_p0: tuple[float, float, float],
axis_p1: tuple[float, float, float],
body_j: int | None = None,
stiffness: float = 100000000.0,
) -> int
Revolute (hinge) joint: pin the axis line through axis_p0/axis_p1 between body_i and body_j (grounded if omitted). One rotational DOF about that axis.
add_fixed_joint
¶
add_fixed_joint(
world: World,
body_i: int,
origin: tuple[float, float, float],
axis_u: tuple[float, float, float],
axis_v: tuple[float, float, float],
body_j: int | None = None,
stiffness: float = 1000000.0,
) -> int
Fixed (weld) joint: rigidly weld body_i to body_j (grounded if omitted), fully constraining their relative rigid pose. Pins the 3-point frame origin, origin + axis_u, origin + axis_v (rest world coords; axis_u, axis_v are non-collinear offset vectors). The welded pair is auto-excluded from contact. Each affine body keeps its residual deformation DOF, so a soft body welded under a stiff one stays pose-locked but still deformable.
add_prismatic_joint
¶
add_prismatic_joint(
world: World,
body_i: int,
anchor: tuple[float, float, float],
axis: tuple[float, float, float],
body_j: int | None = None,
stiffness: float = 100000000.0,
) -> int
Prismatic (slider) joint: lock body_i's orientation relative to body_j (the world if omitted) and let anchor slide only along a rail with direction axis fixed in body_j's frame. anchor and axis are rest world coordinates. The joint coordinate (actuator target / value, limits) is the slide in m along the rail, measured in body_j's frame, 0 at rest. A body-body pair is excluded from contact.
add_actuator
¶
Add a position-target actuator to an existing joint (the handle returned by add_*_joint). A separate energy term layered on the joint that drives its free DOF(s) toward a target set each control step with an implicit PD servo of gain stiffness. Set the command via affine.set_actuator_target / affine.set_actuator_rotation.
add_joint_limit
¶
add_joint_limit(
world: World,
joint: int,
lo: float,
hi: float,
margin: float = 0.05,
stiffness: float = 1000.0,
) -> int
Add a joint-limit barrier (C2 clamped log-barrier) to a revolute or prismatic joint, confining its coordinate to [lo, hi] (revolute angle in rad, must be within (-pi, pi); prismatic slide in m). margin is the activation distance from each limit. Stops over-travel without a wrap-through; spherical joints are unsupported.
add_joint_velocity_limit
¶
add_joint_velocity_limit(
world: World,
joint: int,
omega_max: float,
stiffness: float = 1000000.0,
mode: VelocityPenaltyMode = VelocityPenaltyMode.Barrier,
barrier_width_fraction: float = 0.25,
) -> int
Add a velocity limit to a revolute, prismatic, or spherical joint, capping its rate at omega_max (revolute rad/s, prismatic m/s, spherical angular-velocity magnitude rad/s) on the integrator-consistent joint velocity. mode is VelocityPenaltyMode.Barrier (the default HARD cap), .Quadratic (a soft cap: firmer than Cubic, no asymptote), .Cubic (C2 but soft near the cap). The barrier is a clamped log-barrier that activates barrier_width_fraction * omega_max below the wall and carries an analytic step filter, so Newton sees the cap before it steps through it, and the rate never exceeds omega_max. Fixed (weld) joints are unsupported.
add_line_muscle
¶
add_line_muscle(
world: World,
bodies: Sequence[int],
points: ndarray[float64, (N, 3)],
f_max: float,
l_opt: float,
l_tendon_slack: float,
pennation: float = 0.0,
activation: float = 0.0,
model: MuscleModel = MuscleModel.Hill,
) -> int
Add a Hill-type line muscle through points (n,3 rest world coords) on bodies (one affine body per point; consecutive points may share a body), spanning >= 2 distinct bodies. Hill params: f_max (N), l_opt (optimal fiber length, m), l_tendon_slack (m), pennation (rad). activation in [0,1] is the live command. model selects the force-length law (MuscleModel.Hill, the default, or MuscleModel.Polynomial -- a well-conditioned no-exp variant). Segments are straight -- wrap surfaces are not implemented. Set activation via affine.set_muscle_activation.
bodies
¶
Every affine body in the world, as a set -- there is no i-th body. Iterate it, or hold the handle add_affine_body returned.
surface
¶
Current world-space (V, F) triangle surface of affine body body. The rest surface before the first step.
center_of_mass
¶
Rest-frame centre of mass (3,) of affine body body, in meters. Computed from its rest surface at creation and constant for the body's life; the body's 12 affine DOFs are taken about it.
set_actuator_target
¶
Set the position target of a revolute (relative angle, rad) or prismatic (slide distance, m) actuator. Held until changed.
set_actuator_rotation
¶
Set the target relative orientation of a spherical actuator, as a rotation vector (axis * angle, rad).
set_velocity
¶
set_velocity(
world: World,
body: int,
v: ndarray[float64, (3,)],
omega: ndarray[float64, (3,)] | None = None,
) -> None
Set affine body body's rigid velocity: centre-of-mass velocity v (m/s, world) and angular velocity omega about the centre of mass (rad/s, world; None = no spin). A material point at x moves at v + omega x (x - c), c the body's current centre of mass; any deformation rate is zeroed. Applied at the next step(); only this body's history is rewritten, and the integrator is unchanged.
actuator_value
¶
Current scalar coordinate of a revolute (angle, rad) or prismatic (slide, m) actuator, from the accepted state -- the RL observation. Zero (the joint's rest configuration) before the first step.
actuator_target
¶
Current target of a revolute (rad) or prismatic (m) actuator.
set_muscle_activation
¶
Set the activation (command, typically in [0,1]) of line muscle muscle, the handle add_line_muscle returned. Held until changed.
muscle_activation
¶
Current activation of line muscle muscle.
muscle_length
¶
Muscle-tendon length (m) of line muscle muscle from the accepted state; its rest path length before the first step.
muscle_force
¶
Tension (N) of line muscle muscle at its published length; zero before the first step.
muscle_path
¶
Current world-space via-point polyline (n,3) of line muscle muscle; its rest points before the first step.