javafx多个按钮到同一个处理程序

tog*_*oge 6 javafx button handler

我尝试用20个按钮和一个处理程序制作一个简单的计算器.在java中,我可以在ActionPerformed中使用带有event.getSource()的'if'语句来检查按下了哪个按钮,但它不适用于javafx中的处理程序.在javafx中,所有按钮都有一个处理程序吗?(我不想使用java 8 Lambdas.)上次我尝试使用setId/getId,但同样不起作用(对我而言).

public class Calculator extends Application {

    public Button b0, b1;

    @Override
    public void start(Stage primaryStage) {

        GridPane grid = new GridPane();

        b0 = new Button("0");
        b0.setId("0");
        b0.setMaxSize(Double.MAX_VALUE, Double.MAX_VALUE);
        grid.add(b0, 0, 1);
        b0.setOnAction(myHandler);

        b1 = new Button("1");
        b1.setId("1");
        b1.setMaxSize(Double.MAX_VALUE, Double.MAX_VALUE);
        grid.add(b1, 0, 0);
        b1.setOnAction(myHandler);

        Scene scene = new Scene(grid, 365, 300);
        scene.getStylesheets().add
            (Calculator.class.getResource("calculator.css").toExternalForm());

        primaryStage.setScene(scene);
        primaryStage.setResizable(false);
        primaryStage.show();
    }

    final EventHandler<ActionEvent> myHandler = new EventHandler<ActionEvent>(){

        @Override
        public void handle(final ActionEvent event) {
            Button x = (Button) event.getSource();
            if (x.getId().equals(b0.getId()))
                System.out.println("0");
            else if(x.getId().equals(b1.getId()))
                System.out.println("1");
        }
    };
    public static void main(String[] args) {
        launch(args);
    }
Run Code Online (Sandbox Code Playgroud)

}

Jam*_*s_D 5

我测试了您的代码,它似乎正常工作。

不过,没有真正的理由来测试按钮的ID。如果您确实要使用相同的处理程序(我不建议这样做),只需测试每个按钮与事件源之间是否相等:

final EventHandler<ActionEvent> myHandler = new EventHandler<ActionEvent>(){

    @Override
    public void handle(final ActionEvent event) {

        if (event.getSource() == b0)
            System.out.println("0");
        else if(event.getSource() == b1)
            System.out.println("1");
    }
};
Run Code Online (Sandbox Code Playgroud)

但是(几乎?)对每个动作使用不同的处理程序总会更好。它使代码不受所有if/else构造的影响,这两者在性能方面都变得更加整洁和更好。在这里,由于按钮的作用几乎相同,因此可以使用一个实现,但可以使用多个对象。

这是一个完整的示例:

import javafx.application.Application;
import javafx.beans.binding.Bindings;
import javafx.beans.property.IntegerProperty;
import javafx.beans.property.SimpleIntegerProperty;
import javafx.event.ActionEvent;
import javafx.event.EventHandler;
import javafx.geometry.Insets;
import javafx.geometry.Pos;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.control.TextField;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.GridPane;
import javafx.scene.layout.Priority;
import javafx.stage.Stage;

public class Calculator extends Application {

    private final IntegerProperty value = new SimpleIntegerProperty();


    class NumberButtonHandler implements EventHandler<ActionEvent> {
        private final int number ;
        NumberButtonHandler(int number) {
            this.number = number ;
        }
        @Override
        public void handle(ActionEvent event) {
            value.set(value.get() * 10 + number);
        }

    }

    @Override
    public void start(Stage primaryStage) {

        GridPane grid = createGrid();

        for (int n = 1; n<10; n++) {
            Button button = createNumberButton(n);
            int row = (n-1) / 3;
            int col = (n-1) % 3 ;
            grid.add(button, col, 2 - row);
        }

        Button zeroButton = createNumberButton(0);
        grid.add(zeroButton, 1, 3);

        Button clearButton = createButton("C");

        // without lambdas:

//        clearButton.setOnAction(
//            new EventHandler<ActionEvent>() {
//                @Override
//                public void handle(ActionEvent event) {
//                    value.set(0);
//                }
//            }
//        );

        // with lambdas:
        clearButton.setOnAction(event -> value.set(0));

        grid.add(clearButton, 2, 3);

        TextField displayField = createDisplayField();

        BorderPane root = new BorderPane();
        root.setPadding(new Insets(10));
        root.setTop(displayField);
        root.setCenter(grid);

        Scene scene = new Scene(root, 365, 300);

        primaryStage.setScene(scene);
        primaryStage.setResizable(false);
        primaryStage.show();
    }

     private Button createNumberButton(int number) {
        Button button = createButton(Integer.toString(number));
        button.setOnAction(new NumberButtonHandler(number));
        return button ;
    }

    private Button createButton(String text) {
        Button button = new Button(text);
        button.setMaxSize(Double.POSITIVE_INFINITY, Double.POSITIVE_INFINITY);
        GridPane.setFillHeight(button, true);
        GridPane.setFillWidth(button, true);
        GridPane.setHgrow(button, Priority.ALWAYS);
        GridPane.setVgrow(button, Priority.ALWAYS);
        return button ;
    }


    private GridPane createGrid() {
        GridPane grid = new GridPane();
        grid.setAlignment(Pos.CENTER);
        grid.setHgap(5);
        grid.setVgap(5);
        grid.setPadding(new Insets(10));
        return grid;
    }

    private TextField createDisplayField() {
        TextField displayField = new TextField();
        displayField.textProperty().bind(Bindings.format("%d", value));
        displayField.setEditable(false);
        displayField.setAlignment(Pos.CENTER_RIGHT);
        return displayField;
    }

    public static void main(String[] args) {
        launch(args);
    }
}
Run Code Online (Sandbox Code Playgroud)