202604 海康机器人自定义语音播报
在 RCS-Lite 任务执行过程中,需要根据机器人所在位置控制指定语音。目标是机器人到达目标点后开始播报,离开目标点时停止播报,同时语音方案能够通过任务参数调整,不需要为每一种声音单独维护脚本。
本文基于现场配置界面与 audio.py 执行脚本,整理一套可复用的落地方案。脚本部分只保留核心逻辑,重点说明 audio_cmd 和 volume_idx 如何从任务模板传到控制器,再由音频接口切换手动、自动语音方案。
RCS-Lite 侧配置要点
1. AMR 类型开启透传能力
在“AMR类型编辑”界面中,需要为该车型开启“是否透传”。

这个开关的作用,是允许任务模板中的参数透传到车端脚本。如果这里没有打开,即使任务模板配置了消息体,车端脚本也收不到期望的 audio_cmd 和 volume_idx 参数。
对于自定义语音播报,这一步是前置条件。
2. 服务能力集开启参数任务上报
在“Rcs能力集 -> 本地配置”中,需要开启“amr参数设置值任务上报”。

这个配置决定了任务参数能否按预期传递到控制器业务层。现场联调时,如果脚本日志里打印不到 audio_cmd 或 volume_idx,优先检查这里是否已启用。
3. 客制车参数绑定语音脚本
在 MapStudioPro 的“客制车参数”页面中,需要将语音执行脚本绑定到“第三方机构通信脚本”。

| 配置项 | 建议配置 | 作用 |
|---|---|---|
| 自运行脚本开关 | 开启 | 允许控制器加载客制脚本能力 |
| 第三方机构通信脚本 | audio | 接收透传参数并控制语音方案 |
| 移动过程中取消任务脚本 | 无脚本 | 不通过该入口控制语音 |
第三方机构通信脚本选择 audio,并保证 MapStudioPro 中的选择与 RoboDesigner 上传到控制器的工程名称一致。
任务模板配置
现场任务模板使用“移动到达目标点 -> 开始播报 -> 离开目标点 -> 结束播报”的流程,让机器人在到达目标点后播报,并在离开时停止播报。
开始播报
第一个移动步骤完成、机器人到达目标点后,增加“透传任务”,消息体配置为:
[
{
"key": "audio_cmd",
"type": "String",
"value": "start"
},
{
"key": "volume_idx",
"type": "Int",
"value": 204
}
]

这里的 audio_cmd = start 表示机器人到达目标点后切换到手动语音方案,volume_idx = 204 表示播放索引为 204 的语音方案。
离开目标点
机器人准备离开目标点时执行下一段移动任务。现场配置中开启“是否触发”,触发方式选择“AMR编号”。

开始脚本执行完成后,手动语音方案会保持生效。流程进入离开目标点的步骤后,再由后续透传任务下发结束指令。
结束播报
离开目标点时执行“透传任务”,消息体配置为:
[
{
"key": "audio_cmd",
"type": "String",
"value": "stop"
},
{
"key": "volume_idx",
"type": "Int",
"value": 204
}
]

这里的 audio_cmd = stop 表示结束手动播报并恢复自动语音方案。停止分支不会使用 volume_idx,消息体保留该字段,是为了让开始和结束步骤使用同一套任务参数结构。
从任务编排角度看,这种做法有两个直接好处:
- 播报时机清晰,到达目标点开始播报,离开目标点停止播报。
- 脚本维护简单,不同语音只需要修改
volume_idx,不需要复制新的 Python 脚本。
RoboDesigner 脚本配置
在 RoboDesigner 的任务脚本工程中,配置 audio_cmd 和 volume_idx 两个任务参数。

| 参数 | 类型 | 示例值 | 含义 |
|---|---|---|---|
audio_cmd | String | start / stop | 开始播报或结束播报 |
volume_idx | Int | 204 | 手动语音方案索引 |
参数保存后,需要将工程上传到机器人控制器,并确认远程执行时能够在日志中看到本次任务传入的参数。
控制脚本设计
参数约定
脚本约定使用 audio_cmd 作为动作参数,使用 volume_idx 指定开始播报时采用的语音方案:
[
{"key": "audio_cmd", "type": "String", "value": "start"},
{"key": "volume_idx", "type": "Int", "value": 204}
]
其中:
| 参数 | 含义 |
|---|---|
audio_cmd = start | 调用手动语音方案,开始播报 |
audio_cmd = stop | 恢复自动语音方案,结束播报 |
volume_idx | 手动语音方案索引,仅在 start 分支使用 |
这样定义后,任务模板、控制器日志和语音脚本之间的语义是一致的,联调时可以直接根据参数判断当前执行的是开始还是结束动作。
核心代码
下面只保留脚本中的核心部分,用来说明任务参数解析和音频接口分发逻辑:
from sec_dev import AudioApi, TemplateBusiness
from dev_api import SecDevInterface
from param import ParamOperator
from definition import BusinessStatus
class Business(TemplateBusiness):
def __init__(self, robot: SecDevInterface, params):
super().__init__()
robot.log(f"audio params: {params}")
self.params = params
def execute(self, robot: SecDevInterface, args):
audio_cmd = None
try:
task_params = args if args is not None else self.params
robot_operator = ParamOperator(robot, __file__, task_params)
volume_idx = robot_operator.get_value_in_task_data("volume_idx")
audio_cmd = str(
robot_operator.get_value_in_task_data("audio_cmd")
).strip().lower()
if audio_cmd == "start":
ret = AudioApi.set_manual_audio_scheme(robot, volume_idx)
elif audio_cmd == "stop":
ret = AudioApi.set_auto_audio_scheme(robot)
else:
robot.log(f"未知的 audio_cmd: {audio_cmd}")
return BusinessStatus.FAILED
if ret != 0:
robot.log(f"语音控制失败: audio_cmd={audio_cmd}, ret={ret}")
return BusinessStatus.FAILED
return BusinessStatus.FINISHED
except Exception as exc:
robot.log(f"语音控制异常: audio_cmd={audio_cmd}, error={exc}")
return BusinessStatus.FAILED
这段代码体现了 3 个核心设计点。
1. 每次执行都读取本次任务参数
脚本在 execute() 中优先解析本次任务传入的 args,而不是只使用创建 Business 对象时的初始化参数。这样同一个脚本实例连续收到 start、stop 两个任务时,能够分别执行对应接口。
2. 开始和结束动作由同一个参数分发
audio_cmd = start 时调用 set_manual_audio_scheme(),audio_cmd = stop 时调用 set_auto_audio_scheme()。脚本不需要等待固定播放时长,播报持续时间完全由任务模板中两个透传步骤的位置决定。
3. 接口结果统一校验
无论开始还是结束动作,音频接口返回非 0、参数值不是 start/stop,或者执行过程中出现异常,脚本都会返回 FAILED。只有接口调用成功时才返回 FINISHED,避免任务模板在语音控制失败后继续误判为成功。