Skip to main content

CLI tools

Standalone executables shipped by Humanoid Control. The primary entry point is the unified hc CLI from humanoid_control_clihc bus ping, hc bus discover, hc motor slider, hc viz rerun, hc viz viser, hc calibrate. Every underlying executable is also reachable directly as ros2 run <package> <executable>; the hc CLI is a thin verb/noun wrapper that calls os.execvp on those same targets.

humanoid_control_policy and pianist_policy each ship a prepare console script (the launch-time policy-artifact prep step); pianist_policy also ships the piano_state_bridge and midi_keyboard_driver key-state nodes. These are normally driven by their launch files, but are reachable via ros2 run … too.

Index

ExecutablePackageRepoWhat it does
hc (unified CLI)humanoid_control_cliHumanoid ControlVerb/noun entry point (hc bus ping, hc bus discover, hc motor slider, hc viz rerun, …).
robstride_pinghumanoid_devices_robstrideHumanoid ControlSingle-actuator probe (GetDeviceId / OperationStatus). Read-only.
robstride_discoverhumanoid_devices_robstrideHumanoid ControlScan a CAN ID range, print every device that replies. Read-only.
mit_slider_guihumanoid_devices_robstrideHumanoid ControlQt slider window publishing Float64MultiArray to a forward_command_controller.
mode_managerhumanoid_controllersHumanoid ControlThe FSM orchestrator. Normally launched by bringup; sometimes useful to start manually.
calibrate_robothumanoid_bringup_liteHumanoid ControlSample (min, max) per joint; write calibration.yaml on Ctrl+C.
rerun_vizhumanoid_bringup_liteHumanoid ControlNative rerun viewer subscribed to /robot_description + /lite/joint_states.
viser_vizhumanoid_bringup_liteHumanoid ControlBrowser viewer (default port 8080). Same subscriptions.
preparehumanoid_control_policyHumanoid ControlLaunch-time prep: resolve the ONNX (local / W&B), convert the LeRobot motion → .mcap bag, emit the rl_policy_controller overlay (used by lite_policy.launch.py).
preparepianist_policypianist_ros2Piano counterpart of humanoid_control_policy prepare (song → key-state .mcap; used by piano_policy.launch.py).
piano_state_bridgepianist_policypianist_ros2Sim-side bridge — JointState piano keys → std_msgs/Float32MultiArray on /piano/key_state.
midi_keyboard_driverpianist_policypianist_ros2USB-MIDI input → /piano/key_state (std_msgs/Float32MultiArray, real-piano counterpart of the sim bridge).

Per-tool reference

robstride_ping

ros2 run humanoid_devices_robstride robstride_ping --iface can0 --id 11
ros2 run humanoid_devices_robstride robstride_ping --iface can0 --id 11 --read-status

# Equivalent via the unified CLI:
hc bus ping --iface can0 --id 11
ArgDefaultDescription
--ifacecan0SocketCAN interface
--id32Target Robstride device ID
--timeout-ms500How long to wait for the reply
--read-status(off)After GetDeviceId, also Enable → wait for OperationStatus → Disable, for a one-shot pose / fault read

Read-only when --read-status is omitted. With --read-status, the motor is briefly Enabled and Disabled — no MIT operation control, no commanded motion, but the actuator does transition Enable → Disable internally.

Used in: Tutorials → Drive one Robstride, How-to → Probe CAN bus.

robstride_discover

ros2 run humanoid_devices_robstride robstride_discover --iface can0
ros2 run humanoid_devices_robstride robstride_discover --iface can0 \
--scan-from 1 --scan-to 127 --per-id-wait-ms 8

# Equivalent via the unified CLI:
hc bus discover --iface can0
ArgDefaultDescription
--ifacecan0SocketCAN interface
--scan-from1Lowest ID to ping
--scan-to32Highest ID to ping (inclusive; clamped to 127)
--host-id253Host CAN ID used in the GetDeviceId frame
--per-id-wait-ms8Gap between successive ping sends
--drain-ms200Listen window after the last ping

Read-only — only GetDeviceId is sent. Background drain thread keeps the RX ring from filling during long scans.

Exit code: 0 if anything answered, 3 if scan completed cleanly with zero replies. Both are useful in CI.

