无法在jar文件中播放嵌入的声音

时间:2013-01-17 08:58:45

标签: java nullpointerexception embedded-resource javasound

我正在创建一个名为BatteryBeeper的个人用软件。它会提醒我在笔记本电脑充电的时候充电是我设置的提醒。

当电荷达到设定的阈值时,应该播放声音。

我看了一下答案:sound not playing in jar而我的AudioInputStream的构造类似于Jigar Joshi所提到的。

但是我得到一个空例外:

java.lang.NullPointerException
    at com.sun.media.sound.SoftMidiAudioFileReader.getAudioInputStream(Unknown Source)
    at javax.sound.sampled.AudioSystem.getAudioInputStream(Unknown Source)
    at demo.BatteryBeeper.setupSoundPlayback(BatteryBeeper.java:169)
    at demo.BatteryBeeper.<init>(BatteryBeeper.java:41)
    at demo.BatteryBeeper.main(BatteryBeeper.java:35)  

这是加载声音的代码:

public void setupSoundPlayback(){
        try{
            buzzer = AudioSystem.getClip();
            in = AudioSystem.getAudioInputStream(BatteryBeeper.class.
                    getResourceAsStream("sound/buzzer3_x.wav"));
            buzzer.open(in);
        }catch(Exception e){
            e.printStackTrace();
        }

    }  

以下是播放它的代码:

public void playSound(){
        buzzer.start();
    }  

导致问题的原因是什么?

其他

这是一个常见的Eclipse项目。 sound下有src个文件夹,其中包含wave文件

编辑

在AlexR的回答之后,我改变了路径并得到了一个新的例外:

javax.sound.sampled.UnsupportedAudioFileException: could not get audio input stream from input stream
    at javax.sound.sampled.AudioSystem.getAudioInputStream(Unknown Source)
    at demo.BatteryBeeper.setupSoundPlayback(BatteryBeeper.java:169)
    at demo.BatteryBeeper.<init>(BatteryBeeper.java:41)
    at demo.BatteryBeeper.main(BatteryBeeper.java:35)

2 个答案:

答案 0 :(得分:5)

问题不在于播放声音。您的问题是访问嵌入式资源。当您使用BatteryBeeper.class.getResourceAsStream("sound/buzzer3_x.wav")时,您尝试检索位于类BatteryBeeper所在的同一包中的资源。这意味着您的文件位于/demo/sound/buzzer3_x.wav。看来这是错的。如果您的文件确实在sound/buzzer3_x.wav中,请使用getResourceAsStream("/sound/buzzer3_x.wav")(注意路径中的前导斜杠)。

答案 1 :(得分:0)

如果您仍然收到消息“无法从InputStream获取AudioInputStream”,则问题很可能是InputStream阶段没有引发信息错误。

如果查看AudioSystem.getAudioInputStream(InputStream)的规范,您会看到输入流可能由于不支持Mark / Reset操作而失败,但由于某种原因,它会选择抛出其他错误消息!! < / p>

http://docs.oracle.com/javase/7/docs/api/javax/sound/sampled/AudioSystem.html#getAudioInputStream%28java.io.InputStream%29

更好的是,使用AudioSystem.getAudioInputStream(URL)形式,音频文件的可标记性不是问题,因为永远不会创建中间的InputStream。

http://docs.oracle.com/javase/7/docs/api/javax/sound/sampled/AudioSystem.html#getAudioInputStream%28java.net.URL%29

URL表格还具有与嵌入在Jar中的文件配合良好的额外好处。当然,您仍需提供正确的地址。