您好我正在制作2D平台游戏。 我想在我的播放器(一个矩形)和一个自由形式的地形(使用斜面,一个BufferedImage)之间进行逐像素碰撞。
我对这个概念有点困惑,检查我的矩形是否有任何部分 与地形相撞。
目前,我正在尝试查看我的地形的一部分是否包含非透明像素。 我将其与矩形中的每个坐标进行比较,看看它们是否相遇,但是我没有运气。
这是我的代码:
public boolean rgbCollide () {
int a = terrain.getRGB(x, y);
System.out.println(a);
// Per-pixel Bitwise collision check
for (int i =0; i < width; i++) {
for (int j =0; j < height; j++) {
//Hmm what to do here...?
}
}
return false;
}
其中:terrain是我的bufferedImage x,y,width和height是我的玩家的矩形坐标
答案 0 :(得分:1)
我认为你的游戏没有滚动?
至少你需要 玩家的位置 - 比如矩形左下角的x,y 球员的宽度,高度 地形位图
所以它会像那样:
public boolean rgbCollide (
terrain,
playerX,
playerY,
playerWidth,
playerHeight
) {
int startX = max(playerX,0);
int endX = min(playerX + playerWidth, terrain.width());
int startY = max(playerY-playerHeight,0); //because Y goes from top to bottom
int endY = min(playerY, terrain.height());
for (int y = startY; y < endY; y++) {
for (int x = startX; x < endX; x++) {
if (terrain.getRGB(x, y) is not transparent) {
return true;
}
}
}
return false;
}
我不知道java2d api,所以也许在那里调用方法width()和height()。检查“如果不透明”也取决于api,所以它留给学生锻炼:)。
答案 1 :(得分:0)
假设您使用的是ARGB格式,最高8位代表alpha(透明度)通道。 像素完美碰撞
public class RectanglePixelCollisionChecker implements CollisionChecker {
private static final RectangleCollisionChecker RECTANGLE_COLLISION_CHECKER = new RectangleCollisionChecker();
/*
ax,ay ___________ax + a.width
| |
| |
| bx, by_________|__ bx + b.width
| |(INTERSECTION)| |
|__|______________| |
ay + height |
|______________________|
by + height
*/
@Override
public boolean collide(Collidable collidable, Collidable collidable2) {
// check if bounding boxes intersect
if(!RECTANGLE_COLLISION_CHECKER.collide(collidable, collidable2)) {
return false;
}
// get the overlapping box
int startX = Math.max(collidable.getX(), collidable2.getX());
int endX = Math.min(collidable.getX() + collidable.getWidth(), collidable2.getX() + collidable2.getWidth());
int startY = Math.max(collidable.getY(), collidable2.getY());
int endY = Math.min(collidable.getY() + collidable.getHeight(), collidable2.getY() + collidable2.getHeight());
for(int y = startY ; y < endY ; y++) {
for(int x = startX ; x < endX ; x++) {
// compute offsets for surface
if((!isTransparent(collidable2.getBufferedImage(), x - collidable2.getX(), y - collidable2.getY()))
&& (!isTransparent(collidable.getBufferedImage(), x - collidable.getX(), y - collidable.getY()))) {
return true;
}
}
}
return false;
}
private boolean isTransparent(BufferedImage bufferedImage, int x, int y) {
int pixel = bufferedImage.getRGB(x, y);
if((pixel & 0xFF000000) == 0x00000000) {
return true;
}
return false;
}
}
矩形碰撞
public class RectangleCollisionChecker implements CollisionChecker {
@Override
public boolean collide(final Collidable c1, Collidable c2) {
if((c1.getX() + c1.getWidth() < c2.getX()) || (c2.getX() + c2.getWidth() < c1.getX())) {
return false;
}
if((c1.getY() + c1.getHeight() < c2.getY()) || (c2.getY() + c2.getHeight() < c1.getY())) {
return false;
}
return true;
}
}
可碰撞界面
public interface Collidable {
boolean collide(Collidable collidable);
int getX();
int getY();
int getWidth();
int getHeight();
BufferedImage getBufferedImage();
}