Ein FXML-File mehrfach einfügen

Ø

Øtzi

Mitglied
Hallo Zusammen,

für mein Programm möchte ich ein FXML-File (FourButtons.fxml) in mein Haupt-FXML-File (Main.fxml) mehrfach einfügen. In FourButtons.fxml sind 4 Buttons in einem Grid angeordnet. Durch den Aufruf <fx:include source ="FourButtons.fxml"/> kann ich diese auch in Main.fxml einfügen. Das klappt alles wunderbar, auch wenn ich diese mehrfach einfüge.
Mein Problem ist nun, wie kann ich unterscheiden, ob ich den Button1 aus dem einem FourButtons.fxml gedrückt habe oder aus dem anderen? Den die ID-Bezeichung bleibt ja immer gleich. Ich hab dem Eingefügten ebenfalls eine ID gegeben, weiß aber nicht wie ich dies in meinem Controller einbaue.

Ich hoffe, das hier zusammen getackerte Beispiel erklärt es ein wenig.
Könnt ihr mir weiterhelfen?

Jetzt schon mal: Vielen Dank

FourButtons.fxml:
<?xml version="1.0" encoding="UTF-8"?>

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

<GridPane
    xmlns:fx="http://javafx.com/fxml/1"
    xmlns="http://javafx.com/javafx/2.2"
    fx:controller="Controller"
    hgap="5"
    vgap="5">
    
    <children>
    
        <Button
            fx:id="button1"
            prefHeight="50"
            prefWidth="50"
            onAction="#actionButton"
            GridPane.rowIndex="0" GridPane.columnIndex="0">
        </Button>

        <Button
            fx:id="button2"
            prefHeight="50"
            prefWidth="50"
            onAction="#actionButton"
            GridPane.rowIndex="1" GridPane.columnIndex="0">
        </Button>
        
        <Button
            fx:id="button3"
            prefHeight="50"
            prefWidth="50"
            onAction="#actionButton"
            GridPane.rowIndex="0" GridPane.columnIndex="1">
        </Button>
        
        <Button
            fx:id="button4"
            prefHeight="50"
            prefWidth="50"
            onAction="#actionButton"
            GridPane.rowIndex="1" GridPane.columnIndex="1">
        </Button>
    
    </children>
    
</GridPane>

Main.fxml:
<?xml version="1.0" encoding="UTF-8"?>

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

<GridPane
    xmlns:fx="http://javafx.com/fxml/1"
    xmlns="http://javafx.com/javafx/2.2"
    fx:controller="Controller"
    hgap="5"
    vgap="5">
    
    <children>

        <HBox
            spacing="10"
            alignment="bottom_right"
            GridPane.rowIndex="0" GridPane.columnIndex="0">
            <children>
                <fx:include
                    fx:id="fourButtons1"
                    source="FourButtons.fxml"/>
            </children>
        </HBox>
        
        <HBox
            spacing="10"
            alignment="bottom_right"
            GridPane.rowIndex="1" GridPane.columnIndex="0">
            <children>
                <fx:include
                    fx:id="fourButtons2"
                    source="FourButtons.fxml"/>
            </children>
        </HBox>
      
    </children>
    
</GridPane>

Controller.java:
package test;

import java.net.URL;
import java.util.ResourceBundle;
import javafx.event.ActionEvent;
import javafx.fxml.FXML;
import javafx.fxml.Initializable;
import javafx.scene.control.Button;

public class Controller implements Initializable {
    @FXML private Button button1;

    @Override
    public void initialize(URL url, ResourceBundle rb) {
        // ToDo
    }
    
    public void actionButton(ActionEvent event) {
        if(event.getSource() == button1) {
            System.out.println("Ein Button wurde betätigt.");
        }
    }
    
}

TestProg.java:
package test;

import java.io.IOException;
import java.net.URISyntaxException;
import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.scene.layout.StackPane;
import javafx.stage.Stage;

public class TestProg extends Application {
    
    @Override
    public void start(Stage primaryStage) throws IOException {
        FXMLLoader loaderViewMain = new FXMLLoader(getClass().
                getResource("Main.fxml"));
        Parent rootViewMain = loaderViewMain.load();
        Scene sceneViewMain = new Scene(rootViewMain, 800, 600);
        primaryStage.setTitle("TestProg");
        primaryStage.setScene(sceneViewMain);
        primaryStage.show();
    }
    
    public static void main(String[] args) {
        launch(args);
    }
    
}
 
