2012-07-18 18 views
48

He escrito una pequeña aplicación de Java con fines de prueba que captura el sonido de un mezclador en ubuntu 12.04.Captura de sonido de Wine con TargetDataLine

El código funciona bien, puedo capturar el sonido de todas las aplicaciones a excepción de cualquier cosa que se ejecute en Wine.

Cada vez que comienzo mi programa, después de haber Vino comenzado, la llamada a targetDataLine.read() bloqueará siempre

cuando el vino no se está ejecutando en segundo plano, emite correctamente 0 cuando no hay entrada, o el número de bytes lea si hay entrada, como se esperaba.

Si inicio mi programa antes de iniciar Wine, el controlador de sonido no estará disponible dentro del vino.

He intentado utilizar tanto los mezcladores proporcionados por Alsa como el dispositivo predeterminado, el mismo resultado.

Me imagino que el vino bloquea de alguna manera a Alsa (por alguna razón), pero ¿por qué una simple llamada a TargetDataLine.read() hace que el sonido falle en Wine? mixerInfo[0] está predeterminado en mi sistema por cierto, y la aplicación, por supuesto, siempre se está ejecutando fuera de Wine utilizando el último JRE de Oracle (7).

private void readSound() 
{ 
    byte tempBuffer[] = new byte[10000]; 
    int cnt = 0; 
    Mixer.Info[] mixerInfo = AudioSystem.getMixerInfo(); 

    System.out.println("Available mixers:"); 
    for (int p = 0; p < mixerInfo.length; p++) 
     System.out.println(mixerInfo[p].getName()); 

    format = getAudioFormat(); 
    DataLine.Info dataLineInfo = new DataLine.Info(TargetDataLine.class, format); 
    Mixer mixer = AudioSystem.getMixer(mixerInfo[0]); 

    try 
    { 
     targetDataLine = (TargetDataLine) mixer.getLine(dataLineInfo); 
     targetDataLine.open(format); 
    } 
    catch(Exception e) 
    { 
     e.printStackTrace(); 
    } 
    targetDataLine.start(); 

    while (true) 
    { 
     i++; 
     cnt = targetDataLine.read(tempBuffer, 0, tempBuffer.length); 
     System.out.println("read " + cnt + " bytes:" + tempBuffer[i]);    
     calculateLevel(tempBuffer, 0, 200); 
     targetDataLine.flush(); 
     System.out.println(level); 
    } 
} 
+2

Puede proporcionar, en el mensaje, la salida del programa en ambos escenarios, cuando Wine se está ejecutando, y cuando Wine no se está ejecutando. –

+0

Creo que usar DataLine :: disponible podría ayudar con el bloqueo. – IceGlow

+2

Comprueba la configuración de Wine para ver cómo accede al audio. http://askubuntu.com/questions/77210/how-to-change-the-default-audio-in-wine-to-alsa-only – IceGlow

Respuesta

1

Haz uso del método AudioSystem.write(). Es mucho más fácil

targetDataLine.open(format); 
targetDataLine.start(); 
AudioInputStream ais=new AudioInputStream(targetDataLine); 
AudioFileFormat.Type fileformat=AudioFileFormat.Type.WAVE; 
/* 
Other Audio file formats supported: 
AudioFileFormat.Type.AU 
AudioFileFormat.Type.AIFF 
AudioFileFormat.Type.AIFC 
AudioFileFormat.Type.SND 
*/ 
File audoutputfile=new File('myfile'); 
//adjust extension according to AudioFileFormat 
AudioSystem.write(ais,fileformat, audoutputfile); 
+0

Oh. Solo noté la fecha de la pregunta ... –