I've been trying to make a pong game recently, and I can't get the rectangle collision right, between a paddle(one rectangle) and a few tiles (another few rectangles). I've tried many ways to do the collision, but I can't get it right.
Here are some Images you might need
Here is my current code
Element
import java.awt.Color;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.Rectangle;
public class Element {
public int x;
public int y;
public int w;
public int h;
public int id;
public Image image;
public Rectangle cr;
public Element(int x2, int y2, int n, Image i) {
this.x = x2;
this.y = y2;
this.id = n;
this.image = i;
}
public int getID() {
return id;
}
public Image getImage() {
return image;
}
public int getX() {
return x;
}
public int getY() {
return y;
}
public int getWidth() {
return w;
}
public int getHeight() {
return h;
}
public Rectangle getCollisionRec(){
return cr = new Rectangle(getX(), getY(),getWidth(),getHeight());
}
public void draw(Graphics2D g) {
g.drawImage(getImage(), getX(), getY(), null);
g.draw(getCollisionRec());
g.setPaint(null);
g.setColor(Color.GRAY);
}
}
Templetes
import java.awt.Image;
public class Templetes extends Element {
///////////////For 4 sided shapes///////////////
public Templetes(int x, int y,int n, Image i) {
super(x, y, n,i);
}
////////////////////////////////////////////////
}
Level
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.Rectangle;
import javax.swing.ImageIcon;
public class Level {
public Element[][] overallLevel;
public Element[] elements;
public Rectangle[][] collisionRecs;
public Rectangle[] recColElements;
public int Lines;
public int levelLength;
public int leftBorder;
public int rightBorder;
public int unit = 20;
/////////Images/////////
public Image background;
public Image square13;
/////////////////////////
public Image getBackground() {
return background;
}
public Level() {
square13 = new ImageIcon(this.getClass().getResource("/ultrapong/levels/images/Square13.png")).getImage();
}
/*
Legend
: = empty slot
S = square with all borders
*/
public void defineLevel(String[] definitions) {
overallLevel = new Element[Lines][definitions[0].length()];
collisionRecs = new Rectangle[Lines][definitions[0].length()];
levelLength = definitions[0].length() * unit;
leftBorder = 0;
rightBorder = 500;
int elementsCounter = 0;
for (int i = 0; i < definitions.length; i++) {
char[] lineDefinition = definitions[i].toCharArray();
for (int j = 0; j < lineDefinition.length; j++) {
if (lineDefinition[j] == ':') {
overallLevel[i][j] = null;
collisionRecs[i][j] = null;
} else if (lineDefinition[j] == 'S') {
Templetes t13 = new Templetes(j * unit, i * unit, 1, square13);
overallLevel[i][j] = t13;
collisionRecs[i][j] = t13.getCollisionRec();
elementsCounter++;
}
}
}
elements = new Element[elementsCounter];
recColElements = new Rectangle[elementsCounter];
int counter = 0;
for (int i = 0; i < overallLevel.length; i++) {
for (int j = 0; j < overallLevel[i].length; j++) {
if (overallLevel[i][j] != null) {
elements[counter] = overallLevel[i][j];
recColElements[counter] = collisionRecs[i][j];
counter++;
}
}
}
}
public void checkCollision(Rectangle p, Rectangle t) {
if (recColElements != null) {
if (t.intersects(p)) {
if (p.x + p.width == t.x) {
p.x = t.x - p.width;
} else if (p.x == t.x + t.width) {
p.x = t.x + t.width;
}
}
}
}
public void drawLevel(Graphics2D g) {
try {
for (int i = 0; i < elements.length; i++) {
elements[i].draw(g);
}
} catch (Exception e) {
System.out.toString();
}
}
public void drawBackground(Graphics2D g) {
g.drawImage(getBackground(), 0, 0, null);
}
}
BoxLevel
import javax.swing.ImageIcon;
import ultrapong.levels.Config.*;
public class BoxLevel extends Level {
public static final String row1 = "SS:::::::::::::::::::::SS";
public static final String row2 = "SS:::::::::::::::::::::SS";
public static final String row3 = ":::::::::::::::::::::::::";
public static final String row4 = ":::::::::::::::::::::::::";
public static final String row5 = ":::::::::::::::::::::::::";
public static final String row6 = ":::::::::::::::::::::::::";
public static final String row7 = ":::::::::::::::::::::::::";
public static final String row8 = ":::::::::::::::::::::::::";
public static final String row9 = ":::::::::::::::::::::::::";
public static final String row10 = ":::::::::::::::::::::::::";
public static final String row11 = ":::::::::::::::::::::::::";
public static final String row12 = ":::::::::::::::::::::::::";
public static final String row13 = ":::::::::::::::::::::::::";
public static final String row14 = ":::::::::::::::::::::::::";
public static final String row15 = ":::::::::::::::::::::::::";
public static final String row16 = ":::::::::::::::::::::::::";
public static final String row17 = ":::::::::::::::::::::::::";
public static final String row18 = ":::::::::::::::::::::::::";
public static final String row19 = ":::::::::::::::::::::::::";
public static final String row20 = ":::::::::::::::::::::::::";
public static final String row21 = ":::::::::::::::::::::::::";
public static final String row22 = "SS:::::::::::::::::::::SS";
public static final String row23 = "SS:::::::::::::::::::::SS";
public static final String row24 = ":::::::::::::::::::::::::";
public static final String row25 = ":::::::::::::::::::::::::";
public BoxLevel() {
Lines = 25;
background = new ImageIcon(this.getClass().getResource("/ultrapong/levels/images/backgrounds/whitebackground.PNG")).getImage();
String[] definitions = {row1, row2, row3, row4, row5,
row6, row7, row8, row9, row10, row11, row12, row13,
row14, row15, row16, row17, row18, row19, row20,
row21, row22, row23, row24, row25};
super.defineLevel(definitions);
}
}
Paddle
import java.awt.;
import javax.swing.;
public class Paddle {
public Image paddleImage;
public int width;
public int height;
public Rectangle paddleRec;
public float x, y;
public float originalX;
public int centerX = width / 2;
public Paddle(int i) {
paddleImage = new ImageIcon(this.getClass().getResource("/ultrapong/Paddle" + i + ".png")).getImage();
width = paddleImage.getWidth(null);
height = paddleImage.getHeight(null);
}
public float recX;
public float recY;
public float moveX;
public boolean movable = false;
public Rectangle paddleRec() {
return new Rectangle(Math.round(getX()), Math.round(getY()), getWidth(), getHeight());
}
public void update() {
keepinbounds();
move();
}
public void keepinbounds() {
if (x < 0) {
x = 0;
moveX = 0;
}
if (y < 0) {
y = 0;
}
if (x + width > 500) {
x = 500 - width;
}
if (y + height > 500) {
y = 500 - height;
}
if (x < 0) {
x = 0;
}
if (y < 0) {
y = 0;
}
}
public float move() {
return x = x + moveX;
}
public float getX() {
return x;
}
public float getY() {
return y;
}
public int getWidth() {
return width;
}
public int getHeight() {
return height;
}
public Image getImage() {
return paddleImage;
}
}
Player
import java.awt.event.KeyEvent;
public class Player extends Paddle {
public Player() {
super(1);
y = 450;
x = 220;
}
public void keyPressed(KeyEvent e) {
int keyCode = e.getKeyCode();
if (keyCode == KeyEvent.VK_D || keyCode == KeyEvent.VK_RIGHT) {
moveX = 4;
}
if (keyCode == KeyEvent.VK_A || keyCode == KeyEvent.VK_LEFT) {
moveX = -4;
}
}
public void keyReleased(KeyEvent e) {
int keyCode = e.getKeyCode();
if (keyCode == KeyEvent.VK_D || keyCode == KeyEvent.VK_RIGHT) {
moveX = 0;
}
if (keyCode == KeyEvent.VK_A || keyCode == KeyEvent.VK_LEFT) {
moveX = 0;
}
}
}
MainConfig
import java.awt.;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import javax.swing.;
import ultrapong.levels.;
import ultrapong.levels.Config.;
public class MainConfig extends JPanel implements Runnable {
public int setSizeX, setSizeY;
public Player player;
public Thread mainLoop;
public Ball ball = new Ball();
public Level currentLevel;
public int counter;
public MainConfig() {
player = new Player();
setDoubleBuffered(true);
addKeyListener(new KL());
setFocusable(true);
setSizeX = 506;
setSizeY = 498;
currentLevel = new BoxLevel();
}
public void addNotify() {
super.addNotify();
mainLoop = new Thread(this);
mainLoop.start();
}
public void paint(Graphics g) {
super.paint(g);
Graphics2D g2d = (Graphics2D) g;
currentLevel.drawBackground(g2d);
g2d.drawImage(player.getImage(), player.paddleRec().x, player.paddleRec().y, null);
g2d.drawImage(ball.getImage(), ball.ball().x, ball.ball().y, null);
currentLevel.drawLevel(g2d);
Toolkit.getDefaultToolkit().sync();
g.dispose();
}
public class KL extends KeyAdapter {
@Override
public void keyPressed(KeyEvent e) {
player.keyPressed(e);
}
@Override
public void keyReleased(KeyEvent e) {
player.keyReleased(e);
}
}
public void update() {
ball.updateBounce(player.paddleRec(), ball.ball());
ball.update();
player.update();
for (int i = 0; i < currentLevel.elements.length; i++) {
currentLevel.checkCollision(player.paddleRec(), currentLevel.recColElements[i]);
}
}
public void run() {
float startingTime = System.currentTimeMillis();
float cumTime = System.currentTimeMillis() - startingTime;
while (true) {
float timePassed = System.currentTimeMillis() - cumTime;
cumTime += timePassed;
update();
repaint();
try {
Thread.sleep(20);
} catch (Exception e) {
System.err.toString();
}
}
}
}
Ball
import java.awt.Rectangle;
import java.util.Random;
import java.awt.Image;
import javax.swing.ImageIcon;
import static java.lang.Math.*;
public class Ball {
public int x;
public int y;
public int dx = 0;
public int dy = 0;
public int diameter;
public Image ballImg;
public Player player = new Player();
public Ball() {
x = 250;
y = 250;
dx = 3;
dy = 3;
diameter = 5;
ballImg = new ImageIcon(this.getClass().getResource("/ultrapong/Ball.png")).getImage();
}
public Random random = new Random();
public void updateBounce(Rectangle r, Rectangle b) {
if (r.intersects(b)) {
bounceY();
}
if (getY() >= 500 - 10 && getX() >= player.getX() && getX() <= player.x + player.paddleRec().width) {
bounceY();
}
}
public void update() {
if (y < 0) {
bounceY();
}
if (y + diameter > 460) {
for (int i = 250; i < 350 && i > 100; i++) {
y = random.nextInt(i);
}
for (int i = 250; i < 350 && i > 100; i++) {
x = random.nextInt(i);
}
for (int i = 0; i < 3 && i > 0; i++) {
dx = random.nextInt(i);
}
for (int i = 0; i < 3 && i > 0; i++) {
dy = random.nextInt(i);
}
}
if (x < 0) {
bounceX();
}
if (x + diameter + (diameter / 2) > 500) {
bounceX();
}
x = x + dx;
y = y + dy;
}
public Rectangle ball() {
return new Rectangle(getX(), getY(), diameter(), diameter());
}
public Image getImage() {
return ballImg;
}
public int getX() {
return x;
}
public int getY() {
return y;
}
public int diameter() {
return diameter;
}
public void velocityX(int vx) {
this.dx = vx;
}
public void velocityY(int vy) {
this.dy = vy;
}
public void bounceX(Paddle p) {
double angle = atan(dx / dy);
if (dx < 0) {
angle += PI;
}
double mag = sqrt(pow(dy, 2) + pow(dx, 2));
dx *= -1;
}
public void bounceX() {
dx *= -1;
}
public void bounceY(Paddle p) {
double angle = atan(dx / dy);
if (dy < 0) {
angle += PI;
}
double mag = sqrt(pow(dy, 2) + pow(dx, 2));
dy += -1;
}
public void bounceY() {
dy *= -1;
}
}
UltraPongCopy
import javax.swing.JFrame;
public class UltraPongCopy {
public UltraPongCopy() {
JFrame f = new JFrame();
MainConfig mc = new MainConfig();
f.add(mc);
f.setTitle("UltraPong");
f.setSize(mc.setSizeX , mc.setSizeY);
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.setVisible(true);
f.setResizable(false);
}
public static void main(String[] args) {
UltraPongCopy ultraPongCopy = new UltraPongCopy();
}
}