0

I was building a small test tool with Java Swing using Netbeans IDE.

I am trying to update a label, which is somehow not getting 'repainted'/'refreshed'. I looked into a couple of similar questions on SO but was not able to resolve my problem.

private void excelFileChooserActionPerformed(java.awt.event.ActionEvent evt)
{
    if(!JFileChooser.CANCEL_SELECTION.equals(evt.getActionCommand()))
    {
        String selectedFile = excelFileChooser.getSelectedFile().getAbsolutePath();
        loaderLabel.setText("Please Wait..");
        try {
            //This is sort of a blocking call, i.e. DB calls will be made (in the same thread. It takes about 2-3 seconds)
            processFile(selectedFile);
            loaderLabel.setText("Done..");
            missingTransactionsPanel.setVisible(true);
        }
        catch(Exception e) {
            System.out.println(e.getMessage());
            loaderLabel.setText("Failed..");
        }
    }
}

loaderLabel is a JLabel and the layout used is AbsoluteLayout.

So, my problem is "Please Wait..." is never shown. Although call to the method processFile takes about 2-3 seconds, "Please Wait..." is never shown. However, "Done..."/"Failed..." are shown.

If I add a popup (JOptionPane) before the call to processFile, "Please Wait.." is shown. I am not able to clearly understand why this is happening.

Is there a "good practice" that I should follow before a heavy method call? Do I need to call an explicit repaint/refresh/revalidate?

4

2 に答える 2

3

You need to call

 processFile(selectedFile);

in another thread (not in the AWT thread). To do so you can do something like this :

Thread t = new Thread(){
   public void run(){
       processFile(selectedFile);
       // now you need to refresh the UI... it must be done in the UI thread
       // to do so use "SwingUtilities.invokeLater"
       SwingUtilities.invokeLater(new Runnable(){
          public void run(){
              loaderLabel.setText("Done..");
              missingTransactionsPanel.setVisible(true);
          }
          }
       )
   }
};
t.start();

Please not that I didn't work with swing for a long time, so there may be some syntax issues with this code.

于 2012-12-20T12:15:46.983 に答える
2

Have you tried dispatching the call to the EDT with SwingUtilities.invokeLater() ?

http://www.javamex.com/tutorials/threads/invokelater.shtml

于 2012-12-20T12:04:45.370 に答える