我想开始为Android编写一个简单的2D游戏,并决定在cavas上绘制所有内容。但是我的游戏环已经不能正常工作了。任何人都知道为什么我的游戏循环中的deltatime(看下面)会随机变得非常大并导致一个口吃的画布?
@Override
public void run(){
while(running){
if (!holder.getSurface().isValid()){
continue;
}
float deltaTime;
int sleepTime;
Canvas c = holder.lockCanvas();
synchronized (holder) {
long startTime = System.currentTimeMillis();
//update
background.update();
bomberman.update();
//draw
if (background.getX()+background.getiWidth() >= 0 || (background.getX() >= 0 && background.getX() <= getWidth()))
c.drawBitmap(background.getBackground(), background.getX(), 0, null);
if (background.getX()+background.getiWidth()+background.getiWidth() >= 0 || (background.getX()+background.getiWidth() <= getWidth()))
c.drawBitmap(background.getBackground(), (background.getX()+background.getBackground().getWidth()), 0, null);
c.drawBitmap(bomberman.getImage(), bomberman.getX()-(bomberman.getImage().getWidth()/2), bomberman.getY()-(bomberman.getImage().getHeight()/2), null);
deltaTime = (System.currentTimeMillis() - startTime);
sleepTime = (int) (FRAME_PERIOD - deltaTime);
Paint paint = new Paint();
paint.setColor(Color.BLACK);
paint.setStyle(Style.FILL);
paint.setTextSize(40);
c.drawText("deltaTime:" + deltaTime, 10, 50, paint);
c.drawText("sleepTime:" + sleepTime, 10, 100, paint);
}
holder.unlockCanvasAndPost(c);
//faster
if(sleepTime > 0){
try{
Thread.sleep(sleepTime);
}
catch(InterruptedException e) {
e.printStackTrace();
}
}
//slower
while(sleepTime < 0){
//update
background.update();
bomberman.update();
sleepTime += FRAME_PERIOD;
}
}
}
答案 0 :(得分:0)
不要使用System#currentTimeMillis()
。在Android上,它使用设备的挂钟&#34;作为它的时间来源。如果网络决定更新时钟,则当前时间将向前或向后跳跃。
由于您只对帧之间的时间差异感兴趣,请改用System#nanoTime()
。它使用单调时钟。
FWIW,您可以使用Choreographer(API 16+)来改善游戏循环,以获得实际的显示刷新时间,而不是将显示队列填满。请参阅explanation here。