Quantcast
Channel: Notify PropertyChangeListener faster - Stack Overflow
Viewing all articles
Browse latest Browse all 2

Notify PropertyChangeListener faster

$
0
0

So I'm creating a JProgressBar that displays the progress of a CSV manipulation, where every line is read and checked if there are no null values in obligatory (NOT NULL) columns. For that, I've created a SwingWorker Task that handles converting the number of lines in the file to 100% on the maximum progress value, and adding up on the progress on the correct rate.

That's the SwingWorker:

public static class Task extends SwingWorker<String, Object> {

    private int counter;
    private double rate;

    public Task(int max) {
        // Adds the PropertyChangeListener to the ProgressBar
        addPropertyChangeListener(
             ViewHandler.getExportDialog().getProgressBar());
        rate = (float)100/max;
        setProgress(0);
        counter = 0;
    }

    /** Increments the progress in 1 times the rate based on maximum */
    public void step() {
        counter++;
        setProgress((int)Math.round(counter*rate));
    }

    @Override
    public String doInBackground() throws IOException {
        return null;
    }
    @Override
    public void done() {
      Toolkit.getDefaultToolkit().beep();
      System.out.println("Progress done.");
    }
}

My PropertyChangeListener, which is implemented by the JProgressBar wrapper:

@Override
    public void propertyChange(PropertyChangeEvent evt) {
        if ("progress".equals(evt.getPropertyName())) {
            progressBar.setIndeterminate(false);
            progressBar.setValue((Integer) evt.getNewValue());
        }
    }

Then, where I actually use it, I override the doInBackground() method with the processing I need, calling step() on every iteration.

    Task read = new Task(lines) {
        @Override
            public String doInBackground() throws IOException {
                while(content.hasNextValue()) {
                step();
                // Processing
            }
            return output.toString();
        }
   };
   read.execute();
   return read.get();

So what is happening: the processing works and succeeds, then done() is called, and just after that the propertyChange() registers two 'state' events and one 'progress' event, setting the ProgressBar's progress from 0% to 100%.

What is happening What I thought was happening (check Hovercraft's answer for clarification) is described in the JavaDocs:

Because PropertyChangeListeners are notified asynchronously on the Event Dispatch Thread multiple invocations to the setProgress method might occur before any PropertyChangeListeners are invoked. For performance purposes all these invocations are coalesced into one invocation with the last invocation argument only.

So, after all that, my question is: am I doing something wrong? If not, is there a way for me to make the Event Dispatch Thread notify the PropertyChangeListeners as the onProgress() happens, or at least from time to time?

Obs.: the processing I'm testing takes from 3~5s.


Viewing all articles
Browse latest Browse all 2

Latest Images

Trending Articles





Latest Images