Need help on processing game frogger

Hi guys,

I am creating a game called frogger, and I’m confused about why my codes not working. Hope get some help here.
I created the hazards, but I can’t move them, tried many ways to fix but still failed :< (move to the right for bottom line of hazards, move opposite direction for line above, there were 3 lines of hazards for level 1. Number of lines changed when level increase.)
Here are my codes without movement, I deleted my movement codes just to make my codes looks more clear.

float level = 1;
float bandHeight;
float BANDWIDTH;
float middleBand_y;
final int BAND_X = 0;
final int TOPBAND_Y = 0;
float bottomBand_y;
float frog_X;
float frog_Y;
float frogSize;
float edge; 
float radius;
float inner;
float x0;
float x1;
float x2;
void setup()
{
  fullScreen();
  bandHeight = height/(level+4);
  BANDWIDTH = width;
  frog_X = width/2;
  frog_Y = height-bandHeight/2;
  frogSize = bandHeight/2;
  radius = frogSize/100;
  edge = frogSize;
  inner = edge+radius;
}
void draw()
{
  drawWorld();
  drawFrog(frog_X,frog_Y,frogSize);
  drawHazards();
  
 
}
void drawWorld()
{
  for (int i=1;i<level+3;i++)
  {
    fill(0,0,255);
    stroke(0,0,255);
    rect(BAND_X,middleBand_y,BANDWIDTH,bandHeight);
    middleBand_y = bandHeight*i;
  }
  fill(0);
  stroke(0);
  rect(BAND_X,TOPBAND_Y,BANDWIDTH,bandHeight);
  rect(BAND_X,bottomBand_y,BANDWIDTH,bandHeight);
  bottomBand_y = height-bandHeight;
}
void drawFrog(float x, float y, float diam)
{
  fill(0,100,0);
  ellipse(x,y,diam,diam);
  
}
void moveFrog(float xChange, float yChange)
{
  if (objectInCanvas(frog_X, frog_Y, frogSize))
    {
      frog_X = frog_X+xChange;
      frog_Y = frog_Y+yChange;
      frog_X = constrain(frog_X,inner,width-inner);
      frog_Y = constrain(frog_Y,inner,height-inner);
    }
}
void keyPressed()
{
  if ( key == 'w' || key == 'i')
  moveFrog(0,-bandHeight);
  if ( key == 's' || key == 'k')
  moveFrog(0,bandHeight);
  if ( key == 'a' || key == 'j')
  moveFrog(-bandHeight,0);
  if ( key == 'd' || key == 'l')
  moveFrog(bandHeight,0);
}
boolean objectInCanvas(float x, float y, float diam)
{
  boolean InCanvas = true;
  if ( x < 0 || x > width || y < 0 || y > height || diam < 0)
  InCanvas = false;
  return InCanvas;
}
void drawHazard(int type, float x, float y, float size)
{
  if (type == 0)//draw type 0 hazard when 0 is called
  {
    fill(255,0,0);
    ellipse(x,y,size,size);
    
  }
  if (type == 1)
  {
    fill(0);
    rect(x,y,size,size);
  }
  if (type == 2)
  {
    fill(255);
    ellipse(x,y,size,size);
  }
}
void drawHazards()
{
  for (int j=0;j<width;j++)// 
  {
    for (float i=0;i<level+2;i++)
    {
      float y0 = (height-bandHeight*1.5)-i*(bandHeight*3);
      if (y0 < bandHeight)
        {
          y0 = height-bandHeight*1.5;
        }
      float y1 = (height-bandHeight*2.8)-i*(bandHeight*3);
      if (y1 < bandHeight)
        {
          y1 = height-bandHeight*2.8;
        }
      float y2 = (height-bandHeight*3.5)-i*(bandHeight*3);
      if (y2 < bandHeight)
        {
          y2 = height-bandHeight*3.5;
        }
         x0 = j*(bandHeight*3);
         x1 = j*(bandHeight*4)-((bandHeight-50)/2);
         x2 = j*(bandHeight*5);
      drawHazard(0,x0,y0,bandHeight/1.5);
      drawHazard(1,x1,y1,bandHeight/1.5);
      drawHazard(2,x2,y2,bandHeight/1.5);
   
    }
   
  }  
  
}

