A2DP stream sounds weird #705
-
Code (it is a spaghetti code, but it's a basis for future changes): #include <OneButton.h>
#include "AudioTools.h"
#include "AudioTools/AudioLibs/AudioBoardStream.h" // install https://github.com/pschatzmann/arduino-audio-driver
#include "AudioTools/AudioCodecs/CodecMP3Helix.h"
#include "BluetoothA2DPSink.h"
#include "lamesound2.h"
#define KEY_VOLUP 18
#define KEY_NEXT 23
#define KEY_PLAY 19
#define KEY_PREV 13
#define KEY_VOLDN 36
#define BATT_PIN 15
uint8_t curVolume = 63;
bool isMuted = false;
uint16_t battTick = 0;
uint16_t battCheckTick = 30000;
AudioBoardStream kit(AudioKitEs8388V1);
BluetoothA2DPSink a2dp_sink(kit);
MemoryStream mp3;
MP3DecoderHelix helix;
EncodedAudioStream out(&kit, &helix);
StreamCopy copier(out, mp3);
OneButton volup_btn(KEY_VOLUP, true);
OneButton next_btn(KEY_NEXT, true);
OneButton play_btn(KEY_PLAY, true);
OneButton prev_btn(KEY_PREV, true);
OneButton voldn_btn(KEY_VOLDN, true);
void playSound(int index) {
const uint8_t* data = nullptr;
uint32_t data_len = 0;
ESP_LOGI("SoundPlay", "Playing sound %d", index);
switch (index) {
case 0: {
data = battlow;
data_len = battlow_len;
break;
}
case 1: {
data = connected;
data_len = connected_len;
break;
}
case 2: {
data = disconnected;
data_len = disconnected_len;
break;
}
case 3: {
data = initSnd;
data_len = initSnd_len;
break;
}
case 4: {
data = linkloss;
data_len = linkloss_len;
break;
}
case 5: {
data = volmax;
data_len = volmax_len;
break;
}
case 6: {
data = volmin;
data_len = volmin_len;
break;
}
case 7: {
data = poweron;
data_len = poweron_len;
break;
}
default: {
data = poweroff;
data_len = poweroff_len;
break;
}
}
ESP_LOGW("SoundPlay", "Init data, len = %u", data_len);
if (data == nullptr || data_len == 0) {
ESP_LOGE("SoundPlay", "Something is wrong, wrong or empty data supplied.!!");
return;
}
mp3.setValue(data, data_len);
mp3.begin();
helix.setOutput(kit);
ESP_LOGW("SoundPlay", "Start play...");
helix.begin();
ESP_LOGW("SoundPlay", "Enter loop");
while (mp3.available()) {
copier.copy();
};
ESP_LOGW("SoundPlay", "Exit loop, destroy Helix decoder...");
helix.end();
ESP_LOGW("SoundPlay", "Freeing reserved memory for MemoryStream...");
mp3.end();
ESP_LOGW("SoundPlay", "Play sound %d ok...", index);
}
void goNext() {
ESP_LOGI("OneButton", "NEXT action initiated");
a2dp_sink.next();
}
void goPlay() {
ESP_LOGI("OneButton", "PLAY action initiated");
if (a2dp_sink.is_output_active() == true) {
a2dp_sink.pause();
} else {
a2dp_sink.play();
}
}
void goPrev() {
ESP_LOGI("OneButton", "PREV action initiated");
a2dp_sink.previous();
}
void mute() {
ESP_LOGI("OneButton", "MUTE action initiated");
if (isMuted) {
ESP_LOGI("VolumeMgr", "Volume set to %d", curVolume);
a2dp_sink.set_volume(curVolume);
}
else {
ESP_LOGI("VolumeMgr", "Volume set to 0");
curVolume = a2dp_sink.get_volume(); // Update current volume with actual volume
a2dp_sink.set_volume(0);
}
isMuted = !isMuted;
}
void connectionStatusChanged(esp_a2d_connection_state_t state, void *ptr) {
switch (state) {
case esp_a2d_connection_state_t::ESP_A2D_CONNECTION_STATE_DISCONNECTED:
ESP_LOGI("Bluedroid", "A2DP Source Disconnected");
playSound(2);
break;
case esp_a2d_connection_state_t::ESP_A2D_CONNECTION_STATE_CONNECTED:
ESP_LOGI("Bluedroid", "A2DP Source Connected");
playSound(1);
break;
default:
// Nothing
break;
}
}
void volumeUpFine() {
curVolume = a2dp_sink.get_volume();
curVolume = curVolume + 1;
if (curVolume > 127) {
curVolume = 127;
ESP_LOGI("VolumeMgr", "Volume is at 127");
}
ESP_LOGI("VolumeMgr", "Volume set to %u", curVolume);
a2dp_sink.set_volume(curVolume);
}
void volumeUpCoarse() {
curVolume = a2dp_sink.get_volume();
curVolume = curVolume + 4;
if (curVolume > 127) {
curVolume = 127;
ESP_LOGI("VolumeMgr", "Volume is at 127");
}
ESP_LOGI("VolumeMgr", "Volume set to %u", curVolume);
a2dp_sink.set_volume(curVolume);
}
void volumeDownFine() {
curVolume = a2dp_sink.get_volume();
curVolume = curVolume - 1;
if (curVolume <= 0) {
curVolume = 0;
ESP_LOGI("VolumeMgr", "Volume is at 0");
}
ESP_LOGI("VolumeMgr", "Volume set to %u", curVolume);
a2dp_sink.set_volume(curVolume);
}
void volumeDownCoarse() {
curVolume = a2dp_sink.get_volume();
curVolume = curVolume - 4;
if (curVolume <= 0) {
curVolume = 0;
ESP_LOGI("VolumeMgr", "Volume is at 0");
}
ESP_LOGI("VolumeMgr", "Volume set to %u", curVolume);
a2dp_sink.set_volume(curVolume);
}
void setupKeys() {
ESP_LOGI("OneButton", "Begin setting up buttons...");
// Setup buttons
ESP_LOGI("OneButton", "Attach button int...");
volup_btn.attachClick(volumeUpFine);
volup_btn.attachDuringLongPress(volumeUpCoarse);
next_btn.attachClick(goNext);
play_btn.attachClick(goPlay);
prev_btn.attachClick(goPrev);
voldn_btn.attachClick(volumeDownFine);
voldn_btn.attachDuringLongPress(volumeDownCoarse);
// Set delays
ESP_LOGI("OneButton", "Set key debounce...");
volup_btn.setDebounceMs(100);
next_btn.setDebounceMs(100);
play_btn.setDebounceMs(100);
prev_btn.setDebounceMs(100);
voldn_btn.setDebounceMs(100);
ESP_LOGI("OneButton", "Set key duration...");
volup_btn.setClickMs(500);
next_btn.setClickMs(500);
play_btn.setClickMs(500);
prev_btn.setClickMs(500);
voldn_btn.setClickMs(500);
ESP_LOGI("OneButton", "Set key hold duration");
volup_btn.setPressMs(1000);
next_btn.setPressMs(1000);
play_btn.setPressMs(1000);
prev_btn.setPressMs(1000);
voldn_btn.setPressMs(1000);
ESP_LOGI("OneButton", "Key setup OK?");
}
void setup() {
Serial.begin(115200);
auto cfg = kit.defaultConfig();
cfg.sample_rate = 44100;
cfg.channels = 2;
kit.begin(cfg);
out.begin();
infoDump();
setupKeys();
logWhodunit();
playSound(7);
a2dp_sink.set_on_connection_state_changed(connectionStatusChanged);
a2dp_sink.start("ESP-BT-DRG");
logWhodunit();
ESP_LOGI("System", "Ready");
}
void loop() {
volup_btn.tick();
next_btn.tick();
play_btn.tick();
prev_btn.tick();
voldn_btn.tick();
} The prompt sound works, however the moment the sound plays through the Bluetooth connection, the sound is low in pitch and the CPU gets unstable. I'm pretty sure I did something wrong, and I need some help figuring out why. Potential answers:
|
Beta Was this translation helpful? Give feedback.
Replies: 4 comments 5 replies
-
Just store the actual AudioInfo and restore it back to the original after you are done playing your file. |
Beta Was this translation helpful? Give feedback.
-
I have tried few fixes that were suggested, and here's the result: The audio was stuttering and low in pitch before, with a long delay between play and pause (playing the audio and stopping the playback when I tell it to stop) before the change.
After the change, the sound is fixed but it's taking up too much memory. |
Beta Was this translation helpful? Give feedback.
-
How come setting the ring buffer size to three times its original intended size still result in "ring buffer full" error? I don't get it... Experiments:
|
Beta Was this translation helpful? Give feedback.
-
I think I partially know what's going on -- PSRAM settings. If it's turned on, no matter the configuration, it will always fail to work correctly. |
Beta Was this translation helpful? Give feedback.
Just store the actual AudioInfo and restore it back to the original after you are done playing your file.