为什么我的Swingworker第一次取消它的线程?

时间:2011-02-25 21:59:55

标签: java multithreading swingworker

我有一个Swingworker,我有时需要取消。如果我执行然后取消,它按预期工作。如果我运行该Swingworker的新实例然后尝试取消它,则调用cancel函数,它返回true,但“doInBackground”方法完全运行而不被取消。完全,我的意思是Swingworker线程运行的函数中的while循环完成(我只能在第一次取消)。

如果我明白问题,请告诉我,这是一种奇怪的行为,我无法弄明白。

这是我的代码:

protected void firePlayButtonPlotWorker() {
    /*Cancel any previous plotWorker threads that may be running. The user might click the play
     * button again, so we ignore that if the thread isn't finished.*/
    if(plotWorker != null && !plotWorker.isDone())
    {
        System.err.println("Cancelling plot thread");
        plotWorker.cancel(true);
    }


    /*Create a SwingWorker so that the computation is not done on the Event Dispatch Thread*/
    plotWorker = new SwingWorker<Void, Void>() 
    {
        @Override
        public Void doInBackground() 
        {

            System.err.println("Plot Swing Worker Thread starting");
            playAudio(sceneManager.getScenes()); //Computation that requires an asynchronous while loop
            System.err.println("Plot Swing Worker Thread ended");
            return null;
        }

        @Override
        public void done() 
        {
            plotWorker = null;
        }
    };


    plotWorker.execute();
}

public void handleAudioEvent(AudioState audioState)
{
    switch (audioState)
    {
    case PLAY:
        firePlayButtonPlotWorker();
        break;
    case PAUSE:
        if(plotWorker != null)
        {
            boolean cancelBool = plotWorker.cancel(true);
            System.out.println("Cancelled? " + cancelBool);
        }
        break;
    case STOP:
        if(plotWorker != null)
        {
            plotWorker.cancel(true);
        }
        audioPlayerMarkerBean.setMarkerLocation(0);
        double[] coord = {0.0, 0.0};
        marker.drawMarker(coord);
        break;
    }
}

1 个答案:

答案 0 :(得分:2)

使用true作为参数调用cancel将使用Thread.interrupt方法中断线程。

因此,如果您的线程正在等待,休眠或加入,则会抛出InterruptedException。 否则,将设置线程的中断状态。

如果吞下InterruptedException,线程将一直持续到结束。如果线程在被中断时正在运行(即不等待,休眠或加入),它也将继续运行。您必须定期检查后台任务中线程的中断状态(使用Thread.currentThread.isInterrupted()),并在返回true时立即停止执行。