No one can help you until you post your code so that it is formatted like code.

Edit your post. Select the code. Press the MAGIC FORMAT THIS LIKE CODE button, which looks like this: </>

Getting this right is basically a requirement to get help here.

I am pretty sure that I’m in your computer science class. If I were you I would experiment with the offset function a bit more. For one, the obstacles only move if the offset does not exceed bandHeight, and 2, you will need to use a modulus function in order to check whether each function is a multiple of the row below it, and if so, change direction.
Also, the way you use the drawHazard function in your drawHazards function is a little bit weird, you should be able to do that in one line of code, not 3, that would explain why you are having most of your issues, for mine I did:drawHazard(i%3,jhazardGaps+levelOffset,height-((i+1.5)(bandHeight)),obstacleSize);, which drew all of the obstacles in only one line, that will make it MUCH easier to make them move.

Hope this helped

I’m so sorry about the mess, but now I fix it, plz help… :slight_smile:

It is very glad to see my classmates here, how’s doing.:wink:
tbh, I also feel that my codes are weird, I spent a lot of time on it, and finally the codes are working, but I think I just made it super complex.

I noticed u wrote (I%3) for (int I) part, could u tell me more about drawHazard function? Thx!!

Your code is pretty complex, and it’s turning into a mess. Let’s take a different approach and simplify it by using objects to section off different parts of data and logic. There are two kinds of objects in this game: the Frog, and Hazards.

Pretend you are the Frog. To be a good Frog, you need to know where you are. As a Frog, the main things you can do are start existing, move when you are told, draw yourself, check if you should die, and die if you should.

Pretend you are a Hazard. To be a good Hazard, you need to know which type you are, where you are, and which way you are moving. You need to be able to start existing, stop existing, and draw yourself.

With just that basic breakdown, we can start to use objects and classes:

float grid_size;

class Frog {
  int x, y;
  Frog(int ix, int iy){
    x = ix;
    y = iy;
  }
  void move(){
    // TODO - move the frog.
  }
  void draw(){
    // TODO - update and draw the frog.
  }
  boolean should_die(){
    // TODO - return if the frog should die.
    return( false );
  }
  void die(){
    // TODO - cause the frog to die.
  }
}

class Hazard {
  int type;
  float x, y, dx;
  Hazard(int itype, float ix, float iy, float idx){
    type = itype;
    x = ix;
    y = iy;
    dx = idx;
  }
  boolean draw(){
    // TODO - update and draw the hazard. Return if it is off the screen.
    return( false );
  }
}

// We have one frog.
Frog the_frog;
// We have a dynamic number of Hazards.
ArrayList<Hazard> hazards = new ArrayList();

// Now we can write a much simpler setup() and draw().
void setup(){
  fullScreen();
  the_frog = new Frog(1,1);
}

void draw(){
  background(0,0,200);
  // Draw the frog.
  the_frog.draw();
  // Draw the hazards.
  for( int i = hazards.size()-1; i >= 0; i--){
    if( hazards.get(i).draw() ){
      // Remove hazards that have moved off the screen.
      hazards.remove(i);
    }
  }
}
1 Like

Now we can just start filling that in. Since we want to be able to see the hazards and frog before anything else, let’s complete their draw functions and add a basic means to make a hazard for testing it.

float grid_size;

class Frog {
  int x, y;
  Frog(int ix, int iy){
    x = ix;
    y = iy;
  }
  void move(){
    // TODO - move the frog.
  }
  void draw(){
    fill(0,200,0);
    ellipse( (x+.5) * grid_size, (y+.5) * grid_size, grid_size *.8, grid_size * .8);
  }
  boolean should_die(){
    // TODO - return if the frog should die.
    return( false );
  }
  void die(){
    // TODO - cause the frog to die.
  }
}

class Hazard {
  int type;
  float x, y, dx;
  Hazard(int itype, float ix, float iy, float idx){
    type = itype;
    x = ix;
    y = iy;
    dx = idx;
  }
  boolean draw(){
    x += dx;
    fill(200,0,0);
    ellipse( x, y, grid_size *.8, grid_size * .8);
    return( x < - 10 * grid_size || x > width + 10 * grid_size );
  }
}

