Los diálogos representan una forma de interactuar con el usuario para darle información de algún proceso o para poder introducir información. En general existen dos posibilidades de creación de diálogos: personalizados o preconstruidos. En el caso de los preconstruidos representan un porcentaje muy alto de lo que se necesita en una GUI. Para poder construirlos se utiliza una clase llamada Alert o Dialog y como se verá a continuación los métodos que se utilizan son recurrentes siendo la diferencia el tipo de diálogo

Diálogo de Información, Warning, Error

Los diálogos de información, warning y error son utilizados para informar al usuario de parte del trabajo. La diferencia entre ellos el el icono que está representado.

Alert dialogoInfo = new Alert(Alert.AlertType.INFORMATION);
dialogoInfo.setTitle("Diálogo de información");
dialogoInfo.setHeaderText("Cabecera del cuadro de diálogo de información");
dialogoInfo.setContentText("Contenido del cuadro de diálogo de información");
dialogoInfo.showAndWait();

Alert dialogoWarning = new Alert(Alert.AlertType.WARNING);
dialogoWarning.setTitle("Diálogo de warning");
dialogoWarning.setHeaderText("Cabecera del cuadro de diálogo de warning");
dialogoWarning.setContentText("Contenido del cuadro de diálogo de warning");
dialogoWarning.showAndWait();

Alert dialogoError = new Alert(Alert.AlertType.ERROR);
dialogoError.setTitle("Diálogo de error");
dialogoError.setHeaderText("Cabecera del cuadro de diálogo de error");
dialogoError.setContentText("Contenido del cuadro de diálogo de error");
dialogoError.showAndWait();

Diálogo de confirmación

Un diálogo de confirmación es utilizado para un feedback directo con el usuario ya que este deberá pulsar un botón para realizar una acción concreta. Por defecto este diálogo incluye las opciones de aceptar y cancelar

Alert dialogoConfirmacion = new Alert(Alert.AlertType.CONFIRMATION);
dialogoConfirmacion.setTitle("Diálogo de confirmación");
dialogoConfirmacion.setHeaderText("Cabecera del cuadro de diálogo de confirmación");
dialogoConfirmacion.setContentText("Contenido del cuadro de diálogo de confirmación");
Optional<ButtonType> opciones = dialogoConfirmacion.showAndWait();
if (opciones.get() == ButtonType.OK) {
       System.out.println("Pulsado botón OK");
} else if (opciones.get() == ButtonType.CANCEL) {
       System.out.println("Pulsado botón CANCELAR");
}

Para poder evaluar la opción pulsada se utiliza una variable que recoge el resultado mediante el método showAndWait(), guardando un objeto de tipo ButtonType

En el caso de querer realizar un diálogo de confirmación personalizado con más botones o con botones diferentes se deberán de crear los mismos y agregar al cuadro de diálogo, evaluando el resultado de la misma forma que el caso anterior

Alert dialogoConfirmacionPerso = new Alert(Alert.AlertType.CONFIRMATION);
dialogoConfirmacionPerso.setTitle("Diálogo de confirmación");
dialogoConfirmacionPerso.setHeaderText("Cabecera del cuadro de diálogo de confirmación personalizado");
dialogoConfirmacionPerso.setContentText("Contenido del cuadro de diálogo de personalizado");
ButtonType boton1 = new ButtonType("Botón 1");
ButtonType boton2 = new ButtonType("Botón 2");
ButtonType boton3 = new ButtonType("Botón 3");
ButtonType boton4 = new ButtonType("Botón 4");
dialogoConfirmacionPerso.getButtonTypes().setAll(boton1, boton2, boton3, boton4);
Optional<ButtonType> opciones = dialogoConfirmacionPerso.showAndWait();
if (opciones.get() == boton1) {
         System.out.println("Pulsado botón 1");
} else if (opciones.get() == boton2) {
         System.out.println("Pulsado botón 2");
} else if (opciones.get() == boton3) {
         System.out.println("Pulsado botón 3");
} else if (opciones.get() == boton4) {
         System.out.println("Pulsado botón 4");
}

