Why Is this Code Not Working

class Points{
  PVector pos;
  PVector vel = new PVector();
  PVector acc = new PVector();
  Points(float x_, float y_){
    pos = new PVector(x_,y_);
  }
  void applyForce(PVector force){
    acc.add(force);
  }
  void update(){
    vel.add(acc);
    pos.add(vel);
    acc.mult(0);
    show();
  }
  void show(){
    strokeWeight(3);
    stroke(255);
    ellipse(pos.x,pos.y,10,10);
  }
}
ArrayList<PVector> charges = new ArrayList<PVector>();
ArrayList<Points> particles = new ArrayList<Points>();


void setup(){
  size(500,500);
  for(int i = 0; i < 2; i++){
    charges.add(new PVector(random(height),random(width),round(random(1))));
  }
  for(int i = 0; i < 100; i++){
    particles.add(new Points(random(height),random(width)));
    print(particles.get(i).pos);
  }
}

PVector efield(PVector pos){
  PVector force = new PVector();
  for(PVector charge:charges){
    PVector poscopy = pos;
    PVector chargecopy = charge;
    float strength = charge.z/pow(dist(pos.x,pos.y,charge.x,charge.y),2); 
    poscopy.sub(chargecopy);
    poscopy.normalize();
    poscopy.mult(strength);
    force.add(poscopy);
  }
  return force;
}

void draw(){
  background(0);
  for(Points p:particles){
    p.applyForce(efield(p.pos));
    p.update();
  }
}

This code is only showing points in one corner of the screen, instead of simulating electric field lines like it should be doing.

