JavaFX et maven: NullPointerException: L'emplacement est requis

J'ai essayé de configurer Maven avec JavaFX. Même si j'étais inexpérimenté avec Maven et JavaFX, Je ne m'attendais pas à ce que ce soit un défi. Ma connaissance Java est assez solide (y compris Swing), et je ne m'attendais pas à avoir autant de difficulté à le mettre en place.

J'ai commencé avec un projet JavaFX fourni par IntelliJ 13.0 Community Edition. Le code de ma classe principale est relativement petit:

package sample;

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

public class Main extends Application
{
    @Override
    public void start(Stage primaryStage) throws Exception
    {
        //getClass().getResource("../../resources/sample.fxml");
        Parent root = FXMLLoader.load(getClass().getResource("../sample.fxml"));
        primaryStage.setTitle("Hello World");
        primaryStage.setScene(new Scene(root, 300, 275));
        primaryStage.show();
    }


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

Et mon pom.xml n'est pas trop grand non plus:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>sample</groupId>
    <artifactId>JavaFXDemo</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>jar</packaging>

    <organization>
        <name>RubberDucky</name>
    </organization>

    <build>
        <pluginManagement>
            <plugins>
                <plugin>
                    <groupId>com.zenjava</groupId>
                    <artifactId>javafx-maven-plugin</artifactId>
                    <version>2.0</version>
                </plugin>
            </plugins>
        </pluginManagement>
        <plugins>
            <plugin>
                <groupId>com.zenjava</groupId>
                <artifactId>javafx-maven-plugin</artifactId>
                <version>2.0</version>
                <configuration>
                    <mainClass>sample.Main</mainClass>
                </configuration>
            </plugin>
        </plugins>
    </build>

