• ベストアンサー
※ ChatGPTを利用し、要約された質問です(原文:進捗バーが更新されません。)

進捗バーが更新されない問題の修正方法

このQ&Aのポイント
  • プログレスバーの進捗状況が更新されない問題について、修正方法を説明します。
  • タイマーを使用せずにプログレスバーの進捗を自動的に更新する方法を紹介します。
  • サンプルコードを修正して、プログレスバーの進捗状況を正しく表示するようにします。

質問者が選んだベストアンサー

  • ベストアンサー
  • _ranco_
  • ベストアンサー率58% (126/214)
回答No.1

JavaのGUIはシングルスレッドなので、ほかの長時間タスクとパラレルに動作(画面更新)するためには、長時間タスクを別スレッドとして動かし、その中でGUIタスクはGUIのスレッド(EDT,イベントディスパッチスレッド)に登録してやる必要があります。JDK 1.6以降は、そのためにSwingWorkerクラスを使います。下記のコードは、SwingWorker以前の古典的なやり方です。 -------------------------------------------------- import javax.swing.*; import java.awt.*; import java.awt.event.*; public class SampleProgressBar extends JFrame implements ActionListener {  private static final long serialVersionUID = 1L;  private JPanel jContentPane = null;  JButton startButton;  JButton stopButton;  JProgressBar bar;  JLabel label;  int i;  boolean go;  public void actionPerformed(ActionEvent arg0) {   String cmd = arg0.getActionCommand();   if (cmd.equals("start")){    go = true;    startButton.setEnabled(false);    stopButton.setEnabled(true);    Thread t = new Thread(new Runnable(){     public void run(){      for (i = 0; i< 20000; i++ ){       SwingUtilities.invokeLater(new Runnable(){        public void run(){         label.setText(i + " count");         bar.setValue(i);         int per = (int)(bar.getPercentComplete() * 100);         bar.setString(per + "% 完了");        }       });       try {        Thread.sleep(1);       }       catch(InterruptedException err) {        err.printStackTrace();       }       if (!go){        break;       }      }     }    });    t.start();   }   else if (cmd.equals("stop")){    startButton.setEnabled(true);    stopButton.setEnabled(false);    go = false;   }  }  public static void main(String[] args) {   SampleProgressBar frame = new SampleProgressBar();   frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);   frame.setBounds(10, 10, 300, 200);   frame.setTitle("Sample");   frame.setVisible(true);  }  public SampleProgressBar() {   super();   initialize();  }  private void initialize() {   this.setSize(300, 200);   this.setContentPane(getJContentPane());   this.setTitle("JFrame");   label = new JLabel("Not Start");   JPanel labelPanel = new JPanel();   labelPanel.add(label);   startButton = new JButton("start");   startButton.addActionListener(this);   startButton.setActionCommand("start");   stopButton = new JButton("stop");   stopButton.addActionListener(this);   stopButton.setActionCommand("stop");   stopButton.setEnabled(false);   JPanel buttonPanel = new JPanel();   buttonPanel.add(startButton);   buttonPanel.add(stopButton);   bar = new JProgressBar(0, 20000);   bar.setStringPainted(true);   bar.setString("");   bar.setValue(0);   JPanel barPanel = new JPanel();   barPanel.add(bar);   getContentPane().add(labelPanel, BorderLayout.PAGE_START);   getContentPane().add(buttonPanel, BorderLayout.PAGE_END);   getContentPane().add(barPanel, BorderLayout.CENTER);  }  private JPanel getJContentPane() {   if (jContentPane == null) {    jContentPane = new JPanel();    jContentPane.setLayout(new BorderLayout());   }   return jContentPane;  } } ------------------------------------------

Zepetto
質問者

補足

ありがとうございます。 SwingWorker なんてものがあるんですね。 サンプルなどをちょっと触ってみたので こちらを使用してみたいと思っています。 それ以前のやり方についても参考になりました。 ありがとうございました。

その他の回答 (1)

  • _ranco_
  • ベストアンサー率58% (126/214)
回答No.2

まだこのスレッドは締め切られていないようなので、SwingWorkerを使う超簡単なやつをご紹介しておきましょう。まあ、元々、SwingWorkerを使うのはもったいないようなプログラムですが(笑)。 ---------------------------------------------------- import javax.swing.*; import java.beans.*; import java.awt.*; import java.awt.event.*; import java.util.logging.*; public class SampleProgressBar2 extends JFrame implements ActionListener {  private static final long serialVersionUID = 1L;  private JPanel jContentPane = null;  JButton startButton;  JButton stopButton;  JProgressBar bar;  JLabel label;  int i;  Counting counting;  public void actionPerformed(ActionEvent arg0) {   String cmd = arg0.getActionCommand();   if (cmd.equals("start")){    startButton.setEnabled(false);    stopButton.setEnabled(true);    counting = new Counting();    counting.addPropertyChangeListener(new PropertyChangeListener(){     public void propertyChange(PropertyChangeEvent e) {      if ("c".equals(e.getPropertyName())) {       i = (Integer)e.getNewValue();       label.setText(i + " count");       bar.setValue(i);       // 以下はSwingWorkerのprogressプロパティをそのまま利用してもよい       int per = (int)(bar.getPercentComplete() * 100);       bar.setString(per + "% 完了");      }     }    });    counting.execute();   }   else if (cmd.equals("stop")){    startButton.setEnabled(true);    stopButton.setEnabled(false);    counting.cancel(true);   }  }  public static void main(String[] args) {   SampleProgressBar2 frame = new SampleProgressBar2();   frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);   frame.setBounds(10, 10, 300, 200);   frame.setTitle("Sample2");   frame.setVisible(true);  }  public SampleProgressBar2() {   super();   initialize();  }  private void initialize() {   this.setSize(300, 200);   this.setContentPane(getJContentPane());   this.setTitle("JFrame");   label = new JLabel("Not Start");   JPanel labelPanel = new JPanel();   labelPanel.add(label);   startButton = new JButton("start");   startButton.addActionListener(this);   startButton.setActionCommand("start");   stopButton = new JButton("stop");   stopButton.addActionListener(this);   stopButton.setActionCommand("stop");   stopButton.setEnabled(false);   JPanel buttonPanel = new JPanel();   buttonPanel.add(startButton);   buttonPanel.add(stopButton);   bar = new JProgressBar(0, 20000);   bar.setStringPainted(true);   bar.setString("");   bar.setValue(0);   JPanel barPanel = new JPanel();   barPanel.add(bar);   getContentPane().add(labelPanel, BorderLayout.PAGE_START);   getContentPane().add(buttonPanel, BorderLayout.PAGE_END);   getContentPane().add(barPanel, BorderLayout.CENTER);  }  private JPanel getJContentPane() {   if (jContentPane == null) {    jContentPane = new JPanel();    jContentPane.setLayout(new BorderLayout());   }   return jContentPane;  } } class Counting extends SwingWorker<Object, Integer>{  Logger logger;  public Counting(){   logger = Logger.getAnonymousLogger();  }  public Object doInBackground() {   int c = 0;   while (! isCancelled() && ++c <= 20000) {    firePropertyChange("c", c - 1, c);    try{     Thread.sleep(1);    }    catch (InterruptedException ie){     logger.info(ie.toString());    }   }   return null;  } } ---------------------------------------

Zepetto
質問者

補足

ありがとうございます! Java による開発で進めてきまして 一応、サンプル版としては作業終えました。 このプログレスバーについては まだ組み込めてないので締め切ってないのです。 もしかしたら言語を変更するという話しもありまして。。。

関連するQ&A