En este caso tan solo aparecerán los botones indicados, pero si se quieren añadir los botones por defecto aceptar y cancelar se utiliza el método addAll() en vez del setAll()

dialogoConfirmacionPerso.getButtonTypes().addAll(boton1, boton2, boton3, boton4);

Diálogo de entrada texto

Un diálogo de entrada texto es utilizado para que el usuario introduzca información información concreta al sistema. Esta se introduce mediante un TextField, pudiendo personalizar el tipo de entrada. En este caso el tipo de dialogo es TextInputDialog

TextInputDialog dialogoTexto = new TextInputDialog("Valor por defecto");
dialogoTexto.setTitle("Diálogo de text input");
dialogoTexto.setHeaderText("Cabecera del cuadro de diálogo de text input");
dialogoTexto.setContentText("Contenido del cuadro de diálogo de text input");
Optional<String> texto = dialogoTexto.showAndWait();
if (texto.isPresent()) {
    System.out.println(texto.get());
}

Diálogo de selección lista

Un diálogo de selección lista es muy parecido al anterior con la diferencia que el usuario no puede introducir información personalizada, sino que deberá de elegir las opciones entre una lista dada. El tipo de diálogo en este caso es ChioceDialog

List<String> opciones = new ArrayList<>();
            opciones.add("opción 1");
            opciones.add("opción 2");
            opciones.add("opción 3");
            opciones.add("opción 4");

ChoiceDialog<String> dialogoEleccion = new ChoiceDialog<String>("opción 1", opciones);
dialogoEleccion.setTitle("Diálogo de elección");
dialogoEleccion.setHeaderText("Cabecera del cuadro de diálogo de elección");
dialogoEleccion.setContentText("Contenido del cuadro de diálogo de elección");
Optional<String> texto = dialogoEleccion.showAndWait();
if (texto.isPresent()) {
     System.out.println(texto.get());
}

Diálogo personalizado

En ocasiones no es suficiente con los diálogos preconstruidos y es necesario crear un cuadro de diálogo que se amolde a las necesidades. Para ello se utiliza un objeto de tipo Dialog al cual se le agregan los componentes deseados. Hay que tener en cuenta que para poder asociar el nodo principal (normalmente layout) con el cuadro de diálogo se utiliza el método

dialogoPersonalizado.getDialogPane().setContent(layout);

Para poder poner los botones que se quieran se realizaría de la misma forma:

dialogoPersonalizado.getDialogPane().getButtonTypes().addAll(ButtonType.APPLY,ButtonType.CANCEL);

Dialog dialogoPersonalizado = new Dialog();
dialogoPersonalizado.setTitle("Diálogo personalizado");
dialogoPersonalizado.setHeaderText("Cabecera del diálogo personalizado");
dialogoPersonalizado.setContentText("Contenido del diálogo personalizado");
dialogoPersonalizado.setGraphic(new ImageView(new Image(getClass().getResourceAsStream("recursos/print.png"))));
dialogoPersonalizado.getDialogPane().getButtonTypes().addAll(ButtonType.APPLY,ButtonType.CANCEL);
GridPane grid = new GridPane();
grid.setHgap(10);
grid.setVgap(10);
TextField nombreFichero = new TextField();
nombreFichero.setPromptText("nombre fichero");
TextField ruta = new TextField();
ruta.setPromptText("ruta fichero");
grid.add(new Label("Nombre"),0,0);
grid.add(nombreFichero,1,0);
grid.add(new Label("Ruta"),0,1);
grid.add(ruta,1,1);
dialogoPersonalizado.getDialogPane().setContent(grid);
Optional<ButtonType> resultado = dialogoPersonalizado.showAndWait();
if (resultado.get() == ButtonType.APPLY){
     System.out.println("Pulsado aceptar");
} else {
     System.out.println("Pulsado cancelar");
}

El código utilizado para este ejemplo es

<?xml version="1.0" encoding="UTF-8"?>

<?import javafx.scene.control.*?>
<?import java.lang.*?>
<?import javafx.scene.layout.*?>

<GridPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="100.0" prefWidth="800.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="fundamentos.Controller_Dialog">
    <columnConstraints>
        <ColumnConstraints hgrow="SOMETIMES" minWidth="10.0" prefWidth="100.0" />
    </columnConstraints>
    <rowConstraints>
        <RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" />
    </rowConstraints>
    <children>
      <HBox alignment="CENTER" prefHeight="100.0" prefWidth="200.0" spacing="20.0" GridPane.halignment="CENTER" GridPane.valignment="CENTER">
         <children>
              <Button fx:id="bInfo" mnemonicParsing="false" text="Información" />
              <Button fx:id="bWarning" mnemonicParsing="false" text="Warning" />
              <Button fx:id="bError" mnemonicParsing="false" text="Error" />
              <Button fx:id="bConfirm" mnemonicParsing="false" text="Confirmación" />
              <Button fx:id="bConfirmPerso" mnemonicParsing="false" wrapText="true" text="Confirmación personalizado" />
              <Button fx:id="bEntrada" mnemonicParsing="false" text="Entrada" />
              <Button fx:id="bEleccion" mnemonicParsing="false" text="Elección" />
              <Button fx:id="bPerso" mnemonicParsing="false" text="Personalizado" />
         </children>
      </HBox>
    </children>
</GridPane>
package fundamentos;

import javafx.event.ActionEvent;
import javafx.event.EventHandler;
import javafx.fxml.FXML;
import javafx.fxml.Initializable;
import javafx.scene.control.*;
import javafx.scene.image.Image;
import javafx.scene.image.ImageView;
import javafx.scene.layout.GridPane;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
import java.util.ResourceBundle;

public class Controller_Dialog implements Initializable, EventHandler<ActionEvent> {

    @FXML
    Button bInfo;
    @FXML
    Button bWarning;
    @FXML
    Button bError;
    @FXML
    Button bConfirm;
    @FXML
    Button bConfirmPerso;
    @FXML
    Button bEntrada;
    @FXML
    Button bEleccion;
    @FXML
    Button bPerso;

    @Override
    public void initialize(URL location, ResourceBundle resources) {

        bInfo.setOnAction(this);
        bWarning.setOnAction(this);
        bError.setOnAction(this);
        bConfirm.setOnAction(this);
        bConfirmPerso.setOnAction(this);
        bEntrada.setOnAction(this);
        bEleccion.setOnAction(this);
        bPerso.setOnAction(this);
    }

