Skip to content

About

人面机器人表情电机的 Protocol 6 CAN 控制与动作时间轴软件

Topics

Resources

Contributing

Security policy

Stars

0 stars

Watchers

0 watching

Forks

Repository files navigation

Action Editor

中文 | English

Action Editor 是面向人面机器人表情电机的独立 Electron 桌面控制软件,提供 Protocol 6 CAN 单电机控制、电机控制时间轴、命名动作编辑和多轨动作时间轴。项目自带 JavaScript 桥接客户端与纯标准库 Python SocketCAN 桥接器,不依赖其他 LumDriver 源码目录。

真实 CAN 运行面向 Linux SocketCAN;界面和协议流程也可在仿真模式下开发、演示和测试。 涉及真实机械前请先阅读 硬件安全说明。

快速开始

环境要求:

  • Node.js 24.20.0 或更高兼容版本(建议使用 Node 24 LTS);
  • npm 11.19.0(Node 24.20.0 官方发行包自带);
  • Python 3.9 或更高版本;
  • 真实 CAN:Linux、已启用的 SocketCAN 接口和对应硬件驱动。

克隆或下载仓库后,在项目根目录运行:

cd action-editor
npm ci
npm start

首次检查界面时可以勾选顶栏“仿真”,不需要 CAN 硬件。开发和提交前运行:

npm run verify

桌面 Linux 可安装一个始终指向当前项目目录的快捷方式:

npm run desktop:install

如果桌面会话的 PATH 找不到 Node.js,scripts/run.sh 会继续检查 $HOME/.local/nodejs/node-v*/bin/node,也可以通过 ACTION_EDITOR_NODE 指定 Node 可执行文件; 旧变量 LUMMOTOR_NODE 仍作为兼容别名。Python 解释器可通过 ACTION_EDITOR_PYTHON 覆盖, 旧变量 LUMDRIVER_PYTHON 仍可继续使用。

SocketCAN 准备

Action Editor 不会调用 sudo,也不会替系统配置 CAN 比特率。以下是 1 Mbit/s can0 的典型 系统配置示例,具体命令应按所用 CAN 适配器调整:

sudo ip link set can0 down 2>/dev/null || true
sudo ip link set can0 up type can bitrate 1000000
ip -details link show can0

当前用户还需要具备访问该接口的权限。同一总线不要同时运行多个会发送运动指令的程序。

项目结构

action-editor/
├── README.md / README_EN.md # 中文 / English 使用文档
├── LICENSE                  # Apache License 2.0
├── NOTICE                   # 版权与归属声明
├── main.js                  # Electron 主进程、安全校验和文件对话框
├── preload.js               # 最小化渲染器 API
├── renderer/                # 单窗口 GUI
├── src/                     # 电机、指令、时间轴模型和桥接客户端
├── bridge/                  # Python SocketCAN / 仿真桥接器
├── scripts/                 # 可移植启动和桌面快捷方式安装脚本
├── tests/                   # Node 回归与独立桥接仿真测试
└── .github/                 # CI、依赖更新和协作模板

Linux 上继续使用历史配置目录 ~/.config/lumdriver-motor-terminal,这样升级应用时,已有 电机 ID、动作和时间轴不会消失。该目录名仅为兼容旧数据而保留,不代表当前产品名称, 也不是源码依赖。

使用说明

Action Editor 是单窗口 Protocol 6 CAN 发送终端。当前电机全部展开 在同一个页面,没有“先选电机再进入控制页”的切换操作。创建电机时先确定名称和 所属分组;创建后名称和分组固定。每一行都可直接配置节点 ID、相对步数、速度、加速度 及开环/闭环模式,并可独立正转、反转、 停止或失能。

电机位置

软件首次运行默认提供 26 个物理电机位置:

  • 眉毛 4 个:左眉外侧、左眉内侧、右眉内侧、右眉外侧;
  • 左眼 4 个:上眼皮、下眼皮、眼球左右、眼球上下;
  • 右眼 4 个:上眼皮、下眼皮、眼球左右、眼球上下;
  • 嘴部 9 个:左嘴角 A/B、右嘴角 A/B、上嘴唇左/右、下嘴唇左/右、下颚;
  • 头颈 5 个:左连杆、右连杆、扭头、扭头2、颈部。

