我现在有点困惑,我甚至不知道这个问题是否符合这个问题,但我也不知道其他任何问题。
我开始编写一个带有灯光和东西的小型2D游戏引擎,我在测试期间偶然发现了这个问题。我实现了一个Timer来重新绘制每16毫秒重绘一次,以获得60 fps的帧速率。 它完美运行,直到我重新启动程序并意识到帧速率已降至约32 fps。 我找不到任何解释,因为我知道我没有太大变化。在一天结束时,我只是更改了一些值,使程序再次看起来很好。一段时间后我再次重新启动,只是意识到,帧速率再次增加到60.
这一次,我真的想到了我所做的一切。我知道我最后一次听音乐,而我之前没有听过。
我做的是,我在程序运行时关闭了iTunes并且帧率再次下降。我启动了iTunes并且帧率增加了。我做了几次这样做,甚至重新启动计算机并发生了同样的效果。 我还尝试了在运行另一个程序(这次是Star Citizen Launcher)时会发生什么,并且发生了同样的事情。另一方面,Firefox和GIMP似乎没有任何影响。
所以,这就是故事。现在的问题是,有没有人听说过这个。为什么会发生这种情况,这可能只是我实施中的一个错误?为了保证它与我的引擎没有任何关系,我在这里写了一个简单的小应用程序,我可以看到完全相同的效果。在小应用程序中,我还打印出自上次重绘后已过期的毫秒数,当没有iTunes或Star Citizen Launcher运行时,此值确实增加,而当其他正在运行时,它保持给定值。
所以我希望你们中的任何人都可以帮助我,因为我根本没有任何想法。我希望这个问题能够得到解答,因为我不知道这个答案会是什么样子......谢谢!
import java.awt.Color;
import java.awt.Graphics;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.Timer;
@SuppressWarnings("serial")
public class TimerTest extends JPanel implements ActionListener {
private final Timer timer;
private long lastFrame;
private long fps;
private long lastMilis;
public static void main(String[] args) {
JFrame frame = new JFrame();
frame.setSize(200, 100);
frame.setLocationRelativeTo(null);
frame.setResizable(false);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new TimerTest());
frame.setVisible(true);
}
public TimerTest() {
this.timer = new Timer(16, this);
this.timer.start();
// exclude the following for simple Timer run (I get ~32 fps) include for some stress-testing (I get between 55 and 200 fps)
// Thread thread = new Thread(new TestThread());
// thread.start();
}
@Override
public void actionPerformed(ActionEvent e) {
System.out.println(System.currentTimeMillis() - this.lastMilis);
if (e.getSource() == this.timer) {
this.fps = 1000000000 / (System.nanoTime() - this.lastFrame);
this.repaint();
this.lastFrame = System.nanoTime();
}
this.lastMilis = System.currentTimeMillis();
}
@Override
public void paint(Graphics g) {
g.setColor(Color.WHITE);
g.fillRect(0, 0, 200, 100);
g.setColor(Color.RED);
g.drawString("FPS: " + this.fps, 80, 40);
g.dispose();
}
}
class TestThread implements Runnable {
@Override
public void run() {
while (true)
System.out.println("TEST THREAD: " + System.nanoTime());
}
}