为什么我的 javafx 标签在更改后没有显示?
Why is my javafx label not showing after it being changed?
我是 javafx 编程的新手,我不明白为什么我的 javafx 文本在更改后没有得到更新。
我想制作一个计时器,从 60 计数到 0。我正在尝试更改 timeCounter 文本,每一秒都过去了。
帮助将不胜感激!
这是我的控制器代码:
public class Controller {
TimerUtil timerUtil;
@FXML
private Button startButton;
@FXML
private Text timeCounter;
@FXML
private Text pointCounter;
@FXML
private Circle circle;
@FXML
private void handleStartButtonClick(ActionEvent event) {
timerUtil = new TimerUtil();
}
private class TimerUtil extends Pane {
private int tmp = 60;
private Timeline animation;
public TimerUtil(){
getChildren().add(timeCounter);
animation = new Timeline(new KeyFrame(Duration.seconds(1), e -> timeLabel()));
animation.setCycleCount(Timeline.INDEFINITE);
animation.play();
}
private void timeLabel(){
if(tmp > 0){
tmp--;
}
timeCounter.setText(String.valueOf(tmp));
System.out.println(tmp);
}
}
}
您的错误发生是因为标签已从其显示的父节点中静默删除:
- 您有 TimerUtil class 扩展窗格(我不知道为什么)。
- 您将 timeCounter 文本添加到 TimeUtil 窗格(同样,我不知道为什么)。
- 将 timeCounter 文本添加到 TimeUtil 窗格 将静默地将其从 FXML 加载程序注入它的父项 中删除。
- 您可能只显示 FXML 加载程序注入的父项。
- 您永远不会显示 TimerUtil 窗格。
- 因此,即使您的时间线正在更新文本,您也永远看不到它。
为了更好地理解您的错误,请阅读:
- JavaFX - Why does adding a node to a pane multiple times or to different panes result in an error?
来自 Node
javadoc:
If a program adds a child node to a Parent (including Group, Region, etc) and that node is already a child of a different Parent or the root of a Scene, the node is automatically (and silently) removed from its former parent.
修复错误后,基本概念对我有用。这是我根据您的代码创建的可运行示例:
import javafx.animation.*;
import javafx.application.Application;
import javafx.geometry.Insets;
import javafx.scene.Scene;
import javafx.scene.layout.StackPane;
import javafx.scene.text.Text;
import javafx.stage.Stage;
import javafx.util.Duration;
public class Timer extends Application {
private int tmp = 60;
private Text counter = new Text();
private Timeline animation = new Timeline(
new KeyFrame(Duration.seconds(1), e -> updateCounter())
);
@Override
public void start(Stage stage) {
animation.setCycleCount(Timeline.INDEFINITE);
animation.play();
StackPane layout = new StackPane(counter);
layout.setPadding(new Insets(20));
stage.setScene(new Scene(layout));
stage.show();
}
private void updateCounter() {
if (tmp > 0){
tmp--;
} else {
animation.stop();
}
counter.setText(String.valueOf(tmp));
System.out.println(tmp);
}
public static void main(String[] args) {
launch(args);
}
}
我是 javafx 编程的新手,我不明白为什么我的 javafx 文本在更改后没有得到更新。 我想制作一个计时器,从 60 计数到 0。我正在尝试更改 timeCounter 文本,每一秒都过去了。 帮助将不胜感激!
这是我的控制器代码:
public class Controller {
TimerUtil timerUtil;
@FXML
private Button startButton;
@FXML
private Text timeCounter;
@FXML
private Text pointCounter;
@FXML
private Circle circle;
@FXML
private void handleStartButtonClick(ActionEvent event) {
timerUtil = new TimerUtil();
}
private class TimerUtil extends Pane {
private int tmp = 60;
private Timeline animation;
public TimerUtil(){
getChildren().add(timeCounter);
animation = new Timeline(new KeyFrame(Duration.seconds(1), e -> timeLabel()));
animation.setCycleCount(Timeline.INDEFINITE);
animation.play();
}
private void timeLabel(){
if(tmp > 0){
tmp--;
}
timeCounter.setText(String.valueOf(tmp));
System.out.println(tmp);
}
}
}
您的错误发生是因为标签已从其显示的父节点中静默删除:
- 您有 TimerUtil class 扩展窗格(我不知道为什么)。
- 您将 timeCounter 文本添加到 TimeUtil 窗格(同样,我不知道为什么)。
- 将 timeCounter 文本添加到 TimeUtil 窗格 将静默地将其从 FXML 加载程序注入它的父项 中删除。
- 您可能只显示 FXML 加载程序注入的父项。
- 您永远不会显示 TimerUtil 窗格。
- 因此,即使您的时间线正在更新文本,您也永远看不到它。
为了更好地理解您的错误,请阅读:
- JavaFX - Why does adding a node to a pane multiple times or to different panes result in an error?
来自 Node
javadoc:
If a program adds a child node to a Parent (including Group, Region, etc) and that node is already a child of a different Parent or the root of a Scene, the node is automatically (and silently) removed from its former parent.
修复错误后,基本概念对我有用。这是我根据您的代码创建的可运行示例:
import javafx.animation.*;
import javafx.application.Application;
import javafx.geometry.Insets;
import javafx.scene.Scene;
import javafx.scene.layout.StackPane;
import javafx.scene.text.Text;
import javafx.stage.Stage;
import javafx.util.Duration;
public class Timer extends Application {
private int tmp = 60;
private Text counter = new Text();
private Timeline animation = new Timeline(
new KeyFrame(Duration.seconds(1), e -> updateCounter())
);
@Override
public void start(Stage stage) {
animation.setCycleCount(Timeline.INDEFINITE);
animation.play();
StackPane layout = new StackPane(counter);
layout.setPadding(new Insets(20));
stage.setScene(new Scene(layout));
stage.show();
}
private void updateCounter() {
if (tmp > 0){
tmp--;
} else {
animation.stop();
}
counter.setText(String.valueOf(tmp));
System.out.println(tmp);
}
public static void main(String[] args) {
launch(args);
}
}