Wie erstelle und zeige ich einen allgemeinen Dialog (Fehler, Warnung, Bestätigung) in JavaFX 2.0?

74

Wie erstelle und zeige ich allgemeine Dialoge (Fehler, Warnung, Bestätigung) in JavaFX 2.0? Ich kann keine „Standard“ Klassen wie finden Dialog, DialogBox, Messageoder so etwas.

Anton
quelle
Vielleicht
möchten
Backport von JavaFX 8-Dialogen zu JDK7: github.com/BertelSpA/openjfx-dialogs-jdk7
Paolo Fulgoni

Antworten:

94

Kürzlich veröffentlichtes JDK 1.8.0_40 hat Unterstützung für JavaFX-Dialoge , Warnungen usw. hinzugefügt . Um beispielsweise ein Bestätigungsdialogfeld anzuzeigen, würde die Alert-Klasse verwendet:

Alert alert = new Alert(AlertType.CONFIRMATION, "Delete " + selection + " ?", ButtonType.YES, ButtonType.NO, ButtonType.CANCEL);
alert.showAndWait();

if (alert.getResult() == ButtonType.YES) {
    //do stuff
}

Hier ist eine Liste der hinzugefügten Klassen in dieser Version:

Ali Cheaito
quelle
Ich fand das eine gute Lösung, ich fand keinen Weg, den Anfang des Dialogs zu benennen, aber keine große Sache. Aber andererseits, würden Sie auch brauchen ...? Prost
Gideon Sassoon
@GideonSassoon Das Warnobjekt kann nach der Erstellung geändert werden. Ein Aufruf von alert.setTitle () vor showAndWait () sollte gut funktionieren.
Ali Cheaito
Excelente-Lösung ohne externe
Bibliotheken
@ GideonSassoon Sie können den Kopfzeilentext mit setzen, alert.setHeaderText("header text");wenn das ist, was Sie benötigen
nonybrighto
Einfach und précis! Merci ^^
Mangue Sutcliff
51

BEARBEITEN : JavaFX wurde Dialogunterstützung hinzugefügt, siehe https://stackoverflow.com/a/28887273/1054140


In einem Jahr 2011 gab es keine gemeinsame Dialogunterstützung. Sie mussten diese selbst schreiben, indem Sie Folgendes erstellten new Stage():

Stage dialogStage = new Stage();
dialogStage.initModality(Modality.WINDOW_MODAL);

VBox vbox = new VBox(new Text("Hi"), new Button("Ok."));
vbox.setAlignment(Pos.CENTER);
vbox.setPadding(new Insets(15));

dialogStage.setScene(new Scene(vbox));
dialogStage.show();
Sergey Grinev
quelle
11
Hmm, vielleicht erscheinen sie später wie FileChooser? Oder möchten sie, dass jeder Entwickler das Rad neu erfindet?)
Anton
9
Bereit Standarddialoge Projekt für JavaFX 2.0. Arbeitet für mich
Anton
2
Die offizielle Plattformunterstützung für den Warnungsdialog
juelsea
1
@Anton können Sie ein Beispiel für die Verwendung Ihres Dialogs zeigen? Vielen Dank!
Likejudo
3
VBoxBuilder ist jetzt veraltet. Dies ist immer noch eine nützliche Antwort, obwohl sie ein kleines Update vertragen könnte.
Adam Jensen
40

Aktualisieren

Offizielle Standarddialoge kommen in Version 8u40 als Teil der Implementierung von RT-12643 zu JavaFX . Diese sollten ab März 2015 in der endgültigen Release-Form und jetzt in Quellcode-Form im JavaFX-Entwicklungs-Repository verfügbar sein .

In der Zwischenzeit können Sie die unten stehende ControlsFX-Lösung verwenden ...


ControlsFX ist die Standardbibliothek von Drittanbietern für die allgemeine Unterstützung von Dialogen in JavaFX (Fehler, Warnung, Bestätigung usw.).

