Files
IAEngine/Src/IAEngine/imp/cpp/IAEngine.cpp
Isuru Samarathunga 50f3f14c47 Texture Rendering
2025-09-13 14:12:08 +05:30

161 lines
3.9 KiB
C++

// IAEngine: 2D Game Engine by IA
// Copyright (C) 2025 IAS (ias@iasoft.dev)
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
#include <IAEngine/Audio.hpp>
#include <IAEngine/IAEngine.hpp>
#include <IAEngine/Input.hpp>
#include <IAEngine/Physics/Physics.hpp>
#include <IAEngine/Random.hpp>
#include <IAEngine/Time.hpp>
#include <SDL3/SDL.h>
#include <imgui.h>
#include <backends/imgui_impl_sdl3.h>
namespace ia::iae
{
struct EngineContext
{
SDL_Window *Window{};
SDL_Event Event{};
BOOL ShouldClose{false};
};
} // namespace ia::iae
namespace ia::iae
{
CONSTEXPR FLOAT32 GAME_UPDATE_INTERVAL = 1000.0f / 60.0f;
Engine::Engine() : m_context(MakeRefPtr<EngineContext>())
{
}
Engine::~Engine()
{
}
BOOL Engine::Initialize(IN CONST InitConfig &config)
{
IAE_LOG_INFO("Booting IAEngine for \"", config.GameName, "\"");
if (!SDL_Init(SDL_INIT_VIDEO | SDL_INIT_AUDIO | SDL_INIT_GAMEPAD))
{
IAE_LOG_ERROR("Couldn't intialize SDL3: ", SDL_GetError());
return false;
}
if (!(m_context->Window = SDL_CreateWindow(config.GameName.c_str(), config.WindowWidth, config.WindowHeight, SDL_WINDOW_RESIZABLE)))
{
IAE_LOG_ERROR("Couldn't create SDL3 window: ", SDL_GetError());
return false;
}
SDL_SetWindowResizable(m_context->Window, false);
Time::Initialize();
if (!Renderer::Initialize(this))
return false;
Random::Initialize();
Input::Initialize();
Audio::Initialize();
Physics::Initialize();
return true;
}
VOID Engine::Terminate()
{
IAE_LOG_INFO("Shutting down IAEngine");
m_resourceManager.reset();
Physics::Terminate();
Audio::Terminate();
Renderer::Terminate();
SDL_DestroyWindow(m_context->Window);
SDL_Quit();
}
VOID Engine::BeginFrame()
{
SDL_PollEvent(&m_context->Event);
if (m_context->Event.type == SDL_EVENT_QUIT)
m_context->ShouldClose = true;
ProcessEvents();
m_updateTimer += Time::GetFrameDeltaTime();
if (m_updateTimer >= GAME_UPDATE_INTERVAL)
{
UpdateGame();
while (m_updateTimer >= GAME_UPDATE_INTERVAL)
m_updateTimer -= GAME_UPDATE_INTERVAL;
}
Renderer::BeginFrame();
RenderGame();
}
VOID Engine::EndFrame()
{
Renderer::EndFrame();
Time::NextFrame();
}
BOOL Engine::ShouldClose()
{
return m_context->ShouldClose;
}
VOID Engine::ProcessEvents()
{
ImGui_ImplSDL3_ProcessEvent(&m_context->Event);
Input::OnEvent(&m_context->Event);
}
VOID Engine::UpdateGame()
{
Physics::Update();
if B_LIKELY (m_activeScene)
m_activeScene->Update();
}
VOID Engine::RenderGame()
{
if B_LIKELY (m_activeScene)
m_activeScene->Draw();
}
VOID Engine::ChangeScene(IN RefPtr<Scene> scene)
{
m_activeScene = scene;
}
RefPtr<Scene> Engine::CreateScene()
{
return MakeRefPtr<Scene>(this);
}
PVOID Engine::GetWindowHandle() CONST
{
return m_context->Window;
}
} // namespace ia::iae