Page 1 of 1

Playing sounds from SD card

Posted: Thu Oct 15, 2020 8:12 pm
by samwarez
I have an SD card filled with small .wav files and I am trying to find a way to play specific ones on command. I am currently trying to get the ESP32-audioI2S library from https://github.com/schreibfaul1/ESP32-audioI2S to work as so far its gotten me closer than anything else. The current examples queue up a single file to be played in the setup() then plays it when the board starts.

What I am looking to do is play a list of files from a function so say I press a button the triggers the function and plays a file, press a different button and a different file plays. I will also need to string a few files together to play one after the other.

Here is what I have so far:

Code: Select all

#include "Audio.h"
#include "SD.h"
#include "FS.h"

// Digital I/O used
#define SD_CS          5
#define SPI_MOSI      23
#define SPI_MISO      19
#define SPI_SCK       18
#define I2S_DOUT      25
#define I2S_BCLK      27
#define I2S_LRC       26
#define buttonPin      2
#define ledPin         0

int buttonState = 0; 
    
Audio audio;
void setup() {
    pinMode(SD_CS, OUTPUT);
    pinMode(ledPin, OUTPUT);     
    pinMode(buttonPin, INPUT);
    digitalWrite(SD_CS, HIGH);
    SPI.begin(SPI_SCK, SPI_MISO, SPI_MOSI);
    Serial.begin(115200);
    SD.begin(SD_CS);
    audio.setPinout(I2S_BCLK, I2S_LRC, I2S_DOUT);
    audio.setVolume(10); // 0...21
    audio.connecttoFS(SD, "100.wav");
}

void loop()
{
    buttonState = digitalRead(buttonPin);

    if (buttonState == HIGH) {
    digitalWrite(ledPin, HIGH);
    playsound();
  } else {
    digitalWrite(ledPin, LOW);
  }
}


void playsound()
{
  audio.loop();
}
This works, but only once before I need to reset the board.

Code: Select all

void setup() {
    pinMode(SD_CS, OUTPUT);
    pinMode(ledPin, OUTPUT);     
    pinMode(buttonPin, INPUT);
    digitalWrite(SD_CS, HIGH);
    SPI.begin(SPI_SCK, SPI_MISO, SPI_MOSI);
    Serial.begin(115200);
    SD.begin(SD_CS);
    audio.setPinout(I2S_BCLK, I2S_LRC, I2S_DOUT);
    audio.setVolume(10); // 0...21
    // audio.connecttoFS(SD, "100.wav"); <---Removed
}

void loop()
{
    buttonState = digitalRead(buttonPin);

    if (buttonState == HIGH) {
    digitalWrite(ledPin, HIGH);
    playsound();
  } else {
    digitalWrite(ledPin, LOW);
  }
}


void playsound()
{
  audio.connecttoFS(SD, "100.wav");
  audio.loop();
}
This does not, nothing plays.

So the main question is how do I get that connecttoFS bit to work outside of the main setup function?

Eventually I want something akin to this:

Code: Select all

void playsound (string file) {
audio.connecttoFS(SD, file);
audio.loop();
}
Then somewhere else:

Code: Select all

playsound ("Hello.wav");
playsound ("World.wav");
if buttonPressed=1 {
playsound ("Foo.wav");
} elseif buttonPressed=2 {
playsound ("bar.wav");
}
Any ideas on how to get this to work with this library?

I feel like this should be a stupid simple task, but I am having a heck of a time working this out.

Re: Playing sounds from SD card

Posted: Wed Sep 08, 2021 10:35 pm
by arifshanji
@samwarez check out the audio_eof_mp3 event that is triggered at the end of the audio file playing
https://github.com/schreibfaul1/ESP32-a ... -are-there
That should solve your issue.

Re: Playing sounds from SD card

Posted: Sun May 21, 2023 12:56 pm
by rob2000000
Hi, I am new to ESP32 but had some success with WAV files in Arduino - hopefully the ESP32 works in the same way.
My problem was picking a file where the file name is created rather than presented in sting quotes " ".
I found that generating the file name - say number.WAV where number is any value up to around 32,000 , the Arduino Nano using tmrpcm.play library would not accept anything that was not presented in string quotes.
My solution was to generate file names and place them directly into the string buffer as below:
************************************************
//Need to convert String variable to char*, per TMRpcm documentation
num = random(104) +1;

audioFileTitle = (String(num) + ".wav");

char charBuf[audioFileTitle.length()+1];

audioFileTitle.toCharArray(charBuf, 10);

//Play sound from charBuf

tmrpcm.play(charBuf);
do
{
// wait for sound to finish

} while (tmrpcm.isPlaying());
buttonState = digitalRead(buttonPin);
************************************************
I hope this is of use to you.