Es stehen zahlreiche andere Bibliotheken von Drittanbietern zur Verfügung, die allgemeine Dialogunterstützung bieten, wie in einigen anderen Antworten dargelegt, und Sie können mithilfe des Beispielcodes in Sergeys Antwort ganz einfach Ihre eigenen Dialoge erstellen.

Ich glaube jedoch, dass ControlsFX auf einfache Weise die derzeit verfügbaren Standard-JavaFX-Standarddialoge bietet. Hier einige Beispiele aus der ControlsFX-Dokumentation .

Standarddialog

Befehlsverknüpfungen

Juwelensee
quelle
1
Abgestimmt, aber Dokumentationslinks sind auf der verlinkten Site nicht ersichtlich. Außerdem sagt die Site, dass Maven 8.0.2 aktiv ist, aber für mich funktioniert es nur mit Maven 8.0.1 .. und ich erhalte eine "Nicht unterstützte major.minor Version 52.0", wenn ich Dialogs.create (). Message ("great"). ShowConfirm aufrufe ();
Daniel Gerson
2
Dokumentationslinks funktionieren gut für mich. In der Dokumentation heißt es derzeit: "Wichtiger Hinweis: ControlsFX funktioniert nur unter JavaFX 8.0 b102 oder höher." Wahrscheinlich versuchen Sie, ControlsFX gegen eine inkompatible Java-Version auszuführen. Wenn Sie weitere Probleme haben, sollten Sie diese im ControlsFX Issue Tracker protokollieren .
Jewelsea
Viel Glück beim Finden der Dokumentation für diese Bibliothek.
Ojonugwa Jude Ochalifu
12

Sergey ist korrekt, aber wenn Sie eine Antwort von Ihren selbst gesponnenen Dialogen zur Auswertung in demselben Codeblock erhalten müssen, in dem es aufgerufen wurde, sollten Sie .showAndWait () verwenden, nicht .show (). Hier ist meine Wiedergabe einiger Dialogtypen, die im Optionsfenster von Swing bereitgestellt werden:

public class FXOptionPane {

public enum Response { NO, YES, CANCEL };

private static Response buttonSelected = Response.CANCEL;

private static ImageView icon = new ImageView();

static class Dialog extends Stage {
    public Dialog( String title, Stage owner, Scene scene, String iconFile ) {
        setTitle( title );
        initStyle( StageStyle.UTILITY );
        initModality( Modality.APPLICATION_MODAL );
        initOwner( owner );
        setResizable( false );
        setScene( scene );
        icon.setImage( new Image( getClass().getResourceAsStream( iconFile ) ) );
    }
    public void showDialog() {
        sizeToScene();
        centerOnScreen();
        showAndWait();
    }
}

static class Message extends Text {
    public Message( String msg ) {
        super( msg );
        setWrappingWidth( 250 );
    }
}

public static Response showConfirmDialog( Stage owner, String message, String title ) {
    VBox vb = new VBox();
    Scene scene = new Scene( vb );
    final Dialog dial = new Dialog( title, owner, scene, "res/Confirm.png" );
    vb.setPadding( new Inset(10,10,10,10) );
    vb.setSpacing( 10 );
    Button yesButton = new Button( "Yes" );
    yesButton.setOnAction( new EventHandler<ActionEvent>() {
        @Override public void handle( ActionEvent e ) {
            dial.close();
            buttonSelected = Response.YES;
        }
    } );
    Button noButton = new Button( "No" );
    noButton.setOnAction( new EventHandler<ActionEvent>() {
        @Override public void handle( ActionEvent e ) {
            dial.close();
            buttonSelected = Response.NO;
        }
    } );
    BorderPane bp = new BorderPane();
    HBox buttons = new HBox();
    buttons.setAlignment( Pos.CENTER );
    buttons.setSpacing( 10 );
    buttons.getChildren().addAll( yesButton, noButton );
    bp.setCenter( buttons );
    HBox msg = new HBox();
    msg.setSpacing( 5 );
    msg.getChildren().addAll( icon, new Message( message ) );
    vb.getChildren().addAll( msg, bp );
    dial.showDialog();
    return buttonSelected;
}

public static void showMessageDialog( Stage owner, String message, String title ) {
    showMessageDialog( owner, new Message( message ), title );
}
public static void showMessageDialog( Stage owner, Node message, String title ) {
    VBox vb = new VBox();
    Scene scene = new Scene( vb );
    final Dialog dial = new Dialog( title, owner, scene, "res/Info.png" );
    vb.setPadding( new Inset(10,10,10,10) );
    vb.setSpacing( 10 );
    Button okButton = new Button( "OK" );
    okButton.setAlignment( Pos.CENTER );
    okButton.setOnAction( new EventHandler<ActionEvent>() {
        @Override public void handle( ActionEvent e ) {
            dial.close();
        }
    } );
    BorderPane bp = new BorderPane();
    bp.setCenter( okButton );
    HBox msg = new HBox();
    msg.setSpacing( 5 );
    msg.getChildren().addAll( icon, message );
    vb.getChildren().addAll( msg, bp );
    dial.showDialog();
}

}}

