2009-11-19 11 views
5

Necesito construir un gráfico visual que represente los niveles de voz (dB) en un archivo grabado. Traté de hacerlo de esta manera:AVAudioPlayer - Metering - Quiere construir una forma de onda (gráfico)

NSError *error = nil; 
AVAudioPlayer *meterPlayer = [[AVAudioPlayer alloc]initWithContentsOfURL:[NSURL fileURLWithPath:self.recording.fileName] error:&error]; 

if (error) { 
    _lcl_logger(lcl_cEditRecording, lcl_vError, @"Cannot initialize AVAudioPlayer with file %@ due to: %@ (%@)", self.recording.fileName, error, error.userInfo); 
} else { 
    [meterPlayer prepareToPlay]; 
    meterPlayer.meteringEnabled = YES; 

    for (NSTimeInterval i = 0; i <= meterPlayer.duration; ++i) { 
     meterPlayer.currentTime = i; 
     [meterPlayer updateMeters]; 
     float averagePower = [meterPlayer averagePowerForChannel:0]; 
     _lcl_logger(lcl_cEditRecording, lcl_vTrace, @"Second: %f, Level: %f dB", i, averagePower); 
    } 
} 
[meterPlayer release]; 

Sería genial si funcionó, pero no fue así. Siempre recibo -160 dB. ¿Alguna otra idea sobre cómo implementar eso?

UPD: Aquí es lo que tengo por último:

alt text http://img22.imageshack.us/img22/5778/waveform.png

+0

Ver aquí [https://github.com/prodia/AudioVisualizer](https://github.com/prodia/AudioVisualizer) –

Respuesta

0

Bien chicos, parece que voy a responder mi propia pregunta de nuevo: http://www.supermegaultragroovy.com/blog/2009/10/06/drawing-waveforms/ No hay muchos aspectos concretos, pero al menos sabrá lo que Apple necesita para leer.

+1

Sé que ahora tiene menos de un año, pero en su publicación original dijo que iba a publicar un componente de código abierto. Leí tu publicación de blog pero no vi nada descargable. ¿Me he perdido algo o has cambiado de opinión? –

+0

No cambié de opinión, pero simplemente nunca tuve la oportunidad de hacerlo. Escríbeme un correo electrónico con sus necesidades, y probablemente pueda ayudarlo. –

3

No he utilizado yo mismo, pero avTouch muestra de iPhone de Apple tiene gráficos de barras impulsados ​​por AVAudioPlayer, y se puede comprobar fácilmente a ver cómo lo hacen.

+0

Conozco esta muestra y la diferencia clave es que están _playing_ el archivo de audio. No necesito jugarlo. Necesito investigar una parte arbitraria del archivo en un momento arbitrario sin realmente jugarlo. Y para construir un gráfico que visualizaría esas características. –

+0

Ahhhh ... Tendrá que leer los datos usted mismo y buscar los niveles para períodos seleccionados. Y dado que el archivo no se descomprime, deberá decodificarlo o utilizar otros marcos para acceder a los datos de PCM. Entiendo que ExtAudio, Audio Queue y Remote IO AudioUnit serían áreas en las que debe tener en cuenta. Todavía estoy aprendiendo a mí mismo. – mahboudz

+0

>> Y como el archivo no está descomprimido, deberá decodificarlo -> Por favor, no responda si no sabe la respuesta. No hay diferencia en la lectura de datos comprimidos o en bruto. SDK está manejando todo esto. Por lo tanto, solo está engañando a las personas que le leerán después. –

0

No creo que pueda usar AVAudioPlayer según sus limitaciones. Incluso si pudiera hacer que "comience" sin reproducir realmente el archivo de sonido, solo lo ayudaría a crear un gráfico tan rápido como el archivo de audio se transmitiría. De lo que estás hablando es de hacer un análisis estático del sonido, que requerirá un enfoque muy diferente. Tendrá que leer el archivo usted mismo y analizarlo manualmente. No creo que haya una solución rápida que use algo en el SDK.

6

Solo quiero ayudar a los demás que han llegado a esta misma pregunta y han usado mucho tiempo para buscar. Para ahorrarle tiempo, pronuncié mi respuesta. No me gusta que alguien aquí que tratan esto como tipo de secreto ...

Después de la búsqueda alrededor de los artículos sobre extaudioservice, cola de audio y AVFoundation.

Me di cuenta de que debería usar AVFoundation, la razón es simple, es el último paquete y es Objective C pero no tan estilo cpp.

Así que los pasos para hacerlo no es complicado:

  1. Crear AVAsset del archivo de audio
  2. Crear avassetreader del avasset
  3. Crear avassettrack de avasset
  4. Crear avassetreadertrackoutput de avassettrack
  5. Agregue el avassetreadertrackoutput al anterior s avassetreader para iniciar la lectura de los datos de audio

Desde el avassettrackoutput que pueda copyNextSampleBuffer uno a uno (que es un bucle para leer todos los datos de salida).

Cada copyNextSampleBuffer le da una CMSampleBufferRef que se puede utilizar para obtener AudioBufferList por CMSampleBufferGetAudioBufferListWithRetainedBlockBuffer. AudioBufferList es una matriz de AudioBuffer. AudioBuffer es el conjunto de datos de audio que se almacena en su parte mData.

Puede implementar lo anterior en extAudioService también. Pero creo que el anterior avfoundation enfoque es más fácil.

Entonces la siguiente pregunta, ¿qué hacer con el mData? Tenga en cuenta que cuando obtiene el avassetreadertrackoutput, puede especificar su formato de salida, por lo que especificamos que el resultado es lpcm.

Luego, el mData que finalmente obtiene es en realidad un valor de amplitud de formato flotante.

¿No? Aunque utilicé mucho tiempo para organizar esto de una pieza aquí y allá.

Dos recurso útil para compartir: Lee este artículo para conocer los términos y conceptos básicos: https://www.mikeash.com/pyblog/friday-qa-2012-10-12-obtaining-and-interpreting-audio-data.html

Código de ejemplo: https://github.com/iluvcapra/JHWaveform puede copiar la mayor parte del código mencionado anteriormente de esta muestra directamente y se utiliza para su propio propósito .

Cuestiones relacionadas