Search code examples
javajavafxdynamiccomboboxlistener

Update the content of a ComboBox dynamically created in Javafx, from another ComboBox dynamically created


In a GridPane I am dynamically creating two ComboBox's. For the first ComboBox I am charging the items when the Scene is loaded. Then I want that when I perform an action in this ComboBox, the items of the other ComboBox are loaded according to the value selected.

ComboBox<String> combobox1 = loadItems();
ComboBox<String> combobox2 = new ComboBox<String>();

gridpane.add(combobox1, 0, 0);
gridpane.add(combobox2, 1, 0);

I've tried by using a listener, but it didn't seem to work:

combobox1.getSelectionModel().selectedItemProperty().addListener(new ChangeListener<String>() {
    @Override
    public void changed(ObservableValue<? extends String> observable, String oldValue, String newValue) {
            loadList(combobox2, newValue);
                }
            }); 

private void loadList(ComboBox<String> combobox, String value) {
        combobox = getCorrespondingList(value);
    }

public ComboBox<String> getCorrespondingList(String value) {
        ComboBox<String> combobox = new ComboBox<String>();
        ArrayList<String> list = new ArrayList<String>();
        try {
            String query = "select ... where Item = '" + value 
                    + "' order by c";
            statement = connection.prepareStatement(query);
            result = statement.executeQuery();
            while (result.next()) {
                list.add(result.getString(1));
            }
        }
        catch (SQLException e) {
            e.getMessage();
        }
        ObservableList<String> observableList = FXCollections.observableArrayList(list);
        combobox.setItems(observableList);
        return combobox;
    }

I really appreciate any help.


Solution

  • Java is call by reference. Any assignment to a method parameter will only have an effect inside the method. Furthermore as far as I can tell you did create the ComboBox you want to modify earlier. Instead of creating a new ComboBox, just fill the modify the existing one:

    private void loadList(ComboBox<String> combobox, String value) {
        combobox.getItems().setAll(getCorrespondingList(value));
    }
    
    public List<String> getCorrespondingList(String value) {
        ArrayList<String> list = new ArrayList<String>();
        try {
            // use PreparedStatement's placeholder functionality to avoid
            // issues with quotes inside the string
            String query = "SELECT ... WHERE Item = ? ORDER BY c";
            PreparedStatement ps = connection.prepareStatement(query);
            ps.setString(1, value);
    
            // no need to keep this after the method exits
            ResultSet rs = ps.executeQuery();
    
            while (rs.next()) {
                list.add(rs.getString(1));
            }
        } catch (SQLException e) {
            e.printStackTrace(System.err); // should provide more info in case an exception happens
        }
        return list;
    }