// We have one frog.
Frog the_frog;
// We have a dynamic number of Hazards.
ArrayList<Hazard> hazards = new ArrayList();

// Now we can write a much simpler setup() and draw().
void setup(){
  fullScreen();
  grid_size = height / 5.0;
  the_frog = new Frog(1,1);
  noStroke();
}

void draw(){
  background(0,0,200);
  fill(0);
  rect(0,0,width,grid_size);
  rect(0,height-grid_size,width,grid_size);
  
  // Draw the frog.
  the_frog.draw();
  // Draw the hazards.
  for( int i = hazards.size()-1; i >= 0; i--){
    if( hazards.get(i).draw() ){
      // Remove hazards that have moved off the screen.
      hazards.remove(i);
    }
  }
}

void mousePressed(){
  // Create a sample hazard
  hazards.add( new Hazard( 0, mouseX, mouseY, -1 ) );
}

Oh, and we want the frog to move, so let’s take note of key presses and move the frog if we see one we care about.

float grid_size;

class Frog {
  int x, y;
  Frog(int ix, int iy){
    x = ix;
    y = iy;
  }
  void move(int dx, int dy){
    x += dx;
    y += dy;
  }
  void draw(){
    fill(0,200,0);
    ellipse( (x+.5) * grid_size, (y+.5) * grid_size, grid_size *.8, grid_size * .8);
  }
  boolean should_die(){
    // TODO - return if the frog should die.
    return( false );
  }
  void die(){
    // TODO - cause the frog to die.
  }
}

class Hazard {
  int type;
  float x, y, dx;
  Hazard(int itype, float ix, float iy, float idx){
    type = itype;
    x = ix;
    y = iy;
    dx = idx;
  }
  boolean draw(){
    x += dx;
    fill(200,0,0);
    ellipse( x, y, grid_size *.8, grid_size * .8);
    return( x < - 10 * grid_size || x > width + 10 * grid_size );
  }
}

// We have one frog.
Frog the_frog;
// We have a dynamic number of Hazards.
ArrayList<Hazard> hazards = new ArrayList();

// Now we can write a much simpler setup() and draw().
void setup(){
  fullScreen();
  grid_size = height / 5.0;
  the_frog = new Frog(1,1);
  noStroke();
}

void draw(){
  background(0,0,200);
  fill(0);
  rect(0,0,width,grid_size);
  rect(0,height-grid_size,width,grid_size);
  
  // Draw the frog.
  the_frog.draw();
  // Draw the hazards.
  for( int i = hazards.size()-1; i >= 0; i--){
    if( hazards.get(i).draw() ){
      // Remove hazards that have moved off the screen.
      hazards.remove(i);
    }
  }
}

void mousePressed(){
  // Create a sample hazard
  hazards.add( new Hazard( 0, mouseX, mouseY, -1 ) );
}

void keyPressed(){
  if( key == 'w' ) the_frog.move( 0, -1 );
  if( key == 'a' ) the_frog.move( -1, 0 );
  if( key == 's' ) the_frog.move( 0, 1 );
  if( key == 'd' ) the_frog.move( 1, 0 );
}

Well, it’s a start. There are still some method that you need to work out. Like, the check to see if the frog should die. Also, what is going to cause new hazards to appear? You might consider adding a Spawner object that periodically creates a new hazard.

In any case, notice how much easier this is to understand than having loops inside loops inside loops.

Oh the i%3 checks the types, it will find when i is a multiple of 1 2 and 3 and set those to the types if that makes sense

Thank u for the help! But, I think ur codes doesn’t accords with what I’m working for. For example, I didn’t learn “class” yet, and all the functions and parameters I wrote in my codes are required for this work, like I have to follow the construction. Plz plz help.:pleading_face:

int level = 1;
float bandHeight;
float BANDWIDTH;
float middleBand_y;
final int BAND_X = 0;
final int TOPBAND_Y = 0;
float bottomBand_y;
float frog_X;
float frog_Y;
float frogSize;
float edge; 
float radius;
float inner;
float offset;
float x0;
float x1;
float x2;
final float SPEED = 0.75;