    @Override
    public void handle(ActionEvent event) {
        Object fuente = event.getSource();

        if (fuente.equals(bInfo)) {
            Alert dialogoInfo = new Alert(Alert.AlertType.INFORMATION);
            dialogoInfo.setTitle("Diálogo de información");
            dialogoInfo.setHeaderText("Cabecera del cuadro de diálogo de información");
            dialogoInfo.setContentText("Contenido del cuadro de diálogo de información");
            dialogoInfo.showAndWait();

        } else if (fuente.equals(bWarning)) {
            Alert dialogoWarning = new Alert(Alert.AlertType.WARNING);
            dialogoWarning.setTitle("Diálogo de warning");
            dialogoWarning.setHeaderText("Cabecera del cuadro de diálogo de warning");
            dialogoWarning.setContentText("Contenido del cuadro de diálogo de warning");
            dialogoWarning.showAndWait();

        } else if (fuente.equals(bError)) {
            Alert dialogoError = new Alert(Alert.AlertType.ERROR);
            dialogoError.setTitle("Diálogo de error");
            dialogoError.setHeaderText("Cabecera del cuadro de diálogo de error");
            dialogoError.setContentText("Contenido del cuadro de diálogo de error");
            dialogoError.showAndWait();

        } else if (fuente.equals(bConfirm)) {
            Alert dialogoConfirmacion = new Alert(Alert.AlertType.CONFIRMATION);
            dialogoConfirmacion.setTitle("Diálogo de confirmación");
            dialogoConfirmacion.setHeaderText("Cabecera del cuadro de diálogo de confirmación");
            dialogoConfirmacion.setContentText("Contenido del cuadro de diálogo de confirmación");
            Optional<ButtonType> opciones = dialogoConfirmacion.showAndWait();
            if (opciones.get() == ButtonType.OK) {
                System.out.println("Pulsado botón OK");
            } else if (opciones.get() == ButtonType.CANCEL) {
                System.out.println("Pulsado botón CANCELAR");
            }
        } else if (fuente.equals(bConfirmPerso)) {

            Alert dialogoConfirmacionPerso = new Alert(Alert.AlertType.CONFIRMATION);
            dialogoConfirmacionPerso.setTitle("Diálogo de confirmación");
            dialogoConfirmacionPerso.setHeaderText("Cabecera del cuadro de diálogo de confirmación personalizado");
            dialogoConfirmacionPerso.setContentText("Contenido del cuadro de diálogo de personalizado");
            ButtonType boton1 = new ButtonType("Botón 1");
            ButtonType boton2 = new ButtonType("Botón 2");
            ButtonType boton3 = new ButtonType("Botón 3");
            ButtonType boton4 = new ButtonType("Botón 4");
            dialogoConfirmacionPerso.getButtonTypes().setAll(boton1, boton2, boton3, boton4);
            Optional<ButtonType> opciones = dialogoConfirmacionPerso.showAndWait();
            if (opciones.get() == boton1) {
                System.out.println("Pulsado botón 1");
            } else if (opciones.get() == boton2) {
                System.out.println("Pulsado botón 2");
            } else if (opciones.get() == boton3) {
                System.out.println("Pulsado botón 3");
            } else if (opciones.get() == boton4) {
                System.out.println("Pulsado botón 4");
            }

        } else if (fuente.equals(bEntrada)) {
            TextInputDialog dialogoTexto = new TextInputDialog("Valor por defecto");
            dialogoTexto.setTitle("Diálogo de text input");
            dialogoTexto.setHeaderText("Cabecera del cuadro de diálogo de text input");
            dialogoTexto.setContentText("Contenido del cuadro de diálogo de text input");
            Optional<String> texto = dialogoTexto.showAndWait();
            if (texto.isPresent()) {
                System.out.println(texto.get());
            }

        } else if (fuente.equals(bEleccion)) {

            List<String> opciones = new ArrayList<>();
            opciones.add("opción 1");
            opciones.add("opción 2");
            opciones.add("opción 3");
            opciones.add("opción 4");

            ChoiceDialog<String> dialogoEleccion = new ChoiceDialog<String>("opción 1", opciones);
            dialogoEleccion.setTitle("Diálogo de elección");
            dialogoEleccion.setHeaderText("Cabecera del cuadro de diálogo de elección");
            dialogoEleccion.setContentText("Contenido del cuadro de diálogo de elección");
            Optional<String> texto = dialogoEleccion.showAndWait();
            if (texto.isPresent()) {
                System.out.println(texto.get());
            }

        } else if (fuente.equals(bPerso)) {
            Dialog dialogoPersonalizado = new Dialog();
            dialogoPersonalizado.setTitle("Diálogo personalizado");
            dialogoPersonalizado.setHeaderText("Cabecera del diálogo personalizado");
            dialogoPersonalizado.setContentText("Contenido del diálogo personalizado");
            dialogoPersonalizado.setGraphic(new ImageView(new Image(getClass().getResourceAsStream("recursos/print.png"))));
            dialogoPersonalizado.getDialogPane().getButtonTypes().addAll(ButtonType.APPLY,ButtonType.CANCEL);
            GridPane grid = new GridPane();
            grid.setHgap(10);
            grid.setVgap(10);
            TextField nombreFichero = new TextField();
            nombreFichero.setPromptText("nombre fichero");
            TextField ruta = new TextField();
            ruta.setPromptText("ruta fichero");
            grid.add(new Label("Nombre"),0,0);
            grid.add(nombreFichero,1,0);
            grid.add(new Label("Ruta"),0,1);
            grid.add(ruta,1,1);
            dialogoPersonalizado.getDialogPane().setContent(grid);
            Optional<ButtonType> resultado = dialogoPersonalizado.showAndWait();
            if (resultado.get() == ButtonType.APPLY){
                System.out.println("Pulsado aceptar");
            } else {
                System.out.println("Pulsado cancelar");
            }

        }
    }
}