java swing timer在调试中工作正常,但在运行时不起作用

问题描述 投票:1回答:1

我已经尝试了一个小时,而现在却迷失了方向。我想以30 fps的速度运行游戏。摆动定时器延迟设置为1000/30。即使我将其减慢到1000或2000,它也不会改变任何东西。在逐步调试中,一切都会按预期进行。下次刷新计时器时,将调用“ updateALL()”方法。但是在运行时,永远不会调用updateAll,甚至不会调用一次(sysout永远不会打印)。香港专业教育学院修剪下面的代码只是为了显示关键部分。它应该编译。

这是我的侦听器类:

public class Observer implements ActionListener {

    private int timerFrame;
    private int fps;
    private boolean frameComplete;

    public Observer() {
        this.frameComplete = true;
        this.timerFrame = 0;
    }

    @Override
    public void actionPerformed(ActionEvent aEvent) {
            nextTimerFrame();
    }

    public void frameCompleted() {
        frameComplete = true;
        System.out.println("Fcompleted");
    }

    public int getTimerFrame() {
        return timerFrame;
    }

    public void setFps(int fps) {
        this.fps = fps;
    }

    private void nextTimerFrame() {
        System.out.println(timerFrame);
        if(frameComplete) {
            if(timerFrame == fps) {
                timerFrame = 1;
            } else {
                ++timerFrame;
            }
            frameComplete = false;
        }
    } 
}

这是我的GameClock类中的代码:

public class GameClock {
    private Timer timer;
    private Observer observer;
    private GameEngine gameEngine;
    private View view;
    private boolean paused;
    private boolean quit;
    private int clockFrame;

    public GameClock() {}
    public GameClock(GameEngine gameEngine) {
        this.gameEngine = gameEngine;
        this.paused = false;
        this.quit = false;
        setupTimer();
        this.clockFrame = 0;
        run();
    }

    public void updateAll() {
            readInputs();
            updateGameEngine();
            updateCanvas2D();
            updateCanvas3D();
            clockFrame = clockFrame == 30? 1:clockFrame+1;  
            observer.frameCompleted(); // puts frameComplete at "true" in Observer
            System.out.println("update" + clockFrame);
    }

    public void run() {
        while(!quit) {
            int timerFrame = observer.getRefreshFrame();
            if(!paused && (clockFrame < timerFrame || (clockFrame == 30 && timerFrame == 1))) {
                updateAll();
                //System.out.println("update");
            }
        }
    }

    private void setupTimer() {
        int fps = Config.getFps();
        int delay = Math.round(1000/fps); 
        observer.setFps(fps);
        this.timer = new Timer(delay, observer);
        timer.start();
    }   
    private void readInputs() {

    }

    private void updateGameEngine() {
    }

    private void updateCanvas2D() {
    }

    private void updateCanvas3D() {
    }
}

更新:

一些奇怪的发现:

如果我将2 sysout放入我的while循环的“ if”语句中,则它们从不打印。这没有打印输出:

public void run() {
    while(!quit) {
        int clockFrame = observer.getRefreshFrame();
        //System.out.println("clock" + clockFrame);
        //System.out.println("frame" + refreshFrame);
        if(!paused && (refreshFrame < clockFrame || (refreshFrame == 30 && clockFrame == 1))) {
            System.out.println("clock" + clockFrame);
            System.out.println("frame" + refreshFrame);
            updateAll();
            //System.out.println("update");
        }
    }
}

如果我将先前的sysout放在注释中,并从这样的“ if”语句之外的2中删除//,则://]

public void run() {
    while(!quit) {
        int clockFrame = observer.getRefreshFrame();
        System.out.println("clock" + clockFrame);
        System.out.println("frame" + refreshFrame);
        if(!paused && (refreshFrame < clockFrame || (refreshFrame == 30 && clockFrame == 1))) {
            //System.out.println("clock" + clockFrame);
            //System.out.println("frame" + refreshFrame);
            updateAll();
            //System.out.println("update");
        }
    }
}

我看到refreshFrame总是与clockFrame一起递增。这是没有道理的。如果从不调用updateAll,则refreshframe的喊叫不会增加。

更新2-一些说明:

  • 摆动计时器需要一个侦听器,并在它打勾时会生成actionPerformed()事件。那就是为什么我需要一个观察员。
  • 我无法使计时器直接调用“ updateAll()”,因为计时器位于其自己的线程上。如果我这样做,则计时器可能会调用“ updateAll()”,而之前的更新尚未完全完成。
  • “它应该”工作的方式:一会儿循环不断,什么也不做,直到看到计时器已计时(clockFrame低于timerFrame)。然后更新。除非最后一个updateAll()完全完成(在updateAll的末尾,frameComplete设置为true),否则不能递增timerFrame。更新完成后,下一个计时器刻度将递增timerFrame,从而生成新的更新。
  • 理论上并逐步进行调试,但不能在运行时使用。

我已经尝试了一个小时,而现在却迷失了方向。我想以30 fps的速度运行游戏。摆动定时器延迟设置为1000/30。即使我将其减慢到1000或2000,它也不会改变...

java swing timer frame-rate
1个回答
1
投票

以下是一个文件mre(将整个代码复制粘贴到GameClock.java中,演示了使用挥杆Timer以30fps更新挥杆View

© www.soinside.com 2019 - 2024. All rights reserved.