Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

JavaFX - Show Alert Dialog within ChangeListener event

I want to show a alert dialog when the valueProperty of a spinner is changed. Therefore i've added a ChangeListener to my valueProperty:

this.spinnerColumns.setValueFactory(new SpinnerValueFactory.IntegerSpinnerValueFactory(2,20));

this.spinnerColumns.getValueFactory().valueProperty().addListener((observable, oldValue, newValue) -> {

  if(oldValue > newValue) {
    // Ask for permission
    System.out.println("Ask for permission");
    Alert alert = new Alert(Alert.AlertType.WARNING);
    alert.setTitle("Error");
    alert.setHeaderText("Ask something...");
    alert.showAndWait();

    if(alert.getResult() == ButtonType.OK) {
      // do something
    }
  }
});

This code is not working properly. When the Alert is showing, the spinner keeps decreasing his value until the min value is reached. Some suggestions how to do this?

like image 747
fc90 Avatar asked Dec 05 '25 09:12

fc90


2 Answers

It seems like Bug JDK-8089332 and is similar to Bug JDK-8252863. The workaround there leads to:

this.spinnerColumns.setValueFactory(new SpinnerValueFactory.IntegerSpinnerValueFactory(2, 20));

this.spinnerColumns.getValueFactory().valueProperty().addListener((observable, oldValue, newValue) -> {
    Node increment = spinnerColumns.lookup(".increment-arrow-button");
    if (increment != null) {
        increment.getOnMouseReleased().handle(null);
    }

    Node decrement = spinnerColumns.lookup(".decrement-arrow-button");
    if (decrement != null) {
        decrement.getOnMouseReleased().handle(null);
    }

    if (oldValue > newValue) {
        // Ask for permission
        System.out.println("Ask for permission");
        Alert alert = new Alert(Alert.AlertType.WARNING);
        alert.setTitle("Error");
        alert.setHeaderText("Ask something...");
        alert.showAndWait();

        if (alert.getResult() == ButtonType.OK) {
            // do something
        }
    }
});
like image 157
Misi Avatar answered Dec 07 '25 00:12

Misi


It's difficult to stop spinning without using reflection as far as I know... Try this code.

if(oldValue > newValue) {

    try {
        Skin<?> skin = this.spinnerColumns.getSkin();
        Object behavior = skin.getClass().getMethod("getBehavior").invoke(skin);
        behavior.getClass().getMethod("stopSpinning").invoke(behavior);
    } catch (NoSuchMethodException | IllegalAccessException | InvocationTargetException e) {
        e.printStackTrace();
        return; // If refleciton failed, do nothing
    }

    // Ask for permission
like image 32
monolith52 Avatar answered Dec 06 '25 22:12

monolith52