0

Here is my class in Processing ...

class Stripe {

  PShape s;
  float x, y, w;

  static Stripe lastStripe;


  Stripe() {
    x = width / 2;
    y = 0;
    w = 150;
    s = createShape();
    s.beginShape();
    s.fill(0);
    s.noStroke();
    s.vertex(w, 0);
    s.bezierVertex(w + 50, height * 1/4, w - 50 , height * 1/3, w, height); 
    s.vertex(0, height);
    s.bezierVertex(-50, height * 1/3, 50 , height * 1/4, 0, 0); 
    //s.vertex(0, 0);


    //s.bezierVertex(50, 50, 50, 50, 100, 100); 
    s.endShape(CLOSE);
  }

  void draw() {
    pushMatrix();
    translate(x, y);
    shape(s);
    popMatrix();

  }

  void move() {
    x = x + STRIPE_VEL;

    if (x > (width + OFFSCREEN_BUFFER)) {
      x =  Stripe.lastStripe.x - STRIPE_SPACING;
      Stripe.lastStripe = this;
    }

  }

}

When I try and compile I get the following error ...

The field lastStripe can only be declared static; static fields can only be declared in static or top level types

Looking at this Java tutorial, this seems to be a valid Java pattern. Although the code above is self referential, it still raises the same error if the type is changed to an int or similar.

What is the problem here?

EDIT: By request, here is the rest of the sketch which is in another tab. I'm starting to think that the Processing way is to just declare such variables as a 'global' rather than a static variable on a class ... I'll probably just do that.

float STRIPE_VEL = 0.5;
float OFFSCREEN_BUFFER = 500;
float STRIPE_SPACING = 50;

int numStripes = 0;

Stripe[] stripes;


void setup() {

  float offset = 0;
  size(800, 600, P2D);
  smooth();

  numStripes = (width + 2 * OFFSCREEN_BUFFER) / STRIPE_SPACING;
  stripes = new Stripe[numStripes];

  for (int i=0; i < numStripes; i++) {
    stripes[i] = new Stripe();
    stripes[i].x = offset;
    offset = offset + inc;
  }
  Stripe.lastStripe = stripes[0];

}


void draw() {
  background(255);

  for (int i=0; i < numStripes; i++) {
    stripes[i].draw();
    stripes[i].move();
  }

  //blurAll();


}
Brendan
  • 18,771
  • 17
  • 83
  • 114
  • 5
    By the error message, seems that this class is a nested class. – Luiggi Mendoza May 19 '14 at 22:51
  • 1
    possible duplicate of [Why can't I declare and initialize static variable in inner class?](http://stackoverflow.com/questions/22297722/why-cant-i-declare-and-initialize-static-variable-in-inner-class) – user2864740 May 19 '14 at 23:08
  • This is a 'top level' class in Processing i.e. in a separate tab, but maybe Processing on compilation embeds it in another class, I don't know. I have no experience of Java, but I do know C# pretty well and yeah I wouldn't program like this in C#, but Processing is geared in a C like way. – Brendan May 19 '14 at 23:33
  • Just so you know this isn't pure Java, it is a domain specific language [Processing](http://processing.org/) which wraps up Java in a 'friendly' way. Of course it means that you get the DSL problem of programming in one language and getting error/debug info in another ... – Brendan May 19 '14 at 23:40
  • Is this your entire sketch? If not, can you post the whole thing? – Kevin Workman May 20 '14 at 12:44
  • 2
    @user2864740: This doesn't feel like a duplicate. Processing is a slightly different animal than Java, and there are things that it does behind the scenes. This is one of those which is burning the OP. – Makoto May 31 '14 at 15:22

2 Answers2

2

Try renaming the specific file i.e Stripe.pde to Stripe.java. You are right in your comment there: "Processing on compilation embeds it in another class", actually all the tabs in a processing sketch are wrapped around a big java (top-level) class... So, renaming one of them to .java will force it to be a top level class!

Petros Koutsolampros
  • 2,790
  • 1
  • 14
  • 20
1

Change your inner class Stripe to be declared as a static (inner) class:

static class Stripe {
  ...
}

This will make sure Stripe does not require an instance of the enclosing class per instance of Stripe, and you will be able to create class variables (static fields).


As a side note, it is always a better practice to make an inner class static, if it does not actually need an instance of the enclosing class.

amit
  • 175,853
  • 27
  • 231
  • 333
  • Hmm thanks, so when trying this I get the further error that `Cannot make a static reference to non-static field width`. This would imply that `width` and the other 'globals' in Processing are implemented as an instance variable of some invisible container class? – Brendan May 19 '14 at 23:43
  • @Brendan They are instance variables of the enclosing class, you need to choose - having static fields, or being able to access enclosing class fields, you cannot have both.. – amit May 20 '14 at 07:23