Python: per-step MJCF actuator control + multibody state readback#12
Open
haixuanTao wants to merge 1 commit into
Open
Python: per-step MJCF actuator control + multibody state readback#12haixuanTao wants to merge 1 commit into
haixuanTao wants to merge 1 commit into
Conversation
- GpuMultibodySet::sync_joint_data_from_rapier: refresh every link's joint data (motor targets/gains, limits) from the rapier multibody set in one buffer write, mirroring from_rapier's traversal order. - NexusState::control_multibody_motors: runtime actuation entry point that mutates the rapier joints (e.g. rapier3d-mjcf's apply_controls_multibody) and pushes the refreshed joint data to the GPU, without marking the world dirty (no rebuild). - Viewer::read_multibody_links + links_workspace COPY_SRC: one-readback joint coordinates, link world poses and world-space velocities per env. - Python: NexusState keeps the MjcfRobotHandles from insert_mjcf and exposes actuator_names() / apply_actuator_controls(viewer, ctrl, env) with full MJCF actuator semantics; NexusViewer.read_multibody_links(state, env) returns (coords, positions, quats, linvels, angvels) numpy arrays. Together these make MJCF robots drivable per control step from Python (position-servo PD runs inside the solver) with full state observation -- the two pieces sim-to-sim eval loops need. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Makes MJCF robots drivable per control step from Python, with full state observation — the two pieces an RL / sim-to-sim evaluation loop needs. Follow-up to #7/#8, standalone on main.
What
Control —
NexusState.apply_actuator_controls(viewer, ctrl, env=0)applies one MJCF control vector (one entry per<actuator>, in actuator order —NexusState.actuator_names()reports the order) with full MJCF actuator semantics viarapier3d-mjcf'sapply_controls_multibody(<position>servos with kp/kv,<motor>force/gear, force limits), then pushes the refreshed joint-motor state to the GPU in one buffer write. The PD servo itself runs inside the GPU solver, so there is no per-step solver round-trip beyond that single upload.Observation —
NexusViewer.read_multibody_links(state, env=0)reads every link's state back in one readback:(coords, positions, quats, linvels, angvels)numpy arrays (one row per link, GPU traversal order).coordsare the generalized joint coordinates (a revolute joint's angle iscoords[3], the first angular slot); poses/velocities are world-space.How
GpuMultibodySet::sync_joint_data_from_rapierrefreshes each link'sGenericJointdata (motors, limits) from the rapier multibody set, mirroringfrom_rapier's traversal order, then uploadslinks_staticonce. Only joint data is touched — coordinates/velocities/mass properties are untouched, so this can't teleport links.NexusState::control_multibody_motorswraps "mutate rapier joints, then sync" without marking the world dirty (motor updates are control, not topology — no GPU rebuild).links_workspacegainsCOPY_SRC+ public accessors for the readback.NexusStatekeeps theMjcfRobotHandlesfrominsert_mjcf.Validation
On the LeRobot bipedal platform MJCF (12 position actuators, 13 links): a passive run collapses to torso z ≈ −0.34 within 1 s; driving the servos each step holds it at z ≈ −0.02, and
read_multibody_linkstracks joint angles/limits throughout.cargo checkclean onnexus3d,nexus_viewer3d,nexus_python3d.🤖 Generated with Claude Code