How to reference something else with the same class

edited August 2017 in Questions about Code

I'm making a game where the enemies attack each other, how do I do that?

ArrayList <enemy> enemies = new ArrayList <enemy> ();
ArrayList <wall> walls = new ArrayList <wall> ();
void setup() {
  size(1000, 700);
  frameRate(60);

}
void draw() {
  background(0);
      enemy e = new enemy();
  if (frameCount %100==0) {


    enemies.add(e);
  }
  for (int i = enemies.size() - 1; i >= 0; i-=1) {
    enemy zz = enemies.get(i);
    if (zz.isalive==false) {
      enemies.remove(i);
    } else {
      zz.display();
      zz.move(e);
    }
  }
}
//================================================================
class enemy {
  boolean isalive = true, detected = false;
  float x  = -10000, y = -10000, size = 20,lock = -1,identity = random(99999);
  String names = "hi";
  enemy() {
    x  = random(width);
    y  = random(height);
  }
  void display() {
    fill(200, 0, 0);
    rect(x, y, size, size);
  }
  void move(enemy other) {
    if (dist(other.x, other.y, x, y)<other.size + size + 100) {
      detected = true;
      lock = other.identity;
    }
    if (other.isalive ==false) {
      detected = false;
      lock = -1;
    }
    if (detected && other.identity == lock) {
      if (x > other.x) {
        x -= 5;
      }
      if (x < other.x) {
        x += 5;
      }
      if (y > other.y) {
        y -= 5;
      }
      if (y < other.y) {
        y += 5;
      }
    }
    if (dist(x,y,other.x,other.y)<20){
      other.isalive = true;
    }
  }
}
//==============================================================
class me {
}
//============================================================
class wall {
}