“电机控制”标题区的“+ 添加电机”可以继续增加控制位置;添加弹窗会先要求填写名称 并选择分组。电机创建后名称和所属分组都不再提供修改入口;需要改名或换组时,应删除 该电机,再使用正确名称从目标分组中重新添加。点击“+ 添加分组”可以建立新的控制分组, 分组名称仍可直接修改;分组标题中的“+ 电机”会预选本组。电机控制页的分组按两列连续 紧挨排列,不会因相邻分组高度不同留下大块上下空白。空分组可直接删除,非空分组必须先 逐个删除其中电机。电机与分组 列表、名称、ID 和动作参数都会自动保存在本机,因此重新启动后仍保持上次的布局与配置。

每行的 ID 输入框可绑定一个 1..127 的 CAN 节点 ID,同一个 ID 可以同时填在 多个位置,便于逐行发送小行程指令来确认机械对应关系;留空 表示该位置不用。有效 ID 和参数在修改后立即保存在本机,顶栏状态会显示 “ID 与参数已保存”;保存失败也会直接提示。每个电机的 ID、步数、速度和加速度 以及当前选择的开环/闭环模式都按控制位置独立保存在本机, 不会修改驱动板自身的节点 ID。如果修改了某个电机的 ID,保存着旧 ID 的 历史指令会标记为失效并禁止发送,避免误控其他节点。

ID 可以重复。辨认电机时应先设置低速度、小步数,并保证机械周围无人和无遮挡物。

配置导入与导出

顶栏左侧的“导出配置”和“导入配置”用于在不同设备或不同调试方案之间迁移设置。 导出的 JSON 文件包含 CAN 接口、仿真开关、分组名称与顺序,以及当前全部电机的名称、 所属分组、ID、步数、速度、加速度和开环/闭环模式;指令记录、发送日志、当前位置、 连接状态以及电机控制时间轴的使能状态不会写入配置文件。

导入前必须断开 CAN。软件会先完整校验文件格式、版本、电机列表及参数范围, 全部合法后才一次性应用并保存;重复 ID 会原样保留,校验失败不会改动当前配置。 以前导出的固定轴数配置仍可继续导入;缺少的新版默认位置会按兼容规则补齐。 导入新配置后,本次连接的位置累计会失效,需要重新连接或在确认机械安全后设置起点。 旧版配置中没有运动模式字段时会自动按开环载入,不会把历史配置意外改成闭环。

电机控制时间轴

“电机控制时间轴”是第二个工作页面,顶部 CAN 连接、配置工具和全总线急停始终保留。 时间轨按电机控制页的分组顺序显示当前全部电机位置,并用分组标题分隔轨道。每个位置 (轨道)都有独立的时间轨使能开关, 默认关闭。该开关只决定对应轨道是否参与测试和播放,不限制电机控制页面的手动操作。 直接点击右侧的电机名称或空白轨道即可选中该位置,选中的整行会高亮,左侧动作 编辑器会显示当前控制位置;不再使用容易跳回旧值的电机下拉框。然后可设置正反方向、 开环/闭环模式、开始时间、步数、速度和加速度;“测试动作”会立即向该位置发送一次 当前参数,但不会 把测试自动加入时间轨。点击使能框只改变播放使能,不会切换当前控制位置。 点击“添加为新动作”始终新建一个时间点,因此同一个电机可以在时间轨中重复添加 任意多个动作。选择已有动作后,“更新所选动作”只修改该动作,不会覆盖同一电机的 其他时间点。动作编辑器不再提供单独的“新建”按钮;需要继续添加时,直接选择电机行、 调整参数并点击“添加为新动作”。

时间轨横向是指令发送时间,纵向显示当前电机位置。动作标记可以左右拖动 修改发送时间,也可以上下拖到其他已配置 ID 的位置;默认吸附 100 ms,按住 Alt 拖动可临时关闭吸附。按住顶部时间尺或黄色播放头左右拖动,会实时把取得的时间写入 左侧“开始时间 / ms”;编辑已有动作时只修改编辑框草稿,点击“更新所选动作”后才保存。 选中或悬停标记会展开动作参数;点击动作块会在左侧载入该动作, 进入编辑状态;再次点击电机行则回到该电机的新建动作状态。动作、时长、吸附和缩放 设置都会自动保存在本机,也可以点击“保存时间轴”立即保存并查看动作数量。

