[英]How force the program wait a Task and show Progress Bar to user?
我在程序中使用了Swing应用程序框架。 而且我有一些长期的工作。 我使用org.jdesktop.application.Task
。 在我接受这个项目之前,另一个程序员编写了两个任务(我不能向他询问编程问题)。 当执行任务时,用户会看到进度条,但未显示完成百分比,但是显示“等待”消息的用户无法在任务未结束时单击主窗口。 没事! 但是我找不到创建ProgressBars的地方。 可能是在某些xml文件或属性文件中描述的吗?
我还写了另一个任务,当它们运行时,我创建的进度条没有显示或显示不正确。 我阅读了有关ProgressBar和ProgressMonitor的信息,但这对我没有帮助。 程序在someTask.execute()之后继续运行,但是我希望它显示ProgressBar,ProgressMonitor或其他内容,并且用户无法单击主窗口,并且窗口将正确显示。 现在,当用户对其进行更改时,窗口具有黑色的“块”。
可能是我需要使用org.jdesktop.application.TaskMonitor
。 我尝试在这里使用它https://kenai.com/projects/bsaf/sources/main/content/other/bsaf_nb/src/examples/StatusBar.java?rev=235 ,但是我的主窗口显示不正确,我的不显示ProgressBar。
我需要在Task正在运行时程序等待它,但是用户可以看到ProgressBar,可以取消操作并且不能单击到主窗口。 我该怎么做?
这是我的代码:
public class A{
@Action(name = "ActionName", block = Task.BlockingScope.APPLICATION)
public RequestInfoTask requestInfo() {
RequestInfoTask task = new RequestInfoTask(Application.getInstance());
isSuccessedGetInfo=false;
task.addTaskListener(new TaskListener.Adapter<List<InfoDTO>, Void>() {
@Override
public void succeeded(TaskEvent<List<InfoDTO>> listTaskEvent) {
isSuccessedGetResources=true;
}
});
//Here I want to the program shows ProgressMonitor and user can not click to the main window.
//But small window with message "Progress..." is displayed for several seconds and disappear.
ProgressMonitor monitor = new ProgressMonitor(getMainView(), "Wait! Wait!", "I am working!", 0, 100);
int progress = 0;
monitor.setProgress(progress);
while(!task.isDone()){
monitor.setProgress(progress+=5);
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
}
}
monitor.setProgress(100);
//This code must run after "task" finishes.
if(isSuccessedGetInfo){
MyTask2 task2 = new MyTask2(Application.getInstance());
isSuccessedTask2=false;
task2.addTaskListener(new TaskListener.Adapter<Map<?,?>, Void>(){
@Override
public void succeeded(TaskEvent<Map<String, ICredential>> arg0) {
isSuccessedTask2=true;
}
});
//Do something with results of task2.
}
return task;
}
}
public class RequestInfoTask extends Task<List<InfoDTO>, Void> {
public RequestInfoTask(Application application) {
super(application);
}
@Override
protected List<InfoDTO> doInBackground() throws Exception {
List<InfoDTO> result = someLongerLastingMethod();
return result;
}
}
您的部分问题听起来像是由于未正确使用EDT而引起的 。 任何长时间运行的任务都需要在其自己的线程中启动,以保持GUI响应和重新绘制。
理想情况下,您将遵循MVC模式 。 在这种情况下,将进度条放置在视图中,将标记(指示任务是否应该仍在运行)放置在控件中,将长期运行的任务放置在模型中。
从那时起,如果您的模型定期检查是否应该停止(可能在良好的停止点),则可以重置所有内容。
这是MVC的示例:
import java.awt.BorderLayout;
import java.awt.event.*;
import javax.swing.*;
public class ProgressBarDemo{
public static class View extends JPanel{
Controller control;
public JProgressBar progressBar = new JProgressBar(0, 100);
JButton button = new JButton("Start Long Running Task");
public View(Controller controlIn){
super();
this.control = controlIn;
setLayout(new BorderLayout());
button.addActionListener(new ActionListener(){
@Override
public void actionPerformed(ActionEvent e) {
//Toggle between running or not
if(control.isRunning){
control.isRunning = false;
button.setText("Canceling...");
button.setEnabled(false);
} else{
control.isRunning = true;
button.setText("Cancel Long Running Task");
control.startTask();
}
}});
progressBar.setStringPainted(true);
add(progressBar);
add(button, BorderLayout.SOUTH);
}
}
//Communications gateway
public static class Controller{
View view = new View(this);
boolean isRunning = false;
public void updateProgress(final int progress){
SwingUtilities.invokeLater(new Runnable(){
@Override
public void run() {
view.progressBar.setValue(progress);
}});
}
public void reset(){
SwingUtilities.invokeLater(new Runnable(){
@Override
public void run() {
isRunning = false;
view.button.setText("Start Long Running Task");
view.progressBar.setValue(0);
view.button.setEnabled(true);
}});
}
public void startTask(){
LongRunningClass task = new LongRunningClass(this);
new Thread(task).start();
}
}
public static class LongRunningClass implements Runnable{
Controller control;
public LongRunningClass(Controller reference){
this.control = reference;
}
@Override
public void run() {
try {
for(int i = 0; i < 11; i++){
//Monitor the is running flag to see if it should still run
if(control.isRunning == false){
control.reset();
break;
}
control.updateProgress(i * 10);
Thread.sleep(3000);
}
control.reset();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
public static void main(String[] args) throws InterruptedException {
// Create and set up the window.
JFrame frame = new JFrame("LabelDemo");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
// Add content to the window.
frame.add(new Controller().view);
// Display the window.
frame.pack();
frame.setVisible(true);
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.