2012-11-21 14 views
8

Mam pewne problemy przy użyciu klasy AudioRecord. Chcę przechowywać zarejestrowane dane w buforze, ale nie jestem pewien, jaki jest właściwy sposób, aby to osiągnąć. Przeszedłem przez wiele przykładów, ale większość z nich była skomplikowana i reprezentowała wiele różnych podejść. Szukam prostego lub prostego wyjaśnienia.AudioRecord - jak uzyskać dane do bufora?

Oto moje ustawienia audio dla mojego projektu:

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

short[] buffer = new short[bufferSizeInBytes]; 

AudioRecord audioRecorder = new AudioRecord(audioSource, 
              sampleRateInHz, 
              channelConfig, 
              audioFormat, 
              bufferSizeInBytes); 

Próbuję utworzyć funkcję nagrywania:

public void Recording() { 
    audioRecorder.startRecording(); 
    ... 
    audioRecorder.stop(); 
    audioRecorder.release(); 
} 

wiem, że jestem powinien używać .read (krótkie Funkcja [] audioData, int offsetInShorts, int sizeInShorts). I tutaj zaczynają się moje problemy. Nie jestem pewien, jak działa bufor audioData - zakładam, że funkcja umieszcza nagrane próbki w audioData. Co się stanie, jeśli całkowicie wypełni się danymi? Zaczyna się przepisywanie od najwcześniejszej pozycji? Jeśli tak, to uważam, że muszę skopiować wszystkie zebrane próbki w innym miejscu. Pojawia się kolejne pytanie - jak mogę sprawdzić, czy bufor funkcji .read (...) jest już pełny? Czy muszę mierzyć czas i kopiować zawartość bufora, czy istnieje inny sposób, aby to osiągnąć? Czy muszę również utworzyć wątek dla całej operacji nagrywania?

Przepraszam za pytanie tak wiele pytań w jednym temacie :)

Odpowiedz

3

Odpowiedź na pytania ::

recorder.read (...) niekoniecznie odczytać żadnych danych w ogóle. Najprawdopodobniej powinieneś przepisać tę pętlę, aby wstrzymać na krótki czas (np. 50 ms) między wywołaniami do przeczytania. Nie powinien także umieszczać w kolejce bufora, dopóki bufor nie będzie zawierał danych. Ponadto, ponieważ bufor może nie być pełny, prawdopodobnie musisz użyć struktury danych, która utrzymuje liczbę bajtów. ByteBuffer przychodzi na myśl jako dobry kandydat. Możesz włożyć do niego bajty w pętli do odczytu i gdy stanie się wystarczająco pełny, ustaw go w kolejce do transmisji i uruchom inny.

Oczywiście musisz utworzyć wątek do zapętlenia go. jak pokazano w poniższym kodzie.

Oto zmodyfikowana wersja pętli nagrywania, która przeprowadza poprawne sprawdzanie błędów. Używa Queue<ByteBuffer> zamiast Queue<byte[]>:

private void startRecording() { 

    recorder.startRecording(); 
    isRecording = true; 
    recordingThread = new Thread(new Runnable() { 

     @Override 
     public void run() { 
      bData = ByteBuffer.allocate(BufferElements); 
      bbarray = new byte[bData.remaining()]; 
      bData.get(bbarray); 
      while (isRecording) { 

       int result = recorder.read(bbarray, 0, BufferElements); 
       System.out.println("READ DATA"); 
       if (result > 0) { 
        qArray.add(bData); 

        --your stuffs-- 
        bData = ByteBuffer.allocate(BufferElements); 
       } else if (result == AudioRecord.ERROR_INVALID_OPERATION) { 
        Log.e("Recording", "Invalid operation error"); 
        break; 
       } else if (result == AudioRecord.ERROR_BAD_VALUE) { 
        Log.e("Recording", "Bad value error"); 
        break; 
       } else if (result == AudioRecord.ERROR) { 
        Log.e("Recording", "Unknown error"); 
        break; 
       } 
       try { 
        Thread.sleep(10); 
       } catch (InterruptedException e) { 
        break; 
       } 
      } 
     } 
    }, "AudioRecorder Thread"); 
    recordingThread.start(); 
} 

Oczywiście, gdzieś trzeba zadzwonić recorder.startRecording() lub nie dostaniesz żadnych danych.

dla wyglądu próbki roboczej at this example.

+0

co to jest ** qArray ** tutaj? – OnePunchMan

+0

może być listą array. Nie pamiętam teraz. Lepiej odnieść ten przykład http://stackoverflow.com/questions/8499042/android-audiorecord-example/13487250#13487250 –

Powiązane problemy