    <dependencies>
        <dependency>
            <groupId>com.oracle</groupId>
            <artifactId>javafx</artifactId>
            <version>2.2</version>
            <systemPath>${java.home}/lib/jfxrt.jar</systemPath>
            <scope>system</scope>
        </dependency>
    </dependencies>
</project>

Je suis utilisation du Plugin JavaFX Maven pour construire l'application. Après avoir exécuté mvn clean jfx:jar tout semble bien, toutes les constructions réussissent. Mais quand j'essaye d'exécuter l'application, j'obtiens l'erreur suivante:

Exception in Application start method
java.lang.reflect.InvocationTargetException
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
        at java.lang.reflect.Method.invoke(Unknown Source)
        at com.javafx.main.Main.launchApp(Main.java:698)
        at com.javafx.main.Main.main(Main.java:871)
Caused by: java.lang.RuntimeException: Exception in Application start method
        at com.sun.javafx.application.LauncherImpl.launchApplication1(Unknown So
urce)
        at com.sun.javafx.application.LauncherImpl.access$000(Unknown Source)
        at com.sun.javafx.application.LauncherImpl$1.run(Unknown Source)
        at java.lang.Thread.run(Unknown Source)
Caused by: java.lang.NullPointerException: Location is required.
        at javafx.fxml.FXMLLoader.load(Unknown Source)
        at javafx.fxml.FXMLLoader.load(Unknown Source)
        at javafx.fxml.FXMLLoader.load(Unknown Source)
        at javafx.fxml.FXMLLoader.load(Unknown Source)
        at javafx.fxml.FXMLLoader.load(Unknown Source)
        at sample.Main.start(Main.java:15)
        at com.sun.javafx.application.LauncherImpl$5.run(Unknown Source)
        at com.sun.javafx.application.PlatformImpl$5.run(Unknown Source)
        at com.sun.javafx.application.PlatformImpl$4$1.run(Unknown Source)
        at com.sun.javafx.application.PlatformImpl$4$1.run(Unknown Source)
        at java.security.AccessController.doPrivileged(Native Method)
        at com.sun.javafx.application.PlatformImpl$4.run(Unknown Source)
        at com.sun.glass.ui.InvokeLaterDispatcher$Future.run(Unknown Source)
        at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
        at com.sun.glass.ui.win.WinApplication.access$100(Unknown Source)
        at com.sun.glass.ui.win.WinApplication$3$1.run(Unknown Source)
        ... 1 more

Après un débogage approximatif, le problème semble être dans le chemin à partir duquel je charge mes fichiers. Après avoir codé en dur le sample.fxml à un endroit sur mon disque dur, l'application s'exécute sans aucun problème. Il en va de même pour la configuration actuelle (vue ci-dessus) lors de l'exécution de l'application à partir de IntelliJ.

J'ai l'impression d'avoir épuisé toutes les ressources (y compris StackOverflow, quelques erreurs très similaires) mais je n'arrive tout simplement pas à comprendre ce qui ne va pas exactement.

26
demandé sur OxySocks 2014-02-25 02:23:17

5 réponses

Assurez - vous que votre sample.fxml se trouve dans le répertoire src/main/resources/ (ou dans un sous-répertoire). Ensuite, vous pouvez accéder au fichier comme ceci:

Parent root = FXMLLoader.load(getClass().getClassLoader().getResource("sample.fxml"));

Explication: Pendant la phase de compilation, toutes les ressources et classes sont copiées dans target/classes/. Ainsi, votre fichier fxml réside dans ce répertoire et votre classe dans un sous-répertoire concernant son nom de paquet. Si vous appelez getClass().getResource("sample.fxml"); le fichier sera recherché par rapport à la classe fichier de ce répertoire: target/classes/sample/.

Appeler .getResource() sur le chargeur de classe définit le chemin de recherche relatif à target/classes/ et donc votre fichier est trouvé.

P.S. vous pouvez aussi écrire:

Parent root = FXMLLoader.load(getClass().getResource("/sample.fxml"));
71
répondu Absurd-Mind 2014-02-25 10:21:30

Comme @Absurd-Mind l'a déjà expliqué, maven ne copiera aucun fichier de ressources (comme fxml) qui se trouve sous le répertoire src.

Si vous souhaitez conserver les fichiers fxml en plus des fichiers source java, vous pouvez utiliser le plugin de ressources Maven pour les copier:

<build>
    ...
    <resources>
        <resource>
            <filtering>false</filtering>
            <directory>src/main/java</directory>
            <includes>
                <include>**/*.fxml</include>
            </includes>             
        </resource>
    </resources>
    ...
</build>
7
répondu mrak 2018-08-18 12:45:46

J'ai eu le même problème avec Intelij et Gradle: Étapes à corriger:

1.Déplacer le fichier

Échantillon.fxml

Vers le chemin

\src\main\ressources\fxml

  1. définir le chemin sur ce fichier:

Racine Parent = FXMLLoader.charger (getClass ().getResource ("/FXML / sample.fxml"));

3
répondu user3871754 2016-08-30 13:24:07

Pour ceux qui utilisent gradle {[7] } comme système de construction ajoutez ceci à votre fichier build.gradle:

sourceSets.main.resources {
    srcDirs = ["src/main/java"]; //assume that your java classes are inside this path
    exclude "**/*.java"
}

Ensuite, nettoyez et reconstruisez votre projet.

Alors que va-t-il faire? Si vous avez un view.fxml dans votre paquet com.example.myfxapp, Après avoir construit votre projet, il sera exporté vers <build dir>/resources/com/example/myfxapp/view.fxml

1
répondu Saeed Masoumi 2016-03-06 20:34:12

Pour moi, j'avais pris soin de suivre les choses -

  1. Assurez-vous que le fichier fxml est placé là où réside votre classe principale. Et puis chargez-le en utilisant ceci - (dans mon cas, TechJFX.fxml est le fichier)

    FXMLLoader loader = new FXMLLoader(getClass().getResource("TechJFX.fxml"));
    
  2. Ajouter opencv-*.jar dans votre dossier de projet (Dans mon cas opencv-300.jar)

  3. Ajoutez le jar au chemin de construction en utilisant

Faites un clic droit sur le dossier du projet - > chemin de construction - > configurer le chemin de construction - > onglet Bibliothèques - > ajouter des localiser le pot

Aussi, sous commande et exportation - > cochez opencv-300.bibliothèque système jar et JRE (si elle n'est pas déjà cochée)

  1. Copier opencv_java*.dll (dans mon cas opencv_java300.dll) au même endroit où vous jar est dans le dossier du projet.

  2. Ajoutez la méthode suivante à votre classe principale

     static{ 
            System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
       }
    
  3. C'est fait.

J'espère que cela aidera quelqu'un face à un problème similaire.

0
répondu Techidiot 2015-09-16 13:25:03