Android Studio: attempt to invoke virtual method on a null object reference

Hi, i’m new to this forum but i’ve already have some experience with Processing. Recently i started learning Android programming using Android Studio so i decided to setup the Processing core library. Inspired by a Shiffman’s video tutorial about object trails, my AS project is composed of:

  • a Particle class in which an ArrayList (called history) saves the x-y coordinates of a ball. It contains an update() method for adding a random position to this array and a show() method that draws the ball and his trail:
package com.example.myfirstprocessingapp;


import java.util.ArrayList;
import processing.core.PApplet;

public class Particle extends PApplet {

  private int x;
  private int y;
  private ArrayList<int[]> history = new ArrayList<int[]>();

  public Particle (int x, int y) {
    this.x = x;
    this.y = y;
    this.history.add(new int[] {x, y});
  }

  public void settings() { }

  public void setup() { }

  public void update() {
    this.x += random(-10, 10);
    this.y += random(-10, 10);
    this.history.add(new int[] {this.x, this.y});

    if (this.history.size() > 100) {
      this.history.remove(0);
    }

  }

  public void show() {
    stroke(0);
    fill(0, 150);
    ellipse(this.x, this.y, 12, 12);
    noFill();

    beginShape();

    for (int i = 0; i < this.history.size(); i++) {
      int[] pos = this.history.get(i);
      vertex(pos[0], pos[1]);
    }

    endShape();
  }
}
  • the Sketch class called by the MainActivity as a fragment. It simply set the canvas, draw particles and manage the mousePressed() adding a new Particle instance inside a Particle ArrayList:
package com.example.myfirstprocessingapp;

        import java.util.ArrayList;

        import processing.core.*;

public class Sketch extends PApplet {

    ArrayList<Particle> particles = new ArrayList<Particle>();

    public void settings() {
        fullScreen();
        background(255);
    }

    public void setup() {

    }

    public void mousePressed() {
        particles.add(new Particle(mouseX - width/2, mouseY - height/2));
    }

    public void draw() {
        background(255);
        pushMatrix();
        translate(width/2,height/2);
        ellipse(0,0,50,50);
        for (int i = 0; i < particles.size(); i++) {
            particles.get(i).update();
            particles.get(i).show();
        }
        popMatrix();
    }
}

  • the main Activity class used as launcher:
package com.example.myfirstprocessingapp;

import android.content.Intent;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.ViewGroup;
import android.widget.FrameLayout;

import processing.android.CompatUtils;
import processing.android.PFragment;
import processing.core.PApplet;

public class MainActivity extends AppCompatActivity {

    private PApplet sketch = new PApplet();

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        FrameLayout frame = new FrameLayout(this);
        frame.setId(CompatUtils.getUniqueViewId());
        setContentView(frame, new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT));

        sketch = new Sketch();
        PFragment fragment = new PFragment(sketch);
        fragment.setView(frame,this);
    }

    @Override
    public void onNewIntent(Intent intent) {
        if (sketch != null) {
            sketch.onNewIntent(intent);
        }
    }
}

Although i was able to run the project explained in the Processing for Android (Studio) tutorial, it seems that in this case i forgot some basic steps to write a working Processing code.
Needless to say that this sketch worked in Android Mode in the Processing IDE.
This is the error generated in the logcat:

2019-05-30 10:12:30.354 30472-30507/com.example.myfirstprocessingapp E/AndroidRuntime: FATAL EXCEPTION: Animation Thread
    Process: com.example.myfirstprocessingapp, PID: 30472
    java.lang.NullPointerException: Attempt to invoke virtual method 'void processing.core.PGraphics.stroke(int)' on a null object reference
        at processing.core.PApplet.stroke(PApplet.java:9440)
        at com.example.myfirstprocessingapp.Particle.show(Particle.java:36)
        at com.example.myfirstprocessingapp.Sketch.draw(Sketch.java:29)
        at processing.core.PApplet.handleDraw(PApplet.java:1855)
        at processing.core.PSurfaceNone.callDraw(PSurfaceNone.java:476)
        at processing.core.PSurfaceNone$AnimationThread.run(PSurfaceNone.java:516)
2019-05-30 10:12:30.667 30472-30494/com.example.myfirstprocessingapp W/libEGL: EGLNativeWindowType 0x79384a1010 disconnect failed
2019-05-30 10:12:30.735 30472-30472/com.example.myfirstprocessingapp E/ViewRootImpl: sendUserActionEvent() returned.

Thanks in advance

I suspect that the issue is that your Sketch class (which extends a PApplet) has failed to properly setup the PApplet it is extending from properly. This basic setup usually happens automatically in normal Processing sketches (maybe when the call to size() happens? I’m unsure.). This setup would include things like, for example, creating a PGraphics element to do some drawing on.

