Move game loop into engine lib

This commit is contained in:
Bailey Harrison 2022-10-04 11:54:23 +01:00
parent d7a79abb1c
commit 45a4db4dcf
7 changed files with 101 additions and 27 deletions

View File

@ -38,6 +38,8 @@ add_library(${PROJECT_NAME} STATIC
"include/engine.hpp" "include/engine.hpp"
"include/util.hpp"
"include/log.hpp" "include/log.hpp"
"include/window.hpp" "include/window.hpp"
@ -67,7 +69,6 @@ add_library(${PROJECT_NAME} STATIC
"include/gfx.hpp" "include/gfx.hpp"
"include/gfx_device.hpp" "include/gfx_device.hpp"
) )
# compiling options: # compiling options:

View File

@ -1,13 +1,27 @@
#pragma once #pragma once
#include <memory>
namespace engine { namespace engine {
struct AppInfo { class Window;
const char* name; class GFXDevice;
const char* version;
class Application {
public:
Application(const char* appName, const char* appVersion);
Application(const Application&) = delete;
Application& operator=(const Application&) = delete;
~Application();
void gameLoop();
private:
std::unique_ptr<Window> m_win;
std::unique_ptr<GFXDevice> m_gfx;
}; };
bool versionFromCharArray(const char* version, int* major, int* minor, int* patch);
} }

View File

@ -1,5 +1,6 @@
#pragma once #pragma once
/*
#ifndef ENGINE_API #ifndef ENGINE_API
# ifdef _MSC_VER # ifdef _MSC_VER
# ifdef ENGINE_EXPORTS # ifdef ENGINE_EXPORTS
@ -11,5 +12,6 @@
# define ENGINE_API # define ENGINE_API
# endif # endif
#endif #endif
*/
#define ENGINE_API #define ENGINE_API

View File

