2016-12-08 6 views
0

スーパーコンストラクタを呼び出すクラスがあります。スーパークラスはように、ラッパー内の要素の子としてFXMLラッパーのレイアウトをロードし、その後、別のFXMLレイアウト:JavaFxネストされたコントローラ?

// Reference 'outer' FXML 
URL outer_url = getClass().getResource("/main/resources/fxml/RootNode.fxml"); 
FXMLLoader outer_loader = new FXMLLoader(outer_url); 
outer_loader.setRoot(this); 
outer_loader.setController(this); 

// Reference 'inner' FXML 
URL inner_url = getClass().getResource(fxml_path); 
FXMLLoader inner_loader = new FXMLLoader(inner_url); 

try { 
    outer_loader.load(); 

    /* The root of inner_loader is a component of outer_loader FXML, 
    * thus outer_loader.load() must be called first. */ 
    inner_loader.setRoot(outer_loader.getNamespace().get("vbox_center")); 
    inner_loader.setController(controller); 
    inner_loader.load(); 
} catch (IOException e) { 
    e.printStackTrace(); 
} 

私はinner_loaderのコントローラであることをクラスが必要です。これは可能ですか?私はスーパーコンストラクタを通してクラスへの参照を渡そうとしましたが、スーパーコンストラクタが呼び出される前に 'this'を参照することはできません。

アイデア?前もって感謝します。

EDIT:コントローラーを内部のFXMLファイルで直接指定しようとしましたが、これは問題を引き起こしました。

EDIT 2:2つのFXMLレイアウトをロードするスーパークラスが複数のノードによって継承されるため、コントローラのインスタンスを作成してinner_loaderに直接渡すことはできません。私は(何とか)スーパークラスへのインスタンス参照を渡す必要があり、コントローラとしてそれを使用します。

+0

の重複:のJavaFXネストされた連続ローラー(FXML )](http://stackoverflow.com/questions/12543487/javafx-nested-controllers-fxml-include)? – jewelsea

+0

私はその質問を見ました - 私との違いは、FXMLをロードするスーパークラスは複数の異なるノードによって継承され、そのようなインスタンス参照を渡す必要があるということです。毎回新しいノードを作成することはできません。 – user3668541

+0

"スーパークラスにインスタンス参照を渡す必要があります":そのステートメントが意味することを本当に理解できません。現在のオブジェクト( 'this')はもちろん、それ自身のクラスのインスタンスであり、結果としてスーパークラスのインスタンスでもあります。'this'を渡すことができます。これは2つの異なるFXMLファイルのコントローラと同じオブジェクトを使用することになり、' initialize() 'メソッドがあればそれが2回呼び出されるためです。 –

答えて

1

あなたがしようとしていることは完全にはっきりしていませんが、継承を使用しようとしていて、FXML-based custom componentsという特殊化されたテンプレートを作成しようとしているようです。

これは可能です。コンストラクタで通常の方法でFXMLをロードすることができます。各コンストラクターはそのスーパークラスコンストラクターを呼び出すため、スーパークラスFXMLはサブクラスFXMLの前にロードされます。

プロジェクトレイアウト:

enter image description here

テンプレート:

Template.fxml:

<?xml version="1.0" encoding="UTF-8"?> 

<?import javafx.scene.layout.BorderPane?> 
<?import javafx.scene.control.MenuBar?> 
<?import javafx.scene.control.Menu?> 
<?import javafx.scene.control.MenuItem?> 
<?import javafx.scene.layout.VBox?> 

<fx:root xmlns:fx="http://javafx.com/fxml/1" type="BorderPane"> 
    <top> 
     <MenuBar> 
      <menus> 
       <Menu text="File"> 
        <items> 
         <MenuItem text="Quit" onAction="#quit"/> 
        </items> 
       </Menu> 
      </menus> 
     </MenuBar> 
    </top> 

    <center> 
     <VBox fx:id="vboxCenter"/> 
    </center> 

</fx:root> 

成分(Template.java):

package template; 

import java.io.IOException; 

import javafx.fxml.FXML; 
import javafx.fxml.FXMLLoader; 
import javafx.scene.layout.BorderPane; 
import javafx.scene.layout.VBox; 

public class Template extends BorderPane { 

    @FXML 
    private VBox vboxCenter ; 

    public Template() throws IOException { 
     FXMLLoader loader = new FXMLLoader(Template.class.getResource("Template.fxml")); 
     loader.setRoot(this); 
     loader.setController(this); 
     loader.load(); 
    } 

    protected final VBox getCenterContentHolder() { 
     return vboxCenter ; 
    } 

    @FXML 
    private void quit() { 
     vboxCenter.getScene().getWindow().hide(); 
    } 
} 

専門:

Home.fxml:

<?xml version="1.0" encoding="UTF-8"?> 

<?import javafx.scene.layout.VBox?> 
<?import javafx.scene.control.Label?> 
<?import javafx.scene.text.Font?> 

<fx:root xmlns:fx="http://javafx.com/fxml/1" type="VBox" alignment="CENTER"> 
    <Label fx:id="welcomeLabel" text="Welcome" /> 
</fx:root> 

成分(Home.java):

package home; 

import java.io.IOException; 

import javafx.fxml.FXML; 
import javafx.fxml.FXMLLoader; 
import javafx.scene.control.Label; 
import javafx.scene.text.Font; 
import template.Template; 

public class Home extends Template { 

    @FXML 
    private Label welcomeLabel ; 

    public Home() throws IOException { 

     // not necessary to explicitly call super(), it is called by default 
     // this call loads the template defined by the superclass 
     super(); 

     FXMLLoader loader = new FXMLLoader(Home.class.getResource("Home.fxml")); 
     loader.setRoot(getCenterContentHolder()); 
     loader.setController(this); 

     loader.load(); 

     welcomeLabel.setFont(Font.font("Arial", 48)); 
    } 
} 

アプリケーション:

package application; 

import java.io.IOException; 

import home.Home; 
import javafx.application.Application; 
import javafx.scene.Scene; 
import javafx.stage.Stage; 

public class Main extends Application { 

    @Override 
    public void start(Stage primaryStage) throws IOException { 
     Scene scene = new Scene(new Home(), 400, 400); 
     primaryStage.setScene(scene); 
     primaryStage.show(); 
    } 

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

enter image description here

+0

これはとても助けになりました。ありがとうございました。 – user3668541

関連する問題