Question: I'm trying to open multiple windows with JavaFX, I have an eventlistener that opens a new window when a button is clicked it looks like this:

```
@FXML
private void joinAction() {
    Parent root;
    try {
        Stage stage = (Stage) joinButton.getScene().getWindow();
        stage.close();

        root = FXMLLoader.load(getClass().getResource("main.fxml"));
        stage = new Stage();
        stage.setTitle("TuneUs");
        stage.setScene(new Scene(root));
        stage.show();

    } catch (IOException e) {e.printStackTrace();}
}

```

the first window opens and the new one opens, but my problem is getting events to work with my second window

in `main.fxml` I have this line:

```
<TextField id="chat_bar" onAction="#sendChat" layoutX="14.0" layoutY="106.0" prefHeight="22.0" prefWidth="403.0"/>

```

Then in my controller class I have this method:

```
@FXML
private void sendChat() {
    System.out.println("test");
}

```

but Intellij is telling me that; no controller specified for top level element

So, my question is: Do I need to create multiple controller classes or can I use just one for multiple windows if so how?

Answer: 
The recommended approach is to define a controller for each FXML. Since controllers are very lightweight this shouldn't add much overhead. The controller for your main.fxml file might be as simple as

```
import javafx.fxml.FXML ;

public class MainController {
  @FXML
  private void sendChat() {
    // ...
  }
}

```

I have used this approach with fairly large numbers of FXML files and corresponding controllers in a single project, and have had no issues with managing the code etc. I recommend using a naming convention of the form `Main.fxml <-> MainController`.

If your controllers need to share data, use the techniques outlined in [Passing Parameters JavaFX FXML](https://stackoverflow.com/questions/14187963/passing-parameters-javafx-fxml/14190310#14190310)

As @Vertex points out in the comments, there is an alternative approach provided by the `FXMLLoader.setController(...)` method. So in your example above, you could do

```
@FXML
private void joinAction() {
    Parent root;
    try {
        Stage stage = (Stage) joinButton.getScene().getWindow();
        stage.close();

        FXMLLoader loader = new FXMLLoader (getClass().getResource("main.fxml"));
        loader.setController(this);
        root = loader.load();
        stage = new Stage();
        stage.setTitle("TuneUs");
        stage.setScene(new Scene(root));
        stage.show();

    } catch (IOException e) {e.printStackTrace();}
}

@FXML
private void sendChat() {
    // ...
}

```

This approach is fine if you are not setting any fields (controls) via FXML injection (i.e. with an `fx:id` attribute in the fxml and a corresponding `@FXML` annotation in the controller). If you are, it will be very difficult to keep track of when those fields have been set. Moreover, if your `joinAction` handler is invoked multiple times, you will have multiple instances of the node created by main.fxml, but all sharing a single controller instance (and consequently overwriting the same injected fields). Also note that with this approach, your `initialize()` method will be invoked *both* when the original fxml file is loaded, **and** when the main.fxml file is loaded, which will almost certainly cause undesired effects.

One last note: if you have many FXML files, and corresponding controllers, you might want to look at the [afterburner.fx framework](http://afterburner.adam-bien.com/). This is a very lightweight framework that mandates a naming convention on FXML files and their corresponding controllers, and also provides a (very) easy mechanism for sharing data between them.
I create Borderpane, and inside it vbox at left and scene at the center and also implement initializable . Every time i click diff button in vbox, it changes only scene. For every scene, i create scene.fxml file.