0

I have a problem with a button when trying to work with JavaFX. I am trying to set a custom font to a button. The moment I try to change the font of the button, the program crashes.

The other topics on stack do not seem to help as they do not seem to have the same problem. Excuse me if there is another topic but I did not understand the fix as I am new to JavaFX. Thank you for your help in advance.

Here is my code


import javafx.application.Application;
import javafx.fxml.FXML;
import javafx.fxml.FXMLLoader;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.text.Font;
import javafx.stage.Stage;

import java.io.FileInputStream;

public class Main extends Application {
    @Override
    public void start(Stage primaryStage) throws Exception{

        FXMLLoader loader = new FXMLLoader();
        String fxmlDocPath = "C:\\Users\\Mihai\\Documents\\GitHub\\Kitchen3\\src\\sample\\sample.fxml";
        FileInputStream fxmlStream = new FileInputStream(fxmlDocPath);
        Parent root = loader.load(getClass().getResource("sample.fxml"));
        //Setting the stage and adding my custom style to it
        primaryStage.setTitle("Hello World");
        root.getStylesheets().add("sample/style.css");
        root.setId("pane");

        Controller controller = new Controller();
        loader.setController(controller);

        Font defaultFont = Font.loadFont(getClass().getResourceAsStream("/Aclonica.woff2"), 16);
        controller.homeButton.setFont(defaultFont);
        primaryStage.setScene(new Scene(root, 800 , 600));
        primaryStage.show();
    }


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

This is my fxml file:


<?import javafx.scene.canvas.Canvas?>
<?import javafx.scene.control.Button?>
<?import javafx.scene.control.ButtonBar?>
<?import javafx.scene.layout.BorderPane?>

<BorderPane id="pane" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="600.0" prefWidth="800.0" xmlns="http://javafx.com/javafx/8.0.172-ea" xmlns:fx="http://javafx.com/fxml/1" fx:controller="sample.Controller">
   <center>
      <Canvas height="560.0" width="800.0" BorderPane.alignment="CENTER" />
   </center>
   <top>
      <ButtonBar prefHeight="40.0" prefWidth="200.0" BorderPane.alignment="CENTER">
        <buttons>
          <Button fx:id="homeButton" id="button" mnemonicParsing="false" text="Home" />
        </buttons>
      </ButtonBar>
   </top>
</BorderPane>

And this is my Controller


import javafx.fxml.FXML;
import javafx.scene.control.Button;
import javafx.scene.layout.BorderPane;
import javafx.scene.text.Font;

public class Controller {
    @FXML
    Button homeButton;
    @FXML
    BorderPane pane;

    public Controller(){

    }