Answers

  • In draw you want a nested for loop

    This means two for loops the outer is A the inner B

    A is looping over all enemies and B is looping over all other enemies

    But avoid that each pair is checked twice

    I suggest

    for (enemy_i=0.......

    for (other_i=enemy_i+1......

    Thus you only check the other enemies above the enemy for loop A

    Then say something like

    enemies.get(enemy_i).move( enemies.get(other_i) ) ;

  • code please?

  • I gave you a lot of code- show your attempt

    I am also not at home and can't do it here

  • ArrayList <enemy> enemies = new ArrayList <enemy> ();
    ArrayList <wall> walls = new ArrayList <wall> ();
    void setup() {
      size(1000, 700);
      frameRate(100);
    }
    void draw() {
      background(0);
    
      if (frameCount %100==0) {   
        enemy f = new enemy();
        enemies.add(f);
      }
      for (int i = enemies.size() - 1; i >= 0; i--) {  
            enemy zz = enemies.get(i);
        for (int a = enemies.size() - 1; a >= 0; a--) {
          enemy other = enemies.get(a);
          zz.move(other) ;
        }
        if (zz.isalive==false) {
          enemies.remove(i);
        } else {
          zz.display();
        }
      }
    }
    //================================================================
    class enemy {
      boolean isalive = true, detected = false;
      float x, y, size = 20, lock = -1, identity = random(99999);
      String names = "hi";
      enemy() {
        x  = random(width);
        y = random(height);
      }
      void display() {
    
        fill(200, 0, 0);
        rect(x, y, size, size);
      }
      void move(enemy other) {
            while(lock == identity){
          lock = other.identity;
        }
        if (other.isalive ==false) {
          detected = false;
          lock = -1;
        }
        if (detected && other.identity == lock) {
          if (x > other.x) {
            x -= 5;
          }
          if (x < other.x) {
            x += 1;
          }
          if (y > other.y) {
            y -= 1;
          }
          if (y < other.y) {
            y += 1;
          }
        }
        if (dist(x, y, other.x, other.y)<2) {
         //other.isalive = false;
        }
      }
    }
    //==============================================================
    class me {
    }
    //============================================================
    class wall {
    }
    
  • Line 16 : you want to start at a=i-1

    to avoid double checking of pairs

  • edited August 2017

    This

    if (zz.isalive==false) {
    

    same as

    if ( ! zz.isalive ) {
    

    The ! means not

  • Does it work?

    Well done!

    Remember to use ctrl-t in processing to auto format your code

  • class names like Wall are written with capital first letter Wall, not wall

    Objects like enemies small first letter

  • ArrayList <Enemy> enemies = new ArrayList <Enemy> ();
    ArrayList <Wall> walls = new ArrayList <Wall> ();
    
    void setup() {
      size(1000, 700);
      frameRate(100);
    }
    
    void draw() {
    
      Enemy zz = null;
    
      background(0);
    
      // display text message
      fill(255);
      text(enemies.size(), 13, 13);
    
      //spawn
      if (frameCount %100==0) {   
        Enemy f = new Enemy();
        enemies.add(f);
      }
    
      // loop over all enemies
      for (int i = enemies.size()-1; i >= 0; i--) {
    
        zz = enemies.get(i);
    
        if (!zz.isAlive) {
          enemies.remove(i);
        } else {
    
          for (int a = i - 1; a >= 0; a--) {
            Enemy other = enemies.get(a);
            zz.move(other);
          }//for
    
          if (zz.isAlive) { 
            zz.display();
          }//if
          //
        }//else
      }//for
    }//func
    
    //================================================================
    
    class Enemy {
    
      boolean isAlive = true, 
        detected = false;
      float x, y, size = 20, lock = -1;
      int identity = int(random(99999));
      String names = "hi";
    
      Enemy() {
        x = random(width);
        y = random(height);
      }
    
      void display() {
        fill(200, 0, 0);
        rect(x, y, size, size);
      }
    
      void move(Enemy other) {
        if (!other.isAlive) {
          return;
        }
    
        if (random(100) > 50)
          x++;
        else x--;
    
        if (random(100) > 50)
          y++;
        else y--;
    
    
        if (x > other.x) {
          x -= 1;
        }
        if (x < other.x) {
          x += 1;
        }
        if (y > other.y) {
          y -= 1;
        }
        if (y < other.y) {
          y += 1;
        }
        //
        if (dist(x, y, other.x, other.y)<2) {
          other.isAlive = false;
          isAlive = false;
        }
      }
    }
    
    //==============================================================
    
    class Me {
      //Player
    }
    
    //============================================================
    
    class Wall {
      // Wall
    }
    
  • it's okay, but once the enemy kills the other enemy, it doesn't do anything, i'm guessing that it has no other enemies in its move. here is my current code:

    ArrayList <Enemy> enemies = new ArrayList <Enemy> ();
    ArrayList <Wall> walls = new ArrayList <Wall> ();
    ArrayList <bullet> bullets = new ArrayList <bullet> ();
    PVector bloc;
    void setup() {
      size(1000, 700);
      bloc = new PVector();
    }
    
    void draw() {
      background(0);
    
      // display text message
      fill(255);
      //spawn
      if (frameCount %30==0) {   
        Enemy f = new Enemy();
        enemies.add(f);
      }
      for (bullet s : bullets) {
        if (s.isalive == true) {
          s.bulldis();
          s.bullup();
        }
        for (Enemy f : enemies) {
          if (dist(s.x, s.y, f.x, f.y)<20 && frameCount%10==0) {
            f.health = -1;
            f.points += f.otherpoints/2;
            f.health += 0.5;
            s.isalive = false;
            if (f.health <= 0) {
              f.isAlive = false;
            }
          }
        }
      }
      // draw 
      // loop over all enemies
      for (int i = enemies.size()-1; i >= 0; i--) {
        Enemy zz = enemies.get(i);
        if (!zz.isAlive) {
          enemies.remove(i);
        } else {
          for (int a = i - 1; a >= 0; a--) {
            Enemy other = enemies.get(a);
            bloc.x = zz.x;
            bloc.y = zz.y;
            if (frameCount%50==0 && zz.isAlive) {
              PVector di = PVector.sub(other.trgt, bloc);
              di.normalize();
              di.mult(5);
              bullet s = new bullet (bloc, di);
              bullets.add(s);
            }
            if (!other.isAlive) {
              Enemy others = enemies.get(a);
              zz.move(others);
              if (!others.isAlive) {
                zz.move(other);
              }
            } else {
              zz.move(other);
            }
          }
          zz.display();
          //
        }//else
      }//for
    }
    //================================================================
    
    class Enemy {
      PVector trgt;
      boolean isAlive = true, 
        detected = false;
      float x, y, size = 20, points = 1, speed = 1, health = 1, otherpoints;
      String names = "hi";
      Enemy() {
        x = random(width);
        y = random(height);
        trgt = new PVector();
      }
    
      void display() {
        fill(200, 0, 0);
        rect(x, y, size, size);
        fill(255);
        text(points, x, y + 10);
      }
    
      void move(Enemy other) {
        otherpoints = other.points;
        trgt.x = x;
        trgt.y = y;
        if (x > other.x&& frameCount%1==0) {
          x -= speed;
        }
        if (x < other.x && frameCount%1==0) {
          x += speed;
        }
        if (y > other.y&& frameCount%1==0) {
          y -= speed;
        }
        if (y < other.y&& frameCount%1==0) {
          y += speed;
        }
        //
        if (dist(x, y, other.x, other.y)<20) {
          points += other.points/2;
          other.isAlive = false;
          health += 1;
        }
      }
    }
    
    //==============================================================
    
    class Me {
      //Player
    }
    
    //============================================================
    
    class Wall {
      // Wall
    }
    class bullet extends PVector { 
    
      PVector vel;
      boolean isalive = true;
      // constr 
      bullet(PVector bulloc, PVector vel) { 
        super(bulloc.x, bulloc.y);
        this.vel = vel;
      }  // constr 
    
      void bullup() {
        add(vel);
      }
    
      void bulldis() {
        fill(255);
        ellipse(x, y, 5, 5);
      }
      //
    }//class
    
  • there is a problem, the enemies go too fast, and they change speed, i dont know why that's happening

  • edited September 2017

    this code works a little bit better, none of the enemies are idle, but there are still 2 problems, the speed differs when there are more enemies, and one of the enemies manage to kill all of the other enemies wothout losing. I don't know why that happens, please help, there is also a minor problem, the squares get blurry, I don't know why. thanks!

    ArrayList <enemy> enemies = new ArrayList<enemy>();
    //===============================================================
    void setup() {
      rectMode(CENTER);
      background(200);
      size(1000, 700);
      noStroke();
    }
    //===============================================================
    void draw() {
      background(200);
      if (enemies.size() < 50 && frameCount%5==0) {
        enemy e = new enemy();
        enemies.add(e);
      }
      for (int i = 0; i<enemies.size(); i++) {
        enemy e = enemies.get(i);
        for (int a = i+1; a<enemies.size(); a++) {
          enemy other = enemies.get(a);
                e.edis();
          e.move(other);
          if(!other.isalive){
            enemies.remove(a);
          }
           if(dist(other.x,other.y,e.x,e.y)<20){
            other.isalive = false;
            e.points +=1;
          }
    
        }
      }
    }
    //===============================================================
    class enemy {
      boolean isalive = true, hastarget = false;
      PVector randir;
      float size = 20, speed = 1, x, y;
      int points = 0;
      enemy() {
        x = random(width);
        y = random(height);
      }
      void move(enemy other) {
        if (frameCount%1==0){
        if (dist(other.x, other. y, x, y)<20) {
          other.isalive = false;
        }
        if (x>other.x&& frameCount%1==0) {
          x -= speed;
          hastarget = true;
        }
        if ( x < other.x && frameCount%1==0) {
          x += speed;
          hastarget = true;
        }
        if ( y > other.y&& frameCount%1==0) {
          y -= speed;
          hastarget = true;
        }
        if ( y < other.y&& frameCount%1==0) {
          y += speed;
          hastarget = true;
        }
        }
      }
      void edis() {
        fill(255);
        rect( x, y, size, size);
            fill(0);
        text(points,x-5,y);
      }
    }
    
  • frameCount % 1 == 0
    

    what are these bits doing?

    what remainder do you get when you divide anything by 1?

  • I don't know, I thought it would help scince the move function is in a loop

  • The rest of division by 1 is always 0

    So this if clause doesn't work

  • edited September 2017

    can someone help me woth the speed? it changes for some reason

    ArrayList <enemy> enemies = new ArrayList<enemy>();
    float speed = 5,movex,movey;
    PVector move;
    //===============================================================
    void setup() {
      move = new PVector();
      rectMode(CENTER);
      background(0);
      size(1000, 700);
      noStroke();
      frameRate(100);
    }
    //===============================================================
    void draw() {
      move.x -= movex;
      move.y -=movey;
      if(movey < -5){
        movey = -5;
      }
        if(movey > 5){
        movey = 5;
      }
        if(movex < -5){
        movex = -5;
      }
        if(movex > 5){
        movex = 5;
      }
      translate(move.x,move.y);
      background(0);
      habitable();
      if(move.x >1700){
        move.x = 1700;
      }else if(move.x <-1700){
        move.x = -1700;
      }
        if(move.y >1250){
        move.y = 1250;
      }else if(move.y <-1250){
        move.y = -1250;
      }
      if (enemies.size() < 50 && frameCount%5==0) {
        enemy e = new enemy();
        enemies.add(e);
      }
      for (int i = 0; i<enemies.size(); i++) {
        enemy e = enemies.get(i);
        if (!e.isalive) {
          enemies.remove(e);
        }
        for (int a = i+1; a<enemies.size(); a++) {
          enemy other = enemies.get(a);
          e.edis();
          e.move(other);
        }
      }
    }
    void habitable(){
      fill(200);
      rect(width/2,height/2,4000,2800);
    }
    //================================================================
    void keyPressed() {
        if (key == 'w') { 
          movey -= speed;
        }
        if (key == 's') { 
          movey +=  speed;
        }
        if (key == 'a') { 
          movex -=speed;
        }
        if (key == 'd') { 
          movex +=  speed;
        }
    } //func 
    
    void keyReleased() {
      if (key == 'w' || key == 's') { 
        movey = 0;
      }
      if (key == 'a' || key == 'd') { 
        movex = 0;
      }
    } //func 
    //===============================================================
    class enemy {
      boolean isalive = true, hastarget = false;
      PVector randir;
      float size = 20, espeed = 1, x, y;
      int points = 0;
      enemy() {
        x = random(-1500,1500);
        y = random(-1150,1150);
        randir = new PVector();
        randir.x = random(-0.5,0.5);
        randir.y = random(-0.5,0.5);
      }
      void move(enemy other) {
          if(x >1500){
        x = 1500;
      }else if(x <-1500){
        x = -1500;
      }
        if(y >1050){
        y = 1050;
      }else if(y <-1050){
        y = -1050;
      }
          if (dist(other.x, other. y, x, y)<20) {
            other.isalive = false;
          }
          if (!hastarget){
            x += randir.x;
            y += randir.y;
            if (frameCount%150==0){
                  randir.x = random(-0.5,0.5);
        randir.y = random(-0.5,0.5);
            }
          }
          if (dist(other.x, other.y, x, y)<200) {
            if (x>other.x) {
              x -= espeed;
              hastarget = true;
            }
            if ( x < other.x) {
              x += espeed;
              hastarget = true;
            }
            if ( y > other.y) {
              y -= espeed;
              hastarget = true;
            }
            if ( y < other.y) {
              y += espeed;
              hastarget = true;
            }
          }
        if (dist(other.x, other.y, x, y)<20) {
          hastarget = false;
          other.isalive = false;
          points +=1;
        }
      }
      void edis() {
        fill(255);
        rect( x, y, size, size);
        fill(0);
        text(points, x-5, y);
      }
    }
    //================================================
    class wall{
    
    }
    
  • Which lines should we look at...?

  • ArrayList <enemy> enemies = new ArrayList<enemy>();
    
    float speed = 5, 
      movex, movey; // nad naming here! This is position (of player/hero?)
    
    PVector move; // this is speed / velocity 
    
    //===============================================================
    
    void setup() {
      size(1000, 700);
    
      move = new PVector();
      rectMode(CENTER);
      background(0);
    
      noStroke();
      frameRate(100);
    }
    
    //===============================================================
    
    void draw() {
    
      background(0);
    
      move.x -= movex;
      move.y -= movey;
    
      if (movey < -5) {
        movey = -5;
      }
      if (movey > 5) {
        movey = 5;
      }
      if (movex < -5) {
        movex = -5;
      }
      if (movex > 5) {
        movex = 5;
      }
    
      pushMatrix(); 
      translate(move.x, move.y);
      habitable();
      popMatrix(); 
    
      if (move.x >1700) {
        move.x = 1700;
      } else if (move.x <-1700) {
        move.x = -1700;
      }
      if (move.y >1250) {
        move.y = 1250;
      } else if (move.y <-1250) {
        move.y = -1250;
      }
    
      if (enemies.size() < 50 && frameCount%5==0) {
        enemy e = new enemy();
        enemies.add(e);
      }
    
      for (int i = 0; i<enemies.size(); i++) {
        enemy e = enemies.get(i);
    
        if (!e.isalive) {
          // dead
          enemies.remove(e);
        } else {
          //e is alive ---
          e.edis();
          for (int a = i+1; a<enemies.size(); a++) {
            enemy other = enemies.get(a);
            e.moveVector(other);
          }//for a
          if (e.isalive) 
            e.move();
          // ---
        }//else
      }//for i
    }
    
    void habitable() {
      fill(200);
      rect(width/2, height/2, 4000, 2800);
    }
    
    //================================================================
    
    void keyPressed() {
      if (key == 'w') { 
        movey -= speed;
      }
      if (key == 's') { 
        movey +=  speed;
      }
      if (key == 'a') { 
        movex -=speed;
      }
      if (key == 'd') { 
        movex +=  speed;
      }
    } //func 
    
    void keyReleased() {
      if (key == 'w' || key == 's') { 
        movey = 0;
      }
      if (key == 'a' || key == 'd') { 
        movex = 0;
      }
    } //func 
    
    //===============================================================
    
    class enemy {
    
      boolean isalive = true, 
        hastarget = false;
      PVector randir;
    
      float size = 20, 
        espeedX = 1, espeedY=0, // speed 
        x, y;                   // pos 
      int points = 0;
    
      enemy() {
        x = random(-15, 1500);
        y = random(-11, 1150);
        randir = new PVector();
        randir.x = random(-0.5, 0.5);
        randir.y = random(-0.5, 0.5);
      }
    
      void moveVector(enemy other) {
    
        espeedX = 1; 
        espeedY=0;
    
        if (x >1500) {
          x = 1500;
        } else if (x <-1500) {
          x = -1500;
        }
        if (y >1050) {
          y = 1050;
        } else if (y <-1050) {
          y = -1050;
        }
    
        if (dist(other.x, other. y, x, y)<20) {
          other.isalive = false;
          isalive = false;
          return;
        }
    
    
        if (dist(other.x, other.y, x, y)<200) {
          if (x>other.x) {
            espeedX=-abs(espeedX);
            hastarget = true;
          }
          if ( x < other.x) {
            espeedX=abs(espeedX);
            hastarget = true;
          }
          if ( y > other.y) {
            espeedY=-abs(espeedY);
            hastarget = true;
          }
          if ( y < other.y) {
            espeedY=abs(espeedY);
            hastarget = true;
          }
        } else
          hastarget = false;
    
        if (dist(other.x, other.y, x, y)<20) {
          hastarget = false;
          other.isalive = false;
          isalive = false;
          points +=1;
        }
      }
    
      void move() {
        if (!hastarget) {
          x += randir.x;
          y += randir.y;
          if (frameCount%150==0) {
            randir.x = random(-0.5, 0.5);
            randir.y = random(-0.5, 0.5);
          }
        } else {
          x += espeedX;
          y += espeedY;
        }
      }
    
      void edis() {
        // display 
        fill(255);
        rect( x, y, size, size);
        fill(0);
        text(points, x-5, y);
      }
    }
    //================================================
    class wall {
      //
    }
    //
    
  • they moved so fast because each enemy was checking its position against all others and every time (meaning like 20 times in one draw!) adding a value to x or y (either randir or espeed).

    To change this, I changed the nested (double for loop) in draw().

    I also made two different methods in the class enemy, one is for determine the values for espeedX and espeedY, one is for adding it to x and y. Since the latter is called only once, we only add speed once (and not like 20 times). The former is still run 20 times but this means that only the last other enemy determines the direction (espeedX and espeedY). Alternatively you could add up all those 20 directions and take the average.

    But the question arises of courses which behavior you want? Follow the closest enemy or .... ?

    Chrisir

  • what you did was basically remove the follow or move function, and thus the enemies rely on the random movement,that is why none of them actually follow anybody, and also why when I commented out the random movements they did not move. but I get what you're trying to do... hopefully I can improve it:)

  • I know why, but I don't know how to fix it. the problem's because the're in a double loop, your's worked because the move function was not in a nested loop

  • it moves once every time the a loop gets activated

  • edited September 2017

    fixed! I had to add a boolean that checks if it has moved.. you will see all that in the code. does need some improvements though... like the wall function, I don't know how to make it so that the enemies keep moving after they hit the wall(as you can see I commented it out).

    ArrayList <enemy> enemies = new ArrayList<enemy>();
    ArrayList <wall> walls = new ArrayList<wall>();
    float movex, movey, moving, locx, locy, size;
    int borderx = 1000, bordery = 1000, walx = -borderx + int(random(570, 600)), waly = -bordery + int(random(570, 600));
    PVector move,me;
    //===============================================================
    void setup() {
      surface.setResizable(true);
      move = new PVector();
      me = new PVector();
      me.x = width/2;
      me.y = height/2;
      rectMode(CENTER);
      background(0);
      size(1000, 1000);
      noStroke();
      frameRate(100);
    }
    //================================================================
    //===============================================================
    void draw() {
      move.x -= movex;
      move.y -=movey;
      me.x = -move.x + width/2;
      me.y = -move.y + height/2;
      translate(move.x, move.y);
      background(0);
      habitable();
      fill(255);
        ellipse(me.x,me.y,20,20);
      if (move.x >borderx) {
        move.x = borderx;
      } else if (move.x <-borderx) {
        move.x = -borderx;
      }
      if (move.y >bordery) {
        move.y = bordery;
      } else if (move.y < -bordery) {
        move.y = -bordery;
      }
      //while (walx < borderx + 460) {
      //  while (waly<bordery + 460) {
      //    wall e = new wall(walx, waly, random(70, 110));
      //    walls.add(e);
      //    waly += random(150, 200);
      //  }
      //  waly = -bordery + int(random(570, 600));
      //  walx += random(150, 200);
      //}
      if (enemies.size() < borderx/100 ) {
        enemy e = new enemy();
        enemies.add(e);
      }
      for (int i = 0; i < walls.size(); i++) {
        wall wal= walls.get(i);
        wal.display();
      }
      for (int i = 0; i<enemies.size(); i++) {
        enemy e = enemies.get(i);
        //for (wall w : walls) {
        //  if (dist(w.x, w.y, e.x, e.y)<10 + w.size/2) {
        //    if (!e.moved) {
        //      if (e.x>w.x) {
        //        e.x += 3;
        //      }
        //      if (e.y>w.y) {
        //        e.y += 3;
        //      }
        //      if (e.x<w.x) {
        //        e.x -= 3;
        //      }
        //      if (e.y<w.y) {
        //        e.y -= 3;
        //      }
        //    }
        //    e.moved = true;
        //  }
        //  if (dist(w.x, w.y, e.x, e.y)<w.size/2) {
        //    if (e.x>w.x) {
        //      e.x += 2;
        //    }
        //    if (e.y>w.y) {
        //      e.y += 2;
        //    }
        //    if (e.x<w.x) {
        //      e.x -= 2;
        //    }
        //    if (e.y<w.y) {
        //      e.y -= 2;
        //    }
        //  }
        //}
        for (int a = i + 1; a<enemies.size(); a ++) {
          enemy other = enemies.get(a);
          e.move(other);
          e.moved = true;
          if (dist(other.x, other.y, e.x, e.y)<20) {
            if(random(100)*e.points+1/100<50){
            e.hastarget = false;
            other.isalive = false;
            e.points += other.points/1.5 + 1;
            }else{
            other.hastarget = false;
            e.isalive = false;
            other.points += e.points/1.5 + 1;
            }
          }
        }
        if (!e.isalive) {
          enemies.remove(e);
        }
        e.edis();
      }
    }
    void habitable() {
      fill(200);
      rect(width/2, height/2, borderx * 2, bordery * 2);
    }
    //================================================================
    void keyPressed() {
      if (key == 'w') { 
        movey = -3;
      }
      if (key == 's') { 
        movey =  3;
      }
      if (key == 'a') { 
        movex =-3;
      }
      if (key == 'd') { 
        movex =  3;
      }
    } //func 
    
    void keyReleased() {
    
      if (key == 'w' || key == 's') { 
        movey = 0;
      }
      if (key == 'a' || key == 'd') { 
        movex = 0;
      }
    } //func 
    //===============================================================
    class enemy {
      boolean isalive = true, hastarget = false, moved = false;
      PVector randir;
      float size = 20, espeed = 2, x, y, notmovetime = 0, px, py, otherx, othery;
      int points = 0;
      enemy() {
        x = random(borderx * -1 + width/2, bordery + width/2);
        y = random(bordery * -1 + height/2, bordery + height/2);
        randir = new PVector();
        randir.x = random(-1, 1);
        randir.y = random(-1, 1);
      }
      void move(enemy other) {
        if (!moved) {
          if (px == x && py == y) {
            notmovetime +=1;
            if (notmovetime == 100) {
              hastarget = false;
            }
          }
          px = x;
          py = y;
          otherx = other.x;
          othery = other.y;
          if (x >borderx + width/2) {
            x = borderx + width/2 ;
          } else if (x <-borderx + width/2) {
            x = -borderx +width/2;
          }
          if (y >bordery + height/2) {
            y = bordery + height/2;
          } else if (y < -bordery + height/2) {
            y = -bordery + height/2;
          }
          if (x>otherx) {
            x -= espeed;
            notmovetime = 0;
          }
          if ( x < otherx) {
            x += espeed;
            notmovetime = 0;
          }
          if ( y > othery) {
            y -= espeed;
            notmovetime = 0;
          }
          if ( y < othery) {
            y += espeed;
            notmovetime = 0;
          }
          if (dist(other.x, other.y, x, y)<200) {
            hastarget = true;
          } else if (dist(x, y, other.x, other.y)>width/2) {
            hastarget = false;
          }
          if (!hastarget) {
            x += randir.x;
            y += randir.y;
            randir.x = int(randir.x);
            randir.y = int(randir.y);
            if (frameCount%5==0) {
              randir.x += random(-0.2, 0.2);
              randir.y += random(-0.2, 0.2);
            }
          }
        }
      }
      void edis() {
        moved = false;
        fill(255);
        rect( x, y, size, size);
        fill(0);
        text(points, x-5, y);
      }
    }
    //================================================
    class wall {
      float size = 100, x = -1470, y = -1020;
      wall(float lx, float ly, float sz) {
        x = lx;
        y = ly;
        size = sz;
      }
      void display() {
        fill(100);
        rect(x, y, size, size);
      }
    }
    
                rect(locx, locy, size, size);
              }
            }
    
  • I kind of fixed it, but its stull a little buggy... definitely better than before

    ArrayList <enemy> enemies = new ArrayList<enemy>();
    ArrayList <wall> walls = new ArrayList<wall>();
    float movex, movey, moving, locx, locy, size;
    int borderx = 1000, bordery = 1000, walx = -borderx + int(random(570, 600)), waly = -bordery + int(random(570, 600));
    PVector move, me;
    //===============================================================
    void setup() {
      move = new PVector();
      me = new PVector();
      me.x = width/2;
      me.y = height/2;
      rectMode(CENTER);
      background(0);
      size(1000, 1000);
      noStroke();
      frameRate(100);
    }
    //================================================================
    //===============================================================
    void draw() {
      move.x -= movex;
      move.y -=movey;
      me.x = -move.x + width/2;
      me.y = -move.y + height/2;
      translate(move.x, move.y);
      background(0);
      habitable();
      fill(255);
      ellipse(me.x, me.y, 20, 20);
      if (move.x >borderx) {
        move.x = borderx;
      } else if (move.x <-borderx) {
        move.x = -borderx;
      }
      if (move.y >bordery) {
        move.y = bordery;
      } else if (move.y < -bordery) {
        move.y = -bordery;
      }
      while (walx < borderx + 460) {
        while (waly<bordery + 460) {
          wall e = new wall(walx, waly, random(70, 110));
          walls.add(e);
          waly += random(150, 200);
        }
        waly = -bordery + int(random(570, 600));
        walx += random(150, 200);
      }
      if (enemies.size() < borderx/100 ) {
        enemy e = new enemy();
        enemies.add(e);
      }
      for (int i = 0; i < walls.size(); i++) {
        wall wal= walls.get(i);
        wal.display();
      }
      for (int i = 0; i<enemies.size(); i++) {
        enemy e = enemies.get(i);
              if (!e.isalive) {
            enemies.remove(e);
          }
          e.edis();
        for (wall w : walls) {
          if (dist(w.x, w.y, e.x, e.y)<30 + w.size/2) {
            if (!e.moved) {
              if (e.x>w.x) {
                e.x += 0.2;
              }
              if (e.y>w.y) {
                e.y += 0.2;
              }
              if (e.x<w.x) {
                e.x -= 0.2;
              }
              if (e.y<w.y) {
                e.y -= 0.2;
              }
            }
          }
          if (dist(w.x, w.y, e.x, e.y)<(20 + w.size) / 2) {
            if (e.x>w.x) {
              e.x += 3;
            }
            if (e.y>w.y) {
              e.y += 3;
            }
            if (e.x<w.x) {
              e.x -= 3;
            }
            if (e.y<w.y) {
              e.y -= 3;
            }
          }
        }
        for (int a = i + 1; a<enemies.size(); a ++) {
          enemy other = enemies.get(a);
          for (int w = 0; w < walls.size(); w ++) {
            wall wa = walls.get(w);
            e.move(other, wa);
            e.moved = true;
          }
          if (dist(other.x, other.y, e.x, e.y)<20) {
            if (random(100)*e.points+1/100<50) {
              e.hastarget = false;
              other.isalive = false;
              e.points += other.points/1.5 + 1;
            } else {
              other.hastarget = false;
              e.isalive = false;
              other.points += e.points/1.5 + 1;
            }
          }
        }
      }
    }
    void habitable() {
      fill(200);
      rect(width/2, height/2, borderx * 2, bordery * 2);
    }
    //================================================================
    void keyPressed() {
      if (key == 'w') { 
        movey = -3;
      }
      if (key == 's') { 
        movey =  3;
      }
      if (key == 'a') { 
        movex =-3;
      }
      if (key == 'd') { 
        movex =  3;
      }
    } //func 
    
    void keyReleased() {
    
      if (key == 'w' || key == 's') { 
        movey = 0;
      }
      if (key == 'a' || key == 'd') { 
        movex = 0;
      }
    } //func 
    //===============================================================
    class enemy {
      boolean isalive = true, hastarget = false, moved = false;
      PVector randir;
      float size = 20, espeed = 2, x, y, notmovetime = 0, px, py, otherx, othery;
      int points = 0;
      enemy() {
        x = random(borderx * -1 + width/2, bordery + width/2);
        y = random(bordery * -1 + height/2, bordery + height/2);
        randir = new PVector();
        randir.x = random(-1, 1);
        randir.y = random(-1, 1);
      }
      void move(enemy other, wall w) {
        if (!moved) {
          if (dist(px,py,x,y)<2) {
            notmovetime +=1;
            if (notmovetime == 100) {
              hastarget = false;
            }
          }
          px = x;
          py = y;
          otherx = other.x;
          othery = other.y;
          if (x >borderx + width/2) {
            x = borderx + width/2 ;
          } else if (x <-borderx + width/2) {
            x = -borderx +width/2;
          }
          if (y >bordery + height/2) {
            y = bordery + height/2;
          } else if (y < -bordery + height/2) {
            y = -bordery + height/2;
          }
          if (x>otherx) {
            x -= espeed;
            notmovetime = 0;
            moved = true;
          }
          if ( x < otherx) {
            x += espeed;
            notmovetime = 0;
            moved = true;
          }
          if ( y > othery) {
            y -= espeed;
            notmovetime = 0;
            moved = true;
          }
          if ( y < othery) {
            y += espeed;
            notmovetime = 0;
            moved = true;
          }
          if (dist(other.x, other.y, x, y)<200) {
            hastarget = true;
          } else if (dist(x, y, other.x, other.y)>width/2) {
            hastarget = false;
          }
          if (!hastarget) {
            x += randir.x;
            y += randir.y;
            if (frameCount%5==0) {
              randir.x += random(-0.2, 0.2);
              randir.y += random(-0.2, 0.2);
            }
          }
        }
      }
          void edis() {
            moved = false;
            fill(255);
            rect( x, y, size, size);
            fill(0);
            text(points, x-5, y);
          }
        }
        //================================================
        class wall {
          float size = 100, x = -1470, y = -1020;
          wall(float lx, float ly, float sz) {
            x = lx;
            y = ly;
            size = sz;
          }
          void display() {
            fill(100);
        rect(x, y, size, size);
      }
    }
    
  • Well done!

  • edited September 2017

    Question: Why do enemies kill each other?

    Is that a game or just a play of enemies you can look at?

    But the question arises of course which behavior you want?

    It would be best if one enemy only follows the closest enemy I think.

    When they touch, both should die, no?

  • nah, the enemies have a 50/50 chance of winning when they touch and yes, I want them to follow the closest enemy

  • Thank you!

Sign In or Register to comment.