声源定向 (DOA)
概述
ESP-SR DOA(Direction of Arrival,声源定向)模块用于估计声源相对于麦克风阵列的方位角。该模块基于 Capon/MVDR(最小方差无失真响应)算法,并针对嵌入式平台做了优化,广泛应用于说话人定位、摄像头转向等场景,也可作为波束形成的前级模块(参见 GSC 波束形成)。
备注
本文档介绍的嵌入式 DOA 模块目前仅支持 ESP32-P4。
嵌入式 DOA 模块具有以下特点:
支持任意阵列几何形状:2 至 8 个麦克风,麦克风坐标在运行时配置
帧长:16 kHz 采样率下每通道 128 个采样点(每帧 8 ms)
FFT 点数:256
处理频带:1500–4500 Hz(针对语音优化)
角度分辨率:10 度(36 个候选角度:0°、10°、…、350°)
仅使用单精度浮点运算
处理过程中零动态内存分配(所有缓冲区在创建时预分配)
使用方式
头文件为 include/esp32p4/esp_doa_capon_embedded.h。
基本流程:
定义麦克风阵列几何坐标
麦克风坐标以米为单位,采用右手坐标系,每个麦克风一项。各坐标项可以是任意顺序,但传入
esp_doa_capon_embedded_process()的第i路音频必须始终来自mic_coord[i]对应的麦克风。#include "esp_doa_capon_embedded.h" /* 4 麦均匀圆阵,半径 5 cm;第 i 个麦克风位于 i*90 度方向 */ PlaneCoord mic_coords[4] = { { 0.05f, 0.0f, 0.0f}, { 0.0f, 0.05f, 0.0f}, {-0.05f, 0.0f, 0.0f}, { 0.0f, -0.05f, 0.0f}, };
创建 DOA 实例
所有内存(句柄和内部内存池)由模块自行分配,并由
esp_doa_capon_embedded_destroy()释放。缓冲区默认从 PSRAM 分配,参见下文 内存配置 一节。esp_doa_capon_embedded_handle_t *doa = esp_doa_capon_embedded_create(mic_coords, 4);
处理音频帧
输入为
mic_num通道 16-bit PCM 音频,planar(分通道) 排布([ch0_0..ch0_127, ch1_0..ch1_127, ...]),每帧每通道 128 个采样点。int16_t audio_frame[128 * 4]; // 4 通道,planar 排布 int vad = 1; // 1 = 语音,0 = 噪声/静音 float angle = esp_doa_capon_embedded_process(doa, audio_frame, vad);
返回角度单位为度,范围 0–360,定义在阵列绝对坐标系中(0° = x 轴正方向,逆时针),与
mic_coord中麦克风的排列顺序无关。出错时返回-1.0f。备注
当
vad_result为 0 时,所有自适应状态(协方差递推、矩阵求逆、空间谱)都会被冻结,并直接返回上一次估计的角度。建议接入 AFE 模块的 VAD 结果,避免纯噪声帧破坏估计。协方差递推需要若干帧才能收敛,创建(或复位)后最初几帧的估计结果应丢弃。
(可选)复位处理器状态
复位协方差矩阵和平滑滤波器,适用于长时间静音后重新开始估计等场景:
esp_doa_capon_embedded_reset(doa);
释放资源
esp_doa_capon_embedded_destroy()释放esp_doa_capon_embedded_create()分配的全部资源(传入 NULL 会被安全忽略):esp_doa_capon_embedded_destroy(doa);
警告
将 DOA 与 GSC 波束形成 级联使用时,两个模块必须传入**相同的**麦克风坐标数组,否则估计出的角度会对应错误的通道。
小技巧
esp_doa_capon_embedded_print_info(doa) 可打印处理器配置(帧长、FFT 点数、处理频带等),用于调试。
内存配置
在 ESP32-P4 上,DOA 内部缓冲区(内存池,4 麦约 200 KB)默认分配在 PSRAM 中。
如需改用内部 RAM,可在包含
esp_doa_capon_embedded.h之前定义ESP_DOA_DISABLE_PSRAM,或将其作为编译选项定义。
精度测试
测试程序 test_apps/esp-sr-gsc-doa 在芯片端评估 DOA 估计精度。测试数据集为仿真的 4 麦均匀圆阵(半径 5 cm)纯净语音,声源位于半径 2 m 的圆周上,角度从 0° 到 330°、步进 30°(从 +x 轴逆时针计量)。
测试方法:
对 12 个角度,每个角度向
esp_doa_capon_embedded_process()送入 64 帧(VAD 强制为语音)。跳过前 10 帧,等待协方差递推收敛。
将剩余帧的估计结果与真实角度比较,分别统计完全命中率和误差在一个网格步长(±10°)以内的准确率。
测试结果:
指标 |
结果 |
说明 |
|---|---|---|
完全命中率 |
94.0% (609/648) |
估计角度与真实角度完全一致 |
±10° 内准确率 |
94.0% (609/648) |
误差在一个网格步长以内 |
资源消耗
下表为典型的资源占用与性能数据(16 kHz 采样率):