Used in: How-to → Probe CAN bus, Hardware specs → Bus-bring-up checklist.

mit_slider_gui

ros2 run humanoid_devices_robstride mit_slider_gui
ros2 run humanoid_devices_robstride mit_slider_gui \
--joint actuator_1 \
--command-topic /forward_mit_controller/commands \
--position-range -3.14 3.14 \
--kp-range 0 10

# Equivalent via the unified CLI:
hc motor slider
ArgDefaultDescription
--jointactuator_1Joint name to read from /joint_states
--command-topic/forward_mit_controller/commandsFloat64MultiArray topic to publish to
--state-topic/lite/joint_statesFor the live readout
--position-range-3.14159 3.14159Slider range, rad
--velocity-range-1.0 1.0rad/s
--effort-range-1.0 1.0Nm
--kp-range0.0 10.0N·m/rad
--kd-range0.0 1.0N·m·s/rad
--default-kp2.0Initial slider value
--default-kd0.5Initial slider value

Requires python_qt_binding (installed alongside rqt_reconfigure).

Used in: Tutorials → Drive one Robstride, How-to → mit_slider_gui.

mode_manager

ros2 run humanoid_controllers mode_manager
ros2 run humanoid_controllers mode_manager --ros-args -p tick_rate_hz:=100
ParameterDefaultDescription
tick_rate_hz50.0Timer rate for tick()
controller_manager/controller_managerCM namespace
joy.damp_button2DAMP button index (default = X on Xbox)
joy.quit_button6QUIT button index (default = BACK)
joy.load_combo_a[4, 0]LOAD_A combo (default = L1+A → Pose A)
joy.load_combo_b[4, 1]LOAD_B combo (default = L1+B → Pose B)
joy.start_combo_locomotion[5, 0]START_LOCOMOTION (default = R1+A)
joy.start_combo_remote[5, 1]START_REMOTE (default = R1+B)

Normally launched by real.launch.py / mujoco.launch.py. Useful to run standalone when debugging the joy decoder.

Used in: Concepts → Five-mode FSM, Reference → Controllers.

calibrate_robot

ros2 run humanoid_bringup_lite calibrate_robot --output ./calibration.yaml
ros2 run humanoid_bringup_lite calibrate_robot \
--output ./calibration.yaml --sweep-threshold 0.3
ArgDefaultDescription
--output(required)Path to write the resulting YAML
--sweep-threshold0.5Min sweep (rad) below which the prior homing_offset is preserved

Normally launched by calibrate.launch.py (which sets --output from a launch arg and brings up the rest of the stack). Standalone invocation is useful if you already have real.launch.py running with calibration_file:=''.

Used in: How-to → Calibrate the zero pose.

rerun_viz / viser_viz

The two live-viewer executables. On the tethered deployment they are spawned via ros2 launch humanoid_bringup_lite viz.launch.py on the operator workstation (viewer:=viser by default; viewer:=rerun for the native window). Direct invocation is the single-machine sim/dev shortcut:

ros2 run humanoid_bringup_lite rerun_viz       # native rerun window
ros2 run humanoid_bringup_lite viser_viz # browser viewer at http://0.0.0.0:8080

Both read /robot_description (latched) once, subscribe to a --joint-state-topic (default /lite/joint_states), and render the live pose. rerun-sdk, viser, yourdfpy, and scipy ship in the workspace env.

Used in: How-to → Live viz, Concepts → Architecture → Deployment topology.

Adding a new CLI tool

For a tool that ships from one of the existing packages:

  1. Drop the source in <package>/scripts/<name>.py (Python) or <package>/src/<name>.cpp (C++).
  2. In the package's CMakeLists.txt, install it under lib/${PROJECT_NAME} without the .py extension so ros2 run finds it:
    install(
    PROGRAMS scripts/<name>.py
    DESTINATION lib/${PROJECT_NAME}
    RENAME <name>
    )
    For C++ add the executable target and install it normally — the install(TARGETS ... RUNTIME DESTINATION ...) lines.
  3. Rebuild with colcon build --symlink-install --packages-select <package>.
  4. Verify with ros2 pkg executables <package>.

The --symlink-install flag means Python scripts edit-loop without rebuilding — useful while iterating.