javaswingswingworkeredt

Java - SwingWorker - problem in process() method


I am using javax.swing.SwingWorker for the first time.

I want to update a JLabel from the interim results published by the swing worker as follows:

publish("Published String");

Now to update the JLabel, I have coded the following:

process(List<String> chunks) {
    if (chunks.size() > 0) {
        String text = chunks.get(chunks.size() - 1);
        label.setText(text);
    }
}

The above code works but my problem(or to be more specific, my doubt) is as follows:

The above swing worker task is an annonymous inner class so it can access label field.

But what if I want to make the swing worker class a non-inner class. Should I need to pass label as an argument to the constructor of swing worker class so that the process() method can access.

Or Is there any other way?

What approach does other developer follow to update UI components from the swing worker class' result when the swing worker class is not an inner class?


Solution

  • But what if I want to make the swing worker class a non-inner class. Should I need to pass label as an argument to the constructor of swing worker class so that the process() method can access.

    That's perfectly fine. From the SwingWorker documentation:

    class PrimeNumbersTask extends 
        SwingWorker<List<Integer>, Integer> {
            PrimeNumbersTask(JTextArea textArea, int numbersToFind) { 
                //initialize 
            }
    
            @Override
            public List<Integer> doInBackground() {
                while (! enough && ! isCancelled()) {
                    number = nextPrimeNumber();
                    publish(number);
                    setProgress(100 * numbers.size() / numbersToFind);
                }
            }
            return numbers;
        }
    
        @Override
        protected void process(List<Integer> chunks) {
            for (int number : chunks) {
                textArea.append(number + "\n");
            }
        }
    }
    
    JTextArea textArea = new JTextArea();
    final JProgressBar progressBar = new JProgressBar(0, 100);
    PrimeNumbersTask task = new PrimeNumbersTask(textArea, N);
    task.addPropertyChangeListener(
        new PropertyChangeListener() {
            public  void propertyChange(PropertyChangeEvent evt) {
                if ("progress".equals(evt.getPropertyName())) {
                    progressBar.setValue((Integer)evt.getNewValue());
                }
            }
        });
    
    task.execute();
    

    Notice the constructor PrimeNumbersTask(JTextArea textArea, int numbersToFind). They pass the JTextArea to update.