正如我在我的評論中提到的問題是,Canvas
真的就像一個繪圖板。你已經在上面畫了一些文字,然後你畫了另一個文字而不刪除以前的文字。
在你的情況下,當你想存儲對文本的引用來更新它時,使用Pane
並在其上放置一個Text
實例會更合理。
我已經爲您創建一個例子:
import javafx.application.Application;
import javafx.application.Platform;
import javafx.concurrent.Task;
import javafx.stage.Stage;
import javafx.scene.Scene;
import javafx.scene.control.TextArea;
import javafx.scene.input.KeyCode;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.Pane;
import javafx.scene.text.Text;
public class Main extends Application {
@Override
public void start(Stage primaryStage) {
try {
BorderPane root = new BorderPane();
Scene scene = new Scene(root, 400, 400);
Pane pane = new Pane();
Text text = new Text("");
pane.getChildren().add(text);
Task<Void> task = new Task<Void>() {
String a = "Initial text";
@Override
public Void call() throws Exception {
int i = 0;
while (true) {
if (i > 4)
a = "I is bigger than 4";
if (i > 10)
a = "I is bigger than 10";
Platform.runLater(() -> {
text.setText(a);
// If you want to you can also move the text here
text.relocate(10, 10);
});
i++;
Thread.sleep(1000);
}
}
};
Thread th = new Thread(task);
th.setDaemon(true);
th.start();
root.setCenter(pane);
primaryStage.setScene(scene);
primaryStage.show();
} catch (Exception e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
launch(args);
}
}
注:您也可以通過更新任務的messageProperty
內call()
那麼Text
的textProperty
結合這消除Platform.runlater(...)
塊屬性。
例子:
Pane pane = new Pane();
Text text = new Text("");
text.relocate(10, 10);
pane.getChildren().add(text);
Task<Void> task = new Task<Void>() {
{
updateMessage("Initial text");
}
@Override
public Void call() throws Exception {
int i = 0;
while (true) {
if (i > 4)
updateMessage("I is bigger than 4");
if (i > 10)
updateMessage("I is bigger than 10");
i++;
Thread.sleep(1000);
}
}
};
text.textProperty().bind(task.messageProperty());
Thread th = new Thread(task);
th.setDaemon(true);
th.start();
您是否使用了'Canvas'和圖紙送到'GraphicContext'?因爲在這種情況下,最後的文本仍然存在,因爲'Canvas'實際上就像一個繪圖板。如果你想存儲引用,我會建議使用'Pane'並在其上放置'Shape'對象。 – DVarga
JavaFX是事件驅動和單線程的。這意味着重繪和事件響應不能同時完成。長時間運行的任務應該在單獨的線程上執行,這樣它們不會阻塞UI的渲染,當任務完成時,它可以通過調用FX.deferAction()來同步回FX線程,FX.deferAction()將簡單地執行主線程上的代碼線。看這個http://stackoverflow.com/questions/528313/force-immediate-paint-in-javafx –