2012-11-27 9 views
5

Próbuję nagrać trochę głosu za pomocą klasy AudioRecord, a następnie zapisać go do pliku wyjściowego .pcm. Chcę, aby mój program kontynuował nagrywanie do momentu naciśnięcia przycisku stop. Niestety, bez względu na to, jak długo nagrywam, rozmiar pliku wyjściowego zawsze wynosi 3528 bajtów i trwa około 20 ms. Również zgodnie z Toolsoft Audio Tools, właściwość tego pliku to: 44100Hz, 16 bitów, stereo, nawet jeśli używam mono z zupełnie inną częstotliwością próbkowania.AudioRecord - zapis pliku PCM

Thread recordingThread; 
boolean isRecording = false; 


int audioSource = AudioSource.MIC; 
int sampleRateInHz = 44100; 
int channelConfig = AudioFormat.CHANNEL_IN_MONO; 
int audioFormat = AudioFormat.ENCODING_PCM_16BIT; 
int bufferSizeInBytes = AudioRecord.getMinBufferSize(sampleRateInHz, channelConfig, audioFormat); 

byte Data[] = new byte[bufferSizeInBytes]; 

AudioRecord audioRecorder = new AudioRecord(audioSource, 
              sampleRateInHz, 
              channelConfig, 
              audioFormat, 
              bufferSizeInBytes); 
@Override 
public void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_main); 
} 

@Override 
public boolean onCreateOptionsMenu(Menu menu) { 
    getMenuInflater().inflate(R.menu.activity_main, menu); 
    return true; 
}  

public void startRecording(View arg0) { 
    audioRecorder.startRecording(); 
    isRecording = true; 
    recordingThread = new Thread(new Runnable() { 
     public void run() { 
      String filepath = Environment.getExternalStorageDirectory().getPath(); 
      FileOutputStream os = null; 
      try { 
       os = new FileOutputStream(filepath+"/record.pcm"); 
      } catch (FileNotFoundException e) { 
       e.printStackTrace(); 
      } 
      while(isRecording) { 
       audioRecorder.read(Data, 0, Data.length); 
       try { 
        os.write(Data, 0, bufferSizeInBytes); 
       } catch (IOException e) { 
        e.printStackTrace(); 
       } 
       try { 
        os.close(); 
       } catch (IOException e) { 
        e.printStackTrace(); 
       } 
      } 
     } 
    }); 
    recordingThread.start(); 
} 

public void stopRecording(View arg0) { 
    if (null != audioRecorder) { 
     isRecording = false; 
     audioRecorder.stop(); 
     audioRecorder.release(); 
     audioRecorder = null; 
     recordingThread = null; 
    } 
} 

Czy mogę prosić, aby mi powiedzieć, co jest nie tak? Mam nadzieję, że odpowiedź nie będzie 'wszystko' :)

+0

Myślę, że Twój kod IO może być problemem. Spróbuj użyć Apache Commons IOUtils do skopiowania strumieni: http://commons.apache.org/io/api-release/org/apache/commons/io/IOUtils.html#copy(java.io.InputStream,%20java.io .OutputStream) –

Odpowiedz

2

Change your sample rate to 8000, ponieważ w emulatora ty cant test with 44100 sample rate.

użycie AudioRecord źródło jak pokazano grać w emulatorze

private static final int RECORDER_SAMPLERATE = 8000; 
private static final int RECORDER_CHANNELS = AudioFormat.CHANNEL_IN_MONO; 
private static final int RECORDER_AUDIO_ENCODING = AudioFormat.ENCODING_PCM_16BIT; 

AudioRecord audio_record = new AudioRecord(MediaRecorder.AudioSource.MIC, 
      RECORDER_SAMPLERATE, RECORDER_CHANNELS, 
      RECORDER_AUDIO_ENCODING, BufferElements2Rec * BytesPerElement); 


int BufferElements2Play = 1024; // want to play 2048 (2K) since 2 bytes we use only 1024 
int BytesPerElement = 2; // 2 bytes in 16bit format 

If it din't get worked, then go to this blog. It will work fine for recording and storing the data in .pcm file.

+0

Używam mojego telefonu, nie emulatora. – Arxas

+0

Zużyty cały kod z tego bloga i aplikacji uległ awarii po naciśnięciu przycisku, który uruchamia nagrywanie. – Arxas

+0

zmienić częstotliwość próbkowania na 44100 stereo kodowanie-16bit, sprawdź. Nie powinno się zawieszać, możesz uzyskać plik dziennika błędów. –

1
try { 
       os.write(Data, 0, bufferSizeInBytes); 
      } catch (IOException e) { 
       e.printStackTrace(); 
      } 
      try { 
       os.close(); 
      } catch (IOException e) { 
       e.printStackTrace(); 
      } 

To jest problem. Zamykasz FileOutputStream (os.close()) po zaledwie jednym zapisie. Przenieś to z pętli while:

while(isRecording) { 
      audioRecorder.read(Data, 0, Data.length); 
      try { 
       os.write(Data, 0, bufferSizeInBytes); 
      } catch (IOException e) { 
       e.printStackTrace(); 
      } 

     } 
     try { 
       os.close(); 
      } catch (IOException e) { 
       e.printStackTrace(); 
      } 
    }