修复麦克风PDM数据位宽读取bug,唤醒也能正常使用 (#284)

* 修复麦克风PDM数据位宽读取bug,唤醒也能正常使用

* 重载NoAudioCodecSimplexPdm::Read()
This commit is contained in:
HonestQiao
2025-03-07 00:12:30 +08:00
committed by GitHub
parent d822fc7512
commit 1b338fa71b
3 changed files with 48 additions and 28 deletions

View File

@@ -12,7 +12,7 @@ choice
default LANGUAGE_ZH_CN default LANGUAGE_ZH_CN
help help
Select device display language Select device display language
config LANGUAGE_ZH_CN config LANGUAGE_ZH_CN
bool "Chinese" bool "Chinese"
config LANGUAGE_EN_US config LANGUAGE_EN_US
@@ -79,11 +79,11 @@ choice BOARD_TYPE
config BOARD_TYPE_MAGICLICK_2P4 config BOARD_TYPE_MAGICLICK_2P4
bool "神奇按钮 Magiclick_2.4" bool "神奇按钮 Magiclick_2.4"
config BOARD_TYPE_MAGICLICK_2P5 config BOARD_TYPE_MAGICLICK_2P5
bool "神奇按钮 Magiclick_2.5" bool "神奇按钮 Magiclick_2.5"
config BOARD_TYPE_MAGICLICK_C3 config BOARD_TYPE_MAGICLICK_C3
bool "神奇按钮 Magiclick_C3" bool "神奇按钮 Magiclick_C3"
config BOARD_TYPE_MAGICLICK_C3_V2 config BOARD_TYPE_MAGICLICK_C3_V2
bool "神奇按钮 Magiclick_C3_v2" bool "神奇按钮 Magiclick_C3_v2"
config BOARD_TYPE_M5STACK_CORE_S3 config BOARD_TYPE_M5STACK_CORE_S3
bool "M5Stack CoreS3" bool "M5Stack CoreS3"
config BOARD_TYPE_ATOMS3_ECHO_BASE config BOARD_TYPE_ATOMS3_ECHO_BASE
@@ -97,7 +97,7 @@ choice BOARD_TYPE
config BOARD_TYPE_ESP32S3_KORVO2_V3 config BOARD_TYPE_ESP32S3_KORVO2_V3
bool "ESP32S3_KORVO2_V3开发板" bool "ESP32S3_KORVO2_V3开发板"
config BOARD_TYPE_ESP_SPARKBOT config BOARD_TYPE_ESP_SPARKBOT
bool "ESP-SparkBot开发板" bool "ESP-SparkBot开发板"
config BOARD_TYPE_ESP32S3_Touch_AMOLED_1_8 config BOARD_TYPE_ESP32S3_Touch_AMOLED_1_8
bool "Waveshare ESP32-S3-Touch-AMOLED-1.8" bool "Waveshare ESP32-S3-Touch-AMOLED-1.8"
config BOARD_TYPE_ESP32S3_Touch_LCD_1_85C config BOARD_TYPE_ESP32S3_Touch_LCD_1_85C
@@ -113,13 +113,13 @@ choice BOARD_TYPE
config BOARD_TYPE_LILYGO_T_CAMERAPLUS_S3 config BOARD_TYPE_LILYGO_T_CAMERAPLUS_S3
bool "LILYGO T-CameraPlus-S3" bool "LILYGO T-CameraPlus-S3"
config BOARD_TYPE_MOVECALL_MOJI_ESP32S3 config BOARD_TYPE_MOVECALL_MOJI_ESP32S3
bool "Movecall Moji 小智AI衍生版" bool "Movecall Moji 小智AI衍生版"
config BOARD_TYPE_ATK_DNESP32S3 config BOARD_TYPE_ATK_DNESP32S3
bool "正点原子DNESP32S3开发板" bool "正点原子DNESP32S3开发板"
config BOARD_TYPE_ATK_DNESP32S3_BOX config BOARD_TYPE_ATK_DNESP32S3_BOX
bool "正点原子DNESP32S3-BOX" bool "正点原子DNESP32S3-BOX"
config BOARD_TYPE_DU_CHATX config BOARD_TYPE_DU_CHATX
bool "嘟嘟开发板CHATX(wifi)" bool "嘟嘟开发板CHATX(wifi)"
config BOARD_TYPE_ESP32S3_Taiji_Pi config BOARD_TYPE_ESP32S3_Taiji_Pi
bool "太极小派esp32s3" bool "太极小派esp32s3"
config BOARD_TYPE_XINGZHI_Cube_0_96OLED_WIFI config BOARD_TYPE_XINGZHI_Cube_0_96OLED_WIFI
@@ -155,33 +155,33 @@ choice DISPLAY_LCD_TYPE
config LCD_ST7789_240X320 config LCD_ST7789_240X320
bool "ST7789, 分辨率240*320, IPS" bool "ST7789, 分辨率240*320, IPS"
config LCD_ST7789_240X320_NO_IPS config LCD_ST7789_240X320_NO_IPS
bool "ST7789, 分辨率240*320, 非IPS" bool "ST7789, 分辨率240*320, 非IPS"
config LCD_ST7789_170X320 config LCD_ST7789_170X320
bool "ST7789, 分辨率170*320" bool "ST7789, 分辨率170*320"
config LCD_ST7789_172X320 config LCD_ST7789_172X320
bool "ST7789, 分辨率172*320" bool "ST7789, 分辨率172*320"
config LCD_ST7789_240X280 config LCD_ST7789_240X280
bool "ST7789, 分辨率240*280" bool "ST7789, 分辨率240*280"
config LCD_ST7789_240X240 config LCD_ST7789_240X240
bool "ST7789, 分辨率240*240" bool "ST7789, 分辨率240*240"
config LCD_ST7789_240X240_7PIN config LCD_ST7789_240X240_7PIN
bool "ST7789, 分辨率240*240, 7PIN" bool "ST7789, 分辨率240*240, 7PIN"
config LCD_ST7789_240X135 config LCD_ST7789_240X135
bool "ST7789, 分辨率240*135" bool "ST7789, 分辨率240*135"
config LCD_ST7735_128X160 config LCD_ST7735_128X160
bool "ST7735, 分辨率128*160" bool "ST7735, 分辨率128*160"
config LCD_ST7735_128X128 config LCD_ST7735_128X128
bool "ST7735, 分辨率128*128" bool "ST7735, 分辨率128*128"
config LCD_ST7796_320X480 config LCD_ST7796_320X480
bool "ST7796, 分辨率320*480" bool "ST7796, 分辨率320*480"
config LCD_ILI9341_240X320 config LCD_ILI9341_240X320
bool "ILI9341, 分辨率240*320" bool "ILI9341, 分辨率240*320"
config LCD_ILI9341_240X320_NO_IPS config LCD_ILI9341_240X320_NO_IPS
bool "ILI9341, 分辨率240*320, 非IPS" bool "ILI9341, 分辨率240*320, 非IPS"
config LCD_GC9A01_240X240 config LCD_GC9A01_240X240
bool "GC9A01, 分辨率240*240, 圆屏" bool "GC9A01, 分辨率240*240, 圆屏"
config LCD_CUSTOM config LCD_CUSTOM
bool "自定义屏幕参数" bool "自定义屏幕参数"
endchoice endchoice
config USE_AUDIO_PROCESSOR config USE_AUDIO_PROCESSOR
@@ -197,5 +197,4 @@ config USE_WAKE_WORD_DETECT
depends on IDF_TARGET_ESP32S3 && USE_AFE depends on IDF_TARGET_ESP32S3 && USE_AFE
help help
需要 ESP32 S3 与 AFE 支持 需要 ESP32 S3 与 AFE 支持
endmenu endmenu

View File

@@ -2,6 +2,7 @@
#include <esp_log.h> #include <esp_log.h>
#include <cmath> #include <cmath>
#include <cstring>
#define TAG "NoAudioCodec" #define TAG "NoAudioCodec"
@@ -35,7 +36,7 @@ NoAudioCodecDuplex::NoAudioCodecDuplex(int input_sample_rate, int output_sample_
.sample_rate_hz = (uint32_t)output_sample_rate_, .sample_rate_hz = (uint32_t)output_sample_rate_,
.clk_src = I2S_CLK_SRC_DEFAULT, .clk_src = I2S_CLK_SRC_DEFAULT,
.mclk_multiple = I2S_MCLK_MULTIPLE_256, .mclk_multiple = I2S_MCLK_MULTIPLE_256,
#ifdef I2S_HW_VERSION_2 #ifdef I2S_HW_VERSION_2
.ext_clk_freq_hz = 0, .ext_clk_freq_hz = 0,
#endif #endif
@@ -48,7 +49,7 @@ NoAudioCodecDuplex::NoAudioCodecDuplex(int input_sample_rate, int output_sample_
.ws_width = I2S_DATA_BIT_WIDTH_32BIT, .ws_width = I2S_DATA_BIT_WIDTH_32BIT,
.ws_pol = false, .ws_pol = false,
.bit_shift = true, .bit_shift = true,
#ifdef I2S_HW_VERSION_2 #ifdef I2S_HW_VERSION_2
.left_align = true, .left_align = true,
.big_endian = false, .big_endian = false,
.bit_order_lsb = false .bit_order_lsb = false
@@ -94,7 +95,7 @@ ATK_NoAudioCodecDuplex::ATK_NoAudioCodecDuplex(int input_sample_rate, int output
.sample_rate_hz = (uint32_t)output_sample_rate_, .sample_rate_hz = (uint32_t)output_sample_rate_,
.clk_src = I2S_CLK_SRC_DEFAULT, .clk_src = I2S_CLK_SRC_DEFAULT,
.mclk_multiple = I2S_MCLK_MULTIPLE_256, .mclk_multiple = I2S_MCLK_MULTIPLE_256,
#ifdef I2S_HW_VERSION_2 #ifdef I2S_HW_VERSION_2
.ext_clk_freq_hz = 0, .ext_clk_freq_hz = 0,
#endif #endif
}, },
@@ -106,7 +107,7 @@ ATK_NoAudioCodecDuplex::ATK_NoAudioCodecDuplex(int input_sample_rate, int output
.ws_width = I2S_DATA_BIT_WIDTH_16BIT, .ws_width = I2S_DATA_BIT_WIDTH_16BIT,
.ws_pol = false, .ws_pol = false,
.bit_shift = true, .bit_shift = true,
#ifdef I2S_HW_VERSION_2 #ifdef I2S_HW_VERSION_2
.left_align = true, .left_align = true,
.big_endian = false, .big_endian = false,
.bit_order_lsb = false .bit_order_lsb = false
@@ -153,7 +154,7 @@ NoAudioCodecSimplex::NoAudioCodecSimplex(int input_sample_rate, int output_sampl
.sample_rate_hz = (uint32_t)output_sample_rate_, .sample_rate_hz = (uint32_t)output_sample_rate_,
.clk_src = I2S_CLK_SRC_DEFAULT, .clk_src = I2S_CLK_SRC_DEFAULT,
.mclk_multiple = I2S_MCLK_MULTIPLE_256, .mclk_multiple = I2S_MCLK_MULTIPLE_256,
#ifdef I2S_HW_VERSION_2 #ifdef I2S_HW_VERSION_2
.ext_clk_freq_hz = 0, .ext_clk_freq_hz = 0,
#endif #endif
@@ -166,7 +167,7 @@ NoAudioCodecSimplex::NoAudioCodecSimplex(int input_sample_rate, int output_sampl
.ws_width = I2S_DATA_BIT_WIDTH_32BIT, .ws_width = I2S_DATA_BIT_WIDTH_32BIT,
.ws_pol = false, .ws_pol = false,
.bit_shift = true, .bit_shift = true,
#ifdef I2S_HW_VERSION_2 #ifdef I2S_HW_VERSION_2
.left_align = true, .left_align = true,
.big_endian = false, .big_endian = false,
.bit_order_lsb = false .bit_order_lsb = false
@@ -222,7 +223,7 @@ NoAudioCodecSimplex::NoAudioCodecSimplex(int input_sample_rate, int output_sampl
.sample_rate_hz = (uint32_t)output_sample_rate_, .sample_rate_hz = (uint32_t)output_sample_rate_,
.clk_src = I2S_CLK_SRC_DEFAULT, .clk_src = I2S_CLK_SRC_DEFAULT,
.mclk_multiple = I2S_MCLK_MULTIPLE_256, .mclk_multiple = I2S_MCLK_MULTIPLE_256,
#ifdef I2S_HW_VERSION_2 #ifdef I2S_HW_VERSION_2
.ext_clk_freq_hz = 0, .ext_clk_freq_hz = 0,
#endif #endif
@@ -235,7 +236,7 @@ NoAudioCodecSimplex::NoAudioCodecSimplex(int input_sample_rate, int output_sampl
.ws_width = I2S_DATA_BIT_WIDTH_32BIT, .ws_width = I2S_DATA_BIT_WIDTH_32BIT,
.ws_pol = false, .ws_pol = false,
.bit_shift = true, .bit_shift = true,
#ifdef I2S_HW_VERSION_2 #ifdef I2S_HW_VERSION_2
.left_align = true, .left_align = true,
.big_endian = false, .big_endian = false,
.bit_order_lsb = false .bit_order_lsb = false
@@ -290,7 +291,7 @@ NoAudioCodecSimplexPdm::NoAudioCodecSimplexPdm(int input_sample_rate, int output
.sample_rate_hz = (uint32_t)output_sample_rate_, .sample_rate_hz = (uint32_t)output_sample_rate_,
.clk_src = I2S_CLK_SRC_DEFAULT, .clk_src = I2S_CLK_SRC_DEFAULT,
.mclk_multiple = I2S_MCLK_MULTIPLE_256, .mclk_multiple = I2S_MCLK_MULTIPLE_256,
#ifdef I2S_HW_VERSION_2 #ifdef I2S_HW_VERSION_2
.ext_clk_freq_hz = 0, .ext_clk_freq_hz = 0,
#endif #endif
@@ -321,7 +322,7 @@ NoAudioCodecSimplexPdm::NoAudioCodecSimplexPdm(int input_sample_rate, int output
.gpio_cfg = { .gpio_cfg = {
.clk = mic_sck, .clk = mic_sck,
.din = mic_din, .din = mic_din,
.invert_flags = { .invert_flags = {
.clk_inv = false, .clk_inv = false,
}, },
@@ -372,3 +373,22 @@ int NoAudioCodec::Read(int16_t* dest, int samples) {
} }
return samples; return samples;
} }
int NoAudioCodecSimplexPdm::Read(int16_t* dest, int samples) {
size_t bytes_read;
// PDM 解调后的数据位宽为 16 位
std::vector<int16_t> bit16_buffer(samples);
if (i2s_channel_read(rx_handle_, bit16_buffer.data(), samples * sizeof(int16_t), &bytes_read, portMAX_DELAY) != ESP_OK) {
ESP_LOGE(TAG, "Read Failed!");
return 0;
}
// 计算实际读取的样本数
samples = bytes_read / sizeof(int16_t);
// 将 16 位数据直接复制到目标缓冲区
memcpy(dest, bit16_buffer.data(), samples * sizeof(int16_t));
return samples;
}

View File

@@ -34,6 +34,7 @@ public:
class NoAudioCodecSimplexPdm : public NoAudioCodec { class NoAudioCodecSimplexPdm : public NoAudioCodec {
public: public:
NoAudioCodecSimplexPdm(int input_sample_rate, int output_sample_rate, gpio_num_t spk_bclk, gpio_num_t spk_ws, gpio_num_t spk_dout, gpio_num_t mic_sck, gpio_num_t mic_din); NoAudioCodecSimplexPdm(int input_sample_rate, int output_sample_rate, gpio_num_t spk_bclk, gpio_num_t spk_ws, gpio_num_t spk_dout, gpio_num_t mic_sck, gpio_num_t mic_din);
int Read(int16_t* dest, int samples);
}; };
#endif // _NO_AUDIO_CODEC_H #endif // _NO_AUDIO_CODEC_H