语音相关(TTS/放音/音量)
一、语音功能概述
1.1 语音相关的四件事
Air780EVT 系列是合宙在 EC7xx 平台上内置 Audio Codec(ES8311)的 4G 模组,走 AT 固件时可以做四类语音相关的事情:
- TTS 文字转语音:把中文、数字文本直接念出来,不需要事先准备音频文件,用
AT+CTTS播报,用AT+CTTSPARAM调音色; - 语音文件播放:播放事先存放在模组文件系统里的 AMR / WAV / MP3 文件,用
AT+CAUDPLAY; - 本地播放音量:调 TTS 与语音文件播放的音量,用
AT+CRSL; - 通话音量:调 VoLTE 通话时听筒 / 耳机 / 免提喇叭的输出音量,用
AT+CLVL。
前两类是"模组自己发声",后两类分别决定这两类声音和通话声音的大小。几条链路的音量参数互相独立、叠加生效,调的时候不要混在一起。
1.2 哪些型号能用这套指令
合宙带音频能力的 4G 模组按音频方案分为三类,其中只有第一类里走 AT 固件的型号才有本文这些指令:
| 音频方案 | 型号 | 固件形态 | 本文指令 |
|---|---|---|---|
| 内置 ES8311 Codec | Air780EVT / Air780EVT-1.8V | AT 固件 | 适用 |
| 内置 ES8311 Codec | Air780EHV | LuatOS 固件 | 不适用(无 AT 版本) |
| 可外挂 ES8311 | Air780EHM、Air780EGH/EGG、Air700ECH、Air8000 全系 | LuatOS 固件 | 不适用(无 AT 版本) |
| 无内置 Codec | Air780E、Air780EG、Air780EEN/EEU/EEJ、Air780EP/EPS/EQ/ER/EX、Air700EAQ/ECQ/EMQ 等 | AT 数据固件 | 不适用(无音频通路) |
Air780EVT 与 Air780EVT-1.8V 的区别只在 IO 电平:前者 3.3V,后者 1.8V,软件与 AT 指令完全一致。
在无音频通路的型号上下发这些指令,模组回 +CME ERROR: operation not supported,这属于型号选错,不是固件坏了。
1.3 与 Air724(8910 平台)的区别
Air724 系列用的是一套老 AT 体系,其中 AT+CLVL 是单参数语法 AT+CLVL=<level>;本文所在的 EC7xx 平台是双参数语法 AT+CLVL=<deviceType>,<level>,两者不兼容、不能互相照抄。其余几条指令的差异较小,但参数个数与取值范围也不同,跨平台时请以对应型号的指令手册为准。
二、演示功能概述
本文用 Air780EVT 核心板,依次演示:
- 查、设本地播放音量;
- 用 TTS 念一段中文;
- 调整 TTS 的音量、语速、音高、通道;
- 播放一个存放在模组文件系统里的音频文件;
- 查、设通话音量。
每一步都给出可以直接照抄的 AT 交互过程与预期回显。
三、准备硬件环境
-
Air780EVT 核心板一块(内置 ES8311,板载喇叭或 3.5mm 耳机座);
-
TYPE-C USB 数据线一根,一端接核心板的 TYPE-C 座,另一端接电脑 USB 口(这根线同时供电和提供 AT 串口);
-
发声设备:板载喇叭,或 3.5mm 耳机一副。免提喇叭(
deviceType = 3)测试时要注意 PA 是否使能,部分板子的 PA 需要由模组 GPIO 控制,见 6.3 的<papin>参数; -
如果用 1.8V 版本(Air780EVT-1.8V),外接的 MCU 串口电平也必须是 1.8V,直连 3.3V 会损坏 IO。
四、准备软件环境
-
Luatools 工具:用于给模组烧录 AT 固件;
-
LLCOM 或任意串口工具:用于给模组发 AT 指令、看回显。串口参数 115200-8-N-1,记得勾选"发送新行"(
\r\n),不勾选模组不会响应; -
AT 固件:本文示例使用
AirM2M_780EVT_V2025_LTE_AT。固件在 AT 固件版本页 下载,烧录方式见 Luatools 说明。
提醒:语音相关指令是否可用取决于固件有没有编入 TTS / 音频 AT 功能。刷完固件后先发
AT+CTTS=?、AT+CRSL=?各一次,确认不回+CME ERROR再往下做实验;回+CME ERROR: operation not supported说明这份固件不含对应功能,换用带音频功能的 AT 固件。
五、相关指令
| 指令 | 作用 | 常用写法 |
|---|---|---|
AT+CTTS |
TTS 文字转语音,播报结束后上报 +CTTS: 0 |
AT+CTTS=2,"123,欢迎你的到来" |
AT+CTTSPARAM |
设置 TTS 的音量、读数字模式、音高、语速、通道、Codec 与 PA 时序 | AT+CTTSPARAM=50,0,50,50 |
AT+CAUDPLAY |
播放 / 停止 / 暂停 / 恢复文件系统里的音频文件 | AT+CAUDPLAY=1,"test.mp3" |
AT+CRSL |
本地音频播放音量(TTS、语音文件),1~15 | AT+CRSL=12 |
AT+CLVL |
通话音量,按输出设备分别设置 | AT+CLVL=0,70 |
各指令的完整参数表、版本变更见 AT 指令手册。下面只讲用法和容易踩的坑。
六、AT 操作示例
以下示例都假定模组已经开机、SIM 卡已识别(发 AT+CPIN? 回 +CPIN: READY)、串口已连上。TTS 与语音文件播放不需要 PDP 激活,通话相关的那一步才需要入网。
6.1 查询与设置本地播放音量(AT+CRSL)
AT+CRSL 只管模组自己播放的声音(TTS、语音文件),与通话音量无关。
AT+CRSL=?
+CRSL: <1-15>
OK
AT+CRSL?
+CRSL: 15
OK
AT+CRSL=12
OK
AT+CRSL?
+CRSL: 12
OK
取值范围 1~15,1 最小、15 最大,出厂缺省是 15。注意两点:
- 数值直接就是音量档位,不是百分比;
- 这个值只存在内存里,模组重启后回到 15,掉电不保存。需要固定音量的话,MCU 每次开机后自己下发一次。
6.2 TTS 播放一段中文(AT+CTTS)
AT+CTTS=<mode>[,<text>][,<pcm>],<mode> 决定文本编码:
| mode | 含义 |
|---|---|
| 0 | 停止当前 TTS 播放 |
| 1 | 播放,<text> 用 UCS2 编码 |
| 2 | 播放,中文用 GBK、数字用 ASCII —— 串口工具里直接敲中文就用这个 |
| 3 | 播放,<text> 用 UTF-8 编码(是否支持以实际固件为准) |
播放一个最短的例子:
AT+CTTS=2,"123,欢迎你的到来"
OK
+CTTS: 0 ← 播完自动上报,看到这一行才算这一句念完了
播放过程中想打断,发 AT+CTTS=0 即可:
AT+CTTS=0
OK
查询当前状态:AT+CTTS? 回 +CTTS: <status>,0 表示空闲、1 表示正在播放。
几个实际会碰到的点:
<text>最长 2047 字节,GBK 下一个汉字占 2 字节,太长会报参数错误,长文本请分段下发;- 目前 TTS 引擎对英文只按字母逐个念,不按单词发音,要念英文单词请用语音文件播放(见 6.4);
- 可选第三个参数
<pcm>:0 正常播放(缺省),1 把 TTS 结果以 PCM 数据输出而不是直接放音,用于二次处理,普通播报不用管; - 连续下发两句时,建议等前一句的
+CTTS: 0回来再发第二句,否则后一句会把前一句顶掉。
6.3 调整 TTS 音色(AT+CTTSPARAM)
AT+CTTSPARAM=<volume>,<mode>,<pitch>,<speed>[,<channel>]...,最常用的就是前四个参数:
| 参数 | 含义 | 取值 | 缺省 |
|---|---|---|---|
<volume> |
TTS 播放音量 | 0~100 | 50 |
<mode> |
数字读法 | 0~3(0 自动、1 自动/电报优先、2 按电报规则、3 按数字规则) | 0 |
<pitch> |
音高 | 1~100 | 50 |
<speed> |
语速 | 1~100 | 50 |
<channel> |
播放通道 | 0 主通道、1 辅通道 | 0 |
示例:把 TTS 设成中等音量、正常语速、读数字用数字规则:
AT+CTTSPARAM=60,3,50,55
OK
AT+CTTSPARAM?
+CTTSPARAM: <volume>,<mode>,<pitch>,<speed>,<channel>,<codec>,<papin>,<codecstart>,<pa_open>,<codec_pa_close>,<def_pa_out>
OK
查询回来的字段比设置的多:前四位就是上面设的值,后面依次是 Codec 类型、PA 引脚、播放前的静音时长、PA 打开延时、播完后关闭 PA 的间隔、PA 有效电平,这些是给外接 PA 的板子准备的:
<papin>:PA 使能引脚的具体 GPIO 号,按硬件手册填;不填则用固件里的缺省配置(EC718 平台的板级配置为 GPIO28,以对应硬件手册为准);<codecstart>:播放前先输出多长的静音,避免开头被切掉,缺省 1500ms;<pa_open>:命令下发后多久打开 PA,缺省 150ms;<def_pa_out>:PA 有效电平,0 表示播放时高、静音时低,1 反之;如果你的板子喇叭一直有底噪或播完不静音,多半是这个极性反了。
板载喇叭已经连好 PA 的整机不用改这些,出厂值就能用。
6.4 播放语音文件(AT+CAUDPLAY)
AT+CAUDPLAY=<mode>[,<filename>]:
| mode | 含义 |
|---|---|
| 1 | 开始播放 |
| 2 | 停止播放 |
| 3 | 暂停播放 |
| 4 | 恢复播放 |
<filename> 要带后缀,支持 AMR、WAV、MP3,音频数据建议 8kHz 采样。文件必须先放进模组的文件系统(用 AT+FSCREATE / AT+FSWRITE 写入,或用 Luatools 的文件系统工具上传),不能直接读 TF 卡路径。
播放流程:
AT+CAUDPLAY=1,"test.mp3"
OK
+CAUDPLAY: 1,2585 ← 播放结束上报,2585 是播放时长(毫秒)
中途停止、暂停与恢复:
AT+CAUDPLAY=3 ← 暂停
OK
AT+CAUDPLAY=4 ← 恢复,播完同样上报 +CAUDPLAY: 1,<duration>
OK
AT+CAUDPLAY=2 ← 直接停
OK
容易踩的坑:
- 文件名漏后缀,或者音频采样率明显高于 8kHz 时,可能播不出声或变速;
- 文件系统里没有这个文件时命令仍然回 OK,但不会有
+CAUDPLAY: 1,...上报,要看文件是否真的写进去了; - EC618 平台的 Air780E 系列需要 AUAT V1146 及以上才有这条指令;EC7xx 平台是否需要取决于固件是否编入语音文件功能,先发
AT+CAUDPLAY=?看有没有返回取值列表。
6.5 设置与查询通话音量(AT+CLVL)
AT+CLVL 管的是 VoLTE 通话时对方声音的输出音量,按输出设备分别设置,设置值写入 NV,掉电保存。
语法:AT+CLVL=<deviceType>,<level>,两个参数都必选,不能省略、也不能只给一个。
| 参数 | 含义 | 取值 |
|---|---|---|
<deviceType> |
音频输出设备 | 0 手持听筒(缺省)、1 三段耳机、2 四段耳机、3 免提喇叭 |
<level> |
音量等级 | 0~100,0 最小、100 最大,缺省 70 |
常规操作:
AT+CLVL=0,70 ← 听筒音量 70
OK
AT+CLVL=3,100 ← 免提喇叭最大音量
OK
AT+CLVL? ← 查询
+CLVL: 70
OK
参数越界回 CME 50:
AT+CLVL=5,50 ← deviceType 超出 0~3
+CME ERROR: Incorrect parameters
AT+CLVL=0,120 ← level 超出 0~100
+CME ERROR: Incorrect parameters
AT+CLVL=? 在当前版本没有实现,会回 +CME ERROR: operation not supported,这是正常的,不代表指令不支持。
用之前必须知道四件事:
-
要立刻听到变化,必须在有音频流的时候设。通话中、放音或 TTS 播放中、录音中下发,命令会直接写 codec 芯片并回存 NV;空闲状态下只写 NV、不动硬件,下一次音频通路起来时才按 NV 的值生效。所以空闲下发也回
OK,但当场听不出区别,别以为没生效。 -
AT+CLVL?只回一个音量值,不能指定设备类型。有音频流时读的是 codec 当前缓存值;空闲时读的是 NV 里听筒(deviceType = 0)的值。所以给喇叭设了 100、听筒设了 70,空闲查询只会回 70,这是符合设计的。 -
空闲状态下每次下发都会写一次 NV,不做同值去重。做滑动条式的连续调节时,要么放到通话/放音过程中调,要么在 MCU 侧自己做去重,避免频繁擦写 flash。
-
<level>是百分比刻度,不是绝对音量。实际增益按出厂标定曲线换算,同一档位在不同硬件上的响度可能有差别;换板子、换喇叭后觉得"同样的 70 听起来不一样"属于正常。
6.6 两条音量指令怎么分工
| 对比项 | AT+CRSL |
AT+CLVL |
|---|---|---|
| 管什么 | 本地播放(TTS、语音文件)的音量 | 通话时听筒/耳机/喇叭的输出增益 |
| 取值 | 1~15 | 0~100 |
| 掉电保存 | 不保存,重启回 15 | 保存进 NV |
| 何时生效 | 立即 | 有音频流时立即,空闲时下次通路生效 |
| 典型用途 | 让播报声音大小合适 | 让通话对方声音大小合适 |
两者独立、叠加生效:调播报音量优先用 AT+CRSL;调通话响度、或觉得喇叭整体偏轻用 AT+CLVL。
七、常见问题 Q&A
7.1 问:下发 AT+CTTS 或 AT+CRSL,模组回 +CME ERROR: operation not supported?
先确认型号。这套语音指令只在内置 ES8311 的 Air780EVT / Air780EVT-1.8V 上提供;Air780E、Air780EG、Air780EP 等纯数据型号没有音频通路,AT 固件里根本没有这些指令,换型号才能解决。
型号没错的话,是固件没编入 TTS / 音频 AT 功能。换 AT 固件版本页上最新的 AirM2M_780EVT_*_LTE_AT 固件重刷。
7.2 问:TTS 念英文怎么是一个字母一个字母读的?
当前 TTS 引擎不按单词发音,英文单词会被拆成单个字母念,这是引擎能力限制,不是参数没配对。需要朗读英文单词时,用 TTS 合成或录制好的语音文件,走 AT+CAUDPLAY 播放。
7.3 问:AT+CLVL 设了值也回了 OK,但听起来没变化?
两种情况:
- 当前没有音频流。空闲下发只写 NV、不动 codec,要等下一次通话或放音才生效。想当场听效果,就在通话中或播报过程中设置;
- 调错了设备类型。
AT+CLVL是按输出设备分别保存的,你在听筒(0)上设的值不会作用到免提喇叭(3)。确认当前实际出声的是哪个通道,再对那个deviceType下发。
7.4 问:给喇叭设了 100,AT+CLVL? 却回 70?
AT+CLVL? 不带设备类型参数,空闲时固定读听筒(deviceType = 0)的值。回 70 说明听筒是 70,喇叭的 100 已经在 NV 里了。要确认喇叭的值,在有音频流的时候查询,或者直接听效果。
7.5 问:喇叭没声音,插耳机却有声音?
大概率是外接 PA 没打开。检查 6.3 里 AT+CTTSPARAM 的这几个参数:<papin> 是否填了正确的 PA 使能 GPIO(不填用固件里的缺省配置,EC718 平台为 GPIO28)、<def_pa_out> 的极性是否与板上 PA 一致、<pa_open> 延时是否太短。板载 PA 已接好的整机,恢复出厂缺省参数再试。
7.6 问:AT+CAUDPLAY 回了 OK,但一直没有 +CAUDPLAY: 1,... 上报?
按顺序排查:
- 文件确实在模组文件系统里吗?用
AT+FSLS列一下目录,确认文件名(含后缀)完全一致; - 格式是否在 AMR / WAV / MP3 之内,采样率是否 8kHz 左右。高采样率的 WAV 能打开但播不动或变速;
- 当前是否在通话中或 TTS 正在播,音频通道被占用时文件播放会起不来,先
AT+CTTS=0停掉再试。
7.7 问:AT+CLVL=? 回 +CME ERROR: operation not supported,是不是固件不支持这条指令?
不是。AT+CLVL 的测试命令在当前版本没有实现,只有设置(AT+CLVL=)和查询(AT+CLVL?)两条有效。判断固件是否支持这条指令,用 AT+CLVL? 查询,或下发一次设置命令看是否回 OK。