-1

I'm working on a pong game with Processing. The game works just fine with a single class, however, I have to add multiple classes. Every time I get a Null Pointer Exception. This is part of the main class which extends PApplet

PApplet app = new PApplet();     
void MAINMENU() {

    // Start the Menu Song
    if (musicStartMenu) {
        MENUsong.loop();
        musicStartMenu = false;
    }

    // Stop the Level song if needed
    if (!musicStart) {
        BGsong.stop();
        musicStart = true;
    }

    // Resetting player scores
    ScoreP1 = ScoreP2 = 0;

    // Creating the Background for this scene
    image(menuBG, 0, 0);
    textFont(SC);

    // Setting the title
    text("PONG", width / 2 - 100, 150);

    // Creating the buttons for this scene
   Button Play= new Button(width / 2 - 150, height / 2 - 70, 300, 100, "PLAY", width / 2 - 100, height / 2 + 10, 1, 1,MAIN,app);
   Button Exit= new Button(width / 2 - 150, height / 2 + 70, 300, 100, "EXIT", width / 2 - 100, height / 2 + 150, 3, 2,MAIN,app);
   Play.Create();
   Exit.Create();
}

and this is the button class:

import processing.core.PApplet;


public class Button {

int Bx,By, width, height;

String label;

int labelW, labelH, action, style, MAIN;
PApplet app;



public Button(int Bx, int By, int width, int height, String label, int labelW, int labelH, int action, int style, int MAIN, PApplet app) {

    this.Bx = Bx;
    this.By = By;
    this.width = width;
    this.height = height;
    this.label = label;
    this.labelW = labelW;
    this.labelH = labelH;
    this.action = action;
    this.style = style;
    this.MAIN = MAIN;
    this.app = app;
}

void Create(){
    // Check if we hover the mouse over and select a style
    if (ButtonBorder(Bx, By, height, width)) {

        if (style == 1)
            // light green
            app.fill(100, 155, 100);
        else if (style == 2)
            // light red
            app.fill(255, 100, 100);

    } else app.fill(0, 50); // black transparent

    // Nobody likes borders
    app.stroke(0, 0);

    // Create the button box
    app.rect(Bx, By, width, height);

    // CHeck if the mouse is pressed and is hovering above the button
    if (app.mousePressed && ButtonBorder(Bx, By, height, width)) {

        // Select scene on click
        MAIN = action;
    }



    // SET the fill of the label and create the label
    app.fill(255);
    app.text(label, labelW, labelH);
}


boolean ButtonBorder(int xB, int yB, int ButtonHeight, int ButtonWidth) {

    // returns true if the mouse pointer is located inside the button

    if (!(app.mouseX >= xB && app.mouseX <= xB + ButtonWidth))
        return false;
    if (!(app.mouseY >= yB && app.mouseY <= yB + ButtonHeight))
        return false;

    return true;

}

If anyone has any clue it would be of much help. I want to say that the code is working just fine in a method inside the main class but for some reason that I can't seem to find it doesn't work in another class.

Trace:

