簡體   English   中英

為什么當我停止從按鈕動作偵聽器播放音頻時出現此錯誤(音頻從線程運行)整個代碼在里面

[英]why i get this error when i stop playing an audio from button action listener(the audio ran from Thread)the whole code is inside

我在我的線程中運行了一個音頻文件(這個線程是一個警報)這是線程代碼:

public void waitForAlarm() {
    waiter = new Thread(new Runnable() {
        public void run() {
            while (Thread.currentThread() == waiter) {
                Calendar d = Calendar.getInstance();
                if (getAlarmHours() == d.get(Calendar.HOUR_OF_DAY)) {
                    if (getAlarmMinutes() == d.get(Calendar.MINUTE)) {
                        UserInterface.setAlarmText("No Alarms");
                        try {
                            AudioPlayer playSound = new AudioPlayer(
                                    UserInterface.getSoundFile());//return the sound choosen by user
                            playSound.play();//play the choosen sound
                            waiter.wait();
                        } catch (NoPlayerException e) {
                            // TODO Auto-generated catch block
                            e.printStackTrace();
                        } catch (CannotRealizeException e) {
                            // TODO Auto-generated catch block
                            e.printStackTrace();
                        } catch (IOException e) {
                            // TODO Auto-generated catch block
                            e.printStackTrace();
                        } catch (InterruptedException e) {
                            // TODO Auto-generated catch block
                            e.printStackTrace();
                        } finally {
                            break;
                        }

                    }

                }

            }
        }
    });

    waiter.start();
}

這是按鈕動作偵聽器方法:

stopSound.addActionListener(new ActionListener() {

        public void actionPerformed(ActionEvent e) {
            AudioPlayer player = new AudioPlayer();
            player.stop();//call stop method(this method will stop & close the audio File)
        }
    });

最后,這是我單擊該按鈕時遇到的異常:

Exception in thread "AWT-EventQueue-0" java.lang.NullPointerException
at AudioPlayer.stop(AudioPlayer.java:34)
at UserInterface$4.actionPerformed(UserInterface.java:214)
at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2018)
at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2341)
at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:402)
at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:259)
at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:252)
at java.awt.Component.processMouseEvent(Component.java:6504)
at javax.swing.JComponent.processMouseEvent(JComponent.java:3321)
at java.awt.Component.processEvent(Component.java:6269)
at java.awt.Container.processEvent(Container.java:2229)
at java.awt.Component.dispatchEventImpl(Component.java:4860)
at java.awt.Container.dispatchEventImpl(Container.java:2287)
at java.awt.Component.dispatchEvent(Component.java:4686)
at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4832)
at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4492)
at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4422)
at java.awt.Container.dispatchEventImpl(Container.java:2273)
at java.awt.Window.dispatchEventImpl(Window.java:2713)
at java.awt.Component.dispatchEvent(Component.java:4686)
at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:707)
at java.awt.EventQueue.access$000(EventQueue.java:101)
at java.awt.EventQueue$3.run(EventQueue.java:666)
at java.awt.EventQueue$3.run(EventQueue.java:664)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:87)
at java.awt.EventQueue$4.run(EventQueue.java:680)
at java.awt.EventQueue$4.run(EventQueue.java:678)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.awt.EventQueue.dispatchEvent(EventQueue.java:677)
at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:211)
at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:128)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:117)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:113)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:105)
at java.awt.EventDispatchThread.run(EventDispatchThread.java:90)

更多信息:

- 有一個顯示當前時間的線程

-i 使用此代碼來初始化程序SwingUtilities.invokeLater(new Runnable()

- 這些是 AudioPlayer class 中使用的導入

import javax.media.CannotRealizeException; import javax.media.Manager; import javax.media.NoPlayerException; import javax.media.Player;

這段代碼看起來不應該做任何事情,特別是不應該停止任何播放音頻:

stopSound.addActionListener(new ActionListener() {

    public void actionPerformed(ActionEvent e) {
        AudioPlayer player = new AudioPlayer();
        player.stop();
    }
});

原因是您正在此偵聽器中創建一個新的 AudioPlayer,它似乎與任何其他 AudioPlayer object 完全無關,包括當前正在播放警報的 AudioPlayer object。

這是您當前正在播放的 AudioPlayer:

public void waitForAlarm() {
    waiter = new Thread(new Runnable() {
        public void run() {
            while (Thread.currentThread() == waiter) {
                Calendar d = Calendar.getInstance();
                if (getAlarmHours() == d.get(Calendar.HOUR_OF_DAY)) {
                    if (getAlarmMinutes() == d.get(Calendar.MINUTE)) {
                        UserInterface.setAlarmText("No Alarms");
                        try {
                            // **** here ****
                            AudioPlayer playSound = new AudioPlayer(
                                    UserInterface.getSoundFile());
                            //..
                        } catch .... etc..    
                    }
                }    
            }
        }
    });   
    waiter.start();

在當前播放的 AudioPlayer object 上調用 stop 比在監聽器中創建的虛擬 AudioPlayer object 上調用更有意義。 為了獲得對當前正在播放的 AudioPlayer object 的引用,您需要將其聲明為 class 字段,而不是埋在方法和 try 塊中。 然后,如果您想停止它,請檢查它是否不是 null,如果可以,請在其上調用 stop。

我要在這里在黑暗中刺傷..

您似乎還沒有完全掌握面向 object 的編程。 你聲明一個 AudioPlayer 來啟動你的聲音文件,然后你創建一個的 AudioPlayer 並在它上面調用 stop。 所以現在你有 AudioPlayer A 播放它的聲音文件,而 AudioPlayer B 沒有聲音文件。 AudioPlayer B 嘗試停止播放不存在的文件。 這可能是您的 NullPointerException 的來源。

如果您想讓它按原樣工作,請將 AudioPlayer 的聲音文件變量更改為static 這是一個可怕的想法,不要這樣做。

更好的想法是將您在 waitForAlarm 方法中創建的 AudioPlayer 保存在一個變量中,稍后按下按鈕時可以在您的 actionPerformed 方法中訪問該變量。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM