AI Flappy Bird Processing Java

the problem is i use a table to get my walls into position. I find it easier in the long run just change the map and the table does the rest. So I should times the inputs by height & width right? How would I normalize the dist?

many ways how to normalize.
you can just invert it,
inputs[i] = 1/distance;
or something else

no problem, as long as you keep track where the walls in the program. you are good to go. heres the part where the player sees ( asteroid game by codebullet, again)

//looks in 32 directions to find asteroids
  void look() {
    vision = new float[32];
    //look left
    PVector direction;
    for (int i = 0; i< vision.length; i++) {
      direction = PVector.fromAngle(rotation + i*(PI/16));

      direction.mult(10);

      vision[i] = lookInDirection(direction);
    }
    // can shot? 
    if (canShoot && vision[0] !=0) {
      vision[31] = 1;
    } else {
      vision[31] =0;
    }
  }
  //---------------------------------------------------------------------------------------------------------------------------------------------------------  


  float lookInDirection(PVector direction) {
    //set up a temp array to hold the values that are going to be passed to the main vision array

    PVector position = new PVector(pos.x, pos.y);//the position where we are currently looking for asteroids
    float distance = 0;
    //move once in the desired direction before starting 
    position.add(direction);
    distance +=1;

    //look in the direction until you reach a asteroid
    while (distance< 60) {//!(position.x < 400 || position.y < 0 || position.x >= 800 || position.y >= 400)) {


      for (Asteroid a : asteroids) {
        if (a.lookForHit(position) ) { 
           // found an asteroid
          return  1/distance;
        }
      }

      //look further in the direction
      position.add(direction);

      //loop it
      if (position.y < -50) {
        position.y += height + 100;
      } else
        if (position.y > height + 50) {
          position.y -= height -100;
        }
      if (position.x< -50) {
        position.x += width +100;
      } else  if (position.x > width + 50) {
        position.x -= width +100;
      }


      distance +=1;
    }
    return 0; // if you got no asteroid
  }

I don’t understand it. I normalized the inputs.

i made it easier to see.
run this code to see the visualisation of how the player sees

ArrayList<Ball> balls = new ArrayList<Ball>();
Player p ;
void setup() {
  noStroke();
  fullScreen();
  for (int i = 0; i < 10; i++) {
    balls.add(new Ball(random(width), random(height)));
  }
  p = new Player();
  rectMode(CENTER);
}

void draw() {
  background(0);
  for (Ball b : balls) {
    b.show();
    b.move();
  }
  for (int i=0; i < 10; i++) {
    text("Blind Area", 10, i * 100);
    text("Blind Area", width-60, i * 100);
  }
  p.look();
  p.show();
}

class Ball {
  PVector pos, vel;
  Ball(float x, float y) {
    pos = new PVector(x, y);
    vel = PVector.random2D();
  }

  void show() {
    fill(255, 100, 90);
    noStroke();
    ellipse(pos.x, pos.y, 100, 100);
  }
  
  void move(){
    pos.add(vel);
    loopy();
  }

  // this function is determine if any given location is in the ball
  // if it is a block, use rectangle collision detection instead of circle collision detection
  boolean lookForHit(PVector loc) {
   // circle collision detection
    if (dist(pos.x, pos.y, loc.x, loc.y)< 50) {
      return true;
    }
    return false;
  }
  
  // this is just wrapping edges
  void loopy() {
    // Wrap Edges
    if (pos.y < -50) {
      pos.y = height + 50;
    } else
      if (pos.y > height + 50) {
        pos.y = -50;
      }
    if (pos.x< -50) {
      pos.x = width +50;
    } else  if (pos.x > width + 50) {
      pos.x = -50;
    }
  }
}

class Player {
  PVector pos;
  Player() {
    pos = new PVector(width/2, height/2);
  }

  void show() {
    fill(255, 255, 0);
    noStroke();
    rect(pos.x, pos.y, 30, 30);
  }