    @FXML
    public void initialize(){
    //I have tried this to see if it would help.
        homeButton.setText("Home");
        Font default = Font.getDefault();
        homeButton.setFont(arial);
    }
    @FXML
    public Button getHomeButton() {
        return homeButton;
    }
    @FXML
    public void setHomeButton(Button homeButton) {
        this.homeButton = homeButton;
    }
}

Stacktrace:

java.lang.reflect.InvocationTargetException
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at com.sun.javafx.application.LauncherImpl.launchApplicationWithArgs(LauncherImpl.java:389)
    at com.sun.javafx.application.LauncherImpl.launchApplication(LauncherImpl.java:328)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at sun.launcher.LauncherHelper$FXHelper.main(LauncherHelper.java:767)
Caused by: java.lang.RuntimeException: Exception in Application start method
    at com.sun.javafx.application.LauncherImpl.launchApplication1(LauncherImpl.java:917)
    at com.sun.javafx.application.LauncherImpl.lambda$launchApplication$154(LauncherImpl.java:182)
    at java.lang.Thread.run(Thread.java:748)
Caused by: java.lang.NullPointerException
    at com.sun.javafx.scene.control.skin.Utils.computeTextHeight(Utils.java:130)
    at com.sun.javafx.scene.control.skin.LabeledSkinBase.computeMinLabeledPartHeight(LabeledSkinBase.java:707)
    at com.sun.javafx.scene.control.skin.LabeledSkinBase.computeMinHeight(LabeledSkinBase.java:689)
    at javafx.scene.control.Control.computeMinHeight(Control.java:489)
    at javafx.scene.Parent.minHeight(Parent.java:957)
    at javafx.scene.layout.Region.minHeight(Region.java:1401)
    at javafx.scene.layout.Region.computeChildMinAreaHeight(Region.java:1697)
    at javafx.scene.layout.Region.getMaxAreaHeight(Region.java:1978)
    at javafx.scene.layout.Region.computeMaxMinAreaHeight(Region.java:1847)
    at javafx.scene.layout.HBox.computeMinHeight(HBox.java:415)
    at javafx.scene.Parent.minHeight(Parent.java:957)
    at javafx.scene.layout.Region.minHeight(Region.java:1401)
    at javafx.scene.control.SkinBase.computeMinHeight(SkinBase.java:254)
    at javafx.scene.control.Control.computeMinHeight(Control.java:489)
    at javafx.scene.Parent.minHeight(Parent.java:957)
    at javafx.scene.layout.Region.minHeight(Region.java:1401)
    at javafx.scene.layout.Region.boundedNodeSizeWithBias(Region.java:1917)
    at javafx.scene.layout.BorderPane.layoutChildren(BorderPane.java:517)
    at javafx.scene.Parent.layout(Parent.java:1087)
    at javafx.scene.Scene.doLayoutPass(Scene.java:552)
    at javafx.scene.Scene.preferredSize(Scene.java:1646)
    at javafx.scene.Scene.impl_preferredSize(Scene.java:1720)
    at javafx.stage.Window$9.invalidated(Window.java:864)
    at javafx.beans.property.BooleanPropertyBase.markInvalid(BooleanPropertyBase.java:109)
    at javafx.beans.property.BooleanPropertyBase.set(BooleanPropertyBase.java:144)
    at javafx.stage.Window.setShowing(Window.java:940)
    at javafx.stage.Window.show(Window.java:955)
    at javafx.stage.Stage.show(Stage.java:259)
    at sample.Main.start(Main.java:25)
    at com.sun.javafx.application.LauncherImpl.lambda$launchApplication1$161(LauncherImpl.java:863)
    at com.sun.javafx.application.PlatformImpl.lambda$runAndWait$174(PlatformImpl.java:326)
    at com.sun.javafx.application.PlatformImpl.lambda$null$172(PlatformImpl.java:295)
    at java.security.AccessController.doPrivileged(Native Method)
    at com.sun.javafx.application.PlatformImpl.lambda$runLater$173(PlatformImpl.java:294)
    at com.sun.glass.ui.InvokeLaterDispatcher$Future.run(InvokeLaterDispatcher.java:95)
    at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
    at com.sun.glass.ui.win.WinApplication.lambda$null$147(WinApplication.java:177)
    ... 1 more
Exception running application sample.Main

Process finished with exit code 1 ```
3
  • 1
    edit your question and add the stack trace of the NullPointerException you are getting. Commented Nov 17, 2019 at 14:07
  • It sounds like getClass().getResourceAsStream("/Aclonica.woff2") is returning null. Verify that Aclonica.woff2 is a part of your program. If you’re running from a .jar file, verify that Aclonica.woff2 is in the root of the .jar file. Commented Nov 17, 2019 at 16:26
  • That is my problem, I have also identified that this is the problem. I found another thread that says that sometimes if the font is not loaded it will show the error somewhere else. I have also tried to load Aclonica from a link, It still does not work Commented Nov 17, 2019 at 16:44

1 Answer 1

1

Even though the Code you provided should not even compile I guess the following is your problem:

You assigned your Controller via fx:controller but also override it in your code. The new instance is assigned after load and therefore doesn't know instances of your Controls.

Either remove the fx:controller part from your fxml and set the Controller before(!) calling loader.load(...)

or refer to the existing Controller instead of setting a new one

Sign up to request clarification or add additional context in comments.

4 Comments

Then if I remove the controller how do I access the properties within, because I wish to change the font of the text. I have also the other way, removing the controller from the fxml file. I get the same error, null pointer on this line controller.homeButton.setFont(defaultFont);
@fabian I have created the controller, that is not the issue. In my reply, I asked how do I access the variables in the controller if I delete the controller creation.
Whether you pass data to the controller or retrieving data doesn't make a difference of many of the approaches. However you're basically passing the font to the controller according to the question... Just one additional thing you should note: Using one of the static load methods no connection between the properties of your loader and the scene is established whatsoever. Another instance of FXMLLoader is created inside these kind of load methods that is used to load the fxml. Furthermore you cannot do both: specify fx:contoller and set the controller instance before loading.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.