在 javaFX Eclipse 应用程序中绑定一个主类变量来控制类事件

问题描述 投票:0回答:2

Control类对象在Main类中创建。 Control的按钮事件改变了Main类变量的值。我想将新值显示为同一按钮的文本。变量值已更改但未显示在 Button 中。我在 Main 类中使用 bind 将其变量绑定到 Control 类按钮事件。主类如下:

package application;

import javafx.application.Application;
import javafx.beans.property.SimpleIntegerProperty;
import javafx.stage.Stage;
import javafx.scene.Scene;
import javafx.scene.Parent;
import javafx.scene.layout.AnchorPane;
import javafx.scene.layout.BorderPane;
import javafx.fxml.FXMLLoader;

public class Main extends Application {

Control controller = new Control();
public static int total_time = 60;
public void start(Stage primaryStage) {
    try 
    {
        FXMLLoader loader = new FXMLLoader();
        loader.setLocation(Main.class.getResource("/test.fxml"));
        AnchorPane root = (AnchorPane) loader.load();
        
        primaryStage.setTitle("TEST Bind Another Class Variable");
        Scene scene = new Scene(root);
         
  //scene.getStylesheets().add(getClass().getResource("application.css").toExternalForm());
        primaryStage.setScene(scene);                       
        primaryStage.show();
        controller = (Control) loader.getController();
        
        controller.btnDemo.textProperty().bind(new 
       SimpleIntegerProperty(total_time).asString());
        
    } catch(Exception e) {
        e.printStackTrace();
    }
}

public static void main(String[] args) {
    launch(args);
 }
 }

控制类是: 打包申请;

 import javafx.event.ActionEvent;
 import javafx.event.Event;
 import javafx.fxml.FXML;
 import javafx.stage.Stage;
 import javafx.scene.Scene;
 import javafx.scene.layout.BorderPane;
 import javafx.scene.text.Text;
 import javafx.scene.layout.AnchorPane;
 import javafx.scene.control.Button;
 import javafx.scene.control.TextField;
 import javafx.scene.control.Label;

  public class Control {
  @FXML TextField txtMain;
  @FXML Button btnDemo;
  @FXML
    public void demoBtnHandler(ActionEvent event) 
   {        
    if((Main.total_time+=10) > 60)Main.total_time = 10;
    System.out.print("Button Clicked, Time = ");System.out.println(Main.total_time);
    }
   }

FXML文件是:

  <?import javafx.scene.control.Button?>
  <?import javafx.scene.control.Label?>
  <?import javafx.scene.control.TextField?>
  <?import javafx.scene.layout.AnchorPane?>

 <AnchorPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="- 
 Infinity" prefHeight="630.0" prefWidth="925.0" xmlns="http://javafx.com/javafx/19" 
 xmlns:fx="http://javafx.com/fxml/1" fx:controller="application.Control">
 <children>
   <Button fx:id="btnDemo" layoutX="412.0" layoutY="339.0" mnemonicParsing="false" 
   onAction="#demoBtnHandler" text="DEMO" />
  <TextField id="tf" fx:id="txtMain" layoutX="412.0" layoutY="298.0" prefHeight="26.0" 
  prefWidth="50.0" />
  <Label layoutX="484.0" layoutY="306.0" text="enter roll no. " />
  </children>
  </AnchorPane>

我无法解决。请在你这边运行这段代码。

eclipse class javafx bind
2个回答
3
投票

这是一件非常奇怪的事情,因为

Application
类应该管理应用程序生命周期(它有
start()
stop()
init()
方法用于此目的)。它不应该是您的应用程序数据的存储库。

你的按钮文本没有改变的原因是因为文本绑定到一个

IntegerProperty
,但你永远不会改变
IntegerProperty
。您所更改的只是最初用于初始化
int
IntegerProperty
值。要更改文本,您需要更改属性。

Main
中,做:

public static IntegerProperty totalTime = new SimpleIntegerProperty(60);

然后在

start()
方法中:

controller.btnDemo.textProperty().bind(totalTime.asString());

然后在控制器中做

@FXML
public void demoBtnHandler(ActionEvent event) {
    Main.totalTime.set(Main.totalTime.get()+10);
    if(Main.totalTime.get() > 60)Main.totalTime.set(10);
    System.out.print("Button Clicked, Time = ");System.out.println(Main.totalTime);
}

但是,这里的设计又是错误的。你不应该有公共字段,不应该无缘无故地使字段静态化,也不应该使用

Application
类来存储数据。将值存储在控制器类中可能更有意义,但在实际应用程序中,您可能希望将应用程序状态完全分解为一个单独的类(MVC 和相关体系结构中的“模型”)。


0
投票

我根据如下所示的 MVC 修改了整个代码,并按照一位观众的建议访问了按钮事件。问题解决了,

  import javafx.application.Application;
  import javafx.stage.Stage;
  import javafx.scene.Scene;
  import javafx.scene.layout.BorderPane;


   public class Main {


   public static void main(String[] args) {
    //launch(args);
    Application.launch(Spm.class);
   }
   }

在 spm 类中,创建所有其他类的对象,如下所示。一切都很好。

 public class Spm extends Application {
 static serialPortClass spm_device = new serialPortClass();

static Control controller = new Control();
static PatientDB patientDataBase = new PatientDB();
static UartCom uartcom = new UartCom();
static NewPatientController patientcontrol = new NewPatientController(null, null, null, null, null, null, null, null, null, null); 

public Spm() {
    // TODO Auto-generated constructor stub
}
@Override
public void start(Stage primaryStage) {
    try 
    {   
      //Parent root = FXMLLoader.load(getClass().getResource("/main.fxml"));
        FXMLLoader loader = new FXMLLoader();
        loader.setLocation(getClass().getResource("Abc.fxml"));
        AnchorPane root = (AnchorPane) loader.load();
        
        primaryStage.setTitle("ABC_XYZ");
        Scene scene = new Scene(root);
        //scene.getStylesheets().add(getClass().getResource("application.css").toExternalForm());
        primaryStage.setScene(scene);                       
        primaryStage.show();
        controller = (Control) loader.getController();  

        System.out.println("The Loader Path : "+ loader.getLocation().toURI());

      } catch(Exception e) {
        e.printStackTrace();
    }
    }
    }            
© www.soinside.com 2019 - 2024. All rights reserved.