Search code examples
javacollisionslick2d

Collision detection - preventing player from moving after he hits object


I have the following code:

if(input.isKeyDown(Input.KEY_RIGHT)){
  player = movingRIGHT;
  pposX -= 0.15f;
  if(playerR.intersects(rec1)){
    pposX += 0.15f;
  }
}

if(input.isKeyDown(Input.KEY_LEFT)){
  player = movingLEFT;
  pposX += 0.15f;
  if(playerR.intersects(rec1)){
    pposX -= 0.15f;
}

And two players - playerR and rec1:

playerR = new Rectangle(shiftX-174,shiftY+200,player.getWidth(),player.getHeight());
rec1 = new Rectangle(448+pposX, 640-128+pposY, 32, 32);

My player doesn't stop after he hits the wall. I wanted to know if coordinates are good enough, so I tried do draw rectangles at exactly same coordinates without problem. However, my player just goes through.

I'm using java slick2d with this code:

package javagame;

import org.lwjgl.input.Mouse;
import org.newdawn.slick.Animation;
import org.newdawn.slick.Color;
import org.newdawn.slick.GameContainer;
import org.newdawn.slick.Graphics;
import org.newdawn.slick.Image;
import org.newdawn.slick.Input;
import org.newdawn.slick.SlickException;
import org.newdawn.slick.geom.Rectangle;
import org.newdawn.slick.state.BasicGameState;
import org.newdawn.slick.state.StateBasedGame;

public class Play extends BasicGameState {

Animation player,movingUP,movingDOWN,movingLEFT,movingRIGHT;
Image worldMap;
Image cat;
boolean quit = false;
int [] duration = {200,200,200,200};
int [] duration2 = {200,200};
float pposX;
float pposY;
float shiftX = pposX + 430;
float shiftY = pposY + 320;
float height;
int x = 0;
int y = 0;
boolean jumping = false;
float verticalSpeed;
float mapPosX = 0;
float mapPosY = 0;
Rectangle rec1;
Rectangle rec2;
Rectangle rec3;
Rectangle rec4;
Rectangle rec5;
Rectangle rec6;
Rectangle rec7;
Rectangle rec8;
Rectangle playerR;
boolean Win;
String a = "Victory!";
public Play (int state){

}

public void init(GameContainer gc,StateBasedGame sbg) throws SlickException{
    worldMap = new Image("res/map.png");
    Image[] walkUp = {new Image("res/buckysBack.png") , new Image("res/buckysBack.png")};
    Image[] walkLeft = {new Image("res/1L.png") , new Image("res/2L.png"), new Image("res/3L.png"), new Image("res/4L.png")};
    Image[] walkRight = {new Image("res/1R.png") , new Image("res/2R.png"), new Image("res/3R.png"), new Image("res/4R.png")};
    Image[] walkDown = {new Image("res/buckysFront.png") , new Image("res/BuckysFront.png")};


    movingLEFT = new Animation(walkLeft , duration , true);
    movingRIGHT = new Animation(walkRight,duration,true);
    movingUP = new Animation(walkUp,duration2,false);
    movingDOWN = new Animation(walkDown,duration2,false);

    rec1 = new Rectangle(448+pposX, 640-128+pposY, 32, 32);
    rec2 = new Rectangle(480,640-160,32,32);
    rec3 = new Rectangle(512,640-192,64,32);


    player = movingRIGHT;
}

public void render(GameContainer gc,StateBasedGame sbg,Graphics g)throws SlickException{
    worldMap.draw(pposX,pposY);
    player.draw(shiftX-174,shiftY+200);
    g.drawRect(448+pposX, 640-128+pposY, 32, 32);
    g.drawRect(shiftX-174,shiftY+200,player.getWidth(),player.getHeight());
    g.setColor(Color.blue);
    g.drawString("Your position x: " + pposX * -1 + "\n              y: " + pposY  , 600, 30);
    int mx = Mouse.getX();
    int my = Mouse.getY();
    g.drawString("Your mouse x: " + mx + "y: " + my, 400,400);
    playerR = new Rectangle(shiftX-174,shiftY+200,player.getWidth(),player.getHeight());


    if(quit == true){
        g.drawString("Resume(R)", sbg.getContainer().getWidth()/2, 100);
        g.drawString("Main Menu(M)", sbg.getContainer().getWidth()/2, 150);
        g.drawString("Quit(Q)", sbg.getContainer().getWidth()/2, 200);
        if(quit==false){
            g.clear();
        }
    }
    if(Win){
        g.setColor(Color.red);
        g.drawString(a,sbg.getContainer().getWidth()/2 - a.length()/2,300);
    }


}

public void update(GameContainer gc,StateBasedGame sbg,int delta)throws SlickException{
    Input input = gc.getInput();

    if(input.isKeyDown(Input.KEY_UP)){
        pposY += 0.15f;
    }
    if(input.isKeyDown(Input.KEY_DOWN)){
        pposY -= 0.15f;
    }

    if(jumping){
        verticalSpeed += .007f * delta;
    }
    pposY += verticalSpeed;



    if(input.isKeyDown(Input.KEY_RIGHT)){
        player = movingRIGHT;
        pposX -= 0.15f;
        if(playerR.intersects(rec1)){
        pposX += 0.15f;
        }
        if(pposX>3100){
            Win = true;
        }
    }
    if(input.isKeyDown(Input.KEY_LEFT)){
        player = movingLEFT;
        pposX += 0.15f;
        if(playerR.intersects(rec1)){
        pposX -= 0.15f;
        }
        if(pposX> -1.5f){
            pposX-= 0.15f;
        }
    }

}
public int getID(){
    return 1;
}
}

How can I get the player to stop at the wall?


Solution

  • playerR = new Rectangle(shiftX-174,shiftY+200,player.getWidth(),player.getHeight());
    

    First of all, I have no clue what shiftX is. You have to update the rectangle every frame. Example:

    playerR = new Rectangle(pposX, pposY, player.getWidth(), player.getHeight());
    

    Now put that code right before your collision detection. Note that you should store the width and height in a variable to make it faster instead of having to invoke getWidth and getHeight every frame.