L

lam_tr

Top Contributor
Warum machst du nicht aus der FXML eine Komponente, in dem du es als fx:root definierst, dann kannst du die Komponente direkt als Control einfügen anstatt als fxml includes machst?

Ich hatte früher auch sehr viel fx:includes gemacht bis ich irgendwann das Gefühl habe, dass die Performance darunter leidet. Deswegen habe ich bei komplexen Anwendungen das jetzt vermeidet.

Ansonsten kannst du die FourButtons Fxml auch programmatisch laden, dann kriegst du die jeweiligen Controllers.

Aber warum willst du die FourButtons fxml 4 mal in die Main FXML includen?
 
mrBrown

mrBrown

Super-Moderator
Mitarbeiter
Ansonsten kannst du die FourButtons Fxml auch programmatisch laden, dann kriegst du die jeweiligen Controllers.
Die kann man auch so bekommen, über @FXML FourButtonsController fourButtons2Controller ;)

@Øtzi du solltest für unterschiedliche Views unterschiedliche Controller-Klassen nutzen. In deinem Beispiel gäb es drei Instanzen von Controller, was vermutlich so nicht gewünscht ist :)
 
Ø

Øtzi

Mitglied
Vielen herzlichen Dank für eure schnelle Antwort.

@lam_tr:
Der Hinweis mit fx:root führt mich scheinbar weiter. Ich muss nur noch herausfinden, wie dies zu implementieren ist. Ich versuch mich da selbst erst einmal.

@mrBrown:
An sich ist das ja eine View bzw. ein Fenster. FourButtons.fxml ist nur ein Teil davon, der immer wieder auftaucht.

Zum Hintergrund:
Wenn ich z.B. das Brettspiel "Mensch ärger dich nicht" programmieren würde (ist nicht meine Absicht, aber das Spiel kennt jeder). Die vier Startfelder von den Spielern Rot, Schwarz, Gelb und Grün sind FourButtons.fxml. Diese kommen in meiner Main.fxml viermal vor. Um ein wenig Überblick zu behalten, wollte ich diese Auslagern. Da es sich um FourButtons.fxml um kein extra Fenster handelt, wollte ich auch nicht ein extra Controller erschaffen, der wieder mit dem Haupt-Controller kommunizieren muss. Oder sollte ich es doch?
Mein Plan war eigentlich, die Buttons in eine Array zu packen und diese über eine for-Schleife abzufragen. Ungefähr so (nur ein Beispiel):

Steuerung-Buttons:
public void actionButton(ActionEvent event) {
        for(int stein=0; stein<5; stein++) {
            for(int farbe=0; farbe<5; farbe++) {
                if(event.getSource() == buttons[farbe][stein]) {
                    System.out.println("Das ist Farbe " + farbe + " Stein " + stein);
                }
            }
        }
    }

Da in meinem Programm viele Buttons auftauchen, wäre dieses Vorgehen übersichtlicher und einfacher.
 
mrBrown

mrBrown

Super-Moderator
Mitarbeiter
Controller legt man nicht pro Fenster, sondern pro "logischer Einheit" an – ist in dem Fall also völlig gerechtfertigt, einen extra Controller für die Buttons zu haben.

Problem ist dabei sonst auch, dass der Controller mehrmals initialisert wird. Um bei dem "Mensch ärger dich nicht"-Beispiel ziu bleiben: es gäbe dann 5 "SpielController", wovon 4 nicht wirklich funktnionieren, weil sie nur die 4 Startfelder kennen, aber sonst nichts.
 
L

lam_tr

Top Contributor
Vielen herzlichen Dank für eure schnelle Antwort.

@lam_tr:
Der Hinweis mit fx:root führt mich scheinbar weiter. Ich muss nur noch herausfinden, wie dies zu implementieren ist. Ich versuch mich da selbst erst einmal.

@mrBrown:
An sich ist das ja eine View bzw. ein Fenster. FourButtons.fxml ist nur ein Teil davon, der immer wieder auftaucht.

Zum Hintergrund:
Wenn ich z.B. das Brettspiel "Mensch ärger dich nicht" programmieren würde (ist nicht meine Absicht, aber das Spiel kennt jeder). Die vier Startfelder von den Spielern Rot, Schwarz, Gelb und Grün sind FourButtons.fxml. Diese kommen in meiner Main.fxml viermal vor. Um ein wenig Überblick zu behalten, wollte ich diese Auslagern. Da es sich um FourButtons.fxml um kein extra Fenster handelt, wollte ich auch nicht ein extra Controller erschaffen, der wieder mit dem Haupt-Controller kommunizieren muss. Oder sollte ich es doch?
Mein Plan war eigentlich, die Buttons in eine Array zu packen und diese über eine for-Schleife abzufragen. Ungefähr so (nur ein Beispiel):