动作编辑器会根据步数、速度等级和加速度等级实时计算理论持续时间与预计结束时间。 时间轨中的动作不再只是一个时间点,而是按理论持续时间显示为有长度的动作块。 计算采用与 Protocol 6 固件相同的等级平方映射和 S 曲线模型;连接 CAN 后,软件会 只读获取该节点的每圈整步数、微步细分、S 曲线时间、速度上限和加速度上限并重新 计算。离线或节点没有响应时使用固件默认值(200 整步、128 微步、3000 rpm、 20000 rpm/s、10 ms S 曲线),界面会明确标出参数来源。

开环动作的理论持续时间对应参考 S 曲线完成时间;闭环动作显示的时长也只代表这段 参考轨迹,不能视为闭环实际到位时间。闭环可能还包含电流预充、开闭环安全交接以及 轨迹停止后的编码器纠偏和稳定判定,负载较大时会继续占用 FIFO 等待真正到位。因此, 闭环动作块和“接到同 ID 最后”都只用于编排参考,最终完成仍以节点状态和 FIFO 反馈为准。

如果一个动作的发送时间早于同一物理 ID 的上一动作预计结束时间,动作块会显示为 排队状态;固件播放时它会进入该节点 FIFO,而不是在横轴时间立即起转。左侧的 “接到同 ID 最后”可以把开始时间直接放到该 ID 当前预计完成点并按吸附间隔向上取整, 便于连续编排同一电机的多个动作。不同 ID 的动作块可以重叠,表示并行动作。 持续时间只用于编排参考,不替代到位反馈:负载、失步、限位、故障、CAN 延迟和其他 控制端插入的指令都可能使实际完成时间不同。

“导出动画”会生成独立的动画时间轴 JSON,包含总时长、吸附、缩放、当前全部轨道的 使能状态,以及全部动作的电机位置、节点 ID、时间、方向步数、速度及加速度;它不会 混入顶部导出的硬件配置。每个动作选择的开环/闭环模式也会随动画保存和导出。 “导入动画”会先完整校验文件格式、版本、动作数量和所有参数,全部合法后才整体替换 当前时间轴及轨道使能状态并保存。电机控制时间轴内容和使能状态也会自动保存在本机;它们不属于 顶栏的电机配置。导入动画不会修改当前电机 ID 绑定;若文件中的动作 ID 与当前绑定 不同,动作会标记为失效,更新对应动作后才能播放。以前导出的 25 轴动画也可导入, “扭头2”轨道会自动补为未使能且没有动作。旧版动画中没有运动模式字段的动作会按 开环导入,以保持原有发送行为。

已使能轨道中,相同时间、不同物理节点的动作会成组并发下发,因此可以编排近似同时开始的表情。 CAN 总线本身仍是串行链路,当前固件也没有带时间戳的硬件同步触发,所以横轴只保证 主机按时间点发送,不能承诺多个电机在完全相同的物理时刻起转。相同时间指向同一个 节点 ID 的已使能动作会标红并禁止播放,因为它们实际共用一个 MCU FIFO。未使能轨道 中的动作不会参与播放,也不会参与时间冲突或同节点冲突判断。

未使能轨道中的动作仍可添加、修改、拖动、保存和导出;“测试动作”要求所选动作 对应的轨道已经使能。播放时只发送已使能轨道中的动作,未使能轨道会直接跳过, 不会因此阻止整条时间轴开始。取消使能只影响后续播放,不会停止已经在播放或已进入 驱动板队列的动作;播放期间时间轨使能开关会由界面锁定。

播放过程中可随时点击“停止”;软件会先取消尚未下发的动作,再广播立即 STOP,并 向每个相关节点补发定址 STOP。正常播放只有在最后一条动作序号已完成、Status A 无故障且 Status D FIFO 清空后才结束。长节目不受“整段最多 64 条”限制,播放时会按 每个节点实际报告的 FIFO 容量和水位保护;如果界面或系统停顿造成动作迟到超过 250 ms,软件会保护停止,不会把所有逾期动作瞬间补发。 测试、播放和停止都会进入发送日志;成功接收的运动也会计入本次连接的起点账本。