@ -2,8 +2,6 @@
#include "engine_api.h" #include "engine_api.h"
#include "engine.hpp"
#include <memory> #include <memory>
struct SDL_Window; struct SDL_Window;
@ -13,7 +11,7 @@ namespace engine {
class ENGINE_API GFXDevice { class ENGINE_API GFXDevice {
public: public:
GFXDevice(AppInfo appInfo, SDL_Window* window); GFXDevice(const char* appName, const char* appVersion, SDL_Window* window);
GFXDevice(const GFXDevice&) = delete; GFXDevice(const GFXDevice&) = delete;
GFXDevice& operator=(const GFXDevice&) = delete; GFXDevice& operator=(const GFXDevice&) = delete;

18
include/util.hpp Normal file
View File

@ -0,0 +1,18 @@
#pragma once
#include <cstdio>
namespace engine {
inline bool versionFromCharArray(const char* version, int* major, int* minor, int* patch)
{
if (sscanf(version, "%d.%d.%d", major, minor, patch) != 3) {
*major = 0;
*minor = 0;
*patch = 0;
return false;
}
return true;
}
}

View File

@ -1,18 +1,57 @@
#include "engine.hpp" #include "engine.hpp"
#include <cstdio> #include "window.hpp"
#include "gfx_device.hpp"
namespace engine { namespace engine {
bool versionFromCharArray(const char* version, int* major, int* minor, int* patch) Application::Application(const char* appName, const char* appVersion)
{ {
if (sscanf(version, "%d.%d.%d", major, minor, patch) != 3) { m_win = std::make_unique<Window>(appName);
*major = 0; m_gfx = std::make_unique<GFXDevice>(appName, appVersion, m_win->m_handle);
*minor = 0; }
*patch = 0;
return false; Application::~Application()
{
}
void Application::gameLoop()
{
uint64_t lastTick = m_win->getNanos();
constexpr int TICKFREQ = 20; // in hz
// single-threaded game loop
while (m_win->isRunning()) {
/* logic */
if (m_win->getLastFrameStamp() >= lastTick + (BILLION / TICKFREQ)) {
lastTick = m_win->getLastFrameStamp();
// do tick stuff here
}
if (m_win->getKeyPress(inputs::Key::F11)) {
if (m_win->isFullscreen()) {
m_win->setFullscreen(false);
}
else {
m_win->setFullscreen(true, false); // borderless window
}
}
if (m_win->getKeyPress(inputs::Key::ESCAPE)) {
m_win->setCloseFlag();
}
/* draw */
m_gfx->draw();
/* poll events */
m_win->getInputAndEvents();
} }
return true;
} }
} }

View File

@ -4,6 +4,8 @@
#include "gfx_device.hpp" #include "gfx_device.hpp"
#include "util.hpp"
#include "config.h" #include "config.h"
#include "log.hpp" #include "log.hpp"
@ -49,7 +51,7 @@ namespace engine {
class GFXDevice::Impl { class GFXDevice::Impl {
public: public:
Impl(AppInfo appInfo, SDL_Window* window) Impl(const char* appName, const char* appVersion, SDL_Window* window)
{ {
#ifdef NDEBUG #ifdef NDEBUG
// release mode: don't use validation layer // release mode: don't use validation layer
@ -58,7 +60,7 @@ namespace engine {
// debug mode: use validation layer // debug mode: use validation layer
LayerInfo layerInfo(true); LayerInfo layerInfo(true);
#endif #endif
auto instance = std::make_shared<Instance>(appInfo, layerInfo, getRequiredVulkanExtensions(window)); auto instance = std::make_shared<Instance>(appName, appVersion, layerInfo, getRequiredVulkanExtensions(window));
volkLoadInstanceOnly(instance->getHandle()); volkLoadInstanceOnly(instance->getHandle());
@ -110,19 +112,19 @@ namespace engine {
class Instance { class Instance {
public: public:
Instance(AppInfo appInfo, const LayerInfo& layerInfo, const std::vector<const char*>& windowExtensions) Instance(const char* appName, const char* appVersion, const LayerInfo& layerInfo, const std::vector<const char*>& windowExtensions)
{ {
VkResult res; VkResult res;
int appVersionMajor = 0, appVersionMinor = 0, appVersionPatch = 0; int appVersionMajor = 0, appVersionMinor = 0, appVersionPatch = 0;
assert(versionFromCharArray(appInfo.version, &appVersionMajor, &appVersionMinor, &appVersionPatch)); assert(versionFromCharArray(appVersion, &appVersionMajor, &appVersionMinor, &appVersionPatch));
int engineVersionMajor = 0, engineVersionMinor = 0, engineVersionPatch = 0; int engineVersionMajor = 0, engineVersionMinor = 0, engineVersionPatch = 0;
assert(versionFromCharArray(ENGINE_VERSION, &engineVersionMajor, &engineVersionMinor, &engineVersionPatch)); assert(versionFromCharArray(ENGINE_VERSION, &engineVersionMajor, &engineVersionMinor, &engineVersionPatch));
VkApplicationInfo applicationInfo{ VkApplicationInfo applicationInfo{
.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO, .sType = VK_STRUCTURE_TYPE_APPLICATION_INFO,
.pNext = nullptr, .pNext = nullptr,
.pApplicationName = appInfo.name, .pApplicationName = appName,
.applicationVersion = VK_MAKE_VERSION(appVersionMajor, appVersionMinor, appVersionPatch), .applicationVersion = VK_MAKE_VERSION(appVersionMajor, appVersionMinor, appVersionPatch),
.pEngineName = "engine", .pEngineName = "engine",
.engineVersion = VK_MAKE_VERSION(engineVersionMajor, engineVersionMinor, engineVersionPatch), .engineVersion = VK_MAKE_VERSION(engineVersionMajor, engineVersionMinor, engineVersionPatch),
@ -797,7 +799,7 @@ namespace engine {
}; };
GFXDevice::GFXDevice(AppInfo appInfo, SDL_Window* window) GFXDevice::GFXDevice(const char* appName, const char* appVersion, SDL_Window* window)
{ {
VkResult res; VkResult res;
res = volkInitialize(); res = volkInitialize();
@ -811,7 +813,7 @@ namespace engine {
throw std::runtime_error("The loaded Vulkan version must be at least 1.3"); throw std::runtime_error("The loaded Vulkan version must be at least 1.3");
} }
m_pimpl = std::make_unique<Impl>(appInfo, window); m_pimpl = std::make_unique<Impl>(appName, appVersion, window);
} }