#Code advice for a novice coder

13 messages · Page 1 of 1 (latest)

sturdy heath
#

I have a class that I just want experienced advice on improving.

#

Here is the code

#

I welcome any constructive criticism. I am just teaching myself for fun.

blissful mantle
#

Here is an example of how your code can look if you follow the principle of “don't repeat yourself”. The usage of the setSomenthing methods is easier to read when you initialize your objects.

ArrayList<Ball> balls = new ArrayList<Ball>();

void setup() {
  size(800, 800);
  background(0);
  
  BoundingBox bbox = new BoundingBox(width, height);
  
  Ball b_ball = new Ball()
    .setPosition(-50, 400)
    .setRadius(50)
    .setSpeed(2, 2)
    .setColor(color(0, 0, 255))
    .setBoundingBox(bbox);

  Ball y_ball = new Ball()
    .setPosition(300, 200)
    .setRadius(100)
    .setSpeed(1, 1)
    .setColor(color(255, 255, 0))
    .setBoundingBox(bbox);

  Ball r_ball = new Ball()
    .setPosition(700, 600)
    .setRadius(50)
    .setSpeed(3, 3)
    .setColor(color(255, 0, 0))
    .setBoundingBox(bbox);
  
  // add the balls to the ArrayList
  balls.add(b_ball);
  balls.add(y_ball);
  balls.add(r_ball);
}

void draw() {
  background(0);
  
  for (Ball ball: balls) {
    ball.update(balls);
    ball.show();
  }
}

// helper class for bounding box
class BoundingBox {
  PVector min = new PVector();
  PVector max = new PVector();
  
  BoundingBox() {}
  
  BoundingBox(float maxX, float maxY) {
    max = new PVector(maxX, maxY);
  }
  
  BoundingBox(float minX, float minY, float maxX, float maxY) {
    min = new PVector(minX, minY);
    max = new PVector(maxX, maxY);
  }
  
  PVector test(PVector tmin, PVector tmax, PVector tvel) {
    PVector correction = new PVector(1, 1);
    
    if (tmin.x <= min.x && tvel.x < 0) correction.x = -1;
    if (tmin.y <= min.y && tvel.y < 0) correction.y = -1;
    if (tmax.x >= max.x && tvel.x > 0) correction.x = -1;
    if (tmax.y >= max.y && tvel.y > 0) correction.y = -1;

    return correction;
  }
}

// Ball class now extends a PVector, this makes calculations easier
class Ball extends PVector {
  int radius = 0;
  BoundingBox bbox = new BoundingBox();
  PVector velocity = new PVector();
  color _color = color(255);
  boolean collision = false;
  
  PVector min = new PVector();
  PVector max = new PVector();
  
  Ball() {}
  
  Ball setPosition(int x_, int y_) {
    x = x_;
    y = y_;
    return this;
  }
  
  Ball setSpeed(int x, int y) {
    velocity = new PVector(x, y);
    return this;
  }
  
  Ball setColor(color c) {
    _color = c;
    return this;
  }
  
  Ball setRadius(int r) {
    radius = r;
    return this;
  }
  
  Ball setBoundingBox(BoundingBox _bbox) {
    bbox = _bbox;
    return this;
  }
  
  boolean checkCollision(Ball opponent) {
    float dist = PVector.dist(this, opponent) - (this.radius + opponent.radius);
    
    return (dist <= 0);
  }
  
  void setMinMax() {
    PVector rv = new PVector(radius, radius);
    min.set(x, y).sub(rv);
    max.set(x, y).add(rv); 
  }
  
  void update(ArrayList<Ball> balls) {
    this.add(velocity);

    // calculates the min and max values for x and y
    setMinMax();

    // test on bounding box and returns a PVector,
    // where the values are correction multipliers for the velocity
    PVector correction = bbox.test(min, max, velocity);
    velocity.x *= correction.x;
    velocity.y *= correction.y;
    
    // reset before collision check
    collision = false;
    
    for (Ball ball: balls) {
      // skip if ball is itself
      if (ball == this) {
        continue;
      }
      
      // skip if already collides
      if (!collision && checkCollision(ball)) {
        collision = true;
      }
    }
  }
  
  void show() {
    push();
    
    if (collision) {
      fill(150);
    } else {
      fill(_color);    
    }
    circle(x, y, radius * 2);
    pop();
  }
}
sturdy heath
#

Thanks @blissful mantle I appreciate the tips as always.
Lots new stuff to digest.

cursive solar
#

I like the acronym "DRY" that stands for "don't repeat yourself"

#

"DRY" code is code where you aren't repeating yourself unnecessarily

#

DRY code is generally more stable and it's a lot easier to work with

#

The tradeoff is that (at least in my experience) many languages force you to trade either code efficiency or visual code beauty for this

#

For example, if there is something you need to do many times, you can make a function that does it. Then every time you need to do it, you can just use the function instead of typing out the code.

#

But function calls cause an "overhead" usually. This basically means that when we call the function, the computer has to do a little more work than it would have to do if we had just typed out the function's code

#

This overhead is usually unnoticeable in small projects. But as the project scales, it could make the difference between your code taking 1 minute or 10 minutes to execute