Skip to content

音频格式转化地址: https://online-audio-converter.com/cn/#

ESP32 播放音频

MAX98357A 模块

MAX98357A 模块的使用方法,这是一个采用标准的 I2S 作为数字音频输入,内置解码器,可将数字音频信号解码为模拟信号,并拥有内置放大器,可以直接驱动扬声器的D类放大器。 因其工作效率高,可以以 2.7V~5.5V 的直流电压运行,因此非常适合便携式及电池供电的音频播放项目。

所谓的D类放大器,是指通过控制开关单元的ON/OFF,直接驱动扬声器的放大器。D类放大器是音频功率放大器的一种。 音频功率放大器是最常使用的一种功率放大器,除此之外,还有用于射频信号传输的射频功率放大器和用来驱动电机和执行器的直流功率放大器。 为了区分不同音频放大器的电路特性和行为,采用字母符号来进行标识。因此,音频功率放大器可以分为A、B、AB、C、D等,多种类型。

MAX98357A模块具有诸多的优点,其特点如下:

  1. 输出功率:4欧时为3.2W,THD为10% 8欧时为1.8W,THD为10%
  2. I2S采样率:8KHz-96kHz
  3. D类放大器增益可选:3dB/6dB/9dB/12dB/15dB
  4. 无需主控时钟(MCLK)
  5. 即插即用:只需单电源供电,即可自动配置35种不同的时钟和128种数字音频格式。
  6. 适用于蓝莓派、Arduino以及ESP32等具有I2S音频输出的微控制器或开发板系统

将ESP32与MAX98357A这两者结合起来,可以实现很多有用的功能,下面是一些简单的举例:

  1. 智能音箱:ESP32具有Wifi联网的功能,因此可以作为控制中心,保持设备时刻都可以接入互联网。配合语音助手服务,利用MAX98357A的音频输出能力,就可以很轻易的实现智能音箱的功能。
  2. 蓝牙音箱:ESP32芯片具有蓝牙功能,因此可以方便的利用蓝牙获取音频数据,并使用MAX98357A模块播放出来,这就是一个最简单的蓝牙音箱。
  3. 语音提醒:ESP32芯片可以采集各种传感器的数据,然后根据不同的情况,使用MAX98357A来播放不同的声音提醒。

MAX98357A 模块如下图所示:

MAX98357A 模块的引脚说明如下:

MAX98357A 模块引脚引脚说明
VIN电源正(2.5V-5.5V)
GND电源地
SD关机和频道选择。SD MODE 拉低以将器件处于关断状态。
GAIN增益和频道选择。在TDM模式下,增益固定为 12dB
DIN数字信号输入
BCLK位时钟输入
LRCI2S与LJ模式的左/右时钟。同步时钟用于TDM模式

接下来通过一个程序来看一下 MAX98357A 模块的使用方法。在这里,要实现一个播放 SD 卡中 mp3 文件的功能。 也就是要通过 SD 卡来获取 mp3 声音文件,然后通过 MAX98357A 模块播放出来的功能,这是一个简易 mp3 的雏形。下面就来看一下具体的实现方法。

在这里就要用到 ESP32、SD 卡功能模块和 MAX98357A 这三个模块。具体的连接方法如下:

MAX98357A 与 ESP32 接线

ESP32MAX98357A
+5VVIN
GNDGND
P25DIN
P26BCLK
P27LRC

播放音频

音频下载: test.wav

python
# https://blog.csdn.net/zhusongziye/article/details/128024713

from machine import I2S  # 导入I2S协议库,什么是I2S自行百度
from machine import Pin
import os

os.chdir('/')

"""
GPIO11 -- DIN
GPIO10 --- BCLK
GPIO12 -- LRC
GND -- GND
5V或3.3V -- VCC
"""

# 初始化引脚定义
sck_pin = Pin(11)  # 串行时钟输出
ws_pin = Pin(12)  # 字时钟
sd_pin = Pin(10)  # 串行数据输出

"""
sck 是串行时钟线的引脚对象
ws 是单词选择行的引脚对象
sd 是串行数据线的引脚对象
mode 指定接收或发送
bits 指定样本大小(位),16 或 32
format 指定通道格式,STEREO(左右声道) 或 MONO(单声道)
rate 指定音频采样率(样本/秒)
ibuf 指定内部缓冲区长度(字节)
"""