发送闭环测试或播放包含闭环动作的时间轨前,GUI 会重新读取相关节点状态,并检查 编码器有效和编码器校准有效;任一条件不满足时不会发送闭环动作。运行电流、位置环 增益和速度环增益等闭环执行条件仍由 MCU 在接收运动帧时做最终校验,GUI 预检不能 替代固件安全门控。

动作编辑

“动作编辑”用于把一个或多个电机运动组合成可重复使用的命名动作,例如“眨眼”、 “微笑”或“点头”。每个电机运动独立保存电机位置、相对开始时间、正反方向、步数、 速度、加速度和开环/闭环模式;同一动作可以包含多个电机,也可以让同一个电机在不同 时间连续运动。保存动作前可以立即测试当前电机运动,也可以按相对时间完整测试整个动作。

每个命名动作都有自己的内部小时间轴。时间轴按电机位置自动分轨:同一个电机的多个运动 显示在同一行,不同电机显示在不同行,即使它们暂时配置了相同 CAN ID 也不会合并。单击 运动块可载入参数编辑器,左右拖动可直接调整相对开始时间;拖动遵循“吸附”设置,按住 Alt 可临时取消吸附。同一电机上显示范围重叠的运动块会在该电机轨道内自动错层,保证 每个运动都能选中和删除。拖动只修改当前草稿,点击“保存当前动作”后才会写入动作库并同步 到动作时间轴中的已有实例。拖动标尺或播放头也可以取得新增运动的开始时间;测试整个动作 时,内部时间轴的播放头会跟随实际调度进度。

界面会用电机运动参数计算每个片段的理论持续时间,并以最后一个片段的预计结束时间显示 整个动作的理论时长。连接 CAN 后优先使用节点只读运动参数,离线时使用与电机控制时间轴 相同的固件默认参数。理论时长只用于编排参考,闭环实际到位仍以节点状态和 FIFO 为准。

命名动作会自动保存在本机。修改已保存动作后,动作时间轴中已有的该动作实例会同步使用 新定义;若修改电机 ID,保存着旧 ID 的运动会标记为失效,更新后才能测试或播放。删除某个 电机时,任何包含该电机的命名动作会整体删除,其动作时间轴实例也会一起清理,避免留下 只执行半边的残缺表情。

动作库标题下方的“导出动作库”会把全部已保存动作、电机位置引用及每个运动的节点 ID、 时间、步数、速度、加速度和开环/闭环模式写入独立 JSON 文件;未保存的当前草稿不会被导出, 软件会提示先保存。“导入动作库”采用追加方式:文件会先被完整校验,再为新动作生成本机稳定 ID 并一次性加入现有动作库,已有动作和动作时间轴实例不会被覆盖或删除。同名且内容完全相同 的动作会跳过;同名但内容不同会拒绝整批导入并保持现状。导入不会改写当前 CAN 节点绑定, 文件中的节点 ID 与当前绑定不一致时会保留原值并标记失效,需人工检查并更新后才能播放。 为避免不同设备上的自定义电机内部 ID 恰好相同却代表不同机构,文件记录的电机名称也必须 与当前配置一致,否则会拒绝导入。

动作时间轴

“动作时间轴”是只编排命名动作的页面,不再显示单个电机的步数、速度等编辑项。先在 “动作编辑”中保存动作,动作会显示在页面左侧的可搜索卡片库中。单击卡片可以选择动作, 页面右侧可以自由添加、重命名和删除动作轨道;单击轨道即可把它设为当前目标。点击卡片右侧 +、双击卡片或点击底部按钮,会把动作添加到当前轨道的光标位置;也可以直接把卡片拖到 某一条轨道的指定时间。拖动遵循当前吸附设置,按住 Alt 可临时关闭吸附。同一个命名动作 可以在任意轨道添加多次;已放置动作块可左右拖动修改开始时间,也可上下拖到其他轨道。 不同轨道上的动作允许在同一时刻开始,从而让眉毛、眼睛、嘴部或头部组合动作并行发生。 清空只删除动作实例并保留轨道;删除含有动作的轨道时会明确提示该轨道上的实例也将删除。 轨道名称、轨道顺序、时长、吸附、缩放和全部动作实例都会自动保存在本机;旧版单轨数据 首次读取时会自动迁移为可编辑轨道。

