0

I am using the Maven Shade plugin with Eclipse and JavaFX. Maven Shade creates a runnable jar to allow me to run my program. The program compiles and runs and shows the GUI with no errors via eclipse. The maven build runs with no errors and create the jar, the issue comes when I try to run my jar.

I get the following error.

I have read a few similar issues on here but none of them seemed to have the same setup as myself. Similar This guy moved the fxml files into his resources folder but I wanted to try keep my project MVC. Is there another fix?

My issue seems to be the fx:controller= in the MainMenu.fxml

Error: Caused by: java.lang.IllegalStateException: Location is not set.

ERROR

javafx.fxml.LoadException: 
file:/Users/bob/git/Corkscrew/Corkscrew/Corkscrew%20Server/target/Corkscrew-0.0.1-SNAPSHOT.jar!/io/ironbytes/corkscrew/views/MainMenu.fxml:10

    at javafx.fxml.FXMLLoader.constructLoadException(FXMLLoader.java:2601)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2579)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2441)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3214)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3175)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3148)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3124)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3104)
    at javafx.fxml.FXMLLoader.load(FXMLLoader.java:3097)
    at io.ironbytes.corkscrew.models.MainMenu.start(MainMenu.java:23)
    at com.sun.javafx.application.LauncherImpl.lambda$launchApplication1$162(LauncherImpl.java:863)
    at com.sun.javafx.application.PlatformImpl.lambda$runAndWait$175(PlatformImpl.java:326)
    at com.sun.javafx.application.PlatformImpl.lambda$null$173(PlatformImpl.java:295)
    at java.security.AccessController.doPrivileged(Native Method)
    at com.sun.javafx.application.PlatformImpl.lambda$runLater$174(PlatformImpl.java:294)
    at com.sun.glass.ui.InvokeLaterDispatcher$Future.run(InvokeLaterDispatcher.java:95)
Caused by: java.lang.IllegalStateException: Location is not set.
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2434)
    at javafx.fxml.FXMLLoader.load(FXMLLoader.java:2409)
    at io.ironbytes.corkscrew.models.ConnectionsPane.<init>(ConnectionsPane.java:33)
    at io.ironbytes.corkscrew.controllers.MainMenuController.<init>(MainMenuController.java:32)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
    at java.lang.Class.newInstance(Class.java:442)
    at sun.reflect.misc.ReflectUtil.newInstance(ReflectUtil.java:51)
    at javafx.fxml.FXMLLoader$ValueElement.processAttribute(FXMLLoader.java:927)
    at javafx.fxml.FXMLLoader$InstanceDeclarationElement.processAttribute(FXMLLoader.java:971)
    at javafx.fxml.FXMLLoader$Element.processStartElement(FXMLLoader.java:220)
    at javafx.fxml.FXMLLoader$ValueElement.processStartElement(FXMLLoader.java:744)
    at javafx.fxml.FXMLLoader.processStartElement(FXMLLoader.java:2707)
    at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2527)
    ... 14 more

MainMenu.java

package io.ironbytes.corkscrew.models;

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

public class MainMenu extends Application {
    Parent root;
    Stage stage;