Steuerung-Buttons:
public void actionButton(ActionEvent event) {
        for(int stein=0; stein<5; stein++) {
            for(int farbe=0; farbe<5; farbe++) {
                if(event.getSource() == buttons[farbe][stein]) {
                    System.out.println("Das ist Farbe " + farbe + " Stein " + stein);
                }
            }
        }
    }

Da in meinem Programm viele Buttons auftauchen, wäre dieses Vorgehen übersichtlicher und einfacher.
Ist an sich nicht schwer den auf fx:root zu stellen. Schau mal hier in der ersten Antwort vom Post kannst du ein bisschen abgucken https://stackoverflow.com/questions/23600926/how-to-understand-and-use-fxroot-in-javafx
 
Ø

Øtzi

Mitglied
Beim Durchsuchen des Forums, habe ich etwas gefunden. Mit Hilfe der unteren Codezeile, ist es möglich die fx:id von fx:include abzufragen.

Java:
String farbe = ((Node) event.getSource()).getParent().getId();

Dadurch würde die Button-Abfrage im Controller wie folgt aussehen (mit der Voraussetzung die IDs haben den Namen der jeweiligen Farbe):

Java:
public void actionButton(ActionEvent event) {
    String farbe = ((Node) event.getSource()).getParent().getId();
    for(int stein=0; stein<5; stein++) {
        if(event.getSource() == buttons[stein]) {
            System.out.println("Das ist Farbe " + farbe + " Stein " + stein);
        }
    }
}

Durch diese wenigen Zeilen, könnte man am Beispiel von "Mensch ärgere dich nicht" alle 16 Startfelder auf einem Schlag abfragen, ohne zusätzliche Controller. Mein eigentliches Program hat noch viel mehr Buttons und so würde mein Code etwas übersichtlicher sein.
Das ist natürlich nur meine Meinung. Ist das Ganze ein sauberes Vorgehen? Wie würdet ihr es konkret machen (mit Root schaue ich mir noch mal an).
 
Ähnliche Java Themen
  Titel Forum Antworten Datum
