2015-02-01 3 views
0

Java에서 FXML 파일을 사용하는 데 문제가 있습니다.Javafx 위치가 필요합니다 (다른 폴더/패키지에서 FXML 파일로드)

지금 수 시간 동안 검색 한 결과 내 문제를 해결할 수있는 항목이 없으므로 나의 마지막 희망은 내 특정 사례에 대한 질문을하는 것입니다 (나는 this one과 같은 질문을 알고 있지만 다른 사람은 실제로 나를 도왔습니다. 이 점에 대해

간단한 설명 : Eclipse Java Project가 있고이 질문에 대한 중요한 클래스는 [Project Name] /src/measurements.gui 패키지에 있습니다 .FXML 파일은 [Project Name] 폴더에 있습니다. ]/resources

FXML 파일 ElementsProperties.java를로드하는 내 클래스는 다음과 같습니다.

FXML 파일은 다음과 같은 간단한 라인과 대화로 표시됩니다 : ElementsProperties.show(parent, "TestWindow");

내 FXML 파일합니다 (JavaFXSceneBuilder 2.0 생성)은 다음과 같습니다 `

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

<?import javafx.scene.effect.*?> 
<?import javafx.geometry.*?> 
<?import java.lang.*?> 
<?import java.util.*?> 
<?import javafx.scene.control.*?> 
<?import javafx.scene.layout.*?> 
<?import javafx.scene.paint.*?> 
<?import javafx.scene.text.*?> 

<VBox prefHeight="400.0" prefWidth="640.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1"> 
    <children> 
    <MenuBar VBox.vgrow="NEVER"> 
     <menus> 
     <Menu mnemonicParsing="false" text="File"> 
      <items> 
      <MenuItem mnemonicParsing="false" text="New" /> 
      <MenuItem mnemonicParsing="false" text="Open…" /> 
      <Menu mnemonicParsing="false" text="Open Recent" /> 
      <SeparatorMenuItem mnemonicParsing="false" /> 
      <MenuItem mnemonicParsing="false" text="Close" /> 
      <MenuItem mnemonicParsing="false" text="Save" /> 
      <MenuItem mnemonicParsing="false" text="Save As…" /> 
      <MenuItem mnemonicParsing="false" text="Revert" /> 
      <SeparatorMenuItem mnemonicParsing="false" /> 
      <MenuItem mnemonicParsing="false" text="Preferences…" /> 
      <SeparatorMenuItem mnemonicParsing="false" /> 
      <MenuItem mnemonicParsing="false" text="Quit" /> 
      </items> 
     </Menu> 
     <Menu mnemonicParsing="false" text="Edit"> 
      <items> 
      <MenuItem mnemonicParsing="false" text="Undo" /> 
      <MenuItem mnemonicParsing="false" text="Redo" /> 
      <SeparatorMenuItem mnemonicParsing="false" /> 
      <MenuItem mnemonicParsing="false" text="Cut" /> 
      <MenuItem mnemonicParsing="false" text="Copy" /> 
      <MenuItem mnemonicParsing="false" text="Paste" /> 
      <MenuItem mnemonicParsing="false" text="Delete" /> 
      <SeparatorMenuItem mnemonicParsing="false" /> 
      <MenuItem mnemonicParsing="false" text="Select All" /> 
      <MenuItem mnemonicParsing="false" text="Unselect All" /> 
      </items> 
     </Menu> 
     <Menu mnemonicParsing="false" text="Help"> 
      <items> 
      <MenuItem mnemonicParsing="false" text="About MyHelloApp" /> 
      </items> 
     </Menu> 
     </menus> 
    </MenuBar> 
    <AnchorPane maxHeight="-1.0" maxWidth="-1.0" prefHeight="-1.0" prefWidth="-1.0" VBox.vgrow="ALWAYS"> 
     <children> 
     <Label alignment="CENTER" layoutX="155.0" layoutY="177.0" style="&#10;" text="Drag components from Library here…" textAlignment="CENTER" textFill="#9f9f9f" wrapText="false"> 
      <font> 
      <Font size="18.0" /> 
      </font> 
     </Label> 
      <GridPane layoutX="-2.0" layoutY="-3.0" prefHeight="407.0" prefWidth="659.0"> 
       <columnConstraints> 
       <ColumnConstraints hgrow="SOMETIMES" minWidth="10.0" prefWidth="100.0" /> 
       <ColumnConstraints hgrow="SOMETIMES" minWidth="10.0" prefWidth="100.0" /> 
       </columnConstraints> 
       <rowConstraints> 
       <RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" /> 
       <RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" /> 
       <RowConstraints minHeight="10.0" prefHeight="30.0" vgrow="SOMETIMES" /> 
       </rowConstraints> 
       <children> 
        <HBox prefHeight="134.0" prefWidth="654.0" spacing="20.0" GridPane.rowIndex="1"> 
        <children> 
         <Button mnemonicParsing="false" prefHeight="46.0" prefWidth="60.0" text="Click me" wrapText="true" /> 
         <Button mnemonicParsing="false" prefHeight="47.0" prefWidth="73.0" text="No, click me" wrapText="true" /> 
         <Button mnemonicParsing="false" prefHeight="46.0" prefWidth="120.0" text="Don't you dare click me" wrapText="true" /> 
        </children> 
        <padding> 
         <Insets bottom="20.0" left="20.0" right="20.0" top="20.0" /> 
        </padding> 
        </HBox> 
        <TextField promptText="Type something here..." GridPane.columnIndex="1" GridPane.rowIndex="1"> 
        <GridPane.margin> 
         <Insets left="20.0" right="20.0" /> 
        </GridPane.margin> 
        </TextField> 
       </children> 
      </GridPane> 
     </children> 
    </AnchorPane> 
    </children> 
</VBox> 

이것은 실제로 필요한 모든 것. 프로그램을 실행하고 대화 상자를 표시하려고하면 예외가 발생합니다.

java.lang.NullPointerException: Location is required. 

이 제공됩니다. FXML 파일을 measurements.gui라는 메인 클래스와 같은 패키지로 옮기고 ELementsProperties.java 클래스의 showPath를 "TestWindow.fxml"으로 변경하면 모든 것이 잘 작동하고 응용 프로그램에 생성 된 윈도우가 나타납니다. . 하지만 다른 fxml 파일을 편리하게 삽입 할 수 있도록 별도의 리소스 폴더에 fxml 파일을 저장하려고합니다.

제 문제를 명확하게 설명하고이 문제를 해결할 수 있기를 바랍니다. 주요 클래스가 아닌 다른 패키지에서 fxml 파일을로드하는 방법에 대한 아이디어는 무엇입니까? 는, BTW 이미 해봤 사항은 다음과 같습니다

  1. 처음
  2. 에 슬래시 와 경로에 "/resources/TestWindow.fxml을 '(설정 ​​클래스 경로에 자원 폴더를 추가 FXMLLoader의로드 방법 매개 변수 로
  3. 사용 getClass().getClassLoader().getResource(filePath)

미리 감사드립니다.

+0

내 대답은 도움이 될 수 있습니다. http://stackoverflow.com/questions/23975897/how-to-add-a-css-stylesheet-in-fxml/28123426#28123426 ... 그렇지 않다면 문제의 일부분 만이 아니라 완전한 검증 가능한 예제를 제공하십시오. – Roland

+0

고마워, @ 롤랜드! 그 폴더 구조는 필자에게 필요한 단서를 제공해주었습니다. 미안 문제에 대해 충분히 명확하지 않은 경우이 문제에 대해 알아야 할 모든 것을 작성했다고 생각했습니다. – Chris777

답변

0

고마워, 롤랜드. 폴더 구조를 복사하려고 시도했는데 다음과 같은 문제가 발생했습니다. (동일한 문제가있는 다른 사람들의 경우)

테스트 프로젝트 JavaFXTest를 만들었습니다. org.example.main 패키지에 하나의 메인 클래스가 있습니다. 패키지는 일반적으로 프로젝트의 src 폴더에 있습니다.

MyJavaFXDialog.java는 :

package org.example.main; 

import java.io.IOException; 

import javafx.application.Application; 
import javafx.fxml.FXMLLoader; 
import javafx.scene.Parent; 
import javafx.scene.Scene; 
import javafx.scene.layout.BorderPane; 
import javafx.stage.Modality; 
import javafx.stage.Stage; 

public class MyJavaFXDialog extends Application{ 

    public void start(Stage primaryStage) { 

    MyJavaFXDialog javaFx = new MyJavaFXDialog(); 
    BorderPane root = javaFx.loadFXMLFile("/resources/TestWindow.fxml"); 

    Stage dialog = new Stage(); 
    dialog.initModality(Modality.WINDOW_MODAL); 
    dialog.setScene(new Scene(root)); 
    dialog.show(); 
    } 

    @SuppressWarnings({ "finally", "static-access" }) 
    private BorderPane loadFXMLFile(String filePath) { 
    BorderPane borderPane = null; 
    try { 
     borderPane = new BorderPane(); 
     FXMLLoader fxmlLoader = new FXMLLoader(); 
     Parent content = fxmlLoader.load(getClass().getResource(filePath)); 
     borderPane.setCenter(content); 
    } 
    catch (IOException e) { 
     e.printStackTrace(); 
     System.err.println("Couldn't find the specified file"); 
    } 
    catch(Exception e){ 
     e.printStackTrace(); 
    } 
    finally { 
     return borderPane; 
    } 
    } 

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

나는 src 폴더에서 일반 폴더 "자원"을 만들었습니다. 해당 리소스 폴더에 내 질문에 정확히 동일한 내 TestWindow.fxml 파일 만 포함되어 있습니다. 이제 응용 프로그램을 시작할 때 fxml 파일이 발견되어 기본 창으로 표시됩니다.

그래서 해결책은 실질적으로 리소스 폴더 으로 옮기는 것이 었습니다.이 경우에도 여전히 내 사례에 대해 가능한 솔루션입니다. 필자는 최종 사용자가 자신의 fxml 파일을 저장하기 위해 다른 패키지의 깊이에서 찌르기를 원치 않았습니다.

감사합니다. Roland, 저 해결책을 향해 나를 가리켜주었습니다.

+0

관련없는 코멘트 : 'FXMLLoader.load (URL)'은 정적 메소드입니다. (실제로 사용하지 않는)'fxmlLoader' 인스턴스에서 호출하지 않습니다. 'fxmlLoader' 인스턴스를 제거하고 정적 메소드를 일반적인 방법으로 호출해야합니다 :'Parent content = FXMLLoader.load (...);'('fxmlLoader' 인스턴스에서 위치를 설정하고 인수가없는' load()'메소드). –

+0

사실, FXMLLoader의 정적로드 메소드가 사용되지 않을 예정입니다. 이것이 내가이 접근법을 선택한 이유입니다. – Chris777

+0

그것에 대한 토론이 있었지만 그것이 결정되었는지는 모르겠습니다. 귀하의 코드는 여전히 정적 메서드를 호출합니다. –

관련 문제