如何使用 JavaFX 将选择框、复选框和文本字段实现到一个按钮中

How can a choice box, checkbox, and text field be implemented into one button with JavaFX

我正在尝试创建一个程序,该程序可以从选择框、复选框和文本字段中获取数据并将其放入单个文本区域作为输出。我怎样才能通过一个按钮组合所有信息。我已经创建了选择框、复选框和文本字段。

-有两个文本字段。其中一个需要一个名字,另一个需要一个数字。该数字将决定程序循环多少次。

-复选框将在姓名(先生、夫人等)前面加上什么样的前缀。

-选择框提供有关后续声明的选项。 (今天过得怎么样?我喜欢你的帽子等等)

点击按钮后,如果 textField 中的数字输入为 2,程序将在 textArea 中显示如下内容

"1Hello Mr. Johnson. How was your day?"

"2Hello Mr. Johnson. How was your day?"

这就是我在按钮事件处理程序中的内容。它只实现文本字段

 private class CreateButtonHandler implements EventHandler<ActionEvent> {
        @Override
        public void handle(ActionEvent event) {
        int i = 0;
        String myString = number.getText();
        int foo = Integer.parseInt(myString);
        do {
             OutputTxtArea.setText(OutputTxtArea.getText() + (i + 1) + "Hello " + firstNameTxtFld.getText() + "\n");
        } while(i<foo);
}
}

绑定!

如果将布局与数据和操作分开,然后让操作处理数据,事情就会变得更容易。这使得屏幕只是一个屏幕,您不必担心“我如何处理获取 CheckBox 值?”各种问题。

import javafx.application.Application;
import javafx.beans.binding.Bindings;
import javafx.beans.property.BooleanProperty;
import javafx.beans.property.SimpleBooleanProperty;
import javafx.beans.property.SimpleStringProperty;
import javafx.beans.property.StringProperty;
import javafx.beans.value.ObservableValue;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.scene.Node;
import javafx.scene.Scene;
import javafx.scene.control.CheckBox;
import javafx.scene.control.ChoiceBox;
import javafx.scene.control.TextArea;
import javafx.scene.control.TextField;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;
import org.jetbrains.annotations.NotNull;

import java.util.stream.Collectors;
import java.util.stream.IntStream;

public class Greeter extends Application {

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

    @Override
    public void start(Stage primaryStage) {
        Model model = new Model();
        ChoiceBox<String> questionChoiceBox = new ChoiceBox<>(model.questionList);
        TextArea textArea = new TextArea("");
        textArea.textProperty().bind(model.greetingProperty());
        VBox vBox = new VBox(20,
                             createBoundCheckBox("Miss", model.isMissProperty()),
                             createBoundCheckBox("Missus", model.isMissusProperty()),
                             createBoundCheckBox("Mister", model.isMisterProperty()),
                             questionChoiceBox,
                             createBoundTextField(model.nameProperty()),
                             createBoundTextField(model.loopCountProperty()),
                             textArea);
        primaryStage.setScene(new Scene(vBox, 200, 300));
        primaryStage.show();
    }

    @NotNull
    private Node createBoundCheckBox(String label, BooleanProperty boundProperty) {
        CheckBox checkBox = new CheckBox(label);
        boundProperty.bind(checkBox.selectedProperty());
        return checkBox;
    }

    private Node createBoundTextField(StringProperty boundProperty) {
        TextField textField = new TextField();
        boundProperty.bind(textField.textProperty());
        return textField;
    }

    class Model {
        private StringProperty loopCount = new SimpleStringProperty("");
        private BooleanProperty isMister = new SimpleBooleanProperty(false);
        private BooleanProperty isMissus = new SimpleBooleanProperty(false);
        private BooleanProperty isMiss = new SimpleBooleanProperty(false);
        private StringProperty name = new SimpleStringProperty("");
        private StringProperty question = new SimpleStringProperty("");
        private ObservableList<String> questionList = FXCollections.observableArrayList();

        Model() {
            questionList.add("How was your day?");
            questionList.add("Would you like kippers for breakfast");
        }

        public StringProperty loopCountProperty() {
            return loopCount;
        }

        public BooleanProperty isMisterProperty() {
            return isMister;
        }

        public BooleanProperty isMissusProperty() {
            return isMissus;
        }

        public BooleanProperty isMissProperty() {
            return isMiss;
        }

        public StringProperty nameProperty() {
            return name;
        }

        public StringProperty questionProperty() {
            return question;
        }

        public ObservableList<String> getQuestionList() {
            return questionList;
        }

        public ObservableValue<String> greetingProperty() {
            return Bindings.createStringBinding(() -> buildGreeting(), loopCount, isMiss, isMissus, isMister, question, name);
        }