Since you skip this setup for your Sketch object, it runs into trouble when you try to treat it like a full-blown, ready-to-go PApplet object. In fact, the problem seems to be that the PApplet doesn’t have a PGraphics object to draw on!

So what can we do about this? Well, what we can do is to tell the Sketch object to - in addition to its own setup process - also do the setup process for a PApplet. This involves a single call which you should add to your Sketch class’s setup() function (actually a better place would be to add a constructor (Sketch()) and put it in there):

super();

Try it! I have no idea if it’ll work. Like, this is the most I’m-not-sure-about-this answer I’ve ever given.

1 Like

@TfGuy44 ===
@Gabi ===

this code is written in a weird way for Android AS (and also P5 android mode)
the problem is not with your main of course, neither with your fragment but with your class which is supposed to extend PApplet: that is not ok. Your second class jas to be a nested class and normally the solution is to a) export your code from P5 to android b) import in AS pointing to the export folder “import from existing code” - Then it will work and you can see that the second (nested) class extends nothing. Below the code i have re-written knowing that; try it!

`import java.util.ArrayList;`

import processing.core.PApplet;

public class AndroidParticles extends PApplet {

    ArrayList<Particle> particles ;

    public void settings() {
        fullScreen();
        
    }

    public void setup() {
background(255);
particles = new ArrayList<Particle>();
    }

    public void mouseReleased() {
      Particle part = new Particle(mouseX - width/2, mouseY - height/2);
        particles.add(part);
    }

    public void draw() {
        background(255);
        pushMatrix();
        translate(width/2,height/2);
        ellipse(0,0,50,50);
        if(particles.size()>1){
        for (int i = 0; i < particles.size(); i++) {
            particles.get(i).update();
            particles.get(i).show();
        }
        }
        popMatrix();
    }



//public class Particle extends PApplet {///MODIF!!!
  public class Particle  {

  public int x;
  public int y;
  public ArrayList<int[]> history = new ArrayList<int[]>();
  
  public Particle (int x, int y) {
    this.x = x;
    this.y = y;
    
    this.history.add(new int[] {x, y});
    println(this.x);
  }

  

  public void update() {
    this.x += random(-10, 10);
    this.y += random(-10, 10);
    this.history.add(new int[] {this.x, this.y});

    if (this.history.size() > 100) {
      this.history.remove(0);
    }
    

  }

  public void show() {
    
    stroke(0);
    fill(0, 150);
    ellipse(this.x, this.y, 12, 12);
    noFill();

    beginShape();

    for (int i = 0; i < this.history.size(); i++) {
      int[] pos = this.history.get(i);
      vertex(pos[0], pos[1]);
    }

    endShape();
  }
}
}
1 Like

Thank you so much for your help.
I first tried implementing without success a constructor for the Sketch class with the super() keyword. Probably i need to study in more detail the use of PApplet and PGraphics. If you could suggest a more comprehensive reference for using Processing with Android Studio i would be very grateful.

At the end the solution proposed by @akenaton worked like a charm. I haven’t followed the export-import solution yet but simply copied the rewritten code, so maybe the next question is trivial. As mentioned in the answer, the second class has to be a nested class but what could i do if i want to use the same Particle class (the nested one) inside more PFragments? Is there a way to create more Java classes that extend PApplet?

@Gabi ===

  • you have copied instead of import: not any problem if you have your jars in your AS lib

  • as for the last question i am not sure to understand: is it in the same App that you want to create another PFragment? Is it in another app?

Yes, i’d like to know how to create another PFragment in the same app that uses the same class (Particle, for example). I specify that i haven’t had the time to try the import functionality, so maybe the answer has already been given.

@Gabi ===
ok but i cannot see in what type of case this could be useful except if you want to change the basic settings (size) -
yet ( never tried with P5)i suppose that you can create inside your fragment another fragment or inside your main create a static method for creating it (if…)

In this case i was thinking maybe you could use the same Particle class inside more different “minigames” presented with multiple fragment. But this is just an example, my question was intended to be as generic as possible. In any case, thanks for the reply, i will try these ideas as soon as i can.

@Gabi ====
But in this case or kind of case (“minigames”) you can have in your Particle Class special methods for each of them no?

Considering that the Particle class is minuscule probably yes. Having to implement a nested class for every fragment i create is the only thing that bothers me, it makes all the code less manageable (imho). Nonetheless i could simply create a Particle class that does not extends PApplet and leave all the work (the show() method in Particle) inside the various Pfragments.