    java.lang.NullPointerException
at processing.core.PApplet.fill(PApplet.java:14521)
at ButtonB.Create(ButtonB.java:41)
at Pong.MAINMENU(Pong.java:205)
at Pong.draw(Pong.java:161)
at processing.core.PApplet.handleDraw(PApplet.java:2429)
at processing.awt.PSurfaceAWT$12.callDraw(PSurfaceAWT.java:1557)
at processing.core.PSurfaceNone$AnimationThread.run(PSurfaceNone.java:313)
Kevin Workman
  • 41,537
  • 9
  • 68
  • 107
  • 1
    Please, do post the trace log, so you can easily spot where the exception is thrown! – Glains Oct 01 '18 at 15:12
  • 3
    `If anyone has any clue it would be of much help` - the stack trace gives you a clue. It tells you the line number of the statement that is causing the problem. So you look at the statement and determine which variable is null and then you fix the problem. Don't call your class "Button". There is an AWT component with that class name so it gets confusing trying to read your code. Also, variable names should NOT start with an upper case character. Follow Java conventions. – camickr Oct 01 '18 at 15:15
  • Thanks for the Tips, but the stack trace is not helpful at all in my situation. java.lang.NullPointerException at processing.core.PApplet.fill(PApplet.java:14521) at ButtonB.Create(Button.java:41) at Pong.MAINMENU(Pong.java:205) at Pong.draw(Pong.java:161) at processing.core.PApplet.handleDraw(PApplet.java:2429) at processing.awt.PSurfaceAWT$12.callDraw(PSurfaceAWT.java:1557) at processing.core.PSurfaceNone$AnimationThread.run(PSurfaceNone.java:313) I have already declared the app variable PApplet app = new PApplet(); – Horia Rotaru Oct 01 '18 at 15:28
  • ``the stack trace is not helpful at all in my situation.` - why? I have never seen it not display the statement number causing the problem. If you can't tell us the statement causing the problem then we can't help. Post the stack trace with your question, not as a comment. How do you expect us to read that code? – camickr Oct 01 '18 at 15:30
  • see the edit. I'm clueless cuz at that line is just setting the fill :/ Posted it – Horia Rotaru Oct 01 '18 at 15:32
  • I removed my answer but the intent is the same. app is likely not initialize. The question is why. You have multiple threads, and passing objects around in constructors in a volatile environment can be dangerous. https://developer.android.com/guide/components/processes-and-threads or https://stackoverflow.com/questions/21994612/get-application-context-returns-null – Micromuncher Oct 01 '18 at 15:42
  • I'm not too sure how processing is handling the draw function but other than that, I don't think I have any other threads. Is very strange to me because this should have a very simple answer but I can't find it. – Horia Rotaru Oct 01 '18 at 15:58
  • @Lorelorelore This is not a duplicate of the canonical Java NPE question. This error is happening internal to the Processing library. See my answer below for an explanation, and also see this meta discussion for more info: [Processing != Java](https://meta.stackoverflow.com/q/321127/873165) – Kevin Workman Oct 01 '18 at 16:23

1 Answers1

1

Your code has a few problems, because you aren't using Processing the way it was designed to be used.

First, it doesn't make sense to create an instance of PApplet directly like this:

PApplet app = new PApplet();  

Instead, you want to extend the PApplet class to create your own sketch, like this:

import processing.core.PApplet;

public class MySketch extends PApplet{

    public void settings(){
        size(500, 500);
    }

    public void draw(){
        ellipse(mouseX, mouseY, 50, 50);
    }

    public void mousePressed(){
        background(64);
    }

    public static void main(String[] args){
        String[] processingArgs = {"MySketch"};
        MySketch mySketch = new MySketch();
        PApplet.runSketch(processingArgs, mySketch);
    }
}

Secondly, you have to make sure you don't call Processing's functions (like fill() and rect()) until after the setup() function of your sketch class has been called.

Also, some feedback: please try to use standard naming conventions in your code. Classes and constructors should start with an upper-case letter, and functions and variables should start with a lower-case letter. Following this convention will make your code much easier to read.

Shameless self-promotion: here is a tutorial on using Processing as a Java library.

Kevin Workman
  • 41,537
  • 9
  • 68
  • 107
  • The main class extends the PApplet class. The Button class doesn't have to, or this is how I learned so I have to create a PApplet variable in order to access these functions in the Class. And I have to call these functions in the draw method because I need them redrawn at every frame. – Horia Rotaru Oct 01 '18 at 16:31
  • @HoriaRotaru None of your classes extend the `PApplet` class. And it's fine to call those functions in a draw method, but the problem is you're calling the functions **before** the sketch has been initialized. The `NullPointerException` is caused because Processing has not been internally initialized yet. You need to make sure this code is not called until after that, by putting it inside the `setup()` function of a class that **extends** the `PApplet` class. – Kevin Workman Oct 01 '18 at 17:10
  • That is not the full code. Just the part of it that is not working. do you want me to post a 500+ class here? – Horia Rotaru Oct 01 '18 at 17:55
  • @HoriaRotaru You need to post a [mcve]. Not your full code. But enough code so we can reproduce the problem. But I can tell you right now that your error is caused by calling a Processing function before the sketch has been initialized. – Kevin Workman Oct 01 '18 at 17:57
  • As I said that has to do nothing with my error and is called where it should be. the tracer doesn't even complain about it if you read carefully. The sketch is initialized correctly I give my word for that :) I don't have the code on me rn but I will include that part too if is really that needed. – Horia Rotaru Oct 01 '18 at 18:31
  • @HoriaRotaru Please post a [mcve]. Note that this should **not** be your full program, but should be as few lines as possible to recreate the error. Good luck. – Kevin Workman Oct 01 '18 at 21:13