Answers

  • Line 30 you swap width and height

    Why the 3rd parameter, it’s a 2D sketch?

    You only have 2 charges

  • The third parameter for the charges is for positive or negative charge

  • class Points{
      PVector pos;
      PVector vel = new PVector();
      PVector acc = new PVector();
      Points(float x_, float y_){
        pos = new PVector(x_,y_);
      }
      void applyForce(PVector force){
        acc.add(force);
      }
      void update(){
        vel.add(acc);
        vel.mult(0.9);
        pos.add(vel);
        acc.mult(0);
        if(pos.x > width){
          pos.x = 0;
        }
        if(pos.y > height){
          pos.y = 0;
        }
        if(pos.x < 0){
          pos.x = width;
        }
        if(pos.y < 0){
          pos.y = height;
        }
        show();
      }
      void show(){
        //strokeWeight(3);
        //stroke(255);
        ellipse(pos.x,pos.y,2,2);
      }
    }
    ArrayList<PVector> charges = new ArrayList<PVector>();
    //ArrayList<Points> particles = new ArrayList<Points>();
    
    
    void setup(){
      fullScreen();
      //for(int i = 0; i < 4; i++){
      //  charges.add(new PVector(random(height),random(width),round(random(-1,1))));
      //}
      //for(int i = 0; i < 1000; i++){
      //  particles.add(new Points(random(height),random(width)));
      //  //print(particles.get(i).pos);
      //}
    }
    
    PVector efield(PVector pos){
      PVector force = new PVector();
      for(PVector c:charges){
        PVector poscopy = pos;
        PVector chargecopy = c;
        float strength = c.z*10000/pow(dist(poscopy.x,poscopy.y,chargecopy.x,chargecopy.y),2); 
        poscopy.sub(chargecopy);
        poscopy.normalize();
        poscopy.mult(strength);
        force.add(poscopy);
      }
      //print(force);
      return force;
    }
    
    void draw(){
      background(150);
      //for(Points p:particles){
      //  p.update();
        //p.applyForce(efield(p.pos.copy()));
      //  //print(p.pos);
      //}
      for(int x = 0; x < width; x+= 20){
        for(int y = 0; y < width; y+= 20){
          PVector dir = efield(new PVector(x,y));
          stroke(255);
          drawArrow(x,y,dir.mag(),dir.heading());
        }
      }
      for(PVector c:charges){
        if(c.z < 1){
          fill(0);
        }
        if(c.z < 0){
          noFill();
        }
        else{
          fill(255);
        }
        ellipse(c.x,c.y,2,2);
      }
      if(mousePressed && mouseButton == LEFT){
        charges.add(new PVector(mouseX,mouseY,1));
      }
      if(mousePressed && mouseButton == RIGHT){
        charges.add(new PVector(mouseX,mouseY,-1));
      }
    }
    
    void drawArrow(float cx, float cy, float len, float angle){
      pushMatrix();
      strokeWeight(1);
      translate(cx, cy);
      rotate(angle);
      line(0,0,len, 0);
      line(len, 0, len-2,-2);
      line(len, 0, len-2,2);
      popMatrix();
    }
    

    I changed my code to show arrows instead of points but now only the first point I place has an effect on the code. It should give all charges the same effect based on the distance but it isn't working.

  • WHy don’t you init charges in setup () anymore?

  • I wanted to keep charges empty and have control over where I add them.

  • mainly, in efield you need to use .copy()

            PVector poscopy = pos.copy();
            PVector chargecopy = c.copy();
    
    
    
    
    
    
    
    
    
    
    
    
    
    class Points {
      PVector pos;
      PVector vel = new PVector();
      PVector acc = new PVector();
      Points(float x_, float y_) {
        pos = new PVector(x_, y_);
      }
      void applyForce(PVector force) {
        acc.add(force);
      }
      void update() {
        vel.add(acc);
        vel.mult(0.9);
        pos.add(vel);
        acc.mult(0);
        if (pos.x > width) {
          pos.x = 0;
        }
        if (pos.y > height) {
          pos.y = 0;
        }
        if (pos.x < 0) {
          pos.x = width;
        }
        if (pos.y < 0) {
          pos.y = height;
        }
        show();
      }
      void show() {
        //strokeWeight(3);
        //stroke(255);
        ellipse(pos.x, pos.y, 2, 2);
      }
    }
    
    // ==========================================================
    
    
    ArrayList<PVector> charges = new ArrayList<PVector>();
    //ArrayList<Points> particles = new ArrayList<Points>();
    
    
    void setup() {
      fullScreen();
      //for(int i = 0; i < 4; i++){
      //  charges.add(new PVector(random(height),random(width),round(random(-1,1))));
      //}
      //for(int i = 0; i < 1000; i++){
      //  particles.add(new Points(random(height),random(width)));
      //  //print(particles.get(i).pos);
      //}
    }
    
    PVector efield(PVector pos) {
    
      PVector force = new PVector();
    
      for (PVector c : charges) {
    
        PVector poscopy = pos.copy();
        PVector chargecopy = c.copy();
    
        float strength = c.z*10000/pow(dist(poscopy.x, poscopy.y, chargecopy.x, chargecopy.y), 2);
    
        poscopy.sub(chargecopy);
        poscopy.normalize();
        poscopy.mult(strength);
        force.add(poscopy);
      }
    
      //print(force);
      return force;
    }
    
    void draw() {
      background(150);
      //for(Points p:particles){
      //  p.update();
      //p.applyForce(efield(p.pos.copy()));
      //  //print(p.pos);
      //}
      for (int x = 0; x < width; x+= 20) {
        for (int y = 0; y < width; y+= 20) {
          PVector dir = efield(new PVector(x, y));
          stroke(255);
          drawArrow(x, y, dir.mag(), dir.heading());
        }
      }
      for (PVector c : charges) {
        if (c.z < 1) {
          fill(0);
        }
        if (c.z < 0) {
          noFill();
        } else {
          fill(255);
        }
    
        ellipse(c.x, c.y, 2, 2);
      }//for
    }
    
    void mousePressed() {
    
      if (mousePressed && mouseButton == LEFT) {
        charges.add(new PVector(mouseX, mouseY, 1));
      }
      if (mousePressed && mouseButton == RIGHT) {
        charges.add(new PVector(mouseX, mouseY, -1));
      }
    }
    
    void drawArrow(float cx, float cy, 
      float len, 
      float angle) {
    
      pushMatrix();
      strokeWeight(1);
      translate(cx, cy);
      rotate(angle);
      line(0, 0, len, 0);
      line(len, 0, len-2, -2);
      line(len, 0, len-2, 2);
      popMatrix();
    }
    
Sign In or Register to comment.