2016-12-30 64 views
0

使用AudioInputStream播放示例時出現了一個奇怪的問題。 三種情形:AudioInputStream:在macOS和8位wav文件中使用Java 1.7和1.8播放噪聲

  • MACOS,JAVA 1.6:完美的作品
  • 取勝,JAVA 1.8:完美的作品
  • MACOS,JAVA 1.8:重流行聽起來

我爲測試創建的代碼是直截了當的。樣品是乾淨的(開始和結束時過零)。第一個彈出窗口已經在soundLine.start()上完全獨立於樣本。最後一個彈出發生在soundLine.close()這個樣本已經完成幾秒鐘之後。我在代碼中添加了一些延遲,因此很容易識別代碼在哪個位置。

我創建演示視頻裏可以聽到發生了什麼:

正如你可以看到(聽到)的唯一問題就是Java 1.8在MacOS下。我也用相同的結果測試了Java 1.7。只有在1.6播放是正確的。 彈出的聲音聽起來很奇怪,因爲聲音已經被MBP的內部微記錄下來了。這是一種典型的流行音,當您打開/關閉壞設計的功放時,您可以聽到這種聲音。

附錄:問題似乎只出現在8位wav文件中。 16位工作正常。

附錄:中列爲錯誤的平均時間:http://bugs.java.com/bugdatabase/view_bug.do?bug_id=JDK-8172164

任何人都可以重現該問題?任何想法是什麼原因?我目前假設Java中存在一個錯誤。

import java.io.File; 

import javax.sound.sampled.AudioFormat; 
import javax.sound.sampled.AudioInputStream; 
import javax.sound.sampled.AudioSystem; 
import javax.sound.sampled.DataLine; 
import javax.sound.sampled.SourceDataLine; 

public class Soundtest 
{ 
    protected File sample=new File("user1.wav"); 

    public Soundtest() 
    {     
     SourceDataLine soundLine = null; 
     int BUFFER_SIZE = 1024; 

     System.out.println("AudioInputStream test with "+System.getProperty("java.version")+" on "+System.getProperty("os.name")); 
     // Set up an audio input stream piped from the sound file. 
     try 
     {  

      AudioInputStream audioInputStream = AudioSystem.getAudioInputStream(sample); 
      AudioFormat audioFormat = audioInputStream.getFormat(); 
      DataLine.Info info = new DataLine.Info(SourceDataLine.class, audioFormat); 

      //Soundline ist noch nicht angelegt -> angelegen. 
      if(soundLine==null) 
      { 
       soundLine = (SourceDataLine) AudioSystem.getLine(info); 
       soundLine.open(audioFormat); 
       soundLine.start(); 
      } 
      System.out.println("Started"); 
      Thread.sleep(2000); 

      System.out.println("Playing"); 
      int nBytesRead = 0; 
      byte[] sampledData = new byte[BUFFER_SIZE]; 
      while (nBytesRead != -1) 
      { 
       nBytesRead = audioInputStream.read(sampledData, 0, sampledData.length); 
       if (nBytesRead >= 0) 
       {       
        soundLine.write(sampledData, 0, nBytesRead);       
       }        
      }   
      Thread.sleep(2000); 
      System.out.println("Draining"); 
      soundLine.drain(); 

      Thread.sleep(2000); 
      System.out.println("Closing"); 
      soundLine.close(); 
     }   
     catch (Exception e) 
     { 
      e.printStackTrace(); 
     } 

    } 

    public static void main(String[] args) 
    {   
     new Soundtest(); 
    } 
} 
+0

這在我的Mac上正常工作。 –

+0

謝謝!我發現它只發生在8位wav文件中。你能證實嗎? –

+0

是的,它似乎只有8位 –

回答

0

你可以告訴我的代碼沒有問題。我已經在macOS Sierra 10.12.2上使用Java 1.8.0_60自己運行它,並且耳機沒有彈出聲音,從內置揚聲器出來時也沒有彈出。我現在能想到的唯一原因是,由於某種原因,Java 1.8不喜歡你使用的音頻接口或媒體,如果它與Mac上的通用揚聲器不同。甚至有可能音頻緩衝在1.8版本中完全不同。嘗試提高緩衝區大小以防止溢出(這可能是導致彈出的原因)。

+0

謝謝!我不認爲它是硬件。同樣的MBP,老MBA和我的iMac。緩衝區大小沒有影響。已經測試過它。除此之外,彈出窗口在數據流輸入之前發生。我可以減少代碼並在soundLine.start()之後將其剪切,以引發第一次彈出。 –

+1

你給了我一個主意!它只發生在8位wav文件中! –

+0

@ Dark.Rider真棒很高興你能弄明白! – Jonah