使用ESP32与INMP441麦克风模块实现音频传输

本教程展示了如何使用ESP32开发板与INMP441麦克风模块进行音频采集,并通过UDP将音频数据传输到Windows主机进行播放。通过简单的代码,你可以实时接收和播放麦克风输入的音频。

小提示:确保ESP32和Windows主机连接在同一个WiFi网络下,以便成功传输数据。
1. 硬件连接
  • 材料

  • ESP32开发板
  • INMP441麦克风模块
  • 连接线
  • 连接方式

  • INMP441 VCC → ESP32的3.3V
  • INMP441 GND → ESP32的GND
  • INMP441 SCK → ESP32的GPIO 17
  • INMP441 WS → ESP32的GPIO 18
  • INMP441 SD → ESP32的GPIO 16
  • 2. 硬件端代码

    开发板:ESP32S3 Dev Module
    IDE:Arduino IDE

    #include <Arduino.h>
    #include <WiFi.h>
    #include <driver/i2s.h>
    #include <WiFiUdp.h>
    
    #define I2S_WS 18
    #define I2S_SD 16
    #define I2S_SCK 17
    #define I2S_PORT I2S_NUM_0
    #define bufferLen 1024  // 增加缓冲区大小以适应更多音频数据
    
    const char* ssid = "你的wifi名称";           
    const char* password = "你的wifi密码";    
    const char* host = "接收音频端的IP地址"; // 电脑的IP地址
    const int port = 8888; // 监听的端口
    
    WiFiUDP udp;  // 使用 UDP 协议进行数据传输
    int16_t sBuffer[bufferLen];
    
    void setup() {
        Serial.begin(115200);
        Serial.println("Setup I2S ...");
        
        // 连接WiFi
        setup_wifi();
        
        delay(1000);
        i2s_install();
        i2s_setpin();
        i2s_start(I2S_PORT);
        delay(500);
    }
    
    void loop() {
        size_t bytesIn = 0;
        esp_err_t result = i2s_read(I2S_PORT, &sBuffer, bufferLen * sizeof(int16_t), &bytesIn, portMAX_DELAY);
        if (result == ESP_OK && bytesIn > 0) {
            // 发送音频数据到服务器
            udp.beginPacket(host, port);
            udp.write((uint8_t*)sBuffer, bytesIn);
            udp.endPacket();
        }
    }
    
    void setup_wifi() {
        delay(10);
        Serial.println();
        Serial.print("正在连接到WIFI ");
        Serial.println(ssid);
        WiFi.begin(ssid, password);
        while (WiFi.status() != WL_CONNECTED) {
            delay(600);
            Serial.print("-");
        }
        Serial.println("WiFi 已连接");
        Serial.println("IP 地址: ");
        Serial.println(WiFi.localIP());
    }
    
    void i2s_install() {
        const i2s_config_t i2s_config = {
            .mode = (i2s_mode_t)(I2S_MODE_MASTER | I2S_MODE_RX),
            .sample_rate = 16000,
            .bits_per_sample = I2S_BITS_PER_SAMPLE_16BIT,
            .channel_format = I2S_CHANNEL_FMT_ONLY_LEFT,
            .communication_format = (i2s_comm_format_t)(I2S_COMM_FORMAT_STAND_I2S),
            .intr_alloc_flags = 0,
            .dma_buf_count = 8,
            .dma_buf_len = bufferLen,
            .use_apll = false
        };
    
        i2s_driver_install(I2S_PORT, &i2s_config, 0, NULL);
    }
    
    void i2s_setpin() {
        const i2s_pin_config_t pin_config = {
            .bck_io_num = I2S_SCK,
            .ws_io_num = I2S_WS,
            .data_out_num = I2S_PIN_NO_CHANGE,
            .data_in_num = I2S_SD
        };
    
        i2s_set_pin(I2S_PORT, &pin_config);
    }
    
    
    3. Windows主机端代码

    采用Python进行程序编写

    import socket
    import pyaudio
    
    # 设置音频参数
    CHUNK = 1024  # 每个数据包的大小
    FORMAT = pyaudio.paInt16  # 数据格式为 16 位整型
    CHANNELS = 1  # 单声道
    RATE = 16000  # 采样率 16kHz
    
    # 创建 PyAudio 对象
    p = pyaudio.PyAudio()
    
    # 打开音频流
    stream = p.open(format=FORMAT,
                    channels=CHANNELS,
                    rate=RATE,
                    output=True)
    
    # 设置 UDP 服务器
    server_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
    server_socket.bind(('0.0.0.0', 8888))  # 监听所有可用接口,端口 8888
    
    print("等待音频数据流...")
    
    try:
        while True:
            data, addr = server_socket.recvfrom(CHUNK * 2)  # 接收数据包(每个 int16 占用 2 个字节)
            if not data:
                break
            stream.write(data)  # 播放接收到的音频数据
    except KeyboardInterrupt:
        pass
    finally:
        stream.stop_stream()
        stream.close()
        p.terminate()
        server_socket.close()
    

    作者:rapidSpace

    物联沃分享整理
    物联沃-IOTWORD物联网 » 使用ESP32与INMP441麦克风模块实现音频传输

    发表回复