如何使JavaFX确认警报框等到按下“确定”,但在按下其他按钮时执行其他操作

时间:2018-01-13 23:23:21

标签: java javafx alert

我正在编写一个Java程序,在某个时刻,必须创建一个新目录。但是,应该有一个警告消息,用户是否要继续。警报框必须包含

的选项 1.继续进行 2.停止使用 3.在Windows资源管理器中显示目标目录
我已经创建了一个警报确认框(该方法返回程序是否可以继续将文件移动到目标目录):

private static boolean createDir(Movie movie){
    String name = movie.name.getValue();
    File file = new File(Paths.get(target.getValue(),name).toString());
    if(!file.isDirectory()) {
        file.mkdir();
        return true;
    }
    else{
        Alert alert = new Alert(Alert.AlertType.CONFIRMATION);
        alert.setTitle("Duplicate");
        alert.setHeaderText("This folder already exists");
        alert.setContentText("Do you want to continue (this program will overwrite any files with duplicate names)");

        ButtonType show = new ButtonType("Show in Explorer");
        alert.getButtonTypes().add(show);

        Optional<ButtonType> option = alert.showAndWait();

        if (option.get() == null) {
            return false;
        } else if (option.get() == ButtonType.OK) {
            return true;
        } else if (option.get() == ButtonType.CANCEL) {
            return false;
        } else if (option.get() == show) {
            try {
                Desktop.getDesktop().open(new File(file.getPath()));
            } catch (IOException e) {
                e.printStackTrace();
            }
        } else {
            return false;
        }
    }
    return  false;
}

问题是,当用户点击“在资源管理器中显示”时,我希望警报框保留在屏幕上。用户将查看现有文件夹,然后单击“确定”或取消(或再次在资源管理器中显示)。

提前致谢:)

2 个答案:

答案 0 :(得分:0)

您需要为“在资源管理器中显示”创建常规按钮,而不是使默认创建的按钮与ButtonType对应。 (默认行为是创建一个关闭对话框并设置对话框结果值的按钮。)

如果您想要Alert的便利性,并且可以使用稍微不同的UI,那么您可以执行类似

的操作
    Alert alert = new Alert(Alert.AlertType.CONFIRMATION);
    alert.setTitle("Duplicate");
    alert.setHeaderText("This folder already exists");
    alert.setContentText("Do you want to continue (this program will overwrite any files with duplicate names)");

    Button show = new Button("Show in Explorer");
    show.setOnAction(e -> {
        try {
            Desktop.getDesktop().open(new File(file.getPath()));
        } catch (IOException e) {
            e.printStackTrace();
        }
    });
    alert.setGraphic(show);

    return alert.showAndWait().filter(ButtonType.OK::equals).isPresent();

如果您希望按钮出现在按钮栏中,则需要继承DialogPane并覆盖createButton方法以返回执行所需操作的按钮。

以下是使用此方法的完整示例:

import java.awt.Desktop;
import java.io.File;
import java.io.IOException;

import javafx.application.Application;
import javafx.scene.Node;
import javafx.scene.Scene;
import javafx.scene.control.Alert;
import javafx.scene.control.Alert.AlertType;
import javafx.scene.control.Button;
import javafx.scene.control.ButtonType;
import javafx.scene.control.Dialog;
import javafx.scene.control.DialogPane;
import javafx.scene.layout.StackPane;
import javafx.stage.Stage;

public class AlertWithRegularButton extends Application {

    @Override
    public void start(Stage primaryStage) {
        Button save = new Button("Save");
        save.setOnAction(e -> showDialog(primaryStage));

        StackPane root = new StackPane(save);
        Scene scene = new Scene(root, 250, 250);
        primaryStage.setScene(scene);
        primaryStage.show();
    }

    private void showDialog(Stage owner) {

        ButtonType showFileBrowserType = new ButtonType("Show in system file browser");

        DialogPane dialogPane = new DialogPane() {
            @Override
            protected Node createButton(ButtonType type) {
                if (type == showFileBrowserType) {
                    Button show = new Button(type.getText());
                    show.setOnAction(e -> {
                        try {
                            File home = new File(System.getProperty("user.home"));
                            Desktop.getDesktop().open(home);
                        } catch (IOException exc) {
                            exc.printStackTrace();
                        }
                    });
                    return show ;
                } else {
                    return super.createButton(type);
                }
            }
        };

        Alert alert = new Alert(AlertType.CONFIRMATION);
        alert.setDialogPane(dialogPane);
        alert.setTitle("Duplicate");
        alert.setHeaderText("This folder already exists");
        alert.setContentText("Do you want to continue (this program will overwrite any files with duplicate names)");
        alert.getButtonTypes().addAll(showFileBrowserType, ButtonType.CANCEL, ButtonType.OK);
        alert.initOwner(owner);
        alert.showAndWait().filter(ButtonType.OK::equals).ifPresent(b -> {
            System.out.println("OK chosen");
        });

    }

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

答案 1 :(得分:0)

试试这个

Alert alert = new Alert(Alert.AlertType.CONFIRMATION);
alert.setTitle("Duplicate");
alert.setHeaderText("This folder already exists");
alert.setContentText("Do you want to continue (this program will overwrite any files with duplicate names)");

ButtonType show = new ButtonType("Show in Explorer", ButtonBar.ButtonData.LEFT);
alert.getButtonTypes().add(show);

ButtonBar.setButtonUniformSize(alert.getDialogPane().lookupButton(show), false);
alert.getDialogPane().lookupButton(show).addEventFilter(ActionEvent.ACTION, event -> {
    try {
        Desktop.getDesktop().open(new File(new File(file.getPath())));
    }
    catch (IOException e) {
        e.printStackTrace();
    }

    event.consume();
});

Optional<ButtonType> option = alert.showAndWait();
return ButtonType.OK.equals(option.get());