【问题标题】:Capturing sound from Wine with TargetDataLine使用 TargetDataLine 从 Wine 中捕获声音
【发布时间】:2012-07-18 00:48:59
【问题描述】:

我为测试目的编写了一个小型 Java 应用程序,它从 ubuntu 12.04 上的混音器中捕获声音。

代码运行良好,我可以捕捉所有应用程序的声音,除了在 Wine 下运行的任何应用程序。

每当我启动程序时,在启动 Wine 后,对 targetDataLine.read() 的调用将永远阻塞

当 Wine 不在后台运行时,它会在没有输入时正确输出 0,或者在有输入时正确输出读取的字节数,如预期的那样。

如果我在启动 Wine 之前启动我的程序,声音驱动程序将在 wine 中不可用。

我尝试过使用 Alsa 提供的混音器以及默认设备,结果相同。

我可以想象 wine 以某种方式锁定了 Alsa(无论出于何种原因),但是为什么对 TargetDataLine.read() 的简单调用会导致 Wine 中的声音失败? mixerInfo[0] 是我系统的默认设置 btw,当然,应用程序总是使用 oracle 的最新 JRE (7) 在 Wine 之外运行。

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);
   }
}

【问题讨论】:

  • 您能否在帖子中提供程序在两种情况下的输出,当 Wine 运行时和 Wine 未运行时。
  • 我认为使用 DataLine::available 可能有助于阻止。
  • 检查 Wine 的配置,看看它是如何访问音频的。 askubuntu.com/questions/77210/…

标签: java linux audio alsa wine


【解决方案1】:

利用 AudioSystem.write() 方法。容易多了

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);

【讨论】:

    猜你喜欢
    • 2014-05-02
    • 1970-01-01
    • 2015-03-15
    • 2013-06-28
    • 2011-03-14
    • 2015-10-22
    • 1970-01-01
    • 2016-03-18
    • 1970-01-01
    相关资源
    最近更新 更多