顶部“播放调速”提供 0.25× 到 2.00× 七档慢放/快放,并有两种互斥模式: “时间倍速”会按倍率压缩或拉伸所有动作的触发时间、间隔和整条时间轴的播放时长, 但不改变电机速度或加速度;“电机参数倍率”保持所有动作开始时刻不变,只在本次播放 临时缩放速度等级、加速度等级或两者,结果四舍五入并限制在 1–100。后者改变的是 协议参数等级,不代表机械运动时长会严格按相同比例变化。调速设置只覆盖本次运行, 不会改写命名动作、自动保存内容或导出的动画,软件重新启动后恢复为时间原速 1.00×。

页面顶部的“保存时间轴”可立即把当前命名动作库、轨道和动作实例保存到本机。“导出时间轴” 会生成独立的动作时间轴 JSON,文件中同时包含“动作编辑”页面的全部命名动作定义、电机位置 引用快照、轨道名称与顺序、动作实例、总时长、吸附和缩放设置,因此复制到另一台设备后不会 缺少动作素材;若当前动作有未保存修改,会先提示保存而不会导出旧版本。“导入时间轴”会先完整校验整个文件及动作、轨道、实例之间的引用关系,全部合法 后才整体替换当前命名动作库和动作时间轴并保存;校验失败不会改动现有工程。若当前动作草稿 有未保存修改,替换前会明确提示。导入不会更改当前电机配置或 CAN 节点绑定;当前配置缺少 文件引用的电机位置,或同一电机内部 ID 的名称与文件快照不一致时会拒绝导入;节点 ID 已变化 的运动则会标记为失效,更新后才能测试或播放。 该文件与“电机控制时间轴”导出的逐电机动画文件彼此独立,不能混用。

播放时,软件会把每个命名动作展开为其电机运动,并复用电机控制时间轴的并发下发、ACK、 FIFO 水位、迟到保护、故障停机和全总线急停链路。命名动作按整体执行,不读取电机控制 时间轴上的轨道使能开关,因此不会因为某一侧轨道未使能而只执行半个眨眼。同一时间指向 不同物理 ID 的运动会成组并发下发,轨道本身只负责视觉编排,不会逐轨串行播放;同一物理 ID 即使位于不同轨道,在同一时间出现多条运动仍会标红并禁止播放,避免争用同一个 MCU FIFO。

指令语义

终端使用 LumDriver Protocol 6 格式 6 的开环或闭环相对运动。两种模式的 8 字节 payload 布局相同,模式由标准 CAN 仲裁 ID 决定:开环为 0x200 | node,闭环为 0x280 | node。

  • 相对步数:1..16777215;输入框只填行程步数,方向由 +/- 按钮决定;
  • 速度等级:1..100;
  • 加速度等级:1..100。

每个电机行可以选择开环或闭环,所选模式会随本次指令一起记录;时间轨中的每个动作 也可以独立选择模式。每行的 + 按当前步数正向转动,- 按当前步数反向转动, ■ 立即停止该电机, 断 使该电机硬件失能。电机控制页面不受电机控制时间轴使能状态影响;每次成功触发的 正转或反转都会自动进入右侧指令记录。发送会等待对应节点 和动作序号的硬件 ACK(超时 1 秒);只有 ACK 成功才计入起点账本。 发送失败仍会写入日志,但不会留在可重发记录中。

点击“按顺序发送全部记录”会立即对记录快照逐条生成新的 motion sequence 并等待 ACK,不再弹出二次确认。点击“清空”也会立即删除可重发记录。这两个操作 不会递归追加记录。任何一条失败后停止发送;批量期间按任一行停止、失能或顶栏 全总线急停,也会取消所有尚未发送的后续指令。已经被节点接受的动作仍可能执行。每个 节点的 MCU FIFO 容量为 64,因此终端拒绝一次向同一节点重放超过 64 条记录。 单条记录重发和“按顺序发送全部记录”同样不受电机控制时间轴使能状态影响。

