|
|
@@ -10,7 +10,6 @@ |
|
|
|
#include <string.h> |
|
|
|
|
|
|
|
#include <swan/swan.h> |
|
|
|
#include <swan/util.h> |
|
|
|
|
|
|
|
using namespace Swan; |
|
|
|
|
|
|
@@ -81,13 +80,18 @@ int main(int argc, char **argv) { |
|
|
|
mods.push_back(game.loadMod("core.mod")); |
|
|
|
game.createWorld("core::default", std::move(mods)); |
|
|
|
|
|
|
|
auto prevTime = std::chrono::steady_clock::now(); |
|
|
|
PerfCounter pcounter; |
|
|
|
|
|
|
|
auto prev_time = std::chrono::steady_clock::now(); |
|
|
|
|
|
|
|
float fps_acc = 0; |
|
|
|
float tick_acc = 0; |
|
|
|
|
|
|
|
float fpsAcc = 0; |
|
|
|
float tickAcc = 0; |
|
|
|
int fcount = 0; |
|
|
|
int slowFrames = 0; |
|
|
|
int slow_frames = 0; |
|
|
|
while (1) { |
|
|
|
RTClock total_frame_clock; |
|
|
|
|
|
|
|
SDL_Event evt; |
|
|
|
while (SDL_PollEvent(&evt)) { |
|
|
|
switch (evt.type) { |
|
|
@@ -118,44 +122,72 @@ int main(int argc, char **argv) { |
|
|
|
} |
|
|
|
|
|
|
|
auto now = std::chrono::steady_clock::now(); |
|
|
|
std::chrono::duration<float> dur(now - prevTime); |
|
|
|
prevTime = now; |
|
|
|
std::chrono::duration<float> dur(now - prev_time); |
|
|
|
prev_time = now; |
|
|
|
float dt = dur.count(); |
|
|
|
|
|
|
|
// Display FPS |
|
|
|
fpsAcc += dt; |
|
|
|
fps_acc += dt; |
|
|
|
fcount += 1; |
|
|
|
if (fpsAcc >= 4) { |
|
|
|
if (fps_acc >= 4) { |
|
|
|
info << "FPS: " << fcount / 4.0; |
|
|
|
fpsAcc -= 4; |
|
|
|
fps_acc -= 4; |
|
|
|
fcount = 0; |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
// We want to warn if one frame takes over 0.1 seconds... |
|
|
|
if (dt > 0.1) { |
|
|
|
if (slowFrames == 0) |
|
|
|
if (slow_frames == 0) |
|
|
|
warn << "Delta time too high! (" << dt << "s)"; |
|
|
|
slowFrames += 1; |
|
|
|
dt = 0.1; |
|
|
|
slow_frames += 1; |
|
|
|
|
|
|
|
// And we never want to do physics as if our one frame is greater than |
|
|
|
// 0.5 seconds. |
|
|
|
if (dt > 0.5) |
|
|
|
dt = 0.5; |
|
|
|
} else if (slow_frames > 0) { |
|
|
|
if (slow_frames > 1) |
|
|
|
warn << slow_frames << " consecutive slow frames."; |
|
|
|
slow_frames = 0; |
|
|
|
} |
|
|
|
|
|
|
|
game.update(dt); |
|
|
|
// Simple case: we can keep up, only need one physics update |
|
|
|
RTClock update_clock; |
|
|
|
if (dt <= 1 / 25.0) { |
|
|
|
pcounter.countGameUpdatesPerFrame(1); |
|
|
|
game.update(dt); |
|
|
|
|
|
|
|
if (slowFrames > 0) { |
|
|
|
if (slowFrames > 1) |
|
|
|
warn << slowFrames << " consecutive slow frames."; |
|
|
|
slowFrames = 0; |
|
|
|
// Complex case: run multiple steps this iteration |
|
|
|
} else { |
|
|
|
int count = (int)ceilf(dt / (1/30.0)); |
|
|
|
pcounter.countGameUpdatesPerFrame(count); |
|
|
|
float delta = dt / count; |
|
|
|
info << "Delta time " << dt << "s. Running " << count << " updates in one frame, with a delta as if we had " << 1.0 / delta << " FPS."; |
|
|
|
for (int i = 0; i < count; ++i) |
|
|
|
game.update(delta); |
|
|
|
} |
|
|
|
pcounter.countGameUpdate(update_clock.duration()); |
|
|
|
|
|
|
|
tickAcc += dt; |
|
|
|
while (tickAcc >= 1.0 / TICK_RATE) { |
|
|
|
tickAcc -= 1.0 / TICK_RATE; |
|
|
|
// Tick at a consistent TICK_RATE |
|
|
|
tick_acc += dt; |
|
|
|
while (tick_acc >= 1.0 / TICK_RATE) { |
|
|
|
tick_acc -= 1.0 / TICK_RATE; |
|
|
|
RTClock tick_clock; |
|
|
|
game.tick(1.0 / TICK_RATE); |
|
|
|
pcounter.countGameTick(tick_clock.duration()); |
|
|
|
} |
|
|
|
|
|
|
|
SDL_RenderClear(renderer.get()); |
|
|
|
|
|
|
|
RTClock draw_clock; |
|
|
|
game.draw(); |
|
|
|
pcounter.countGameDraw(draw_clock.duration()); |
|
|
|
|
|
|
|
pcounter.countFrameTime(total_frame_clock.duration()); |
|
|
|
|
|
|
|
RTClock present_clock; |
|
|
|
SDL_RenderPresent(renderer.get()); |
|
|
|
pcounter.countRenderPresent(present_clock.duration()); |
|
|
|
} |
|
|
|
|
|
|
|
exit: |