所以我有几个例子,我希望能够“冻结”我的游戏状态。它是一个自上而下的滚动条,我想让玩家能够通过使用通电暂停屏幕滚动一小段时间(如果你跌到你死的屏幕底部)。我也想在游戏开始时暂停游戏,画一个3,2,1,去吧!为玩家提供准备时间,因为现在只要你点击播放,屏幕就会开始滚动。
我一直在使用Timer来完成此操作,但如果我想在连续的场合冻结屏幕,它就无法工作。就像玩家使用冻结一样,屏幕成功冻结,但如果他们快速使用另一个冻结,它就不起作用。似乎有一种无意识的冷静。我对前面解释过的'介绍延迟'有类似的问题。由于某种原因,它只适用于前2个级别。以下是我使用Timer的方法。
if(gameState != STATE.frozen) {
camera.translate(0, (float) scrollSpeed);
staminaBar.setPosition(staminaBar.getX(), (float) (staminaBar.getY()+scrollSpeed));
staminaMeter.setPosition(staminaMeter.getX(), (float) (staminaMeter.getY()+scrollSpeed));
healthBar.setPosition(healthBar.getX(), (float) (healthBar.getY()+scrollSpeed));
healthMeter.setPosition(healthBar.getX(), (float) (healthMeter.getY()+scrollSpeed));
boostBar.setPosition(boostBar.getX(), (float) (boostBar.getY()+scrollSpeed));
boostMeter.setPosition(boostMeter.getX(), (float) (boostMeter.getY()+scrollSpeed));
screenCeiling += (float) scrollSpeed;
screenFloor += (float) scrollSpeed;
}
else {
Timer.schedule(new Task() { //freeze the screen for 5 seconds
@Override
public void run() {
gameState = STATE.playing;
}
}, 5);
}
根据我的理解,它会在将游戏恢复到“播放”状态之前等待5秒钟。但就像我说的那样,这只有在大间隔时间激活时才有效,我不知道为什么。我有更好的方法吗?
至于介绍延迟,这可能是一个更好问的单独问题,但我使用相同的方法,但它不允许我在我的贴图上绘制精灵,所以如果有人知道如何做到这一点,请将其包括在内你的回应
答案 0 :(得分:0)
在渲染方法中检查你的gameState变量,如果游戏正在播放,那么像往常一样更新游戏并绘制它。
如果游戏没有播放,则跳过游戏的更新方法并从当前时间创建时间延迟:
endTime = TimeUtils.millis()+5000;
然后每次通过render方法检查当前时间是否大于结束时间。当前时间超过延迟时间时,将gameState设置回播放并让游戏返回更新。
你必须有另一个布尔标志,所以你只设置endTime一次(你不想每次都通过渲染循环保持重置),或者如果“STATE”是一个枚举,那么包含一个选项对于暂停游戏的确切帧的“justPaused”,设置结束时间,然后将STATE设置为“notPlaying”。
您还可以使用此方法创建另一种“更新”方法,您可以在其中更新倒计时精灵,但不能更新游戏本身。当游戏正在播放时,将跳过其他更新方法。
答案 1 :(得分:0)
假设您发布的代码位于渲染循环中,那么每当您处于冻结状态时,您就会在每个帧上创建一个新的计时器任务。因此,如果你冻结5秒并且游戏以60fps运行,你将创建300个计时器任务,每个任务都会强制游戏返回到游戏状态。最后一个在第一个发射后5秒内不会发射,因此会有五秒钟的“冷却时间”,在此期间你不能将状态更改为playing
以外的任何内容,因为会有另一个计时器任务触发在那段时间的每一帧。
您需要确保仅在首次进入frozen
州时才创建一个计时器任务。
我确实有一个建议......而不是使用状态来冻结游戏,使用一个乘以scrollSpeed
的变量。当玩家使用通电时,将该变量从1更改为零。然后你可以做一些奇特的东西,比如从一到零快速插值,所以速度变化不是那么突然。并且它可能会使您的代码更简单,因为在算法中必须以不同的方式处理一个较少的状态。