从理解指令到执行动作:具身机器人如何构建推理、执行与验证闭环?
- 写在最前面
- 1 理解指令先要形成明确的任务
- 2 用任务流和反馈流理解模块协作
- 3 从动作意图到执行请求需要经过哪些条件
- 3.1 先确认控制模式已经就绪
- 3.2 再核对本次动作请求是否被受理
- 4 验证要说明这一次任务完成到了哪里
- 4.1 过程与结束状态需要放在一起判断
- 4.2 回复内容应由任务状态决定
- 5 反馈怎样改变下一步决定
- 6 把运行闭环放进可验证的开发过程
- 参考资料
- 启元机器人开发者社区
写在最前面
版权声明:本文为原创架构解读,遵循 CC BY-SA 4.0 协议,转载请注明出处。
“请挥挥手,完成后告诉我。”对机器人来说,这句话包含两个有先后关系的要求:执行挥手,再根据动作结果作出回应。它需要听清楚指令,选对动作,确认身体处于合适的控制状态,并在执行后判断什么时候可以说“完成了”。
我在梳理启元开放资料时,最关注的就是这段衔接:一条已经理解的指令,怎样穿过软件接口变成身体动作;身体产生的新状态,又怎样回到上层,影响下一步决定。沿着这个过程看,机器人架构中的模块名称会变得具体,每个模块都要向下一环交付可以使用的信息。
本文以启元 Q1 SDK v1.0.0.0、配套接口说明和 PrimeConsole 官方资料为依据,用上述指令贯穿分析。接口名称与部署关系来自公开资料,任务理解、调度和结果判断的组织方式,是本文据此展开的应用架构设计。[1][2][5]
1 理解指令先要形成明确的任务
先看“理解”这一环。机器人接收到的语音需要转成文本,但后续程序真正要用的是一个带执行条件的任务。对本例而言,目标动作是挥手,回复时机是动作完成之后。第二个条件决定了语音回复必须等待结果,不能与动作请求同时无条件触发。
Q1 的公开 SDK 提供了语音识别结果话题 /aima/agent/asr_result,消息类型为 AsrResult。其中,text 保存识别文本,is_final 区分中间结果与最终结果,event_id 用于关联同一次对话交互。[2][3]
这些字段会直接影响任务入口的设计。比如用户说到“挥手”之后又补了一句“先别开始”,中间转
写就不足以决定执行。本例可以在收到最终转写后,再把动作目标和时间条件一起交给任务层。同一
轮语音产生的多次识别结果,应按 event_id 做上下文关联,避免反复执行;但它不是运动服务返回的
task_id,应用仍需自行维护二者的对应关系。
随后,任务层需要把日常表达映射到机器人已有的能力。Q1 预设动作列表中,挥手对应 Q_WAVE_HAND,编号为 3004;招手则是另一个动作,编号为 3001。这样的能力对应关系,应由明确的动作目录约束。[2]
固定场景可以用规则完成这个映射;当表达更自由、任务更复杂时,可以引入语言模型进行理解和拆解。无论采用哪种方式,都应保留同一份任务记录,让动作选择、状态跟踪和最终回复围绕同一条指令推进。表 1 给出了本例适合保留的信息。
表 1 一条挥手指令在应用中需要保留的信息
| 信息 | 本例中的内容 | 后续用途 |
|---|---|---|
| 用户目标 | 挥手,并在完成后告知 | 确定动作与回复之间的先后关系 |
| 指令关联 | ASR 的 event_id 与最终文本 | 关联本次交互,避免重复触发 |
| 当前步骤 | 准备模式、提交动作、核对结果等 | 决定哪些请求现在可以发送 |
| 执行记录 | 动作编号、请求回执和返回的 task_id | 跟踪每次尝试,区分受理与拒绝 |
| 完成条件 | 本次动作过程和结束状态符合预期 | 决定何时可以报告完成 |
ASR 和动作响应字段依据 SDK;任务记录为本文设计。event_id 与 task_id 来自不同接口,需由应用关联。[2][3]
2 用任务流和反馈流理解模块协作
启元 SDK 的公开部署图把开发 PC、运控板和大脑板连接在同一套 ROS2 与 FastDDS 通信体系中。运控板承载硬件抽象层 HAL、运动控制 MC 和基础交互服务;大脑板运行核心 AI、感知与规划等程序。开发者的 SDK 程序可以部署在不同设备上,通过统一接口与机器人交互。[1]
这段部署关系解释了模块为什么能够分工。任务程序可以先在开发 PC 上运行,运动控制仍由机器人侧承担;需要搬到板载环境时,业务仍围绕同一组接口组织。阅读架构时,既要看程序放在哪里,也要看它向外提供什么,以及依赖谁的反馈。
如果把视角从 SDK 扩展到启元公开发布的 AI 能力体系,还能看到一层不同的分工:PrimeVista 面向视
觉、语音等多模态交互,PrimeGo 面向多模态感知与跟随,PrimeMotion 重点处理运动的稳定性、柔顺
性和安全性。启元还提出以机器人 Agent 连接环境感知、语言理解和任务执行。需要区别的是,这些
属于产品发布时披露的模型定位与研发方向;Q1 开放 SDK 则规定了开发者能够访问的接口,并支持
接入自研或开源模型。不能因为两者职责相近,就认定 SDK 已公开这些模型的内部推理流程,或认为
图 1 的任务调度模块就是启元的内部部署图。[7][8]
从本次任务出发,可以把协作关系画成图 1。上层负责确定目标、安排当前步骤和核对结果,SDK 连接具体的执行能力与观测能力。动作请求沿执行方向传递,模式状态、请求回执和关节观测沿反馈方向返回。结果判断更新任务进展后,调度层才能决定继续、等待还是结束。
这里有两类交互值得分清。Service 用于一次请求与响应,例如设置运动模式、提交预设动作;Topic 用于订阅持续产生或按事件产生的数据,例如语音识别结果和关节状态。一次服务响应可以回答请求是否被接受,后续状态数据则帮助应用理解机器人正在发生什么。[2]
当任务进一步涉及外部环境,图像也会进入这条反馈链。Q1 SDK 开放了相机图像获取和视频流入口,关节话题则提供本体运动状态。图像可以帮助回答目标在哪里、环境发生了什么变化,关节状态帮助回答身体运动到了哪里。任务层应按需要使用这些信息,并保留观测的时间关系。[2]
因此,模块交接不能只传一个动作名称。调度层还要说明动作对应哪次任务、哪些前提已经满足、后续需要等待什么信息。理解模型给出动作建议之后,动作适配层负责把这些要求转换成当前机型支持的接口与参数。
图 1 围绕同一次任务组织理解、执行与结果反馈
依据 Q1 SDK 接口整理的功能协作示意。虚线框是本文提出的应用职责;实线框对应开放能力。官方公布的 AI 模型定位不等于本图中的 SDK 服务或上层应用模块。[1][2][7][8]
3 从动作意图到执行请求需要经过哪些条件
回到挥手例子。预设挥手已经有明确的动作编号,上层无需为这次固定交互重新生成整段关节轨迹。SDK 将 SetMcPresetMotion 描述为预设动画或关节空间轨迹的播放入口;它与运动模式切换承担不同职责。[2]
3.1 先确认控制模式已经就绪
接口说明要求,调用预设动作前,应先进入 BIPED_WHOLE_BODY_CTRL(1005)全身动作控制模式,
再确认模式进入运行态。不同起始姿态并非都允许直接切到目标模式;官方示例中的
mc_action_switcher.py 会依据允许的状态转移关系规划路径并逐步等待,而不是在任意姿态直接发送挥
手请求。[2][4]
设置模式使用 SetMcAction,查询模式使用 GetMcAction。已核对原始 .srv 和 .msg 定义:前者返回
CommonTaskResponse,其中 response.header.code == 0 表示调度成功,而 response.state.value == 1 在该 接口中的具体含义是“action 设置成功,开始切换逻辑”。这说明切换已被启动,不说明机器人已经
稳定进入目标模式;实际结果还须由后者读取。[2][9]
因此,上层需继续查询 GetMcAction 返回的 info.current_action.value 与 info.status.value,分别确认目标
模式为 1005,且状态达到 McActionStatus.RUNNING(数值 100)。info.switch_ready 也在消息定义中用
于标示切换就绪,但不能用一次设置调用的成功返回替代实际模式查询。这里的 RUNNING 仅描述运动
模式,不是挥手动作已完成。图 2 将三个判断分开。[2][9]
图 2 把动作请求与对应的执行依据逐项对齐
编号与返回结构按 Q1 SDK v1.0.0.0 原始消息定义核对。state.value=1 仅说明启动切换,RUNNING(100) 说明模式运行,header.code=0 说明请求调度成功;三者均不是单次挥手的完成证明。[2][4][9]
3.2 再核对本次动作请求是否被受理
模式准备好后,应用通过 SetMcPresetMotion 提交挥手请求:以 motion.value = 3004 指定动作,另按需
求填写 source、interrupt 等参数。该服务返回 CommonTaskResponse,包含 response.header.code、
response.task_id 和 response.state。这些是此次请求的回执信息,而不是播放完成回调。[2][4][9]
比如 interrupt=false 且机器人正在播放另一段动画时,接口说明指出,新请求可能被拒绝,但返回的业
务 state 仍可能显示 RUNNING。因此应先检查 response.header.code:0 表示调度成功、请求进入执行序
列;1 表示调度失败,在本例中可能是被现有动画占用拦截。再结合 response.state.reason 判断失败原
因;不能把所有 code=1 都归结为动作占用,更不能把 RUNNING 当作本次新动作已启动。[2][9]
原因并不难理解:机器人正在运行动作,和这次新请求被接受,是两个不同的问题。调度层若只看到“正在运行”就推进到下一步,可能会把前一段动画的状态记在新任务上。正确的处理应先保存这次请求的回执,再更新对应任务的进展。
这些字段必须连同消息类型一起理解:CommonState.RUNNING 数值为 400,而
McActionStatus.RUNNING 是 100,前者是业务任务状态,后者是运动模式状态。state.reason 还可说明任
务占用、当前模式不支持等原因。另一个容易误读的名称是 SetMcAction:它属于 ROS2 Service,名
字中的 Action 不代表已经提供 ROS2 Action 的逐步反馈与最终结果回调。[2][9]
4 验证要说明这一次任务完成到了哪里
动作被受理之后,还剩下文章开头的第二个要求:什么时候告诉用户完成了?要回答这个问题,需要把几种反馈放回各自的语义中。表 2 将请求受理、控制准备和动作结果区分开来。
表 2 不同反馈能够支持怎样的判断
| 要回答的问题 | 对应依据 | 可以得出的判断 |
|---|---|---|
| 本次请求是否受理 | SetMcPresetMotion 的 response.header.code,结合 state.reason 等业务字段 | 本次请求已被受理,或被拒绝 |
| 目标模式是否就绪 | GetMcAction 的 current_action 与 status | 目标控制模式已进入运行态 |
| 身体是否产生预期运动 | 与本次执行时段对应的关节位置、速度等观测 | 动作过程是否符合预期,需要应用判据 |
| 是否可以报告完成 | 本次动作过程、结束条件和任务有效性均得到核对 | 满足所定义的完成条件后,再触发回复 |
前两行是 SDK 接口语义;后两行是应用根据公开观测建立的判断。控制模式就绪与单次动作完成需要分别核对。[2][4]
官方 set_preset_motion.py 示例在收到 SetMcPresetMotion 成功响应后打印 task_id,并不会等待这段挥手
真正播完。GetMcAction 也只返回当前运动模式的信息,不返回单次预设动作的播放进度。核对本版
Q1 公开 .srv 目录后,没有发现可直接提供这次挥手完成回执的预设动作状态查询服务。因此,“完成
后告诉我”的最后一步,仍需由应用另行设计结果验证,而不能直接等同于请求成功。[2][4][9]
4.1 过程与结束状态需要放在一起判断
一种可以继续实现的做法,是在应用独占的动作执行时段内,记录动作开始前的关节状态,再检查相关关节是否按预期经历挥手过程,最后核对结束姿态。Q1 的 /aima/hal/joint/state 话题提供关节名称、位置、速度等数据,可以作为这一判断的输入。[2]
同时看过程和结果有实际必要。如果挥手最终回到接近初始的姿态,仅比较开始与结束两张状态快照,难以区分“完整挥过手”和“始终没有动”。反过来,只看到手臂发生运动,也不足以确认预定序列已经结束。
如果能够取得挥手动作的参考轨迹或关键姿态,应用可以检查关节变化是否按预期依次出现,再核对
末段是否达到设定的结束条件。这里的关节观测只是运动过程证据,并非 Q1 SDK 自动提供的“挥手
成功”判定。参考轨迹、角度容差、观察窗口和结束阈值都要结合设备版本标定;缺少足够证据时,
状态应保留为待确认,而不是由请求成功直接推断动作完成。
对挥手这样的例子,开发阶段可以结合关节记录与外部观察核对过程。机器人头部相机的视野未必覆盖完整手臂,不能默认它总能自行看见动作全貌。将来换成面向物体的任务,完成条件还应覆盖环境变化,例如目标物体是否到达指定位置;这时视觉反馈才承担相应的验证职责。
4.2 回复内容应由任务状态决定
启元 SDK 的 PlayTts 服务可以将指定文本合成并播放。[2] 在本例的应用设计中,任务调度层应在完成条件满足后,再触发“挥手完成”的回复。请求被拒绝时,回复的是当前无法开始及可用的原因;结果尚未确认时,说明仍在核对。用户听到的反馈由任务的实际进展决定。
这也解释了验证模块在架构中的位置。它需要把观测整理成调度层能使用的判断,例如“模式仍在切换”“本次请求被拒绝”“动作过程已经符合完成条件”。这样的信息才能改变后续行为。
5 反馈怎样改变下一步决定
一个能处理现场变化的应用,需要为正常推进和暂时无法推进的情况分别安排后续步骤。图 3 给出了本例的任务组织方式。中心问题始终是:根据当前这次任务和最新反馈,下一步现在是否成立。
模式还在切换时,任务可以停留在“等待模式就绪”,按设定的查询节奏与超时条件继续观察。这个阶段无需反复生成新的任务计划,也无需重复下发相同动作。已有计划的下一步,只是在等待前置条件成立。
请求因动作占用被拒绝时,任务层需要记录这次请求没有被接受,再判断等待是否仍符合用户意图。允许打断与否也属于任务约束。不能为了让新动作立即执行,就无条件更改打断策略。
如果服务等待超时,应用也需要区分“没有收到响应”和“机器人明确拒绝”。前一种情况下,请求是否到达执行端可能尚未确认;直接重发可能带来重复动作。更合适的步骤是先结合可用状态与记录核对,再决定是否进行下一次尝试。
还有一类问题来自多轮指令。用户发出了新请求,旧请求的回执却晚到。如果应用只按消息到达顺序更新任务,就可能把旧动作的反馈归给新动作。因此,ASR 的事件关联、应用自己的任务记录和 SDK 返回的任务标识,需要建立明确映射。关节数据则要结合本次执行窗口解释,不能仅凭“最近收到了一条状态”判断它属于当前任务。
在这样的分工下,上层推理既可以继续既有计划,也可以因条件变化而调整计划。模型适合参与目标理解和复杂步骤选择,确定的接口检查可以由明确的程序逻辑完成。动作执行持续产生新状态,应用再用这些状态更新对任务的认识,推理与执行便有了实际的往返关系。
图 3 用最新反馈决定等待、调整或报告完成
本文设计的任务调度示意。等待应有超时,重试应重新检查条件;结果不足时保留待确认状态,避免由单一回执直接推导任务完成。
6 把运行闭环放进可验证的开发过程
运行中的反馈判断,还需要开发阶段的验证来支撑。启元 PrimeConsole 官方页面列出了连接与日志、实时视频、方向控制与急停、机器人仿真、动作与表情测试,以及 Skill 验证等能力;开发页还提供 Q1 的 URDF 和仿真相关资料。[5][6]
这些工具可以沿着前面的任务过程使用。先检查模型中的关节与运动关系,再检查软件是否正确处理最终语音文本、模式切换响应和动作回执,随后在真机条件下核对动作过程与结束判据。每一步解决的问题应当清楚:仿真中的关节运动合理,并不能替代真实设备上的执行结果。
对于“挥手完成后告诉我”,值得保留一份能够串起全过程的记录:本次最终识别文本、任务关联、模式切换及查询结果、挥手请求回执、相关关节观测,以及最终为何判定完成或待确认。SDK 集成指南也提供了日志与 ROS2 Bag 数据的导出说明,便于回看问题。[1]
有了这份记录,排查时就可以沿着交接点定位:文本是否理解正确,目标模式是否就绪,请求是否受理,动作过程是否符合预期,最后的回复是否提前触发。修复一处问题后,再用相同任务和相同判据回看修改效果,开发验证也就围绕任务结果形成了回路。
回到开头那句简单指令,启元开放资料提供了观察这类架构的具体入口:语音结果可以被任务程序接收,动作可以通过明确的接口提交,模式与本体状态可以返回应用。开发者继续完成的工作,是把这些信息组织到同一次任务中,并规定什么证据允许任务进入下一步。这样,机器人说出“完成了”时,这句话就能对应到此前的执行过程与结果判断。
参考资料
主要技术依据为启元官方 SDK 仓库、原始接口定义及开发者页面;模型能力定位另参考启元产品页与 2026 年 9 月新品发布会的公开报道。Q1 SDK 字段按仓库原始文件复核(2026 年 10 月 19 日)。三张图为原创架构示意,不代表已完成 Q1 真机实测。
**[1] 启元 Q1 SDK《PrimeBot SDK 快速入门与集成指南》。**第 1 章系统架构总览;第 6.8 节日志导出与问题反馈。官方仓库中的集成指南
**[2] 启元 Q1 SDK《接口说明》。**接口公共说明;第 2.1.1.1 节运动模式控制;第 2.1.1.2 节预设动作控制;关节状态话题;第 2.2.1.2 节语音合成;第 2.2.1.7 节语音识别;第 2.3.2.1 节视觉采集管理(单帧图像与视频流)。官方仓库中的接口说明
**[3] 启元 Q1 SDK 语音识别消息定义。**aimdk_msgs/agent/msg/AsrResult.msg。用于核对 text、event_id、is_final 等字段。AsrResult 消息定义
**[4] 启元 Q1 SDK 预设动作示例。**examples/python/set_preset_motion.py;重点参照 ensure_ready_state 与 send_motion_request 的模式准备和受理判断。官方预设动作 Python 示例
**[5] 启元开发者社区 PrimeConsole 与资料包。**工作台能力介绍,以及 Q1 SDK v1.0.0.0 官方下载入口。PrimeConsole 与 SDK 下载页
**[6] 启元 Q1 URDF 官方仓库。**Q1 机器人结构描述与仿真资料;资料包功能介绍参见开发者社区下载页。Q1 URDF 官方仓库
[7]启元 Q1 探索版官方产品页。Agent 开发可接入自研或开源大模型,SDK / HDK / API 开放能力参见 启元 Q1 官方介绍。
[8]2026 年 9 月 20 日启元新品发布会公开报道。涉及 PrimeMotion、PrimeGo、PrimeVista 及机器人 Agent 的定位;属公开发布层面的技术介绍,不代表 SDK 内部实现披露。来源:扬子晚报/紫牛新闻。
[9]Q1 SDK 原始服务及消息协议文件。SetMcAction.srv、GetMcAction.srv、SetMcPresetMotion.srv、CommonTaskResponse.msg、CommonState.msg、McActionInfo.msg、McActionStatus.msg。核对入口:官方 SDK 仓库。
本次核对版本:Q1 SDK v1.0.0.0 官方资料包。仓库后续可能更新,文中字段以该版本为准。
启元机器人开发者社区
本文涉及的 Q1 SDK、ROS 2 接口和 PrimeConsole 开发资料,可通过启元机器人开发者社区查阅。
hello,这里是 晓雨的笔记本。感谢阅读,后续继续分享机器人开发与开源技术实践。