# 初始化i2s
audio_out = I2S(1, sck=sck_pin, ws=ws_pin, sd=sd_pin, mode=I2S.TX, bits=16, format=I2S.MONO, rate=16000, ibuf=20000)

wavtempfile = "test.wav"
with open(wavtempfile, 'rb') as f:
    # 跳过文件的开头的44个字节,直到数据段的第1个字节
    pos = f.seek(44)

    # 用于减少while循环中堆分配的内存视图
    wav_samples = bytearray(1024)
    wav_samples_mv = memoryview(wav_samples)

    print("开始播放音频...")

    # 并将其写入I2S DAC
    while True:
        try:
            num_read = f.readinto(wav_samples_mv)

            # WAV文件结束
            if num_read == 0:
                break

            # 直到所有样本都写入I2S外围设备
            num_written = 0
            while num_written < num_read:
                num_written += audio_out.write(wav_samples_mv[num_written:num_read])

        except Exception as ret:
            print("产生异常...", ret)
            break

MAX98357a 播放音频

python
from machine import I2S
from machine import Pin
import urequests
import network
import time


"""
GPIO12 --- BCLK
GPIO15 --- LRC
GPIO13 --- DIN
GND    --- GND
5V     --- VCC
"""

# 初始化引脚定义
sck_pin = Pin(12) # 串行时钟输出
ws_pin  = Pin(15)  # 字时钟
sd_pin  = Pin(13)  # 串行数据输出


"""
sck 是串行时钟线的引脚对象
ws  是单词选择行的引脚对象
sd  是串行数据线的引脚对象
mode 指定接收或发送
bits 指定样本大小(位),16 或 32
format 指定通道格式,STEREO(左右声道) 或 MONO(单声道)
rate 指定音频采样率(样本/秒),数值越大播放速度越快
ibuf 指定内部缓冲区长度(字节)
"""

# 初始化i2s
audio_out = I2S(1, sck=sck_pin, ws=ws_pin, sd=sd_pin, mode=I2S.TX, bits=16, format=I2S.MONO, rate=44100, ibuf=20000)

# 连接网络函数
def do_connect():
    """链接WIFI网络"""
    wlan = network.WLAN(network.STA_IF)
    wlan.active(True)
    if not wlan.isconnected():
        print('connecting to network...')
        wlan.connect('CCMC_jzwy', '285251897_jzwy')  # WIFI名字密码
        i = 1
        while not wlan.isconnected():
            print("正在链接中...{}".format(i))
            i += 1
            time.sleep(1)
    print('network config:', wlan.ifconfig())


# 连接网络
do_connect()

# 注意不要用https,要用http
response = urequests.get("http://doc.itprojects.cn/0006.zhishi.esp32/01.download/audio/chaojimali.wav", stream=True)
response.raw.read(44)  # 跳过开头的44字节音频文件头信息

print("开始播放音频...")

# 并将其写入 I2S DAC
while True:
    try:
        content_byte = response.raw.read(1024)  # 每次读取1024个字节

        # 判断WAV文件是否结束
        if len(content_byte) == 0:
            break
        # 调用I2S对象播放音频
        audio_out.write(content_byte)

    except Exception as ret:
        print("程序产生异常...", ret)
        audio_out.deinit()
        break

audio_out.deinit()  # 音乐播放完毕后,退出

https://blog.csdn.net/qq_16601363/article/details/136263937

https://www.cnblogs.com/FBsharl/p/18336848

# ffmpeg -i baby_welcome.wav -f mp3 -acodec libmp3lame  baby_welcome.mp3

附录

https://blog.csdn.net/qq_16601363/article/details/136263937

物联网开发笔记(51)- 使用Micropython开发ESP32开发板之通过MAX98357 I2S音频模块播放音乐:https://blog.csdn.net/zhusongziye/article/details/128024713

ESP32-DEVKIT V1 -doit: https://blog.csdn.net/m0_46509684/article/details/129105888

详解ESP32模块的引脚分配图和定义: https://blog.csdn.net/lwpoor123/article/details/133132806

【ESP32音视频传输】①用I2S通过内部DAC或MAX98357A播放音乐/录音数据及接受网络广播: https://blog.csdn.net/loveliveoil/article/details/124107132

K210(SiPEED MaixBit) MicroPython使用参考(十、MAX98357A的I2S驱动): https://blog.csdn.net/weixin_41784968/article/details/126440488