我正在开发桌面GUI应用程序。我目前正在使用Swing,但我希望将来能够将它移植到JavaFX或Android。
目前,我正在努力实现一个后台任务类,它将是" UI不可知的":目标是能够从应用程序的核心软件包中提交后台任务(不是取决于特定的GUI)并观察任务的进度,如果有GUI(使用GUI特定的进度条等)。
Swing有SwingWorker<T, V>
(link),JavaFX有Task<V>
(link),Android有AsyncTask<Params, Progress, Result>
({{3} })。它们都有相同的用途,实际上也有类似的API。
此界面为后台任务提供了必要的功能,实际上可以在所有提到的工具包中找到。
public interface BackgroundTask<Result, PartialResult> {
/**
* This is where the background computation belongs. Background thread.
* <p>
* Equivalent of {@link javax.swing.SwingWorker#doInBackground()}, {@link javafx.concurrent.Task#call()}
* and {@link android.os.AsyncTask#doInBackground()}.
*/
public Result computeResult();
/**
* Can be called from {@link #computeResult()} to update GUI with partial
* results. Background thread.
* <p>
* Equivalent of {@link javax.swing.SwingWorker#publish(Object[])}, and
* {@link android.os.AsyncTask#publishProgress(Progress)} (sort of). The equivalent in
* JavaFX is not just a simple method.
*/
public void partialUpdate(PartialResult... partials);
/**
* Called to process partial results. UI thread.
* <p>
* Equivalent of {@link javax.swing.SwingWorker#process(java.util.List)} and
* {@link android.os.AsyncTask#onProgressUpdate(Progress)}
*/
public void onPartialResult(List<PartialResult> partials);
}
我的后台任务将实现此界面。我需要一些代码将BackgroundTask的实例转换为Swing中的SwingWorker(JavaFX中的任务和以后的Android中的AsyncTask)。
直接实施如下:
public class SwingBackgroundTask<Result, PartialResult> extends SwingWorker<Result, PartialResult> {
private final BackgroundTask<Result, PartialResult> task;
public SwingBackgroundTask(BackgroundTask<Result, PartialResult> task) {
this.task = task;
}
@Override
protected Result doInBackground() throws Exception {
return task.computeResult();
}
@Override
protected void process(List<PartialResult> chunks) {
task.onPartialResult(chunks);
}
}
然而,它没用。显然,我无法从BackgroundTask的publish(partialResult)
内部调用SwingWorker computeResult()
。因此,我的用户永远不会看到后台任务的有意义进展。当然,我可以使用不确定的进度条,但我不喜欢它们。
如何克服此问题并制作通用后台任务?
答案 0 :(得分:1)
当您尝试将流程与特定实施方案分离时,您需要提供某种API,以便您能够以统一的方式提供反馈。
可能最简单的方法是为Task
类提供某种观察者/听众,感兴趣的各方可以注册通知,Task
可以用来提供反馈。
这将允许Task
引发有关给定状态更改或其他通知的事件,并且实现将能够以特定于实现的方式处理...