2D游戏平铺碰撞检测

时间:2011-10-22 13:32:37

标签: c# xna collision-detection xna-4.0

我有这样的事情:

        // checking on which tile are players corners
        // ignore this big mess below, please. It can be put in smaller
        //  equations, but for now it does its job
        left_downX = ((int)Position.X) / 32 * 32 / 32 - map.mapOffsetX / 32 * 32 / 32;
        left_downY = ((int)Position.Y + height) / 32 * 32 / 32 - map.mapOffsetY / 32 * 32 / 32;

        right_downX = ((int)Position.X + width) / 32 * 32 / 32 - map.mapOffsetX / 32 * 32 / 32;
        right_downY = ((int)Position.Y + height) / 32 * 32 / 32 - map.mapOffsetY / 32 * 32 / 32;

        left_upX = ((int)Position.X) / 32 * 32 / 32 - map.mapOffsetX / 32 * 32 / 32;
        left_upY = ((int)Position.Y) / 32 * 32 / 32 - map.mapOffsetY / 32 * 32 / 32;

        right_upX = ((int)Position.X + width) / 32 * 32 / 32 - map.mapOffsetX / 32 * 32 / 32;
        right_upY = ((int)Position.Y) / 32 * 32 / 32 - map.mapOffsetY / 32 * 32 / 32;

        // checking if there is collision and responding to it
        if (map.mapData[left_downX, left_downY] == (int)Map.Tiles.air &&
            map.mapData[left_upX, left_upY] == (int)Map.Tiles.air)
        {
            if (keyboardState.IsKeyDown(Keys.A))
            {
                Speed.X = playerSpeed;
                Direction.X = MOVE_LEFT;
            }
        }
        if (map.mapData[right_downX, right_downY] == (int)Map.Tiles.air &&
            map.mapData[right_upX, right_upY] == (int)Map.Tiles.air)
        {
            if (keyboardState.IsKeyDown(Keys.D))
            {
                Speed.X = playerSpeed;
                Direction.X = MOVE_RIGHT;
            }
        }
        if (map.mapData[left_downX, left_downY] == (int)Map.Tiles.air &&
            map.mapData[right_downX, right_downY] == (int)Map.Tiles.air)
        {
            if (keyboardState.IsKeyDown(Keys.S))
            {
                Speed.Y = playerSpeed;
                Direction.Y = MOVE_DOWN;
            }
        }
        if (map.mapData[left_downX, left_downY] == (int)Map.Tiles.air &&
            map.mapData[right_downX, right_downY] == (int)Map.Tiles.air)
        {
            if (keyboardState.IsKeyDown(Keys.W))
            {
                Speed.Y = playerSpeed;
                Direction.Y = MOVE_UP;
            }
        }

因为它似乎工作正常,但事实并非如此。 例如,当玩家与地面发生碰撞时,它会停留在地面上并且无法向任何方向移动 当只与侧面的瓷砖碰撞时类似,但在那里,你可以移动到不同的一侧。

我错了什么? 也许有更好的方法可以在没有循环遍历所有瓷砖的情况下进行校验碰撞?

1 个答案:

答案 0 :(得分:1)

代码的前8行应替换为Rectangle对象,该对象应与Sprite的大小/位置相同。

然后,您可以针对要检查碰撞的切片调用Rectangle.Intersects方法。