OtherBrotherDarryl
quelle
1
Ich habe versucht, Ihre Klasse auszuführen, aber der Compiler drosselt Layout - anscheinend die verwendeten Konstanten. Welchen Import haben Sie verwendet?
Likejudo
Wie erhält man die Antwort, dh welche Schaltfläche wurde ausgewählt? Die Mitgliedsvariable buttonSelected ist privat.
Likejudo
habe es kompiliert und buttonSelected öffentlich gemacht, aber wenn man es so aufruft, wird nichts angezeigt. `Stage Stage = neue Stage (StageStyle.TRANSPARENT); FXOptionPane.showConfirmDialog (Stufe "Möchten Sie die Verbindung trennen?", "Mein Titel"); `
Likejudo
8

Angepasst von der Antwort hier: https://stackoverflow.com/a/7505528/921224

javafx.scene.control.Alert

Eine ausführliche Beschreibung der Verwendung von JavaFX-Dialogen finden Sie unter: JavaFX-Dialoge (offiziell) von code.makery. Sie sind viel leistungsfähiger und flexibler als Swing-Dialoge und können weit mehr als nur Nachrichten anzeigen.

import javafx.scene.control.Alert
import javafx.scene.control.Alert.AlertType;
import javafx.application.Platform;

public class ClassNameHere
{

    public static void infoBox(String infoMessage, String titleBar)
    {
        /* By specifying a null headerMessage String, we cause the dialog to
           not have a header */
        infoBox(infoMessage, titleBar, null);
    }

    public static void infoBox(String infoMessage, String titleBar, String headerMessage)
    {
        Alert alert = new Alert(AlertType.INFORMATION);
        alert.setTitle(titleBar);
        alert.setHeaderText(headerMessage);
        alert.setContentText(infoMessage);
        alert.showAndWait();
    }
}

Beachten Sie, dass JavaFX ein Single-Threaded-GUI-Toolkit ist. Dies bedeutet, dass diese Methode direkt vom JavaFX-Anwendungsthread aufgerufen werden sollte. Wenn ein anderer Thread ausgeführt wird, für den ein Dialogfeld erforderlich ist, werden die folgenden Fragen und Antworten angezeigt: JavaFX2: Kann ich eine Hintergrundaufgabe / einen Hintergrunddienst anhalten? und Platform.Runlater und Task Javafx .

So verwenden Sie diese Methode:

ClassNameHere.infoBox("YOUR INFORMATION HERE", "TITLE BAR MESSAGE");

oder

