带CheckBoxes的JavaFX ComboBox

问题描述

我尝试创建一个JavaFX ComboBox,它在下拉菜单中保存CheckBoxes.
ComboBox应该是可编辑的,并由一个简单的类提供,我们称之为CheckItem.
CheckItems列表应是可检查的 – 并且在做出选择后不应关闭下拉菜单.

最后,ComboBox中的文本应该可用并且选择(所有选中的项目)

这就是我已经解决的问题

(1)使用正确选择将CheckItem呈现为CheckedBox的ComboBox

(2)从ComboBox获取文本

问题即将来临

(1)点击一个项目后,下拉菜单关闭&项目的选择状态不会改变.

(2)据我所知,它一次只能选择一个项目?

这是我测试这些东西的代码:

测试程序

public class ComboButtonSample extends Application {

    @Override
    public void start(Stage stage) {
            final ObservableList<CheckItem> items = fetchItems();
            ComboBox<CheckItem> combo = createComboBox(items);
            combo.setPromptText("enter searchstring here");
            combo.setEditable(true);


            // order the components vertically
            VBox vBox = new VBox();
            vBox.getChildren().add(combo);

            // Button to write out the text and the items of the combobox
            Button btn = new Button();
            btn.setText("combo text to console");
            btn.setOnAction((event) -> {
                    System.out.println("Text is: "+combo.getEditor().getText());
                    System.out.println("Content is: ");
                    for (Iterator<CheckItem> iterator = combo.getItems().iterator(); iterator.hasNext();) {
                            CheckItem ci = (CheckItem) iterator.next();
                            System.out.println(String.format("[%s] %s -> %s", ci.selected ? "X" : " ",ci.getDisplayName(), ci.getInternalName()));

                    }
            });

            vBox.getChildren().add(btn);

            // show you do not need any code to change the selection of the box.
            CheckBox checkBox = new CheckBox();
            checkBox.setText("test box");
            vBox.getChildren().add(checkBox);

            stage.setScene(new Scene(vBox));
            stage.show();
    }

    private ComboBox<CheckItem> createComboBox(ObservableList<CheckItem> data) {
            ComboBox<CheckItem> combo = new ComboBox<>();
            combo.getItems().addAll(data);
            combo.setCellFactory(listView -> new CheckItemListCell());
            return combo;
    }

    class CheckItemListCell extends ListCell<CheckItem> {
            private final CheckBox btn;

            CheckItemListCell() {
                    setContentDisplay(ContentDisplay.GRAPHIC_ONLY);
                    btn = new CheckBox();
            }

            @Override
            protected void updateItem(CheckItem item, boolean empty) {
                    super.updateItem(item, empty);

                    if (item == null || empty) {
                            setGraphic(null);
                    } else {
                            btn.setText(item.getDisplayName());
                            btn.selectedProperty().setValue(item.selected);
                            setGraphic(btn);
                    }
            }
    }

    private ObservableList<CheckItem> fetchItems() {
            final ObservableList<CheckItem> data = FXCollections
                            .observableArrayList();
            for (int i = 1; i < 15; i++) {
                    CheckItem chkItem = new CheckItem();
                    chkItem.selected = i%3==0;
                    chkItem.setDisplayName("DisplayName" + i);
                    chkItem.setInternalName("InternalName" + i);
                    data.add(chkItem);
            }
            return data;
    }

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

CheckItem

public class CheckItem {
    boolean selected;
    String displayName;
    String internalName;    

    public boolean isChecked() {
        return selected;
    }

    public void setChecked(boolean checked) {
        this.selected = checked;
    }

    public String getDisplayName() {
        return displayName;
    }

    public void setDisplayName(String displayName) {
        this.displayName = displayName;
    }

    public String getInternalName() {
        return internalName;
    }

    public void setInternalName(String internalName) {
        this.internalName = internalName;
    }
}

解决方法:

如果您的实施中存在问题,您应该查看ControlsFX项目中的CheckComboBox控件.

源代码可以在here找到.

上一篇:c# – 使组合框可编辑


下一篇:c# – WPF组合框中的不同值