R FXML File kann nicht hinzugefügt werden! AWT, Swing, JavaFX & SWT 2
S JavaFX Variablen in einem FXML File verwenden AWT, Swing, JavaFX & SWT 8
M Schliessen eines FXML Fensters? AWT, Swing, JavaFX & SWT 10
OSchriever Auf Stage von FXML-Controller zugreifen AWT, Swing, JavaFX & SWT 12
L JavaFX Exception nach includieren einer fxml // nested controller AWT, Swing, JavaFX & SWT 1
J FXML - Internationalisierung - Behandung key not found AWT, Swing, JavaFX & SWT 39
J import javafx.fxml* bei JavaFX 13 geht nicht mehr AWT, Swing, JavaFX & SWT 7
T Fxbefehle aus Main umwandeln in @FXML AWT, Swing, JavaFX & SWT 21
L JavaFX JavaFX, FXML und Guice? AWT, Swing, JavaFX & SWT 0
H 3 verschiedene Nachrichten in einer FXML View die Infos kommen aus DB AWT, Swing, JavaFX & SWT 4
H JavaFX Probleme Beim Wechseln der scene als .fxml AWT, Swing, JavaFX & SWT 7
TheWhiteShadow JavaFX Dependencies in fxml AWT, Swing, JavaFX & SWT 17
M JavaFX Altes Fenster (FXML Datei) löschen AWT, Swing, JavaFX & SWT 16
R JavaFX Java FXML Vererbung in Klassen AWT, Swing, JavaFX & SWT 9
F Java FX Von der Fxml Datei zum Objekt AWT, Swing, JavaFX & SWT 8
F FXML Datei aus dem SceneBuilder in Eclipse aufrufen AWT, Swing, JavaFX & SWT 1
I MediaPlayer (MediaView) in FXML (source) AWT, Swing, JavaFX & SWT 0
I FXML: StackPane als Root-Element AWT, Swing, JavaFX & SWT 5
I Bild über FXML (ImageView, Image) anzeigen AWT, Swing, JavaFX & SWT 1
M Übergeben von Paramter bei FXML Aufruf? AWT, Swing, JavaFX & SWT 8
M Wie bettet man Programmcode in JavaFX FXML ein? AWT, Swing, JavaFX & SWT 34
H Java FX List<AlbumsBean> in FXML TableView AWT, Swing, JavaFX & SWT 37
B FXML GUI - Button ausblenden AWT, Swing, JavaFX & SWT 1
D JavaFX Einbinden einer .fxml AWT, Swing, JavaFX & SWT 1
L [Minecraft] Spigot und JavaFX mit fxml AWT, Swing, JavaFX & SWT 0
S java.fxml.load.exception und keine automatische Aktualliseriung der Mainausgabe AWT, Swing, JavaFX & SWT 5
L JavaFX Zugriff auf HostServices im FXML Controller AWT, Swing, JavaFX & SWT 1
T Pfad zur *.fxml AWT, Swing, JavaFX & SWT 8
D Java FXML mehrere Fenster AWT, Swing, JavaFX & SWT 4
E JavaFX FXML vs. Java Code AWT, Swing, JavaFX & SWT 3
L Liniendiagramme mit FXML: Quellen mit konkreten Beispielen AWT, Swing, JavaFX & SWT 0
S JavaFX fxml datein mit menübar ändern AWT, Swing, JavaFX & SWT 20
K JavaFX JavaFX und FXML AWT, Swing, JavaFX & SWT 6
F Problem mit der FXML Rectangle Shape AWT, Swing, JavaFX & SWT 2
H JavaFX aus der .fxml Datei einen Konstruktor bedienen AWT, Swing, JavaFX & SWT 3
H JavaFX via .fxml einen abgeleiteten Button erstellen... AWT, Swing, JavaFX & SWT 4
E Java FX FXML Problem mit html Scriptausführung AWT, Swing, JavaFX & SWT 2
R Java FX - Fxml - relative Größenangaben für Breite und Höhe einer TextArea AWT, Swing, JavaFX & SWT 8
U JavaFX Zeichenprogramm mit JavaFX FXML AWT, Swing, JavaFX & SWT 7
B Java FX FXML Textarea SceneBuilder als XML Editor AWT, Swing, JavaFX & SWT 1
C JavaFX Tiefgestellte Zeichen in fxml AWT, Swing, JavaFX & SWT 2
M Java FX SceneBuilder 2.0, FXML, Controller AWT, Swing, JavaFX & SWT 1
B FXML-Layoutdateien schützen AWT, Swing, JavaFX & SWT 4
7 JavaFX Verwendung einer ResizableCanvas-Klasse in fxml-Datei AWT, Swing, JavaFX & SWT 3
C JavaFX Auf Nodes einer FXML-Datei in start Methode zugreifen AWT, Swing, JavaFX & SWT 5
KrokoDiehl JavaFX Gleiche Controller-Instanz für inludiertes FXML AWT, Swing, JavaFX & SWT 1
I Scene Builder kann .fxml nicht mehr laden AWT, Swing, JavaFX & SWT 3
S JavaFX FXML-Editor mit Java 7? AWT, Swing, JavaFX & SWT 2
J JavaFX Zugriff auf FXML-Variablen eines anderen Controllers AWT, Swing, JavaFX & SWT 2
X Java Fxml laden AWT, Swing, JavaFX & SWT 4
N JavaFX GUI Elemente einer anderen (FXML)Klasse ansprechen AWT, Swing, JavaFX & SWT 16
M JavaFX FXML Standartgröße festlegen AWT, Swing, JavaFX & SWT 5
L JavaFX Verständnisfrage zu JavaFX FXML und Controller-Klasse AWT, Swing, JavaFX & SWT 1
Z JavaFX Inhalt einer ViewTable durch Aktion einer Menubar ändern welche in einer anderen fxml ist AWT, Swing, JavaFX & SWT 4
wolfgang63 JavaFX Zugriff auf Guiobjekte die über FXML erstellt wurden AWT, Swing, JavaFX & SWT 2
H JavaFX @FXML Annotation mit Klassen und Instanzen verbinden? AWT, Swing, JavaFX & SWT 5
A Databinding in FXML-Datei AWT, Swing, JavaFX & SWT 1
K JavaFX Erzeugen dynamischer Layouts in fxml AWT, Swing, JavaFX & SWT 3
M JavaFX Stage in einer FXML-Controllerklasse ermitteln? AWT, Swing, JavaFX & SWT 5
G Swing, JavaFx - Felder aus FXML sind null AWT, Swing, JavaFX & SWT 6
M JavaFX Von FXML-Controllerdatei Daten zurückgeben AWT, Swing, JavaFX & SWT 6
M Komplexe Eingabenmasken in FXML definieren? AWT, Swing, JavaFX & SWT 17
M Java FX Innerhalb einem FXML-Dialog weiteren FXML-Dialog einblenden AWT, Swing, JavaFX & SWT 3
E JavaFX fxml files wechseln AWT, Swing, JavaFX & SWT 4
H Taschenrechnerprojekt in Javafx - Frage zu den Buttons in FXML AWT, Swing, JavaFX & SWT 1
T JavaFX FXMLController für mehrere FXML? AWT, Swing, JavaFX & SWT 7
M JavaFX Parameter für Custom Control in FXML übergeben? AWT, Swing, JavaFX & SWT 4
C JavaFX Fxml and stylecheets AWT, Swing, JavaFX & SWT 5
N FXML Dokument laden AWT, Swing, JavaFX & SWT 1
Tort-E JavaFX FXML Grundsatzfrage AWT, Swing, JavaFX & SWT 2
K Controls in Controls / Nested fxml AWT, Swing, JavaFX & SWT 1
D JavaFX Mysteriöser Dropshadow hinter Tablabelschrift - Schatten kann nicht entfernt werden (FXML + CSS) AWT, Swing, JavaFX & SWT 6
G JavaFX NullPointerException bei Zugriff auf FXML Element AWT, Swing, JavaFX & SWT 0
S JavaFX FXML AWT, Swing, JavaFX & SWT 3
G JavaFX Fxml AWT, Swing, JavaFX & SWT 2
K JavaFX Tableview mit fxml ohne Aktualiserung trotz Thread AWT, Swing, JavaFX & SWT 13
F JavaFX Auf FXML ImageView zugreifen AWT, Swing, JavaFX & SWT 6
S Aus XML Datei FXML generieren AWT, Swing, JavaFX & SWT 4
B JavaFX FXML - Eclipse einrichten AWT, Swing, JavaFX & SWT 2
V JavaFX - fxml-Datei laden (neben CSS) AWT, Swing, JavaFX & SWT 2
dzim UI aus FXML und Java gemischt - NPE? AWT, Swing, JavaFX & SWT 4
V Guis erstellen mit FXML und javaFX gemischt AWT, Swing, JavaFX & SWT 5
M File Dateien im ListView als Name anzeigen? AWT, Swing, JavaFX & SWT 6
R JavaFX Runnable jar file doesn't work AWT, Swing, JavaFX & SWT 2
F Output Stream / File Dateien / Speichern AWT, Swing, JavaFX & SWT 13
B JavaFx TreeView mit file system AWT, Swing, JavaFX & SWT 1
J File Sucher AWT, Swing, JavaFX & SWT 4
L JavaFX TreeView mit File Objects AWT, Swing, JavaFX & SWT 0
D Swing JTable mit Inhalt aus XML-File AWT, Swing, JavaFX & SWT 3
Z JAVAFX Stage über Controller weitergeben um css-file zu laden AWT, Swing, JavaFX & SWT 4
M JFX8 Mixed 2D and 3D, Scene Subscene incorrect drawing 3ds-file AWT, Swing, JavaFX & SWT 6
R JavaFX Stage.close() funktioniert nicht im jar-File AWT, Swing, JavaFX & SWT 2
B JAXB , Unmarshal XML File AWT, Swing, JavaFX & SWT 3
T FileFilter: class File wird nicht gefunden AWT, Swing, JavaFX & SWT 2
Guybrush Threepwood Desktop.open(file) hängt AWT, Swing, JavaFX & SWT 4
J SWT jar-File relativ groß AWT, Swing, JavaFX & SWT 5
M JFreeChart in ein File schreiben (bzw. JFrame in ein File Schreiben) AWT, Swing, JavaFX & SWT 2
GUI-Programmer InputStream zu File kopieren - JPrograssbar anzeigen AWT, Swing, JavaFX & SWT 10
C File-Objekte an JList übergeben und abrufen AWT, Swing, JavaFX & SWT 6
Z Component für File-Browser ähnliche Oberfläche AWT, Swing, JavaFX & SWT 6

Ähnliche Java Themen

Anzeige

Neue Themen


Oben