繁体   English   中英

Java 2D Platformer-一些逻辑/物理怪癖

[英]Java 2D Platformer - Some Logic/Physics Quirks

我正在制作Java 2d平台程序,并且正在使用线程,到目前为止,我有4个类:

Main.java-处理主JFrame

Board.java-大多数游戏逻辑是-使用每5毫秒刷新一次的线程-KeyListener

Guy.java-在何处创建了Guy的实例-使用ImageIcon,获取Guy的图像-其他诸如getBounds,getX / Y等有用的功能

Platform.java-启动平台实例的位置-再次,有用的功能

现在,继续我的工作:

我能够从一个平台移动到另一个平台,并且能够跳跃。 这是我的重力代码,用于检查重力需求,并在需要时进行

if(guy.getGravityState() == true) {
        //check need for gravity
        boolean colliding = false;
        for(int a = 0; a < platform.length; a++) {
            if(guy.getBounds().intersects(platform[a].getBounds())) {
                colliding = true;
                //guy.setY(platform[a].getY()-platform[a].getHeight()+3);
            }
        }

        //if needed, do gravity
        if(colliding == false) {
            guy.setYSpeed(3);
                            //move him down by positive y speed
        } else {
            guy.setYSpeed(0);
        }
}

角色移动方式如下:

if(guy.getXSpeed() > 0 && guy.getX() > 500) {
        for(int i = 0; i < platform.length; i++) {
            platform[i].setX(platform[i].getX() - guy.getXSpeed());
        }
    } else if (guy.getXSpeed() < 0 && guy.getX() < 300) {
        for(int i = 0; i < platform.length; i++) {
            platform[i].setX(platform[i].getX() - guy.getXSpeed());
        }
    } else {
        guy.moveX();
    }

    if(guy.getYSpeed() > 0 && guy.getY() > 350) {
        for(int i = 0; i < platform.length; i++) {
            platform[i].setY(platform[i].getY() - guy.getYSpeed());
        }
    } else if  (guy.getYSpeed() < 0 && guy.getY() < 250) {
        for(int i = 0; i < platform.length; i++) {
            platform[i].setY(platform[i].getY() - guy.getYSpeed());
        }
    } else {
        guy.moveY();
    }

很抱歉在这里没有评论,基本上它会检查是否需要移动此人或平台。 如果靠近边缘,它将移动平台;如果不靠近,则将移动该家伙。

现在,跳转代码(不确定是否相关):

if(guy.getGravityState() == false) {
        d++;
        if(d == 35) {
            d = 0;
            guy.setGravityState(true);
        }
    }

可以关闭重力的唯一方法是跳跃,因此如果关闭重力,则使用setYSpeed(-5); 因此角色现在将向上移动(负数),直到d = 35为止,因此35刷新。 此后,重力将恢复正常。

所以现在我希望你能坚持下去,并继续回答我的问题。 看一下游戏在运行时的外观:

在此处输入图片说明

现在,当我向右移动时,角色会根据需要向下移动,但是当我向左移动时,他会穿过平台。 我将如何制造它,以便在有东西停止时它不会移动? 例如看这里,那个家伙会正确地通过:

在此处输入图片说明

我的第二个问题是,与第一个问题有关,当我的角色跳跃并撞到他上方的平台时,我希望它直接向下而不是通过平台。

另外,当我从上方跳到左/右时,他有时甚至会被卡住:

在此处输入图片说明

这些都是我现在所有的问题,如果您能帮助我,我将非常感激,我知道这可能是一个压倒性的问题,但是对您的任何帮助都是值得的。 谢谢。

看起来您正在重力功能中进行碰撞检查,以阻止玩家跌落地面,但是在处理玩家的运动(向左/向右或从跳跃向上移动)时,没有发生碰撞检测。 这就是你们两个问题的问题。

移动播放器时,您需要确定下一个动作是否会与任何东西发生碰撞。 您应该将当前具有的碰撞检测移动到重力功能之外,并通过播放器的移动功能来处理它-实际上,只要根据您的实现设置了他的Y速度,播放器就会连续移动。甚至可能不需要重力就可以循环运行...只要将玩家不跳动的Y速度设置为3。

我不会尝试向您展示我的意思,因为我看不到足够的代码来说明跳跃的工作原理,但是希望这个答案足以使您走上正确的道路。

请注意,这只是一个粗略的指南,由于要移动平台,您还需要考虑其他因素,并且可能必须根据您处理跳跃等的方式来更改此设置。

这也没有考虑到这个人可能会尝试将像素下降3个像素,但地面要相距2个像素,在这种情况下,他会在块上方悬浮2个像素,因为canExecuteMove总是会返回false。

希望这有所帮助。 :)如果卡住了,您应该阅读一下处理简单碰撞检测的方法。 我自己并没有做很多事情,但是我敢肯定其他人也许可以将您链接到有用的教程。

编辑:哎呀,这不会真正解决您的第二个问题,使这个家伙很好地撞了头后倒下了。 根据我的建议,他将坚持在天花板的底部,直到完成跳跃,然后再次开始下降。 显然,您需要确保他与天花板碰撞后跳完(导致他立即开始再次下降),但问题是“这样做的最佳位置在哪里?” 我没时间了,我将把它留给您或其他人!

private void move()
{
    //....your other code
    if(canExecuteMovement(guy.getBounds(), guy.getXSpeed(), 0))
    {
        guy.moveX();
    }

    if(canExecuteMovement(guy.getBounds(), 0, guy.getYSpeed())
    {
        guy.moveY();
    }
}


private boolean canExecuteMovement(Bounds currentBounds, int xChange, int yChange)
{
    int projectedX = currentBounds.getX() + xChange;
    int projectedY = currentBounds.getY() + yChange;
    Bounds projectedBounds = new Bounds(projectedX, projectedY);
    // ^ Making an assumption about Bounds constructor but you get the idea

    for(int i = 0; i < platform.length; i ++)
    {
            if(projectedBounds.intersects(platform[i].getBounds())
            {
                    return false;
            }
    }

    return true;
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM