updating a JProgressBar while processing

人走茶凉 提交于 2019-12-19 21:42:11

问题


I know the subject has already been seen on many Questions and has been answered, but still, I can't get trough it.

I just want to update a progressBar while extracting some stuff of a large xml file. I thought it was enough to have the time-consuming loop in a different thread but ?.. All I managed to get is the progressBar either not showed at all, or updated at the end, just before it's closed.

Instanced somewhere near the launch of the application, I have:

public class SomeClass {
    private SomeClass () {
        myXMLParser reader = new myXMLParser();
        CoolStuff fromXml = reader.readTheXml();
    }
}

while showing and updating a JDialog with a JProgressBar:

public class LoadingDialog extends JDialog {
    private JProgressBar progressBar;
    /* ... */
    public void progress() {
        progressBar.setValue(progressBar.getValue() + 1);
    }
}

So I have this myXMLParser:

public class myXMLParser {
    private LoadingDialog loadingDialog = new LoadingDialog();

    public CoolStuff readTheXml() {
        CoolStuff fromXml = new CoolStuff();
        while(manyIterations) {
            loadingDialog.progress();
            fromXml.add(some() + xml() + reading());
        }
        return fromXml;
    }
}

I have seen many things with SwingWorker and using PropertyChange events update the progressBar, but examples are always given all-in-one, with the processing and the progressbar within the same class, and with classes within classes, and since I begin in Java, I wasn't able to translate that to my situation.

Any help ?.. Any (not too obvious) advices ?

Edit: So thanks to btantlinger it worked like that:

public class SomeClass {
    private SomeClass () {
        myXMLParser reader = new myXMLParser();
        new Thread(new Runnable() {
            @Override
            public void run() {
                CoolStuff fromXml = reader.readTheXml();
            }
        }).start();
    }
}

public class LoadingDialog extends JDialog {
    private JProgressBar progressBar;
    /* ... */
    public void progress() {
        progressBar.setValue(progressBar.getValue() + 1);
    }
}

public class myXMLParser {
    private LoadingDialog loadingDialog = new LoadingDialog();

    public CoolStuff readTheXml() {
        CoolStuff fromXml = new CoolStuff();
        while(manyIterations) {
            SwingUtilities.invokeLater(new Runnable() {
                public void run() {
                    loadingDialog.progress();
                }
            });
            fromXml.add(some() + xml() + reading());
        }
        return fromXml;
    }
}

回答1:


You MUST update the JProgress bar on the Swing Event Dispatch Thread. You cannot modify Swing components on any other thread.

Your only other alternative would be to set the JProgress bar "indeterminate" before you start your thread where the progress bar will just go back and forth.

E.g

progBar.setIndeterminate(true);

See the SwingWorker javadoc: http://docs.oracle.com/javase/6/docs/api/javax/swing/SwingWorker.html

If you don't want to use the SwingWorker, another option is the SwingUtilities.invokeLater method

//inside your long running thread when you want to update a Swing component
SwingUtilities.invokeLater(new Runnable() {
    public void run() {

        //This will be called on the EDT
        progressBar.setValue(progressBar.getValue() + 1);


    }
});



回答2:


In addition to the code provided by @btantlinger, I found after testing that it required an additional line of code in order to update the progress bar on the UI thread while processing. See below.

   SwingUtilities.invokeLater(new Runnable() {
       public void run() {
       progressBar.setValue((int)percentage);
       //below code to update progress bar while running on thread
       progressBar.update(progressBar.getGraphics());}
     });   


来源:https://stackoverflow.com/questions/9578694/updating-a-jprogressbar-while-processing

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!