Creating a JavaFX Dialog Inside a JavaFX Task

I am trying to create a javafx input dialog, I put it in a task, but my code does not create any dialog.

                Task<Void> passwordBox = new Task<Void>() {
                    @Override
                    protected Void call() throws Exception {
                TextInputDialog dialog = new TextInputDialog("walter");
                dialog.setTitle("Text Input Dialog");
                dialog.setHeaderText("Look, a Text Input Dialog");
                dialog.setContentText("Please enter your name:");

                // Traditional way to get the response value.
                Optional<String> result = dialog.showAndWait();
                if (result.isPresent()){
                    System.out.println("Your name: " + result.get());
                }

                // The Java 8 way to get the response value (with lambda expression).
                result.ifPresent(name -> System.out.println("Your name: " + name));
                return null;
                    }
                };
            Thread pt = new Thread(passwordBox);
            pt.start();

when debugging, it enters the following catch method of the Task class

catch (final Throwable th) {
                // Be sure to set the state after setting the cause of failure
                // so that developers handling the state change events have a
                // throwable to inspect when they get the FAILED state. Note
                // that the other way around is not important -- when a developer
                // observes the causeOfFailure is set to a non-null value, even
                // though the state has not yet been updated, he can infer that
                // it will be FAILED because it can be nothing other than FAILED
                // in that circumstance.
                task.runLater(() -> {
                    task._setException(th);
                    task.setState(State.FAILED);
                });
                // Some error occurred during the call (it might be
                // an exception (either runtime or checked), or it might
                // be an error. In any case, we capture the throwable,
                // record it as the causeOfFailure, and then rethrow. However
                // since the Callable interface requires that we throw an
                // Exception (not Throwable), we have to wrap the exception
                // if it is not already one.
                if (th instanceof Exception) {
                    throw (Exception) th;
                } else {
                    throw new Exception(th);
                }

If I do not place the dialog box inside the task, it causes the application to freeze.

+4
source share
1 answer

You need to make sure that the dialog is open in the JavaFX Application Thread , since every GUI update must happen in this thread in JavaFX.

You can achieve this as:

Task<Void> passwordBox = new Task<Void>() {
            @Override
            protected Void call() throws Exception {
                Platform.runLater(new Runnable() {

                    @Override
                    public void run() {
                        TextInputDialog dialog = new TextInputDialog("walter");
                        dialog.setTitle("Text Input Dialog");
                        dialog.setHeaderText("Look, a Text Input Dialog");
                        dialog.setContentText("Please enter your name:");

                        // Traditional way to get the response value.
                        Optional<String> result = dialog.showAndWait();
                        if (result.isPresent()){
                            System.out.println("Your name: " + result.get());
                        }

                        // The Java 8 way to get the response value (with lambda expression).
                        result.ifPresent(name -> System.out.println("Your name: " + name));

                    }
                });

                return null;
            }
        };
+2
source

All Articles