Запись wav-файла с микрофона в Android - проблемы - PullRequest
4 голосов
/ 15 декабря 2010

Мне нужно иметь возможность создавать WAV-файл с помощью микрофона в Android.В настоящее время у меня много проблем.Пока что это моя ситуация.Я использую части кода проекта micDroid для записи таким образом:

//read thread


int sampleRate = 44100;
int bufferSize = AudioRecord.getMinBufferSize(sampleRate,android.media.AudioFormat.CHANNEL_CONFIGURATION_MONO,android.media.AudioFormat.ENCODING_PCM_16BIT);
AudioRecord ar = new AudioRecord(AudioSource.MIC,sampleRate,android.media.AudioFormat.CHANNEL_CONFIGURATION_MONO,android.media.AudioFormat.ENCODING_PCM_16BIT,bufferSize);
short[] buffer = new short[bufferSize];

ar.startRecording();
while(isRunning){
    try{
        int numSamples = ar.read(buffer, 0, buffer.length);
        queue.put(new Sample(buffer, numSamples));
    } catch (InterruptedException e){
        e.printStackTrace();
    }
}


//write thread


int sampleRate = 44100;
WaveWriter writer = new WaveWriter("/sdcard","recOut.wav",sampleRate,android.media.AudioFormat.CHANNEL_CONFIGURATION_MONO,android.media.AudioFormat.ENCODING_PCM_16BIT);
try {
    writer.createWaveFile();
} catch (IOException e) {
    e.printStackTrace();
}
while(isRunning){
    try {
        Sample sample = queue.take();
        writer.write(sample.buffer, sample.bufferSize);
    } catch (IOException e) {
        //snip
    }
}

Что, кажется, работает нормально, однако конечный результат узнаваемо содержит все, что я сказал, но это ужасно искажено.Вот скриншот экрана Audacity (WMP отказывается воспроизводить файл).

alt text

Любая помощь будет принята с благодарностью, дайте мне знать, если вам нужно больше кода / информации.

Обновление

Следуя советам Маркуса, вот мой обновленный код:

int sampleRate = 16000;

writer = new WaveWriter("/sdcard","recOut.wav",sampleRate,android.media.AudioFormat.CHANNEL_IN_MONO,android.media.AudioFormat.ENCODING_PCM_16BIT);

int bufferSize = AudioRecord.getMinBufferSize(sampleRate,android.media.AudioFormat.CHANNEL_IN_MONO,android.media.AudioFormat.ENCODING_PCM_16BIT);
AudioRecord ar = new AudioRecord(AudioSource.MIC,sampleRate,android.media.AudioFormat.CHANNEL_IN_MONO,android.media.AudioFormat.ENCODING_PCM_16BIT,bufferSize);

byte[] buffer = new byte[bufferSize]; //all references changed from short to byte type

... и еще один скринкап смелости: alt text

Ответы [ 4 ]

5 голосов
/ 15 декабря 2010

CHANNEL_CONFIGURATION_MONO устарела, насколько я знаю, используйте CHANNEL_IN_MONO.рассмотрим проект rehearsalassistant , ведь они тоже используют класс AudioRecord.частота выборки должна быть выбрана так, чтобы соответствовать стандартной частоте выборки, как описано в этой статье википедии .

4 голосов
/ 25 июля 2012

Вы можете установить буфер с прямым порядком байтов с помощью следующего:

buffer.order(ByteOrder.LITTLE_ENDIAN);
2 голосов
/ 24 марта 2011

У меня много теорий:

  1. если у вас был насыщенный шумом сигнал, и вы ничего не можете понять или можете что-то понять. Может случиться так, что у вас есть проблемы с прямым и обратным порядком байтов. При записи 16 бит (2 байта) может храниться как AB или как BA (где A и B это байт). В Java все с прямым порядком байтов (http://mindprod.com/jgloss/endian.html), поэтому вы сохраняете 16-битную выборку с коротким порядком байтов, затем вы пытаетесь создать WAV, но WAV должны иметь данные, хранящиеся на младшем порядке *https://ccrma.stanford.edu/courses/422/projects/WaveFormat/). Хорошо, результат ясен, и у вас есть скриншот. Решение состоит в том, чтобы использовать байт всегда, вы это сделали, и, вероятно, теперь все в порядке

если не проверять queue.put и queue.take, я думаю, они вам не нужны, потому что вы сохранили аудио в массиве и этого достаточно. В первый раз я заменил бы queue.put на функцию для хранения буфера в огромном массиве байтов со всеми байтами. Тогда вы можете поставить заголовок wav.

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

Другой вариант: у вас проблема с заголовком wav размером 44 байта. проверьте свою функцию WaveWriter. если вы напишите на нем плохой код, вы услышите много разных звуков вашего голоса.

примечание: я видел функцию WaveWriter или аналогичную в исходном коде Android, но она не была готова к использованию три месяца назад. Что-то новое о waveheader?

1 голос
/ 26 апреля 2012

Это довольно ясно, Audacity считает, что ваш файл с плавающей запятой. Либо заголовок WAV испорчен, либо это то, как вы его открыли.

Сделать запись. В Audacity откройте его, используя Project / Import Raw Data Установите параметры того, как вы думаете, что вы записали это. Бьюсь об заклад, он воспроизводится нормально.

...