Help with Collision detecting of 2 Arrays

I am trying to create a game within processing in which the player must shoot approaching zombies. I have created (with help from others) both classes for the bullets and the zombies but I am unable to figure out how to have the bullet affect the zombie. I'm looking for a way to maybe compare the x,y coordinates of each bullet with the x,y coordinates of each zombie (If that is the best way to approach this problem). I am a beginner with processing so please excuse any basic mistakes. Thanks.

class Bullet { float x, y;

Bullet(float ax, float ay) {
  x=ax;
  y=ay;
}

void display() {
  image(img2,x,y,30,10);
}

void move() {
   x=x+10;
}

void  remove() {
  if(x>displayWidth+200) {
    bullets.remove(0);
 }  


}

void run() {
  move();
  display(); 
  remove();  
}

}

class Zombie { float x; final float y, vx; final PImage img;

Zombie(float xx, float yy, float vv, PImage pic) { x = xx; y = yy; vx = vv; img = pic; }

boolean run() { display(); return move(); }

boolean move() { return (x += vx) < -img.width-50; }

void display() { image(img, x, y, 150, 150); }

}

Answers

  • Your approach sounds valid, but I would suggest starting smaller first. Can you compare the location of a single bullet to a single zombie?

  • I know how to use if-statements to compare two objects but I'm new to Arrays and I'm not exactly sure how to use them. I don't know how to compare two objects that are within Arrays. I have been unable to find a website with good instruction about how to use arraylists.

  • edited January 2014

    Made a method checkHit() for class Bullet to check whether a Zombie were hit (UNTESTED):

    boolean checkHit(Zombie z) { // demands imageMode(CORNER);
      final float xw = z.x + z.img.width, yh = z.y + z.img.height;
      return x > z.x & x < xw & y > z.y & y < yh;
    }
    

    That was an algorithm for a 1D point (Bullet) against a 2D rectangle area (Zombie).

    More about collision checks:
    http://staticvoidgames.com/tutorials/intermediateConcepts/CollisionDetection.jsp

  • Okay so how do I check that method? Would I put something like this in void draw() :

    for (int i=0;i<bullets.size();i++) { bullets.get(i).run(); for (int z = zombies.size(); z-- != 0;) { if(bullets.get(i).checkHit(Zombie z)==true){

       } 
    }
    

    }

  • What happened when you tried that?

  • The console prints out the error: expecting Rparen, found z. I think the error is in this part if(bullets.get(i).checkHit(Zombie z)==true){

    What does the z after Zombie represent? If I delete the z and run the console prints "Could not find anything named Zombie"

  • edited January 2014

    No. You need to go back and look at how calling a method works.

    boolean checkHit(Zombie z) is the method signature, and it tells you how to call the checkHit() method. It tells you that the method returns a boolean and takes a zombie. Similarly, this is the signature for the println() method:

    void println(String s)

    Notice that you call the println() function by simply passing in a String, like so:

    println("testing");

    Similarly, to call the checkHit() function, you would pass in a Zombie:

    Zombie z = //wherever you get your Zombie instance from
    boolean hit = checkHit(z);
    

    You DON'T do this in your code:

    boolean hit = checkHit(Zombie z);

    ...because that makes no sense syntactically, just like it wouldn't make sense to write this in your code:

    println(String x);

    The checkHit() function needs to be added to your sketch, and you call it by passing in an instance of Zombie.

  • edited March 2014 Answer ✓

    Classes are also data-types. So, Zombie is both a class & a data-type!
    When we create a function/method, each of its parameters demand a data-type.

    boolean checkHit(Zombie z) {}
    

    From the example above, that method got a z parameter of data-type Zombie, and returns a primitive data-type boolean.
    Now, in order to invoke that implemented method, we gotta pass a Zombie object as its argument.

    Let's say you've got an ArrayList<Zombie> structure instance referenced by variable zombies.
    It means that each element of that structure is a reference to a Zombie object.

    While we iterate over that ArrayList, we use its get() method to access each of its elements by index.
    However, for each Zombie object, we gotta check against each active Bullet as well. So we're gonna need a double loop!

    I've made a simulation of Bullet Vs. Zombie death-match!
    Check that out below and try to adapt its concepts to your own game! o->

    /** 
     * Zombie Shooting Simulation (v1.02)
     * by GoToLoop (2014/Jan)
     *
     * forum.processing.org/two/discussion/2435/
     * help-with-collision-detecting-of-2-arrays
     */
    
    class Zombie {
      void script() {
      }
    }
    
    class Bullet {
      boolean checkHit(Zombie z) {
        return random(1) < .01;
      }
    
      boolean isOuttaBounds() {
        return random(1) < .05;
      }
    
      boolean script() {
        return isOuttaBounds();
      }
    }
    
    static final int ZOMBIES = 10, BULLETS = 30, FPS = 5;
    
    final ArrayList<Zombie> zombies = new ArrayList(ZOMBIES);
    final ArrayList<Bullet> bullets = new ArrayList(BULLETS);
    
    void setup() {
      size(600, 400);
      frameRate(FPS);
      smooth(4);
      imageMode(CORNER);
    
      for ( int i = 0; i++ != ZOMBIES; zombies.add(new Zombie()) );
      for ( int i = 0; i++ != BULLETS; bullets.add(new Bullet()) );
    }
    
    void draw() {
      clear();
    
      runScripts();
      checkDeath();
      checkVictory();
    }
    
    void runScripts() {
      for (Zombie z: zombies)  z.script();
    
      for (int b = bullets.size(); b-- != 0;)
        if (bullets.get(b).script()) {
          bullets.remove(b);
          println("A bullet has strayed too far from view!");
        }
    }
    
    void checkDeath() {
      for (int z = zombies.size(); z-- != 0;) {
        final Zombie ghoul = zombies.get(z);
    
        for (int b = bullets.size(); b-- != 0;)
          if (bullets.get(b).checkHit(ghoul)) {
            bullets.remove(b);
            zombies.remove(z);
            println("A zombie has been hit and died for good!");
    
            return;
          }
      }
    }
    
    void checkVictory() {
      final int z = zombies.size(), b = bullets.size();
    
      frame.setTitle("Zombies: #" + z + "\t\tBullets: #" + b);
    
      if (z == 0)  println("\nAll zombies are in Hell now!");
      if (b == 0)  println("\nZombies shall wander the Earth forever!");
    
      if (z * b == 0) {
        println("Zombies: #" + z + "\t Bullets: #" + b);
        exit();
      }
    }
    
  • Thanks I'll try it out.

Sign In or Register to comment.