Hello其他程序员。
所以我终于开始使用JavaFX并发现一些不安静的东西似乎是正确的。 如果我覆盖了我的任务的call()方法然后运行它,则该任务的状态将在呼叫完成后开始更新。
我的代码看起来像这样
Task<Boolean> myTask = new Task<Boolean>() {
@Override
protected Boolean call() throws Exception {
try {
// do stuff
return true;
} catch (Exception e){
return false;
}
}
}
在try块中,我有一些需要几秒钟才能完成的调用,并且我不希望我的GUI在此期间简单地阻止。然而,由于无法进一步发展,我使用了ControlsFX库并创建了一个显示它的进度对话框。 (Dialogs Doku)
此对话框需要一名工人,然后会显示进度。一旦工作人员状态更改为“计划”或“正在运行”,它将自动显示。我现在的问题是,由于在状态更改为其中之一之前调用了调用方法,因此永远不会显示此对话框。
我做了一些调试,似乎在Task类中,State更改将应用Platform.runLater()方法,然后直接调用call()方法(没有runLater),我的系统似乎在之前调度国家变化。
所以我的问题是,有人可以复制或有类似的问题吗? 如果是的话,Task类是否按预期工作,或者这可能是一个bug(比如call()也必须通过runLater方法调用)?
帮助真的很感激:) 请原谅我的第二语言英语
以下是Task类的代码
task.runLater(() -> {
task.setState(State.SCHEDULED);
task.setState(State.RUNNING);
});
// Go ahead and delegate to the wrapped callable
try {
final V result = task.call();
if (!task.isCancelled()) {
task.runLater(() -> {
task.updateValue(result);
task.setState(State.SUCCEEDED);
});
return result;
现在我预期的顺序是将状态设置为第一个SCHEDULED,然后在执行call()方法之前运行。在我的情况下,它总是首先调用()然后一段时间后它会改变状态。
示例:
package test;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Executors;
import javafx.application.Application;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.concurrent.Task;
import javafx.concurrent.Worker;
import javafx.stage.Stage;
public class TaskTest extends Application {
@Override
public void start(Stage primaryStage) {
Task<Void> myTask = new Task<Void>() {
@Override
protected Void call() throws Exception {
System.out.println("Executing stuff");
return null;
}
};
myTask.stateProperty().addListener(new ChangeListener<Worker.State>() {
@Override
public void changed(
ObservableValue<? extends javafx.concurrent.Worker.State> observable,
Worker.State oldValue,
Worker.State newValue) {
System.out.println("State change: " + oldValue + " -> " + newValue);
}
});
Executors.newSingleThreadExecutor().execute(myTask);
try {
myTask.get();
} catch (InterruptedException | ExecutionException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public static void main(String[] args) {
launch(args);
}
}
结果:
Executing stuff
State change: READY -> SCHEDULED
State change: SCHEDULED -> RUNNING
State change: RUNNING -> SUCCEEDED
预期:
State change: READY -> SCHEDULED
State change: SCHEDULED -> RUNNING
Executing stuff
State change: RUNNING -> SUCCEEDED