这是我申请的主要窗口:
我希望能够更新窗口,所以我写了一个方法reset
,它按F5触发:
public void reset() {
final ProgressIndicator pi = new ProgressIndicator(-1.0f);
final HBox hb = new HBox(pi);
final VBox vb = new VBox(hb);
hb.setAlignment(Pos.CENTER);
vb.setAlignment(Pos.CENTER);
scene.setRoot(vb);
//this.show();
}
如果我运行它看起来像这样:
但是,如果我取消注释行//this.show();
,则会执行此操作:
public void show() {
final VBox box = API_CALL_AND_BUILDING_BOX_MAGIC_WHICH_I_STRIPPED;
gp.getChildren().clear();
gp.getChildren().add(box);
scene.setRoot(gp);
stage.sizeToScene();
}
我永远无法看到我的ProgressIndicator,因为应用程序将一直挂起,直到APIcall完成并加载新内容。
我尝试使用Threads和Platform.runLater(),但我无法让它工作。我的目标是显示ProgressIndicator,直到APIcall完成,框架构建并且场景被赋予gp
作为新根。
我希望我的目标和问题是可以理解的:)
答案 0 :(得分:1)
您需要创建另一个专用于从远程源获取数据的JVM线程。应用程序的主线程绝不能阻止网络操作:在键盘事件处理程序中,您只需使用进度指示器重新绘制主窗口,然后等待另一个事件,即:
Guava的ListenableFuture伪代码
// Initialize in ctor use MoreExecutors
private final ListeningExecutorService service;
// Keep to call .cancel()
private ListenableFuture<APIData> currentRequest;
// Run in the GUI thread
public void onRefreshEvent() {
showProgressIndicator();
currentRequest = service.submit(/* Some Callable<APIData> */);
Futures.addCallback(currentRequest , this, this);
}
// From FutureCallback<T>
public void onFailure(Throwable t) {} // TODO
public void onSuccess(APIData d) {} // TODO
// From Executor
public void execute(Runnable cmd) {
Platform.runLater(cmd);
}
不要忘记考虑套接字连接和读取超时,以及汇集HTTP连接!还要考虑后台任务是否应检查中断标志