    @Override
    public void start(Stage primaryStage) {

        try {
            root = FXMLLoader.load(getClass().getClassLoader().getResource("io/ironbytes/corkscrew/views/MainMenu.fxml"));

            stage = primaryStage;
            stage.setTitle("Welcome");

            Scene scene = new Scene(root);
            stage.setScene(scene);
            stage.show();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

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

MainMenu.fxml

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

<?import javafx.scene.control.Button?>
<?import javafx.scene.control.TextField?>
<?import javafx.scene.control.ToolBar?>
<?import javafx.scene.image.Image?>
<?import javafx.scene.image.ImageView?>
<?import javafx.scene.layout.BorderPane?>

<BorderPane fx:id="mainPane" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="900.0" xmlns="http://javafx.com/javafx/9" xmlns:fx="http://javafx.com/fxml/1" fx:controller="io.ironbytes.corkscrew.controllers.MainMenuController">
   <left>
      <ToolBar orientation="VERTICAL" BorderPane.alignment="CENTER">
        <items>
          <Button mnemonicParsing="false" onAction="#onConnectionsBtnClick" prefHeight="27.0" prefWidth="82.0" text="Clients" />
            <Button mnemonicParsing="false" onAction="#onBuilderBtnClick" prefHeight="27.0" prefWidth="83.0" text="Builder" />
            <Button mnemonicParsing="false" prefHeight="27.0" prefWidth="83.0" text="Crypter" />
            <Button mnemonicParsing="false" onAction="#onCorkscrewBtnClick" text="Corkscrew" />
            <Button fx:id="listenBtn" mnemonicParsing="false" onAction="#onListenBtnClick" prefHeight="27.0" prefWidth="82.0" text="Listen" textFill="#e43333" />
            <TextField prefHeight="27.0" prefWidth="8.0" promptText="Port: 1337" />
        </items>
      </ToolBar>
   </left>
   <center>
      <ImageView fitHeight="255.0" fitWidth="348.0" pickOnBounds="true" preserveRatio="true" BorderPane.alignment="CENTER">
         <image>
            <Image url="@../../../../img/logo.png" />
         </image>
      </ImageView>
   </center>
</BorderPane>
d3t0x
  • 432
  • 4
  • 15
  • Try to change this `.getResource("io/ironbytes/corkscrew/views/MainMenu.fxml"));` to this `.getResource("/io/ironbytes/corkscrew/views/MainMenu.fxml"));`, and see what happens... – zlakad Jan 04 '18 at 01:14
  • @zlakad java.lang.NullPointerException: Location is required. Is what I get when I run the jar with your edit. I don't think the issue is with locating that file I think the issue is: Caused by: java.lang.IllegalStateException: Location is not set. – d3t0x Jan 04 '18 at 01:17
  • then see this one: https://stackoverflow.com/questions/43513153/include-fxml-file-to-executable-jar?rq=1 – zlakad Jan 04 '18 at 01:19
  • I used the first answer and same error: src/io/ironbytes/corkscrew/views **/*.fxml **/*.css – d3t0x Jan 04 '18 at 01:34
  • Still trying to figure this out. Tried lots of different things. I changed my dir structure to mavens with the src/main/java and src/main/resources source folders and added the entry to my pom.xml but still no luck. The files are confirmed located in the jar. So confused. – d3t0x Jan 04 '18 at 16:58
  • Eh... It seems to me I can't help you. If I may suggest, try to build your application without any IDE. It's not easy if you're used to depend of Ant, Gradle, Maven... I'd (in your shoes) build my jar via console - whatever time is required. Simply, because it would you make you totally independent from any run/build/test/dist scripts. Oh, I know - it TAKES some time. – zlakad Jan 04 '18 at 17:13
  • 1
    Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/162534/discussion-between-zlakad-and-d3t0x). – zlakad Jan 04 '18 at 17:19

1 Answers1

1

I finally found a solution. After hours debugging, playing with pom.xml files and changing paths and file structures, I realized the issue was was the jar could not load or does not like the fx:controller located in the fxml file. So I needed to load the controller and link it to the fxml file without using fx:controller=

Solution:

Remove fx:contorller="io.ironbytes.corkscrew.view.MainMenu.fxml"

and change how you load the contorller:

    try {
        FXMLLoader loader = new FXMLLoader();
        loader.setController(new MainMenuController());
        loader.setLocation(getClass().getResource("/io/ironbytes/corkscrew/views/MainMenu.fxml"));
        root = loader.load();
        Scene scene = new Scene(root);
        primaryStage.setScene(scene);
        primaryStage.show();            
    } catch (Exception e) {
        e.printStackTrace();
    }
}`
d3t0x
  • 432
  • 4
  • 15