Arduino c + & gt; & gt; операция

Я адаптирую пример для библиотеки Arduino AutoAnalogAudio под названием
SDAudioWavPlayer
который может быть найден в примерах-> AutoAnalogAudio-> SDAudio-> SDAudioWavPlayer
В этом примере используются прерывания для многократного вызова функции
void loadBuffer (). Код для этого ниже

/* Function called from DAC interrupt after dacHandler(). Loads data into the dacBuffer */

void loadBuffer() {

if (myFile) {
if (myFile.available()) {
if (aaAudio.dacBitsPerSample == 8) {
//Load 32 samples into the 8-bit dacBuffer
myFile.read((byte*)aaAudio.dacBuffer, MAX_BUFFER_SIZE);
}else{
//Load 32 samples (64 bytes) into the 16-bit dacBuffer
myFile.read((byte*)aaAudio.dacBuffer16, MAX_BUFFER_SIZE * 2);
//Convert the 16-bit samples to 12-bit
for (int i = 0; i < MAX_BUFFER_SIZE; i++) {
aaAudio.dacBuffer16[i] = (aaAudio.dacBuffer16[i] + 0x8000) >> 4;
}
}
}else{
#if defined (AUDIO_DEBUG)
Serial.println("File close");
#endif
myFile.close();
aaAudio.disableDAC();
}
}
}

Конкретная часть, которая меня интересует, это вторая часть утверждения if

{
//Load 32 samples (64 bytes) into the 16-bit dacBuffer
myFile.read((byte*)aaAudio.dacBuffer16, MAX_BUFFER_SIZE * 2);
//Convert the 16-bit samples to 12-bit
for (int i = 0; i < MAX_BUFFER_SIZE; i++) {
aaAudio.dacBuffer16[i] = (aaAudio.dacBuffer16[i] + 0x8000) >> 4;
}
}

Несмотря на комментарий, MAX_BUFFER_SIZE равен 256, поэтому 512 байтов считываются
aaAudio.dacBuffer16. Эти данные изначально были 16-битными целыми числами со знаком (+/- 32k), а dacBuffer16 является массивом 16-битных целых чисел без знака (0-64K). Отрицательный знак удаляется путем прохождения массива и добавления 2 ^ 15 (0x8000) к каждому элементу. Это приводит к переполнению отрицательных чисел, оставляя положительную часть отрицательного числа. Положительные числа просто увеличились на 2 ^ 15. таким образом, значения изменяются на 0 -64K. Затем результат сдвигается на 4 позиции вправо, так что остаются только старшие 12 битов, что может обрабатывать ЦАП Arduino. Все это происходит в очереди

aaAudio.dacBuffer16[i] = (aaAudio.dacBuffer16[i] + 0x8000) >> 4;

Все идет нормально.

Теперь я хочу иметь возможность программно уменьшить громкость. Насколько я могу найти, библиотека не предоставляет функцию для этого, поэтому я подумал, что самый простой
нужно было изменить «4» на «N» и увеличить величину смещения до 5,6,7 и т. д.
например

aaAudio.dacBuffer16[i] = (aaAudio.dacBuffer16[i] + 0x8000) >> N;

где N — целое число Я попробовал это, но я получил ужасно искаженный результат, который я не понял.

Играя, пробуя разные вещи, я попробовал следующее, которое работает

uint16_t sample;
int N = 5;
for (int i = 0; i < MAX_BUFFER_SIZE; i++)
{

sample = (aaAudio.dacBuffer16[i] + 0x8000);
sample = sample >> N;
// sample = sample / 40;
aaAudio.dacBuffer16[i] = sample;
}

Вы также можете видеть, что я прокомментировал просто деление на число, которое работает, если я хочу более точный контроль.

Моя проблема в том, что я не вижу разницы между двумя битами кода.
Кто-нибудь может просветить меня?

1

Решение

Задача ещё не решена.

Другие решения

Других решений пока нет …