是否可以将整个JavaFX应用程序包装到while循环中以触发自动事件?例如在拍卖行模拟器中:
package main;
import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.stage.Stage;
public class Main extends Application {
// Standard JavaFX boilerplate
primaryStage.show();
while(true){
// Get price of this item
// Update table of listings
}
}
public static void main(String[] args) {
launch(args);
}
我知道循环会阻塞GUI的主线程,所以我想在while循环中使用系统时间+几秒钟:
double systemTime = systemTime;
double executeTime = systemTime + 5;
while(systemTime != executeTime){
//Do things
executeTime = systemTime + 5;
}
无论如何,我知道我需要什么,我只是不知道它叫什么或实现了什么。
你是对的,这很可能会阻止JavaFX线程,但你的第二个声明也是如此。因为它仍然循环阻塞线程。你可以做的是使用ScheduledExecutorService运行Runnable或线程来定期刷新gui并用任何信息更新它。但是你应该确保在JavaFX Thread中包装更改GUI的部分,你可以使用Platform.runLater方法来完成。或者对于更重要的后台任务,请使用Task类进行JavaFX。
我将使用runLater方法来简化sakes。
例:
import javafx.application.Application;
import javafx.application.Platform;
import javafx.beans.binding.Bindings;
import javafx.beans.property.SimpleStringProperty;
import javafx.beans.property.StringProperty;
import javafx.collections.FXCollections;
import javafx.collections.ListChangeListener;
import javafx.collections.ObservableList;
import javafx.scene.Scene;
import javafx.scene.control.*;
import javafx.scene.input.MouseEvent;
import javafx.scene.layout.Priority;
import javafx.scene.layout.StackPane;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;
import java.lang.management.PlatformManagedObject;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Random;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.ScheduledThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;
public class Example extends Application {
private Scene myscene;
private TextArea exampleText;
public static void main(String[] args) {
launch(args);
}
@Override
public void start(Stage primaryStage) throws Exception {
//JavaFX boilerplate
VBox rootVBox = new VBox();
exampleText = new TextArea();
VBox.setVgrow(exampleText, Priority.ALWAYS);
myscene = new Scene(rootVBox);
rootVBox.getChildren().add(exampleText);
//End of JavaFX boilerplate
// Scheduler to update gui periodically
ScheduledExecutorService executor =
Executors.newSingleThreadScheduledExecutor();
Random r = new Random();
Runnable addNewNumber = () -> {
Platform.runLater(()->{
System.out.println("I Just updated!!!");
String newNumber = Integer.toString(r.nextInt(100));
System.out.println("adding "+ newNumber +" to textfield ");
exampleText.appendText(newNumber+"\n");
});
};
executor.scheduleAtFixedRate(addNewNumber, 0, 500, TimeUnit.MILLISECONDS);
primaryStage.setScene(myscene);
primaryStage.show();
}
}