Pregunta

Actualmente tengo un programa de bucle para probar audio en dispositivos Android.

Utiliza Audiorecord y AudioTrack para grabar audio PCM desde el micrófono y reproducir audio PCM fuera del auricular.

Aquí está el código:

public class Record extends Thread
  {

          static final int bufferSize = 200000;
          final short[] buffer = new short[bufferSize];
          short[] readBuffer = new short[bufferSize];

          public void run() {  
            isRecording = true;
            android.os.Process.setThreadPriority
            (android.os.Process.THREAD_PRIORITY_URGENT_AUDIO);

            int buffersize = AudioRecord.getMinBufferSize(11025,
            AudioFormat.CHANNEL_CONFIGURATION_MONO,
            AudioFormat.ENCODING_PCM_16BIT);

                           arec = new AudioRecord(MediaRecorder.AudioSource.MIC,
                                           11025,
                                           AudioFormat.CHANNEL_CONFIGURATION_MONO,
                                           AudioFormat.ENCODING_PCM_16BIT,
                                           buffersize);

                           atrack = new AudioTrack(AudioManager.STREAM_VOICE_CALL,
                                           11025,
                                           AudioFormat.CHANNEL_CONFIGURATION_MONO,
                                           AudioFormat.ENCODING_PCM_16BIT,
                                           buffersize,
                                           AudioTrack.MODE_STREAM);


                           atrack.setPlaybackRate(11025);

                           byte[] buffer = new byte[buffersize];
                           arec.startRecording();
                           atrack.play();

                           while(isRecording) {

                                   arec.read(buffer, 0, buffersize);
                                   atrack.write(buffer, 0, buffer.length);
                           }  
          }
  }

Entonces, como puede ver en la creación de AudioTrack y Audiorecord, la codificación se suministra a través del audioformat, pero esto solo permite PCM de 16 bits o 8 bits.

Tengo mi propia implementación del códec G711 ahora y quiero poder codificar el audio del micrófono y decodificarlo en el auricular, así que tengo codificar (corta lin [], int offset, byte enc [], int marcos) y decode (byte enc [], corta lin [], int marco) Métodos, pero no estoy seguro de cómo usarlos para codificar y decodificar el audio desde Audiorecord y AudioTrack.

¿Alguien puede ayudarme o señalarme en la dirección correcta?

¿Fue útil?

Solución

Cambia tu arec.read(buffer, 0, buffersize) llamar para usar el Bytebuffer read() método de AudioRecord.

Una vez que tengas tus bytes en el ByteBuffer objeto, entonces puede insertar su llamada de implementación del G711 de codificación y usar el ByteBuffer.asShortBuffer() Método para llevar sus datos de PCM capturados en el codificador.

Eso resolvería su pregunta inicial sin tener que presentar una biblioteca de terceros para hacer ese trabajo por usted. (Esta respuesta es para las futuras personas que se encuentran con la pregunta).

Mi pregunta es ¿por qué?

En su código anterior, captura los datos de PCM del micrófono y escríbelo directamente al búfer para su reproducción.

No tiene ningún sentido en su implementación seguir la ruta de PCM -> G711 (codificar) -> G711 (decode) -> PCM. Todo lo que está haciendo es introducir un procesamiento y latencia innecesarios. Ahora, si iba a escribir datos codificados en un archivo en lugar de tratar de reproducirlo a través de la pieza del oído que sería una historia diferente, pero su código actual no parece útil para codificar los datos de PCM.

La introducción de su propio códec aquí solo tendría sentido en el contexto de escribir los datos de voz comprimidos en un archivo (grabando datos de llamadas, por ejemplo, de manera comprimida) o enviarlos a través de la red o algo así.

Otros consejos

Me doy cuenta de que esta es una publicación bastante antigua. ¿Pudiste que tu propio G711 funcionara? Mi propio pensamiento inicial sería usar un lib compilado para el núcleo y usar JNI para llamarlo.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top