10

SwingWorker用于以下目的:

  • 用于在不同线程中运行长时间运行的任务,以防止 GUI 无响应
  • 用于通过方法在任务结束时使用长时间运行的任务产生的结果更新 GUI done()
  • publish()用于在和process()方法的帮助下使用任务生成和发布的中间结果不时更新 GUI 。

SwingUtilities.invokeLater()可以按如下方式执行上述任务:

  • SwingWorker.execute()我们可以执行,而不是从 EDT执行方法,ExecutorService.submit(new MyRunnable())因为它还会创建另一个可以执行长时间运行的任务的线程。
  • 为了在任务结束时更新 GUI,我们可以将代码(用done()case1 的方法编写)SwingUtilites.invokeLater(new RunnableToExecuteDoneMethodCode())放在任务结束时。
  • 为了在任务中间更新GUI,我们可以将代码(写在process()case1的方法中)SwingUtilites.invokeLater(new RunnableToExecuteProcessMethodCode())放在我们调用case1方法的地方publish()

我问这个问题是因为问题中指定的问题Java - SwingWorker - 我们可以从其他 SwingWorker 而不是 EDT 调用一个 SwingWorker可以解决SwingUtilities.invokeLater()但不能解决SwingWorker

4

2 回答 2

7

SwingWorker是一个辅助类——不是你需要使用它,而是使用它比手工做同样的工作要简单和清晰得多。(它也使检查进度更容易。)请注意,它是在第 6 版中添加的——在此之前,有些人使用了 Swing 教程中定义的更简单的类,或者执行了与您提到的类似的步骤。

于 2010-05-13T18:59:41.940 回答
1

1.6+ SwingWorker 类的一个重要特性是 doInBackground() 和 done() 之间的 EDT(Event Dispatch Thread) 区别。您应该将 doInBackground() 视为 doWorkOutsideEDT(),将 done() 视为 doWorkInsideEDT()。运行此说明性示例以查看不同之处。

    System.out.println("TID=" + Thread.currentThread().getId() + " (main)");
    final SwingWorker<String, String> x = new SwingWorker<String, String>() {
        @Override
        protected String doInBackground() throws Exception {
            final long tid = Thread.currentThread().getId();
            System.out.println("");
            System.out.println("TID=" + tid + " doInBackground() isEventDispatchThread=" + SwingUtilities.isEventDispatchThread());
            System.out.println("Long running code goes here.");
            return "";
        }

        @Override
        protected void done() {
            final long tid = Thread.currentThread().getId();
            System.out.println("");
            System.out.println("TID=" + tid + "          done() isEventDispatchThread=" + SwingUtilities.isEventDispatchThread());
            System.out.println("GUI updates/changes go here.");
        }
    };
    x.execute();
    x.get();

输出:

TID=1 (main)

TID=9 doInBackground() isEventDispatchThread=false
Long running code goes here.

TID=16          done() isEventDispatchThread=true
GUI updates/changes go here.
于 2014-05-16T14:03:44.243 回答