  void look() {
    PVector direction;
    for (int i = 0; i< 16; i++) {
      // player sees in 16 direction, so we have to divide one full rotation (360 degrees) with 16
      // so angle between two nearest directions will be 22.5 degree
      direction = PVector.fromAngle(i*(TWO_PI/16));
      direction.mult(10);
      // get the normalized distance to the ball if found in the current direction
      // if got no ball in the current direction, mag will be zero
      float mag = lookInDirection(direction); 
      // inputs[i] = mag; //feed this to the input
      
      // this is how the visualisation
      stroke(255);
      if (mag > 0) {
        direction.mult(1/mag);
        direction.add(pos);
        fill(255);
        text(1/mag, direction.x, direction.y);
        stroke(0, 255,0);
      }else{
        //if no ball in current direction
        direction.mult(60);
        direction.add(pos);
        stroke(255, 0,0);
      }
      
      line(pos.x, pos.y, direction.x, direction.y);
    }
  }

  float lookInDirection(PVector direction) {

    PVector position = new PVector(pos.x, pos.y);//the position where we are currently looking for the balls
    float distance = 0;
    //move once in the desired direction before starting 
    position.add(direction);
    distance +=1;

    //look in the direction
    while (distance< 60) {
      for (Ball a : balls) {
        if (a.lookForHit(position) ) { 
          // found ball
          return  1/distance;
        }
      }

      //look further in the direction
      position.add(direction);

      // next distance
      distance +=1;
    }
    return 0;
  }
}

hope this helpful

1 Like

So this gets the PVector of every ball. Then uses dist to see how far it is. So if i’m correct it draws a triangle to find the angle between player and ball and then say if angle is what you can see then um … I got lost. Am I correct of how it works so far? This code is easier to understand ty.

assume we are currently looking for the ball in front the player. start by adding a small step towards to the front of the player to current location that we are gonna check
position.add(direction);
add 1 as a step
distance +=1;

then check at that location if theres a ball

if (a.lookForHit(position) ) { 
          // found ball

the function lookForHit() in the balll class, just return boolean value, not the distance

if theres a ball, then we ended up with normalized distance that we keep track
return 1/distance;
if not, look further in that direction until we found a ball or distance reached 60
if theres no ball along that direction, just return 0

now, we have to check in 16 directions. we have to loop through the checks for each direction

I’m guessing I would then place this in think. Then um … place each direction as an input?

for me, think and look is two different function. no matter at all, just making all the function in the nice looking.
yes, as inputs
this line

.

ty this is the kind of detection I wanted when I started making this.ai. Since mag is only in look would the inputs need to be placed there? ATM I got all my inputs in think().

great!
the think is just all of these

for the asteroid ai, the think is

 //---------------------------------------------------------------------------------------------------------------------------------------------------------      
  //convert the output of the neural network to actions
  void think() {
    //get the output of the neural network
    decision = brain.feedForward(vision);

    if (decision[0] > 0.8) {//output 0 is boosting
      boosting = true;
    } else {
      boosting = false;
    }
    if (decision[1] > 0.8) {//output 1 is turn left
      spin = -0.1;
    } else {//cant turn right and left at the same time 
      if (decision[2] > 0.8) {//output 2 is turn right
        spin = 0.1;
      } else {//if neither then dont turn
        spin = 0;
      }
    }
    //shooting
    if (decision[3] > 0.8) {//output 3 is shooting
      shoot();
    }
  }

So loop through look before calling think. This is new and fun. Ty for walking me through this.

1 Like

yeah thts right!
great!

Now to try to place this new stuff into my game and see how it works.

this part is exciting. good luck!

TY, i’ll keep you in the loop.

1 Like

Would it be better to center the walls or just leave them at the corners?

it depends the way you checking for collision detection. for me, i prefer corners

oh ok, i thought the look might need something special to work.

1 Like