2014-09-12 3 views
0

Привет всем Я получаю всегда ошибку, загружая файл fxml через FXMLLoader. Я получил следующие занятия:StackOverflowError загружает файл FXML

package mediabox.app.model; 

import java.io.IOException; 
import javafx.fxml.FXMLLoader; 
import javafx.scene.Parent; 
import javafx.scene.Scene; 
import javafx.stage.Stage; 
import mediabox.app.controller.Controller; 

/** 
* Objekte diser Klasse repräsentieren Fenster 
* @author Christian 
*/ 
public class Window { 

    private final Stage stage; 

    /** 
    * 
    * @param resourceURL Pfad der zu ladenden FXML Datei 
    * @param controller Controller des Fensters 
    * @param height Höhe des Fensters 
    * @param width Breite des Fensters 
    * @param resizable Gibt an ob das Fenster maximierbar sein soll 
    * @param fullscreen Gibt an ob das Fenster als Vollbild geöffnet wird 
    * @throws IOException 
    */ 
    public Window(String resourceURL, Controller controller, int height, int width, boolean resizable, boolean fullscreen) throws IOException{ 
     FXMLLoader loader = new FXMLLoader(getClass().getResource(resourceURL)); //Lädt die zugehörige FXML 
     loader.setController(controller); 
     Parent root = (Parent)loader.load(); 
     Scene scene = new Scene(root, height, width); 
     stage = new Stage(); 
     stage.setResizable(resizable); 
     stage.setFullScreen(fullscreen); 
     stage.setScene(scene); 
    } 


    /** 
    * Zeigt das Fenster 
    */ 
    public void show(){ 
     stage.show(); 
    } 

    /** 
    * Versteckt das Fenster 
    */ 
    public void hide(){ 
     stage.hide(); 
    } 
} 

Это мой класс окон.

 package mediabox.app.controller; 

import java.io.IOException; 
import java.net.URL; 
import java.sql.SQLException; 
import java.util.ResourceBundle; 
import java.util.logging.Level; 
import java.util.logging.Logger; 
import javafx.fxml.FXML; 
import javafx.fxml.Initializable; 
import javafx.scene.control.TableView; 
import javafx.scene.input.KeyCode; 
import javafx.scene.input.KeyEvent; 
import javafx.scene.layout.VBox; 
import javafx.scene.media.MediaView; 
import javax.naming.NamingException; 
import mediabox.app.model.DatabaseConnector; 
import mediabox.app.model.Music; 
import mediabox.app.model.Window; 
import mediabox.app.model.exceptions.ConnectionException; 

/** 
* FXML Controller class 
* Diese Klasse repräsentiert den MusicscreenController. Er steuert alle Aktion 
* die auf auf dem Musicscreen getätigt werden. D.h auch die Aktionen die 
* innerhalb der Tabelle(Datenbank) und der Playlist ausgeführt werden. 
* @author Christian 
*/ 
public final class MusicscreenController extends Controller implements Initializable { 

    @FXML private VBox box; 

    //@FXML private Node playlistNode; 
    @FXML private final TableView libraryNode; 
    @FXML private MediaView mediaPlayerView; 


    private final Window musicscreen; 

    public MusicscreenController() throws IOException { 
     musicscreen = new Window("/mediabox/app/view/MusicscreenView.fxml", this, 0, 0, false, true); 
     musicscreen.show(); 
     libraryNode = new TableView(); 
     initLibrary(); 
     libraryNode.requestFocus(); 
     libraryNode.getSelectionModel().selectFirst(); 

    } 

    /** 
    * Initialisiert die Bibliothek 
    */ 
    @Override 
    protected void initLibrary(){ 
     try { 
      DatabaseConnector.connectTo("src/mediabox/database/database"); 
      libraryNode.getItems().addAll(DatabaseConnector.loadEntries("Music")); // Einträge der Datenbank 
                      // auslesen und der library Node hinzufügen 
     } catch (SQLException | ConnectionException | NamingException | ClassNotFoundException ex) { 
      Logger.getLogger(MusicscreenController.class.getName()).log(Level.SEVERE, null, ex); 
     } 
    } 

    @Override 
    public void initialize(URL url, ResourceBundle rb) { 
     // TODO 
    } 


    @FXML 
    public void onLibraryRequest(KeyEvent e){ 
     if(e.getCode().equals(KeyCode.ENTER)){ 
      try { 
       MediaPlayerController mediaPlayerController = new MediaPlayerController((Music)libraryNode.getSelectionModel().getSelectedItem()); 
      } catch (IOException ex) { 
       Logger.getLogger(MusicscreenController.class.getName()).log(Level.SEVERE, null, ex); 
      } 

     } 
    } 


} 

Это мой класс контроллера.

В этом коде я не могу найти никаких ссылок. В течение нескольких дней код работает нормально ....

-GhostfaceChilla-

ответ

0

При загрузке FXML, то FXML погрузчик видит атрибут fx:controller="mediabox.app.controller.MusicscreenController" в корневом элементе. Это дает указание создать экземпляр new MusciscreenController. Конструктор MusicscreenController вызывает конструктор Window. Конструктор Window создает новый FXMLLoader и вызывает его метод load(), который анализирует FXML, заставляя его создать новый MusicscreenController.

Итак, у вас есть бесконечная рекурсия.

Вы, вероятно, просто нужно удалить конструктор из контроллера целиком и поместить большую часть логики оттуда в initialize() метода:

@Override 
public void initialize(URL url, ResourceBundle rb) { 
    initLibrary(); 
    libraryNode.requestFocus(); 
    libraryNode.getSelectionModel().selectFirst(); 
} 

Вы не можете показать окно с контроллера, так как конструктор и метод initialize, прежде чем вы получите возможность добавить корневой узел из FXML в Scene. (Кроме того, вы хотите, чтобы ваша пара FXML-контроллер должен быть достаточно гибким, чтобы иметь возможность использовать, когда они не являются корнем Scene.)

Таким образом, вы должны либо просто вызвать show() из Window конструктора, или вы должны вызывать его из любого места, где вы вызываете конструктор Window.

Смежные вопросы