ClassNameHere.infoBox("YOUR INFORMATION HERE", "TITLE BAR MESSAGE", "HEADER MESSAGE");
Troyseph
quelle
1
Bitte posten Sie keine identischen Antworten auf mehrere Fragen. Veröffentlichen Sie eine gute Antwort und stimmen Sie ab, um die anderen Fragen als Duplikate zu schließen. Wenn die Frage kein Duplikat ist, passen Sie Ihre Antworten auf die Frage an .
Martijn Pieters
1
@MartijnPieters Die ursprüngliche Frage gibt Swing als Tag an, ist jedoch offen für allgemeine Java-Dialoge (sie wurden gestellt, bevor JavaFX wirklich eine Sache war). Wenn überhaupt, ist der JavaFX-Inhalt, den ich dort gepostet habe, etwas vom Thema abweichend, aber für Neulinge nützlich, die diese Fragen und Antworten finden während Sie nach Java-Dialogen suchen und nicht feststellen, dass Swing veraltet ist.
Troyseph
Umso mehr Grund, Ihre Antwort dann auf den Kontext abzustimmen!
Martijn Pieters
Ich habe dieses Thema bei Google gefunden, daher ist es besser, Informationen hier zu haben, als ein Fragethema einzugeben, um die Antwort zu sehen, die ich brauche. Diese Antwort verdient mehr Stimmen.
Mateus Viccari
4

Dies funktioniert seit Java 8u40:

Alert alert = new Alert(AlertType.INFORMATION, "Content here", ButtonType.OK);
alert.getDialogPane().setMinHeight(Region.USE_PREF_SIZE);
alert.show();
Clairton Luz
quelle
1
Beachten Sie, dass dies im FXApplicationThread ausgeführt werden muss. (ZB mit Platform.runLater()oder ähnlich)
Lerk
2

Sie können ein Dialogfeld angeben, das vom JavaFX UI Controls Project bereitgestellt wird . Ich denke, es wird dir helfen

Dialogs.showErrorDialog(Stage object, errorMessage,  "Main line", "Name of Dialog box");
Dialogs.showWarningDialog(Stage object, errorMessage,  "Main line", "Name of Dialog box");
Rajeev Gupta
quelle
1
Es gibt keine solchen
Dialogklassen
javafx-dialogs-0.0.3.jar Sie können dieses JAR herunterladen und dann mit demselben Dialogfeld arbeiten.
Rajeev Gupta
Ich habe Ihren Beitrag bearbeitet, um einen Link zu dem JavaFX-Dialogprojekt eines Drittanbieters zu erstellen, auf das Rajeev verwiesen hat. Ich denke, es ist eine ältere Version der Dialoge von ControlsFX .
Jewelsea
2
public myClass{

private Stage dialogStage;



public void msgBox(String title){
    dialogStage = new Stage();
    GridPane grd_pan = new GridPane();
    grd_pan.setAlignment(Pos.CENTER);
    grd_pan.setHgap(10);
    grd_pan.setVgap(10);//pading
    Scene scene =new Scene(grd_pan,300,150);
    dialogStage.setScene(scene);
    dialogStage.setTitle("alert");
    dialogStage.initModality(Modality.WINDOW_MODAL);

    Label lab_alert= new Label(title);
    grd_pan.add(lab_alert, 0, 1);

    Button btn_ok = new Button("fermer");
    btn_ok.setOnAction(new EventHandler<ActionEvent>() {

        @Override
        public void handle(ActionEvent arg0) {
            // TODO Auto-generated method stub
            dialogStage.hide();

        }
    });
    grd_pan.add(btn_ok, 0, 2);

    dialogStage.show();

}



}
Ayadi
quelle
3
Es ist wahrscheinlich eine gute Idee, zumindest zu erklären, was Ihr Code tut. Es gibt ziemlich starke Meinungen darüber, ob Nur-Code-Antworten in Ordnung sind oder nicht.
Dennis Meng
0

Damit ein Beispiel für Clairton Luz funktioniert, müssen Sie das Code-Snippet FXApplicationThreadin der Platform.runLaterMethode ausführen und in die Methode einfügen:

  Platform.runLater(() -> {
                        Alert alert = new Alert(Alert.AlertType.ERROR);
                        alert.setTitle("Error Dialog");
                        alert.setHeaderText("No information.");

                        alert.showAndWait();
                    }
            );

Andernfalls erhalten Sie: java.lang.IllegalStateException: Not on FX application thread

invzbl3
quelle