172 lines
4.3 KiB
C++
172 lines
4.3 KiB
C++
/**
|
|
* Copyright (c) 2022 Dominic Masters
|
|
*
|
|
* This software is released under the MIT License.
|
|
* https://opensource.org/licenses/MIT
|
|
*/
|
|
|
|
#include "DawnSDL2Host.hpp"
|
|
#include "game/DawnGame.hpp"
|
|
#include "dawnopengl.hpp"
|
|
#include "display/BackBufferRenderTarget.hpp"
|
|
|
|
using namespace Dawn;
|
|
|
|
// Static declaration of the host, needed due to GLFW events being C-like
|
|
DawnHost *DAWN_HOST = nullptr;
|
|
|
|
// Host
|
|
DawnHost::DawnHost() {
|
|
this->data = new DawnHostData();
|
|
this->data->window = nullptr;
|
|
}
|
|
|
|
int32_t DawnHost::init(DawnGame *game) {
|
|
// Update values
|
|
this->game = game;
|
|
DAWN_HOST = this;
|
|
|
|
// Init SDL
|
|
if(SDL_Init(SDL_INIT_VIDEO) < 0) {
|
|
return DAWN_SDL2_INIT_RESULT_INIT_FAILED;
|
|
}
|
|
|
|
// Request OpenGL 4.5
|
|
SDL_GL_LoadLibrary(NULL);
|
|
SDL_GL_SetAttribute(SDL_GL_ACCELERATED_VISUAL, 1);
|
|
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 4);
|
|
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 5);
|
|
|
|
SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);
|
|
SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 24);
|
|
|
|
// Create Window
|
|
game->host->data->window = SDL_CreateWindow(
|
|
"Dawn",
|
|
SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED,
|
|
DAWN_SDL2_WINDOW_WIDTH_DEFAULT, DAWN_SDL2_WINDOW_HEIGHT_DEFAULT,
|
|
SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE
|
|
);
|
|
if(game->host->data->window == NULL) {
|
|
return DAWN_SDL2_INIT_RESULT_WINDOW_CREATE_FAILED;
|
|
}
|
|
|
|
// Create OpenGL Context and attach GLAD
|
|
game->host->data->glContext = SDL_GL_CreateContext(game->host->data->window);
|
|
gladLoadGLLoader(SDL_GL_GetProcAddress);
|
|
|
|
// Override engine defaults appropriately.
|
|
game->renderManager.backBuffer.setSize(
|
|
DAWN_SDL2_WINDOW_WIDTH_DEFAULT,
|
|
DAWN_SDL2_WINDOW_HEIGHT_DEFAULT
|
|
);
|
|
|
|
// Default keybinds
|
|
game->inputManager.bind(INPUT_BIND_ACCEPT, SDLK_RETURN);
|
|
game->inputManager.bind(INPUT_BIND_ACCEPT, SDLK_e);
|
|
game->inputManager.bind(INPUT_BIND_ACCEPT, SDLK_SPACE);
|
|
|
|
// Initialize the game
|
|
auto result = game->init();
|
|
if(result != DAWN_GAME_INIT_RESULT_SUCCESS) return result;
|
|
|
|
// Hard-Load the first scene assets.
|
|
if(game->scene != nullptr) {
|
|
auto assets = game->scene->getRequiredAssets();
|
|
game->assetManager.queueLoad(assets);
|
|
game->assetManager.syncLoad();
|
|
game->scene->stage();
|
|
}
|
|
|
|
// Use v-sync
|
|
SDL_GL_SetSwapInterval(1);
|
|
|
|
return DAWN_HOST_INIT_RESULT_SUCCESS;
|
|
}
|
|
|
|
int32_t DawnHost::start(DawnGame *game) {
|
|
uint32_t ticks;
|
|
int32_t updateResult;
|
|
SDL_Event event;
|
|
game->host->data->running = true;
|
|
|
|
// Main Render Loop
|
|
ticks = SDL_GetTicks();
|
|
while(game->host->data->running) {
|
|
// Ticks
|
|
uint32_t newTicks = SDL_GetTicks();
|
|
float_t delta = (newTicks - ticks) / 1000.0f;
|
|
ticks = newTicks;
|
|
|
|
// Perform update
|
|
updateResult = this->update(game, delta);
|
|
|
|
// Did the update complete successfully?
|
|
if(updateResult == DAWN_HOST_UPDATE_RESULT_EXIT) {
|
|
break;
|
|
} else if(updateResult != DAWN_HOST_UPDATE_RESULT_SUCCESS) {
|
|
return DAWN_SDL2_START_RESULT_UPDATE_FAILED;
|
|
}
|
|
|
|
// Swap buffers
|
|
SDL_GL_SwapWindow(game->host->data->window);
|
|
|
|
// Check events.
|
|
while (SDL_PollEvent(&event)) {
|
|
switch( event.type ){
|
|
case SDL_KEYDOWN:
|
|
game->inputManager.rawInputValues[event.key.keysym.sym] = 1.0f;
|
|
break;
|
|
|
|
case SDL_KEYUP:
|
|
game->inputManager.rawInputValues[event.key.keysym.sym] = 0.0f;
|
|
break;
|
|
|
|
case SDL_QUIT:
|
|
game->host->data->running = false;
|
|
break;
|
|
|
|
case SDL_WINDOWEVENT:
|
|
if(event.window.event == SDL_WINDOWEVENT_RESIZED) {
|
|
this->game->renderManager.backBuffer.setSize(
|
|
(float_t)event.window.data1, (float_t)event.window.data2
|
|
);
|
|
}
|
|
break;
|
|
|
|
default:
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
return DAWN_HOST_START_RESULT_EXIT_SUCCESS;
|
|
}
|
|
|
|
|
|
int32_t DawnHost::update(DawnGame *game, float_t delta) {
|
|
// Tick game.
|
|
auto ret = game->update(delta);
|
|
switch(ret) {
|
|
case DAWN_GAME_UPDATE_RESULT_SUCCESS:
|
|
return DAWN_HOST_UPDATE_RESULT_SUCCESS;
|
|
|
|
case DAWN_GAME_UPDATE_RESULT_EXIT:
|
|
return DAWN_HOST_UPDATE_RESULT_EXIT;
|
|
|
|
default:
|
|
return ret;
|
|
}
|
|
}
|
|
|
|
void DawnHost::unload(DawnGame *game) {
|
|
SDL_GL_DeleteContext(game->host->data->glContext);
|
|
SDL_DestroyWindow( game->host->data->window );
|
|
this->data->window = nullptr;
|
|
SDL_Quit();
|
|
}
|
|
|
|
DawnHost::~DawnHost() {
|
|
delete this->data;
|
|
DAWN_HOST = nullptr;
|
|
} |