发送日志显示时间、来源、位置、步数、CAN ID、8 字节 payload 和结果。ACK OK 只表示动作已进入节点队列,不代表电机已经到位;批量重放和返回起点前,终端会先 确认相关节点 Status D 的 FIFO 已清空。

返回起点

连接 CAN 后,软件会先读取所有已配置物理节点的新状态;只有全部节点都确认静止、无故障 且 FIFO 为空,才把当前位置定义为本次会话起点。无法确认时不会猜测起点,需要在机械停止 并确认安全后手动点击“当前位置设为起点”。软件累计所有 ACK 成功的单发、重发、 批量动作、电机控制时间轴和动作时间轴运动,并按每个物理 CAN 节点的净步数生成反向 补偿;超过单帧上限的补偿会自动拆分。两个时间轴页面的播放控制区都提供“恢复起点”按钮, 它们与电机控制页面共用同一份本次连接账本;播放、测试或返回仍在执行时按钮会保持禁用。 如果多个界面位置使用同一个 ID,返回补偿会先按该物理 CAN 节点合并净步数, 不会把各个位置别名分别往返补偿。

这里的“起点”是 GUI 根据已确认指令维护的命令步数账本,不是传感器物理零点; 选择闭环也不会把它自动转换为编码器绝对零点。失步、外力移动或机械打滑后不能保证 仅靠该账本回到真实位置。以下情况会使本地起点立即失效:

  • STOP、DISABLE 或全总线急停;
  • CAN 断开或桥接异常;
  • 节点报告故障;
  • 修改位置与节点 ID 的绑定。

此时应确认机械安全后,点击“当前位置设为起点”。软件会先确认已配置节点的 FIFO 全部为空。如果后续补偿在发帧前被软件安全检查阻止,已经成功补偿的电机会从账本中 扣除,再次返回只补偿尚未归零的电机;任何进入发帧/ACK 阶段后失败或结果不确定的动作 都会立即使起点记录失效,避免重复补偿,此时需要确认机械安全后重新设置起点。

“返回起点”不受电机控制时间轴使能状态、所选动作或动作轨道影响。执行前会等待相关 节点状态新鲜且 FIFO 为空,并在确认后发送反向补偿。停止、硬件失能和全总线急停也始终可用。

开发与验证

npm ci
npm run verify
npm start

npm ci 按 package-lock.json 安装项目自己的 Electron,并且只允许已精确锁定的 Electron 下载脚本运行。npm run verify 会检查全部 JavaScript、Python 桥接器和 Shell 脚本,并运行模型、界面契约、IPC 安全、导入导出、桥接重试与本地仿真的完整回归测试。

持续集成定义在 .github/workflows/ci.yml,只使用仿真桥接,不访问真实 CAN。依赖更新由 Dependabot 每月检查。贡献和安全报告流程见 CONTRIBUTING.md 与 SECURITY.md。

许可证

本项目采用 Apache License 2.0 开源,版权归鹏睿机器人(深圳)有限公司所有; 归属与声明信息见 NOTICE。使用、修改和分发本软件时必须遵守许可证中的版权、 许可声明及 NOTICE 保留要求;Apache License 2.0 同时包含明确的专利许可条款。软件按“原样”提供;许可证不替代 硬件安全说明 中要求的急停、限位、电源切断和现场安全措施。

安全提示

  • 同一时刻只能运行一个向 can0 写指令的 GUI。启动 Action Editor 前应退出其他 LumDriver 控制程序, 否则不同进程独立分配 sequence 会造成指令竞争。
  • 顶栏急停广播 immediate STOP + DISABLE;应用正常退出也会执行同样的保护停机。
  • 同一时间点的多个节点由主机并发请求下发,但 CAN 仍是串行链路,现有协议没有多节点硬件同步触发。
  • 软件不能替代硬件急停、电源切断、机械限位、电流保护和首次低速小行程测试。

About

人面机器人表情电机的 Protocol 6 CAN 控制与动作时间轴软件

Topics

Resources

Contributing

Security policy

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages