ESP32使用XT_DAC_Audio播放音频

3 篇文章 0 订阅
3 篇文章 0 订阅

软硬件:ESP-WROOM-32、Arduino、Audacity、WinHEX
通过在Arduino中使用XT_DAC_Audio库,使ESP32无需外接模块,使用DAC直接通过引脚驱动扬声器播放音频,当然引脚的驱动能力有限,声音会很小,可以接三极管或功放来放大音量。

在这里插入图片描述

安装XT_DAC_Audio库

这个库在Arduino的库管理中搜索不到,也就无法一键安装,那么就需要手动下载.zip进行安装。
这是它的官网下载 XT_DAC_Audio
在这里插入图片描述
如果官网下载不了,可尝试到GitHub搜索下载.zip包,或者CSDN资源 直接下载
下载好后在Arduino中通过项目—加载库—添加.ZIP库选择zip文件添加。

播放示例程序音频

在Arduino中打开以下示例程序,直接编译上传。
在这里插入图片描述

如果出现以下报错cc1plus.exe: some warnings being treated as errors
在这里插入图片描述
那么打开XT_DAC_Audio库的目录,这个根据Arduino目录设置以及电脑用户名不同有所差异,可参照我的路径找:C:\Users\ZJC\Documents\Arduino\libraries\XT_DAC_Audio
然后打开报错的XT_DAC_Audio.cpp文件667行,将它注释掉,保存重新编译上传即可
在这里插入图片描述
如果编译上传一切正常,将扬声器的两根线分别连接ESP32的GPIO25(D25),即可听到示例程序中的音频,不过音量较小。

播放自定义音频

当然更重要的是如何播放任意的音频内容,比如实现语音播报、音乐播放等功能。这里将要用到音频编辑软件Audacity、十六进制编辑器WinHEX,两者都可在百度搜索下载安装。 下载WinHEX

1、首先要有Audacity支持的音频文件,一般是.mp3文件,将它在Audacity中打开。如果有两个波形说明是立体声,点击轨道—混音—混合立体声至单声道,合并为单声道。否则最后生成的音频数组长度会增大2倍,播放速度变慢到正常的0.5倍。
在这里插入图片描述
2、如果是一个波形则为单声道,直接设置采样率,一般电脑手机播放的音乐文件采样率为44.1kHz,但因为ESP32的存储空间有限,双倍的采样率也意味着双倍的存储空间占用,一般建议设置为较低的采样率例如16kHz,但也不能太低,否则声音会失真且噪音较大,在Audacity中可以设置采样率后立即播放试听,在保证音质够用的情况下尽量设置较小的采样率,以节省存储空间。
另外Audacity也提供了一些对音频的剪辑操作,例如复制粘贴剪切等,可以直接使用。
在这里插入图片描述
3、设置好后点击文件—导出—导出为WAV
在这里插入图片描述
确认保存类型设置为WAV(Microsoft),编码设置为Unsigned 8-bit PCM,然后保存。
在这里插入图片描述
4、打开WinHEX,找到并打开刚才保存的.wav文件,点击Copy All—C Source,就将十六进制数组复制到剪贴板。
在这里插入图片描述
5、打开Arduino的PlayWav示例程序,点击SoundData.h,Force数组就存储着音频数据,主程序中通过引用Force数组来播放音频,那么只需将刚才在WinHEX中得到的音频数组替换掉原数组即可。
在这里插入图片描述
替换后记住加const定义为常量,PROGMEM写入到闪存,否则占用存储稍大就无法编译通过。以下显示这个音频文件占用194326Byte的空间。然后编译上传即可听到自定义的音频了。
在这里插入图片描述

音频播放效果

以下为连接一个S8050三极管的音频播放效果

VID_20230502_205945

增大音量

上面都是用GPIO口直接驱动扬声器播放音频,但是GPIO口的电流有限,声音也会很小,此时最简单最便宜的方法是接一个合适的三极管,将基极连接GPIO25(D25)作为音频信号输入,发射极、集电极连接扬声器的一条线和电源,就可以放大电流增大音量了。但是这种方法需要根据电流电压选择合适的三极管、不可调节音量、容易受干扰产生杂音。
因此可选择接一个功放来调节音量。
在这里插入图片描述

  • 3
    点赞
  • 27
    收藏
    觉得还不错? 一键收藏
  • 7
    评论
以下是esp32s2使用内置DAC播放音频的全部代码示例: ```c #include <driver/i2s.h> #define SAMPLE_RATE 44100 #define I2S_PORT I2S_NUM_0 #define I2S_SAMPLE_BITS I2S_BITS_PER_SAMPLE_16BIT #define I2S_CHANNEL_NUM I2S_CHANNEL_FMT_ONLY_RIGHT #define I2S_READ_LEN 1024 void app_main(void) { i2s_config_t i2s_config = { .mode = I2S_MODE_MASTER | I2S_MODE_TX, .sample_rate = SAMPLE_RATE, .bits_per_sample = I2S_SAMPLE_BITS, .channel_format = I2S_CHANNEL_NUM, .communication_format = I2S_COMM_FORMAT_I2S_MSB, .dma_buf_count = 8, .dma_buf_len = 64, .intr_alloc_flags = ESP_INTR_FLAG_LEVEL1, }; i2s_pin_config_t pin_config = { .bck_io_num = 26, .ws_io_num = 25, .data_out_num = 22, .data_in_num = I2S_PIN_NO_CHANGE, }; i2s_driver_install(I2S_PORT, &i2s_config, 0, NULL); i2s_set_pin(I2S_PORT, &pin_config); i2s_set_sample_rates(I2S_PORT, SAMPLE_RATE); size_t written = 0; size_t read = 0; int16_t *sample_buf = (int16_t *)malloc(I2S_READ_LEN * sizeof(int16_t)); while (1) { // 这里需要添加读取音频数据的代码,将读取到的音频数据放入sample_buf中 i2s_write(I2S_PORT, sample_buf, I2S_READ_LEN * sizeof(int16_t), &written, portMAX_DELAY); } } ``` 在这个示例中,我们使用esp32s2的I2S外设,将其配置为主机模式和传输模式。我们将I2S的采样率设置为44100,采样位数为16位,通道格式为仅右声道。我们使用DMA缓冲区,每个缓冲区的长度为64,共有8个缓冲区。我们将I2S的时钟、数据线和帧同步信号分别连接到了GPIO 26、25和22。 在主循环中,我们使用i2s_write函数将读取到的音频数据写入I2S输出缓冲区。这里需要添加读取音频数据的代码,将读取到的音频数据放入sample_buf中。在主循环中,我们可以使用任何方法(例如从SD卡读取文件、从网络接收数据等)读取音频数据。 请注意,这只是一个示例,实际应用中需要根据具体情况进行修改和优化。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值