Lerobot

Table of Contents

机器人:SO101,包含从臂和主臂 Lerobot:v0.5.1

1. 查询主从臂的串口号

lerobot-find-port # 先将机械臂串口插入,运行该命令,然后根据提示拔出串口

2. 校准机械臂

校准时, 必须 将所有的关节位置放置在 中位 ,然后键盘的回车键进行校准。

2.1. 校准主臂 (leader)

lerobot-calibrate \
    --teleop.id=leader \
    --teleop.type=so101_leader \
    --teleop.port=/dev/ttyACM0

2.2. 校准从臂 (follower)

lerobot-calibrate \
    --robot.id=follower \
    --robot.type=so101_follower \
    --robot.port=/dev/ttyACM1

2.3. 校准原理

SO101 有 6 个 DOF,每个关节都需要被校准。主要记录每个关节的最小和最大位置。

2.3.1. 电机配置

  • range_mins: 电机运动范围的最小值
  • range_maxes: 电机运动范围的最大值
  • homing_offsets: 归位偏移量,指电机从物理零点位置到校准零点位置的偏移量
电机名称 id drive_mode range_mins range_maxes homing_offsets 归一化模式
shoulder_pan 1 0 根据实际硬件 根据实际硬件 根据实际硬件 degrees
shoulder_lift 2 0 根据实际硬件 根据实际硬件 根据实际硬件 degrees
elbow_flex 3 0 根据实际硬件 根据实际硬件 根据实际硬件 degrees
wrist_flex 4 0 根据实际硬件 根据实际硬件 根据实际硬件 degrees
wrist_roll 5 0 0 4096 根据实际硬件 degrees
gripper 6 0 根据实际硬件 根据实际硬件 根据实际硬件 range_0_100

2.4. 归一化原理

读取 电机数据时会进行 归一化 处理, 写入 电机数据时会进行 反归一化

min_ = range_min
max_ = range_max
bounded_val = min(max_, max(min_, val))

// 电机分辨率
MODEL_RESOLUTION = {
    "sts_series": 4096,
    "sms_series": 4096,
    "scs_series": 1024,
    "sts3215": 4096,
    "sts3250": 4096,
    "sm8512bl": 4096,
    "scs0009": 1024,
}
  • range_m100_100 模式

    norm = (((bounded_val - min_) / (max_ - min_)) * 200) - 100
    normalized_values[id_] = -norm if drive_mode else norm
    
  • range_0_100 模式

    norm = ((bounded_val - min_) / (max_ - min_)) * 100
    normalized_values[id_] = 100 - norm if drive_mode else norm
    
  • degrees 模式

    mid = (min_ + max_) / 2
    max_res = self.model_resolution_table[self._id_to_model(id_)] - 1
    normalized_values[id_] = (val - mid) * 360 / max_res
    

3. 遥操作

lerobot-teleoperate \
    --teleop.id=leader \
    --teleop.type=so101_leader \
    --teleop.port=/dev/ttyACM0 \
    --robot.id=follower \
    --robot.type=so101_follower \
    --robot.port=/dev/ttyACM1

4. 查询摄像头

lerobot-find-cameras opencv

# --- Detected Cameras ---
# Camera #0:
#   Name: OpenCV Camera @ /dev/video0
#   Type: OpenCV
#   Id: /dev/video0
#   Backend api: V4L2
#   Default stream profile:
#     Format: 0.0
#     Fourcc: YUYV
#     Width: 640
#     Height: 480
#     Fps: 30.0
# --------------------
# 
# Finalizing image saving...
# Image capture finished. Images saved to outputs/captured_images

5. 实时显示画面的遥操作

lerobot-teleoperate \
    --teleop.id=leader \
    --teleop.type=so101_leader \
    --teleop.port=/dev/ttyACM0 \
    --robot.id=follower \
    --robot.type=so101_follower \
    --robot.port=/dev/ttyACM1 \
    --robot.cameras="{handeye: {type: opencv, index_or_path: /dev/video0, width: 640, height: 480, fps: 30}, top: {type: opencv, index_or_path: /dev/video2, width: 640, height: 480, fps: 30}}" \
    --display_data=true

6. 收集数据

lerobot-record \
    --teleop.id=leader \
    --teleop.type=so101_leader \
    --teleop.port=/dev/ttyACM0 \
    --robot.id=follower \
    --robot.type=so101_follower \
    --robot.port=/dev/ttyACM1 \
    --robot.cameras="{handeye: {type: opencv, index_or_path: 0, width: 640, height: 480, fps: 30, fourcc: "MJPG"}, top: {type: opencv, index_or_path: 2, width: 640, height: 480, fps: 30, fourcc: "MJPG"}}" \
    --dataset.repo_id=taocheng/so101 \
    --dataset.num_episodes=5 \
    --dataset.single_task="Pick cube" \
    --dataset.streaming_encoding=true \
    --dataset.push_to_hub=false

6.1. 收集数据的过程

lerobot_record.png

7. 回放数据

lerobot-replay \
    --robot.id=follower \
    --robot.type=so101_follower \
    --robot.port=/dev/ttyACM1 \
    --dataset.repo_id=taocheng/so101 \
    --dataset.episode=0

8. 训练

lerobot-train \
    --dataset.repo_id=taocheng/so101 \
    --policy.type=act \
    --output_dir=outputs/train/act_so101 \
    --policy.device=cuda \
    --wandb.enable=false \
    --policy.repo_id=taocheng/so101_act_policy

8.1. 恢复训练

lerobot-train \
  --config_path=outputs/train/act_so101/checkpoints/last/pretrained_model/train_config.json \
  --resume=true

9. 模型评估

lerobot-record \
    --teleop.id=leader \
    --teleop.type=so101_leader \
    --teleop.port=/dev/ttyACM0 \
    --robot.id=follower \
    --robot.type=so101_follower \
    --robot.port=/dev/ttyACM1 \
    --robot.cameras="{front: {type: opencv, index_or_path: 2, width: 640, height: 480, fps: 30}}" \
    --dataset.repo_id=taocheng/eval_so101 \ # 录制评估数据集
    --dataset.num_episodes=10 \
    --dataset.single_task="Pick cube" \
    --dataset.streaming_encoding=true \
    --dataset.push_to_hub=false \
    --policy.path=outputs/train/act_so101/checkpoints/100000/pretrained_model \ # 训练的模型路径
    --display_data=true

Date: 2026-04-10 Fri 00:00

Author: taocheng

Created: 2026-04-15 Wed 13:42

Validate