0

我在创建设置为不确定的JProgressBar时遇到问题。 下面的代码是我实现JProgressBar的,被称为/从另一个类构成:JProgressBar不确定线程​​

public class Progress implements Runnable 
{ 
    private JFrame frameProgress; 
    private JProgressBar progressBar; 

    public Progress(String title, String message) 
    { 
    try 
    { 
     UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); 
    } 
    catch (Exception e) 
    { 
     GlobalVariables.LOGGING_logger.error("Error instatiating progress bar.", 
      e); 
    } 

    UIManager.put("ProgressBar.selectionForeground", Color.black); 
    UIManager.put("ProgressBar.selectionBackground", Color.black); 

    this.frameProgress = new JFrame(title); 
    this.frameProgress.setIconImage(GlobalVariables.GUI_icon.getImage()); 
    this.frameProgress.setSize(300, 60); 
    this.frameProgress.setLocation(16, 16); 
    this.progressBar = new JProgressBar(); 
    this.progressBar.setStringPainted(true); 
    this.progressBar.setString(message); 
    this.progressBar.setIndeterminate(true); 
    this.frameProgress.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
    this.frameProgress.add(this.progressBar); 
    this.frameProgress.setResizable(false); 
    this.frameProgress.setVisible(true); 
    } 

    public void start() 
    { 
    new Thread(this).start(); 
    } 

    public void close() 
    { 
    this.frameProgress.dispose(); 
    this.frameProgress = null; 
    this.progressBar = null; 
    } 

    @Override 
    public void run() 
    { 
    SwingUtilities.invokeLater(new Runnable() 
    { 
     public void run() 
     { 
     // do nothing, because progress bar is indeterminate 
     } 
    }); 
    } 
} 

此JProgressBar的调用者是下面的代码片段:

Progress p = new Progress("bla", "blub"); 
    p.start(); 
    boolean successfull = xmlWriter.writeCommonSettingsFromGUI(this); 
    p.close(); 

,现在我想同时, xmlWriter.writeCommonSettingsFromGUI(this);正在做某事,JProgressBar显示给用户,并且正在运行该算法。

我该如何做到这一点?我对许多其他论坛的线程和搜索知之甚少,但对于我的问题我没有找到任何答案。

请帮助我,谢谢你提前;)

编辑: 进展的JFrame打开了,没有内容那段时间,算法运行。

+0

你能描述什么对你当前的代码不起作用吗? – 2013-04-11 08:07:44

+0

进度条不显示,我得到一个异常:线程“AWT-EventQueue-0”中的异常java.lang.NullPointerException \t at de.Progress $ 1.run(Progress。的java:63) \t在java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:251) \t在java.awt.EventQueue.dispatchEventImpl(EventQueue.java:727) \t在java.awt.EventQueue.access $ 200(EventQueue.java:103))... – 2013-04-11 08:08:59

+0

好吧...没有更多的错误....但:如果我启动线程,它打开Progress JFrame,但没有内容(没有JProgressBar) ... – 2013-04-11 08:15:33

回答

3

您可能正面临着Swing的并发问题。假设在EDT(Event Dispatching Thread)上运行以下代码:

Progress p = new Progress("bla", "blub"); 

最终,这将打开一个带有进度条的JFrame。

  • 我会考虑使用一个JDialog代替JFrame
  • 我不会强迫JFrame的大小,而是叫pack()

然后,在EDT仍在运行(并因此阻断所有的用户界面事件,如重画,鼠标点击等...),你打电话p.start()开始new Thread()这将调用run()其本身称为

SwingUtilities.invokeLater(new Runnable() 
{ 
    public void run() 
    { 
    // do nothing, because progress bar is indeterminate 
    } 
}); 

除了在EventQueue上推送一个附加事件,它基本上不会做任何事情,它会在所有当前未决事件之后运行。此事件将运行...“没有”,因为你的Runnable只是空的。新的Thread几乎立即死亡。所以这些代码都是没用的。

在美国东部时间仍然追求,你打电话boolean successfull = xmlWriter.writeCommonSettingsFromGUI(this);(顺便说一句,“成功”结束只有一个'l')。这将继续阻止EDT,防止重新发生,并防止自行绘制。最终你会放弃JFrame,但由于所有代码都在EDT上运行,用户将看不到很多进度条,并且界面看起来会被冻结。

考虑阅读Swing tag wiki(特别是最后一部分有3个重要链接)。

使用SwingWorker应该可以帮到你。