        private String buildGreeting() {
            int howMany;
            try {
                howMany = Integer.parseInt(loopCount.get());
            } catch (Exception e) {
                return "";
            }
            String title = "Master of Time and Space";
            if (isMiss.get()) {
                title = "Miss";
            }
            if (isMissus.get()) {
                title = "Mrs.";
            }
            if (isMister.get()) {
                title = "Mr.";
            }
            String greeting = "Hello " + title + " " + name.get() + " " + question.get();
            return IntStream.range(1, howMany + 1).mapToObj(idx -> idx + greeting).collect(Collectors.joining("\n"));
        }
    }
}

所以现在布局只是一个布局,屏幕上的所有控件都将其值属性绑定到模型。然后该模型具有将所有内容放在一起以创建结果的代码。从技术上讲,该代码应该属于某种业务逻辑 class,但这至少应该给你一个想法。

我省略了这个按钮,因为它并没有真正添加任何有意义的功能,而且它对 UI 来说有点问题。无法指示 TextArea 中的结果是否是最后一次单击按钮时的结果。例如,您可以单击按钮,然后选择另一个标题复选框,现在屏幕上的选择与 TextArea 不匹配。但是用户无法知道这一点,要实现它,您可能必须使用 DirtyFX 库之类的东西。

但是如果您真的想要一个按钮,那么您所要做的就是为结果引入一个新的 StringProperty,然后让按钮在其事件处理程序中调用 Model.buildGreeting():

import javafx.application.Application;
import javafx.beans.property.BooleanProperty;
import javafx.beans.property.SimpleBooleanProperty;
import javafx.beans.property.SimpleStringProperty;
import javafx.beans.property.StringProperty;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.scene.Node;
import javafx.scene.Scene;
import javafx.scene.control.*;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;
import org.jetbrains.annotations.NotNull;

import java.util.stream.Collectors;
import java.util.stream.IntStream;

public class GreeterButton extends Application {

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

    @Override
    public void start(Stage primaryStage) {
        Model model = new Model();
        ChoiceBox<String> questionChoiceBox = new ChoiceBox<>(model.questionList);
        TextArea textArea = new TextArea("");
        textArea.textProperty().bind(model.greetingProperty());
        Button button = new Button("Say Hi!");
        button.setOnAction(evt -> model.updateGreeting());
        VBox vBox = new VBox(20,
                             createBoundCheckBox("Miss", model.isMissProperty()),
                             createBoundCheckBox("Missus", model.isMissusProperty()),
                             createBoundCheckBox("Mister", model.isMisterProperty()),
                             questionChoiceBox,
                             createBoundTextField(model.nameProperty()),
                             createBoundTextField(model.loopCountProperty()),
                             button,
                             textArea);
        primaryStage.setScene(new Scene(vBox, 200, 300));
        primaryStage.show();
    }

    @NotNull
    private Node createBoundCheckBox(String label, BooleanProperty boundProperty) {
        CheckBox checkBox = new CheckBox(label);
        boundProperty.bind(checkBox.selectedProperty());
        return checkBox;
    }

    private Node createBoundTextField(StringProperty boundProperty) {
        TextField textField = new TextField();
        boundProperty.bind(textField.textProperty());
        return textField;
    }

    class Model {
        private StringProperty loopCount = new SimpleStringProperty("");
        private BooleanProperty isMister = new SimpleBooleanProperty(false);
        private BooleanProperty isMissus = new SimpleBooleanProperty(false);
        private BooleanProperty isMiss = new SimpleBooleanProperty(false);
        private StringProperty name = new SimpleStringProperty("");
        private StringProperty question = new SimpleStringProperty("");
        private StringProperty greeting = new SimpleStringProperty("");
        private ObservableList<String> questionList = FXCollections.observableArrayList();

        Model() {
            questionList.add("How was your day?");
            questionList.add("Would you like kippers for breakfast");
        }

        public StringProperty loopCountProperty() {
            return loopCount;
        }

        public BooleanProperty isMisterProperty() {
            return isMister;
        }

        public BooleanProperty isMissusProperty() {
            return isMissus;
        }

        public BooleanProperty isMissProperty() {
            return isMiss;
        }

        public StringProperty nameProperty() {
            return name;
        }

        public StringProperty questionProperty() {
            return question;
        }

        public ObservableList<String> getQuestionList() {
            return questionList;
        }

        String buildGreeting() {
            int howMany;
            try {
                howMany = Integer.parseInt(loopCount.get());
            } catch (Exception e) {
                return "";
            }
            String title = "Master of Time and Space";
            if (isMiss.get()) {
                title = "Miss";
            }
            if (isMissus.get()) {
                title = "Mrs.";
            }
            if (isMister.get()) {
                title = "Mr.";
            }
            String greeting = "Hello " + title + " " + name.get() + " " + question.get();
            return IntStream.range(1, howMany + 1).mapToObj(idx -> idx + greeting).collect(Collectors.joining("\n"));
        }

        public void updateGreeting() {
            greeting.set(buildGreeting());
        }

        public StringProperty greetingProperty() {
            return greeting;
        }
    }
}