Reputation: 1453
private void StartActionPerformed(java.awt.event.ActionEvent evt) {
Queue queue=new Queue();
int target=Integer.parseInt(Target.getText());
String path=Path.getText();
final Producer p=new Producer(queue, target);
Consumer c=new Consumer(queue);
p.start();
c.start();
while(p.finish !=true)
{
Runnable r = new Runnable() {
public void run() {
ProgressPrecent.setValue(Producer.ProgressPercent);
}
};
if(EventQueue.isDispatchThread()) {
r.run();
}
else {
EventQueue.invokeLater(r);
}
}
}
I have two classes that have a shared Queue. one of them is Producer that produces till a target other one consume those elements. all of two extends Thread. I want to display the progress percent to the user, but it freeze my GUI so what should I do?
Upvotes: 3
Views: 12670
Reputation: 8560
I think you will have to put the whole while loop into a thread. Otherwise the loop will block your ActionEvent and thus freezes the UI.
Something like:
new Thread(){
public void run(){
while(!p.finish){
SwingUtilities.invokeLater(new Runnable(){
public void run(){
ProgressPrecent.setValue(Producer.ProgressPercent);
}
});
try{
Thread.sleep(100);
}catch(...){}
}
}
}.start();
Upvotes: 6
Reputation: 109813
Worker Threads
by default never to invoked EventDispatchThread
, you have issue with Concurency in Swing
all updates to Swing GUI must be done on EDT
Runnable
could be proper way but ProgressPrecent.setValue(Producer.ProgressPercent);
must be wrapped in invokeLater
code
SwingUtilities.invokeLater(new Runnable(){
public void run(){
ProgressPrecent.setValue(Producer.ProgressPercent);
}
});
code lines
if(EventQueue.isDispatchThread()) {
r.run();
}
Workers Thread
by defaut never ever to invoke EDT, then doesn't matter if is started from EDT, nor tested for isDispatchThread()
doesn't make me some sence
never ever, don't to use Thread.sleep(int
) inside Swing Listeners
, because caused freeze Swing GUI too
I think you can to use SwingWorker for this job too
Upvotes: 6