void setup()
{
  fullScreen();
  bandHeight = height/(level+4);
  BANDWIDTH = width;
  frog_X = width/2;
  frog_Y = height-bandHeight/2;
  frogSize = bandHeight/2;
  radius = frogSize/100;
  edge = frogSize;
  inner = edge+radius;

}
void draw()
{
  drawWorld();
  drawFrog(frog_X,frog_Y,frogSize);
  drawHazards();
 
  displayMessage("level"+str(level));
 
}
void drawWorld()
{
  for (int i=1;i<level+3;i++)
  {
    fill(0,0,255);
    stroke(0,0,255);
    rect(BAND_X,middleBand_y,BANDWIDTH,bandHeight);
    middleBand_y = bandHeight*i;
    if (detectWin())
    {
      level++;
      frog_Y = height-bandHeight/2;
    }
  }
  fill(0);
  stroke(0);
  rect(BAND_X,TOPBAND_Y,BANDWIDTH,bandHeight);
  rect(BAND_X,bottomBand_y,BANDWIDTH,bandHeight);
  bottomBand_y = height-bandHeight;
}
void drawFrog(float x, float y, float diam)
{
  fill(0,100,0);
  ellipse(x,y,diam,diam);
  
  
}
void moveFrog(float xChange, float yChange)
{
  if (objectInCanvas(frog_X, frog_Y, frogSize))
    {
      frog_X = frog_X+xChange;
      frog_Y = frog_Y+yChange;
      frog_X = constrain(frog_X,inner,width-inner);
      frog_Y = constrain(frog_Y,inner,height-inner);
    }
}
void keyPressed()
{
  if ( key == 'w' || key == 'i')
  moveFrog(0,-bandHeight);
  if ( key == 's' || key == 'k')
  moveFrog(0,bandHeight);
  if ( key == 'a' || key == 'j')
  moveFrog(-bandHeight,0);
  if ( key == 'd' || key == 'l')
  moveFrog(bandHeight,0);
}
boolean objectInCanvas(float x, float y, float diam)
{
  boolean InCanvas = true;
  if ( x < 0 || x > width || y < 0 || y > height || diam < 0)
  InCanvas = false;
  return InCanvas;
}
void drawHazard(int type, float x, float y, float size)
{
  if (type == 0)
  {
    fill(255,0,0);
    ellipse(x,y,size,size);
    
  }
  if (type == 1)
  {
    fill(0);
    rect(x,y,size,size);
  }
  if (type == 2)
  {
    fill(255);
    ellipse(x,y,size,size);
  }
}
void drawHazards()
{
  
  for (int j=0;j<width;j++)
  {
    for (float i=0;i<level+2;i++)
    {
      float y0 = (height-bandHeight*1.5)-i*(bandHeight*3);
      if (y0 < bandHeight)
        {
          y0 = height-bandHeight*1.5;
        }
      float y1 = (height-bandHeight*2.8)-i*(bandHeight*3);
      if (y1 < bandHeight)
        {
          y1 = height-bandHeight*2.8;
        }
      float y2 = (height-bandHeight*3.5)-i*(bandHeight*3);
      if (y2 < bandHeight)
        {
          y2 = height-bandHeight*3.5;
        }
         x0 = j*(bandHeight*3);
         x1 = j*(bandHeight*4)-((bandHeight-50)/2);
         x2 = j*(bandHeight*5);
      drawHazard(0,x0,y0,bandHeight/1.5);
      drawHazard(1,x1,y1,bandHeight/1.5);
      drawHazard(2,x2,y2,bandHeight/1.5);
   
    }
   
  }  
  
}
void displayMessage(String m)
{
  
  textSize(bandHeight/2);
  text(m,width/2.4,bandHeight/1.5);
  if (detectWin())
  {
    
    frog_Y = height-bandHeight/2;
  
  }
  
}
boolean detectWin()
{
  boolean win=false;
  if (frog_Y < bandHeight)
  {
    win=true;
   
  
  }
  return win;
}