123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138 |
- #include <time.h>
- #include <unistd.h>
- #include <stdio.h>
- #include <vector>
- #include <memory>
- #include <chrono>
- #include <ratio>
-
- #include <SDL2/SDL.h>
- #include <SDL2/SDL_image.h>
-
- #include <swan/common.h>
- #include <swan/World.h>
- #include <swan/Game.h>
- #include <swan/Timer.h>
- #include <swan/Win.h>
-
- using namespace Swan;
-
- #define errassert(expr, str, errfn) do { \
- if (!(expr)) { \
- fprintf(stderr, "%s: %s\n", str, errfn()); \
- return EXIT_FAILURE; \
- } \
- } while (0)
-
- #define sdlassert(expr, str) errassert(expr, str, SDL_GetError);
- #define imgassert(expr, str) errassert(expr, str, IMG_GetError);
-
- template<typename T>
- using DeleteFunc = void (*)(T *);
-
- int main() {
- sdlassert(SDL_Init(SDL_INIT_VIDEO) >= 0, "Could not initialize SDL");
- std::unique_ptr<void, DeleteFunc<void>> sdl(nullptr, [](void *){ SDL_Quit(); });
-
- int imgflags = IMG_INIT_PNG;
- imgassert(IMG_Init(imgflags) == imgflags, "Could not initialize SDL_Image");
- std::unique_ptr<void, DeleteFunc<void>> sdl_image(nullptr, [](void *){ IMG_Quit(); });
-
- std::unique_ptr<SDL_Window, DeleteFunc<SDL_Window>> window(
- SDL_CreateWindow(
- "Project: SWAN",
- SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED,
- 640, 480,
- SDL_WINDOW_SHOWN | SDL_WINDOW_RESIZABLE),
- SDL_DestroyWindow);
-
- std::unique_ptr<SDL_Renderer, DeleteFunc<SDL_Renderer>> renderer(
- SDL_CreateRenderer(
- window.get(), -1, SDL_RENDERER_ACCELERATED),
- SDL_DestroyRenderer);
- sdlassert(renderer, "Could not create renderer\n");
-
- Win win(renderer.get());
-
- Game game(win);
- std::vector<std::unique_ptr<Mod>> mods;
- mods.push_back(game.loadMod("core.mod"));
- game.createWorld("core::default", std::move(mods));
-
- auto prevTime = std::chrono::steady_clock::now();
-
- float fpsAcc = 0;
- float tickAcc = 0;
- int fcount = 0;
- int slowFrames = 0;
- while (1) {
- SDL_Event evt;
- while (SDL_PollEvent(&evt)) {
- switch (evt.type) {
- case SDL_QUIT:
- goto exit;
- break;
-
- case SDL_KEYDOWN:
- game.onKeyDown(evt.key.keysym);
- break;
-
- case SDL_KEYUP:
- game.onKeyUp(evt.key.keysym);
- break;
-
- case SDL_MOUSEMOTION:
- game.onMouseMove(evt.motion.x, evt.motion.y);
- break;
-
- case SDL_MOUSEBUTTONDOWN:
- game.onMouseDown(evt.button.x, evt.button.y, evt.button.button);
- break;
-
- case SDL_MOUSEBUTTONUP:
- game.onMouseUp(evt.button.x, evt.button.y, evt.button.button);
- break;
- }
- }
-
- auto now = std::chrono::steady_clock::now();
- std::chrono::duration<float> dur(prevTime - now);
- prevTime = now;
- float dt = dur.count();
-
- // Display FPS
- fpsAcc += dt;
- fcount += 1;
- if (fpsAcc >= 4) {
- fprintf(stderr, "FPS: %.3f\n", fcount / 4.0);
- fpsAcc -= 4;
- fcount = 0;
- }
-
- game.update(dt);
-
- if (dt > 0.1) {
- if (slowFrames == 0)
- fprintf(stderr, "Warning: delta time is too high! (%.3fs).\n", dt);
- slowFrames += 1;
- } else {
- if (slowFrames > 0) {
- if (slowFrames > 1)
- fprintf(stderr, "%i consecutive slow frames.\n", slowFrames);
- slowFrames = 0;
- }
-
- tickAcc += dt;
- while (tickAcc >= 1.0 / TICK_RATE) {
- tickAcc -= 1.0 / TICK_RATE;
- game.tick(1.0 / TICK_RATE);
- }
- }
-
- game.draw();
- SDL_UpdateWindowSurface(window.get());
- }
-
- exit:
- return EXIT_SUCCESS;
- }
|