diff --git a/CMakeLists.txt b/CMakeLists.txt index 590f039..6ebb9f2 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -138,6 +138,15 @@ add_library(Engine STATIC engine/src/loader/assets/AssetManager.h engine/src/renderer/entities/PointLight.cpp engine/src/renderer/entities/PointLight.h + engine/src/core/inputsOutputs/inputs/MouseButton.h + engine/src/core/inputsOutputs/inputs/Mouse.cpp + engine/src/core/inputsOutputs/inputs/Mouse.h + engine/src/core/inputsOutputs/inputs/Keyboard.cpp + engine/src/core/inputsOutputs/inputs/Keyboard.h + engine/src/core/inputsOutputs/context/InputContextStack.cpp + engine/src/core/inputsOutputs/context/InputContextStack.h + engine/src/core/inputsOutputs/controller/CameraController.cpp + engine/src/core/inputsOutputs/controller/CameraController.h ) target_include_directories(Engine PUBLIC engine/src) target_link_libraries(Engine PUBLIC OpenGL::GL glfw glad glm::glm imgui spdlog::spdlog tinyobjloader stb_image) @@ -181,6 +190,8 @@ add_executable(ColorRace engine/src/layer/SceneManager.h game/src/GameScene.cpp game/src/GameScene.h + engine/src/core/inputsOutputs/context/InputContext.cpp + engine/src/core/inputsOutputs/context/InputContext.h ) diff --git a/engine/src/core/Application.cpp b/engine/src/core/Application.cpp index 7f205d4..34ed369 100644 --- a/engine/src/core/Application.cpp +++ b/engine/src/core/Application.cpp @@ -9,9 +9,13 @@ #include "utils/openglWrapper/GLStateCache.h" namespace engine { - Application::Application(const EngineConfig& config) : m_config(config) { - m_window = std::make_unique(config); - } + Application::Application(const EngineConfig& config) + : m_config(config), + m_window(std::make_unique(config)), + m_inputContextStack(), + m_keyboard(*m_window), + m_mouse(*m_window), + m_sceneManager(m_inputContextStack) {} Application::~Application() = default; diff --git a/engine/src/core/Application.h b/engine/src/core/Application.h index 2a26d65..bbd9434 100644 --- a/engine/src/core/Application.h +++ b/engine/src/core/Application.h @@ -9,7 +9,10 @@ #include "EngineConfig.h" #include "Window.h" - +#include "inputsOutputs/context/InputContextStack.h" +#include "inputsOutputs/inputs/Keyboard.h" +#include "inputsOutputs/inputs/Mouse.h" +#include "layer/SceneManager.h" namespace engine { @@ -23,10 +26,19 @@ namespace engine { protected: virtual void onUpdate(float deltaTime) {} virtual void onRender() {} + InputContextStack& getInputContextStack() { return m_inputContextStack; } + SceneManager& getSceneManager() { return m_sceneManager; } + Keyboard& getKeyboard() { return m_keyboard; } + Mouse& getMouse() { return m_mouse; } private: EngineConfig m_config; std::unique_ptr m_window; + InputContextStack m_inputContextStack; + Keyboard m_keyboard{*m_window}; // braucht Window& im Konstruktor + Mouse m_mouse{*m_window}; + SceneManager m_sceneManager{m_inputContextStack}; + }; } diff --git a/engine/src/core/Window.cpp b/engine/src/core/Window.cpp index a02c0af..82e984f 100644 --- a/engine/src/core/Window.cpp +++ b/engine/src/core/Window.cpp @@ -61,6 +61,7 @@ namespace engine { glViewport(0, 0, config.windowWidth, config.windowHeight); + glfwSetWindowUserPointer(m_handle, &m_callbackTarget); } Window::~Window() { @@ -72,4 +73,15 @@ namespace engine { void Window::swapBuffers() { glfwSwapBuffers(m_handle); } void Window::pollEvents() { glfwPollEvents(); } + int Window::getWidth() const { + int width, height; + glfwGetFramebufferSize(m_handle, &width, &height); + return width; + } + + int Window::getHeight() const { + int width, height; + glfwGetFramebufferSize(m_handle, &width, &height); + return height; + } } diff --git a/engine/src/core/Window.h b/engine/src/core/Window.h index 1b79c76..71d32dd 100644 --- a/engine/src/core/Window.h +++ b/engine/src/core/Window.h @@ -10,11 +10,19 @@ #include "EngineConfig.h" + struct GLFWwindow; namespace engine { + class Keyboard; + class Mouse; + class Window { public: + struct CallbackTarget { + Mouse* mouse = nullptr; + Keyboard* keyboard = nullptr; + }; Window(const EngineConfig& config); ~Window(); @@ -22,11 +30,15 @@ namespace engine { void swapBuffers(); void pollEvents(); - GLFWwindow* getHandle() const { - return m_handle; - } + [[nodiscard]] GLFWwindow* getHandle() const { return m_handle; } + [[nodiscard]] int getWidth() const; + [[nodiscard]] int getHeight() const; + + void setMouse(Mouse* mouse) { m_callbackTarget.mouse = mouse; } + void setKeyboard(Keyboard* keyboard) { m_callbackTarget.keyboard = keyboard; } private: GLFWwindow* m_handle; + CallbackTarget m_callbackTarget; }; } diff --git a/engine/src/core/inputsOutputs/context/InputContext.cpp b/engine/src/core/inputsOutputs/context/InputContext.cpp new file mode 100644 index 0000000..4d6e197 --- /dev/null +++ b/engine/src/core/inputsOutputs/context/InputContext.cpp @@ -0,0 +1,5 @@ +// +// Created by sebastian on 02.08.26. +// + +#include "InputContext.h" diff --git a/engine/src/core/inputsOutputs/context/InputContext.h b/engine/src/core/inputsOutputs/context/InputContext.h new file mode 100644 index 0000000..5136ba5 --- /dev/null +++ b/engine/src/core/inputsOutputs/context/InputContext.h @@ -0,0 +1,19 @@ +// +// Created by sebastian on 02.08.26. +// + +#ifndef COLORRACE_INPUTCONTEXT_H +#define COLORRACE_INPUTCONTEXT_H + + +namespace engine { + class InputContext { + public: + virtual ~InputContext() = default; + virtual void onActivate() {}; + virtual void onDeactivate() {}; + }; + +} + +#endif //COLORRACE_INPUTCONTEXT_H diff --git a/engine/src/core/inputsOutputs/context/InputContextStack.cpp b/engine/src/core/inputsOutputs/context/InputContextStack.cpp new file mode 100644 index 0000000..51c7b82 --- /dev/null +++ b/engine/src/core/inputsOutputs/context/InputContextStack.cpp @@ -0,0 +1,24 @@ +// +// Created by sebastian on 02.08.26. +// + +#include "InputContextStack.h" + + +void engine::InputContextStack::push(std::shared_ptr context) { + if (!m_stack.empty()) m_stack.back()->onDeactivate(); + context->onActivate(); + m_stack.push_back(std::move(context)); +} + +void engine::InputContextStack::pop() { + if (m_stack.empty()) return; + m_stack.back()->onDeactivate(); + m_stack.pop_back(); + if (!m_stack.empty()) m_stack.back()->onActivate(); +} + + +bool engine::InputContextStack::isActive(const InputContext &context) const { + return !m_stack.empty() && m_stack.back().get() == &context; +} diff --git a/engine/src/core/inputsOutputs/context/InputContextStack.h b/engine/src/core/inputsOutputs/context/InputContextStack.h new file mode 100644 index 0000000..3e10bd3 --- /dev/null +++ b/engine/src/core/inputsOutputs/context/InputContextStack.h @@ -0,0 +1,25 @@ +// +// Created by sebastian on 02.08.26. +// + +#ifndef COLORRACE_INPUTCONTEXTSTACK_H +#define COLORRACE_INPUTCONTEXTSTACK_H +#include +#include + +#include "InputContext.h" + + +namespace engine { + class InputContextStack { + public: + void push(std::shared_ptr context); + void pop(); + [[nodiscard]] bool isActive(const InputContext& context) const; + private: + std::vector> m_stack; + }; +} + + +#endif //COLORRACE_INPUTCONTEXTSTACK_H diff --git a/engine/src/core/inputsOutputs/controller/CameraController.cpp b/engine/src/core/inputsOutputs/controller/CameraController.cpp new file mode 100644 index 0000000..481187c --- /dev/null +++ b/engine/src/core/inputsOutputs/controller/CameraController.cpp @@ -0,0 +1,18 @@ +// +// Created by sebastian on 02.08.26. +// + +#include "CameraController.h" + +#include "GLFW/glfw3.h" +#include "glm/vec3.hpp" +#include "renderer/entities/Camera.h" + +void engine::CameraController::update(const Keyboard &keyboard, Camera &camera, float deltaTime) { + if (!m_stack.isActive(*m_gameContext.get())) return; + + if (keyboard.isKeyDown(GLFW_KEY_W)) camera.moveRelative(glm::vec3(0.0f, 0.0f, 1.0f), 10.0f * deltaTime, deltaTime); + if (keyboard.isKeyDown(GLFW_KEY_S)) camera.moveRelative(glm::vec3(0.0f, 0.0f, -1.0f), 10.0f * deltaTime, deltaTime); + if (keyboard.isKeyDown(GLFW_KEY_A)) camera.moveRelative(glm::vec3(-1.0f, 0.0f, 0.0f), 10.0f * deltaTime, deltaTime); + if (keyboard.isKeyDown(GLFW_KEY_D)) camera.moveRelative(glm::vec3(1.0f, 0.0f, 0.0f), 10.0f * deltaTime, deltaTime); +} diff --git a/engine/src/core/inputsOutputs/controller/CameraController.h b/engine/src/core/inputsOutputs/controller/CameraController.h new file mode 100644 index 0000000..d6bf470 --- /dev/null +++ b/engine/src/core/inputsOutputs/controller/CameraController.h @@ -0,0 +1,25 @@ +// +// Created by sebastian on 02.08.26. +// + +#ifndef COLORRACE_CAMERACONTROLLER_H +#define COLORRACE_CAMERACONTROLLER_H +#include "core/inputsOutputs/context/InputContextStack.h" +#include "core/inputsOutputs/inputs/Keyboard.h" + + +namespace engine { + class Camera; + + class CameraController { + public: + CameraController(InputContextStack& stack, std::shared_ptr gameContext) : m_stack(stack), m_gameContext(std::move(gameContext)) {} + void update(const Keyboard& keyboard, Camera& camera, float deltaTime); + private: + InputContextStack& m_stack; + std::shared_ptr m_gameContext; + }; +} + + +#endif //COLORRACE_CAMERACONTROLLER_H diff --git a/engine/src/core/inputsOutputs/inputs/Keyboard.cpp b/engine/src/core/inputsOutputs/inputs/Keyboard.cpp new file mode 100644 index 0000000..e1fe426 --- /dev/null +++ b/engine/src/core/inputsOutputs/inputs/Keyboard.cpp @@ -0,0 +1,79 @@ +// +// Created by sebastian on 02.08.26. +// + +#include "Keyboard.h" + +#include "core/Window.h" +#include "GLFW/glfw3.h" + +engine::Keyboard::Keyboard(engine::Window &window) { + window.setKeyboard(this); + addKeyListener(window); + addTextListener(window); +} + +void engine::Keyboard::update() { + keysPressedThisFrame.clear(); + keysRepeatedThisFrame.clear(); + charsThisFrame.clear(); + keysReleasedThisFrame.clear(); +} + +bool engine::Keyboard::isKeyDown(const int key) const { + return keysDown.contains(key); +} + +const std::vector & engine::Keyboard::getCharsThisFrame() { + return charsThisFrame; +} + +auto engine::Keyboard::keyPressEvent(const int key) const -> bool { + return keysPressedThisFrame.contains(key); +} + +auto engine::Keyboard::keyPressEvent(const int key, bool checkRepeats) const -> bool { + return keysPressedThisFrame.contains(key) || (checkRepeats && keysRepeatedThisFrame.contains(key)); +} + +bool engine::Keyboard::keyReleaseEvent(const int key) const { + return keysReleasedThisFrame.contains(key); +} + +void engine::Keyboard::addTextListener(Window &window) { + glfwSetCharCallback(window.getHandle(), [](GLFWwindow* handle, unsigned int key) { + auto* target = static_cast(glfwGetWindowUserPointer(handle)); + if (!target || !target->keyboard) return; + + target->keyboard->reportChar(key); + }); +} + +void engine::Keyboard::addKeyListener(Window &window) { + glfwSetKeyCallback(window.getHandle(), [](GLFWwindow* handle, int key, int scancode, int action, int mods) { + auto* target = static_cast(glfwGetWindowUserPointer(handle)); + if (!target || !target->keyboard) return; + + if (action == GLFW_PRESS) target->keyboard->reportKeyPress(key); + else if (action == GLFW_RELEASE) target->keyboard->reportKeyRelease(key); + else if (action == GLFW_REPEAT) target->keyboard->reportKeyRepeat(key); + }); +} + +void engine::Keyboard::reportKeyPress(int key) { + keysDown.insert(key); + keysPressedThisFrame.insert(key); +} + +void engine::Keyboard::reportKeyRelease(int key) { + keysDown.erase(key); + keysReleasedThisFrame.insert(key); +} + +void engine::Keyboard::reportKeyRepeat(int key) { + keysRepeatedThisFrame.insert(key); +} + +void engine::Keyboard::reportChar(int key) { + charsThisFrame.push_back(key); +} diff --git a/engine/src/core/inputsOutputs/inputs/Keyboard.h b/engine/src/core/inputsOutputs/inputs/Keyboard.h new file mode 100644 index 0000000..ca3b52c --- /dev/null +++ b/engine/src/core/inputsOutputs/inputs/Keyboard.h @@ -0,0 +1,46 @@ +// +// Created by sebastian on 02.08.26. +// + +#ifndef COLORRACE_KEYBOARD_H +#define COLORRACE_KEYBOARD_H +#include +#include + +namespace engine { + class Window; +} + +namespace engine { + + class Keyboard { + public: + explicit Keyboard(engine::Window& window); + + void update(); + bool isKeyDown(int key) const; + + const std::vector &getCharsThisFrame(); + + bool keyPressEvent(int key) const; + bool keyPressEvent(int key, bool checkRepeats) const; + bool keyReleaseEvent(int key) const; + private: + std::unordered_set keysPressedThisFrame; + std::unordered_set keysRepeatedThisFrame; + std::unordered_set keysReleasedThisFrame; + std::unordered_set keysDown; + std::vector charsThisFrame; + + void addTextListener(Window& window); + + void addKeyListener(Window& window); + void reportKeyPress(int key); + void reportKeyRelease(int key); + void reportKeyRepeat(int key); + void reportChar(int key); + }; +} + + +#endif //COLORRACE_KEYBOARD_H diff --git a/engine/src/core/inputsOutputs/inputs/Mouse.cpp b/engine/src/core/inputsOutputs/inputs/Mouse.cpp new file mode 100644 index 0000000..06e9a2f --- /dev/null +++ b/engine/src/core/inputsOutputs/inputs/Mouse.cpp @@ -0,0 +1,105 @@ +// +// Created by sebastian on 02.08.26. +// + +#include "Mouse.h" + +#include "core/Window.h" +#include "GLFW/glfw3.h" + +engine::Mouse::Mouse(Window &window) { + window.setMouse(this); + addClickListener(window); + addMoveListener(window); + addScrollListener(window); +} + +bool engine::Mouse::isButtonDown(const MouseButton button) const { + return buttonsDown.contains(MouseButtonToInt(button)); +} + +bool engine::Mouse::isClickEvent(const MouseButton button) const { + return buttonsClickedThisFrame.contains(MouseButtonToInt(button)); +} + +bool engine::Mouse::isReleaseEvent(const MouseButton button) const { + return buttonsReleasedThisFrame.contains(MouseButtonToInt(button)); +} + +float engine::Mouse::getX(const bool ndc) const { + return ndc ? 2 * x - 1 : x; +} + +float engine::Mouse::getY(const bool ndc) const { + return ndc ? 1 - 2 * y : y; +} + +float engine::Mouse::getDX() const { + return dx; +} + +float engine::Mouse::getDY() const { + return dy; +} + +float engine::Mouse::getScroll() const { + return scroll; +} + +void engine::Mouse::update() { + updateDetlas(); + scroll = 0; + + buttonsClickedThisFrame.clear(); + buttonsReleasedThisFrame.clear(); +} + +glm::vec2 engine::Mouse::getXY(bool ndc) const { + return {getX(ndc), getY(ndc)}; +} + +void engine::Mouse::reportButtonClick(int button) { + buttonsDown.insert(button); + buttonsClickedThisFrame.insert(button); +} + +void engine::Mouse::reportButtonRelease(int button) { + buttonsDown.erase(button); + buttonsReleasedThisFrame.insert(button); +} + +void engine::Mouse::updateDetlas() { + dx = x - lastX; + dy = y - lastY; + lastX = x; + lastY = y; +} + +void engine::Mouse::addMoveListener(Window &window) { + glfwSetCursorPosCallback(window.getHandle(), [](GLFWwindow* handle, double xPos, double yPos) { + auto* target = static_cast(glfwGetWindowUserPointer(handle)); + if (!target || !target->mouse) return; + + int width, height; + glfwGetFramebufferSize(handle, &width, &height); + target->mouse->x = static_cast(xPos / width); + target->mouse->y = static_cast(yPos / height); + }); +} + +void engine::Mouse::addScrollListener(Window &window) { + glfwSetScrollCallback(window.getHandle(), [](GLFWwindow* handle, double xoff, double yoff) { + auto* target = static_cast(glfwGetWindowUserPointer(handle)); + if (target && target->mouse) target->mouse->scroll = static_cast(yoff); + }); +} + +void engine::Mouse::addClickListener(Window &window) { + glfwSetMouseButtonCallback(window.getHandle(), [](GLFWwindow* handle, int button, int action, int mods) { + auto* target = static_cast(glfwGetWindowUserPointer(handle)); + if (!target || !target->mouse) return; + + if (action == GLFW_PRESS) target->mouse->reportButtonClick(button); + else if (action == GLFW_RELEASE) target->mouse->reportButtonRelease(button); + }); +} diff --git a/engine/src/core/inputsOutputs/inputs/Mouse.h b/engine/src/core/inputsOutputs/inputs/Mouse.h new file mode 100644 index 0000000..84c513b --- /dev/null +++ b/engine/src/core/inputsOutputs/inputs/Mouse.h @@ -0,0 +1,53 @@ +// +// Created by sebastian on 02.08.26. +// + +#ifndef COLORRACE_MOUSE_H +#define COLORRACE_MOUSE_H +#include + +#include "MouseButton.h" +#include "glm/vec2.hpp" + + +namespace engine { + class Window; + + class Mouse { + public: + explicit Mouse(Window& window); + bool isButtonDown(MouseButton button) const; + bool isClickEvent(MouseButton button) const; + bool isReleaseEvent(MouseButton button) const; + float getX(bool ndc) const; + float getY(bool ndc) const; + float getDX() const; + float getDY() const; + float getScroll() const; + void update(); + glm::vec2 getXY(bool ndc) const; + private: + std::unordered_set buttonsDown; + std::unordered_set buttonsClickedThisFrame; + std::unordered_set buttonsReleasedThisFrame; + + float x = 0.0f, y = 0.0f; + float dx = 0.0f, dy = 0.0f; + float scroll = 0.0f; + float lastX = 0.0f, lastY = 0.0f; + + void reportButtonClick(int button); + void reportButtonRelease(int button); + void updateDetlas(); + + static void addMoveListener(Window& window); + static void addScrollListener(Window& window); + static void addClickListener(Window& window); + + static int MouseButtonToInt(MouseButton button) { + } + }; +} + + +#endif //COLORRACE_MOUSE_H diff --git a/engine/src/core/inputsOutputs/inputs/MouseButton.h b/engine/src/core/inputsOutputs/inputs/MouseButton.h new file mode 100644 index 0000000..56a58cd --- /dev/null +++ b/engine/src/core/inputsOutputs/inputs/MouseButton.h @@ -0,0 +1,14 @@ +// +// Created by sebastian on 02.08.26. +// + +#ifndef COLORRACE_MOUSEBUTTON_H +#define COLORRACE_MOUSEBUTTON_H +namespace engine { + enum class MouseButton { + LEFT, + RIGHT, + MIDDLE + }; +} +#endif //COLORRACE_MOUSEBUTTON_H diff --git a/engine/src/layer/Layer.cpp b/engine/src/layer/Layer.cpp index 9c60048..fa6a83b 100644 --- a/engine/src/layer/Layer.cpp +++ b/engine/src/layer/Layer.cpp @@ -3,3 +3,15 @@ // #include "Layer.h" + +void engine::Layer::onAttach(InputContextStack &inputStack) { + m_inputStack = &inputStack; + m_context = std::make_shared(); + inputStack.push(m_context); + onAttachImpl(); +} + +void engine::Layer::onDetach(InputContextStack &inputStack) { + inputStack.pop(); + onDetachImpl(); +} diff --git a/engine/src/layer/Layer.h b/engine/src/layer/Layer.h index e377932..2337c51 100644 --- a/engine/src/layer/Layer.h +++ b/engine/src/layer/Layer.h @@ -4,18 +4,34 @@ #ifndef COLORRACE_LAYER_H #define COLORRACE_LAYER_H +#include "core/inputsOutputs/context/InputContextStack.h" +#include "core/inputsOutputs/inputs/Keyboard.h" +#include "core/inputsOutputs/inputs/Mouse.h" #include "ecs/EntityRegistry.h" namespace engine { class Layer { public: - Layer() = default; + Layer(Keyboard& keyboard, Mouse& mouse) : m_keyboard(keyboard), m_mouse(mouse){}; virtual ~Layer() = default; - virtual void onAttach() {} - virtual void onDetach() {} + void onAttach(InputContextStack& inputStack); + void onDetach(InputContextStack& inputStack); virtual void onUpdate() {} virtual void onRender() {} + protected: + virtual void onAttachImpl() {} + virtual void onDetachImpl() {} + std::shared_ptr& getInputContext() { return m_context; } + InputContextStack& getInputStack() { return *m_inputStack; } + Keyboard& getKeyboard() { return m_keyboard; } + Mouse& getMouse() { return m_mouse; } + private: + std::shared_ptr m_context; + InputContextStack* m_inputStack = nullptr; + + engine::Keyboard& m_keyboard; + engine::Mouse& m_mouse; }; } diff --git a/engine/src/layer/Scene.cpp b/engine/src/layer/Scene.cpp index aac9938..9e01875 100644 --- a/engine/src/layer/Scene.cpp +++ b/engine/src/layer/Scene.cpp @@ -8,6 +8,8 @@ #include #include +#include "core/inputsOutputs/context/InputContextStack.h" + void engine::Scene::onUpdate() { for (const auto& layer : m_layers) { layer->onUpdate(); @@ -26,7 +28,7 @@ void engine::Scene::onRegisterLoadedAsset(LoadedAsset loadedAsset) { } void engine::Scene::addLayer(std::unique_ptr layer) { - layer->onAttach(); + layer->onAttach(m_inputStack); m_layers.push_back(std::move(layer)); } diff --git a/engine/src/layer/Scene.h b/engine/src/layer/Scene.h index 71a27be..351de13 100644 --- a/engine/src/layer/Scene.h +++ b/engine/src/layer/Scene.h @@ -15,14 +15,19 @@ namespace engine { + class Keyboard; + class Mouse; + class InputContextStack; + class Scene { public: - explicit Scene(): assetManager(std::make_unique()) {} + explicit Scene(engine::InputContextStack& inputStack, engine::Keyboard& keyboard, engine::Mouse& mouse): + assetManager(std::make_unique()), m_inputStack(inputStack), m_keyboard(keyboard), m_mouse(mouse) {} virtual ~Scene() = default; virtual void onEnter() {} virtual void onExit() { for (const auto& layer : m_layers) { - layer->onDetach(); + layer->onDetach(m_inputStack); } } @@ -39,6 +44,10 @@ namespace engine { engine::EntityRegistry entityRegistry; std::unique_ptr assetManager; + InputContextStack& m_inputStack; + + engine::Keyboard& m_keyboard; + engine::Mouse& m_mouse; }; } diff --git a/engine/src/layer/SceneManager.h b/engine/src/layer/SceneManager.h index aa3fa66..cd1a238 100644 --- a/engine/src/layer/SceneManager.h +++ b/engine/src/layer/SceneManager.h @@ -7,13 +7,14 @@ #include #include "Scene.h" +#include "core/inputsOutputs/context/InputContextStack.h" #include "loader/AssetLoader.h" namespace engine { class SceneManager { public: - SceneManager() = default; + explicit SceneManager(InputContextStack& inputStack) :m_inputStack(inputStack) {} void switchTo(std::unique_ptr scene, std::function onSceneLoaded = nullptr); void update(); void render() const; @@ -26,6 +27,8 @@ namespace engine { bool isTransitioning = false; std::function onSceneLoaded; AssetLoader assetLoader; + + InputContextStack& m_inputStack; }; diff --git a/game/src/ColorRaceApp.cpp b/game/src/ColorRaceApp.cpp index ba73a0f..d10ad2c 100644 --- a/game/src/ColorRaceApp.cpp +++ b/game/src/ColorRaceApp.cpp @@ -12,9 +12,9 @@ void ColorRaceApp::onUpdate(float deltaTime) { - sceneManager->update(); + getSceneManager().update(); } void ColorRaceApp::onRender() { - sceneManager->render(); + getSceneManager().render(); } \ No newline at end of file diff --git a/game/src/ColorRaceApp.h b/game/src/ColorRaceApp.h index 5b2f353..8c1f51a 100644 --- a/game/src/ColorRaceApp.h +++ b/game/src/ColorRaceApp.h @@ -33,11 +33,9 @@ public: config.debugContext = true; return config; } - ColorRaceApp() : Application(makeConfig()), sceneManager(std::make_unique()) { - sceneManager->switchTo(std::make_unique()); + ColorRaceApp() : Application(makeConfig()) { + getSceneManager().switchTo(std::make_unique(getInputContextStack(), getKeyboard(), getMouse())); } -private: - std::unique_ptr sceneManager; protected: void onUpdate(float deltaTime) override; void onRender() override; diff --git a/game/src/GameLayer.cpp b/game/src/GameLayer.cpp index faa7833..15ec3b3 100644 --- a/game/src/GameLayer.cpp +++ b/game/src/GameLayer.cpp @@ -13,14 +13,16 @@ #include "renderer/MeshRenderSystem.h" #include "renderer/primitives/CubeFactory.h" using namespace engine; -void GameLayer::onAttach() { +void GameLayer::onAttachImpl() { m_renderState.depthTesting = false; m_renderState.backfaceCulling = false; m_renderer = std::make_unique(); + + m_cameraController = std::make_unique(getInputStack(), getInputContext()); } -void GameLayer::onDetach() { +void GameLayer::onDetachImpl() { } @@ -35,6 +37,8 @@ void GameLayer::onUpdate() { m_entityRegistry.addComponent(entity, updatedTransform); } + m_cameraController->update(getKeyboard(), *m_camera, 1); + } void GameLayer::onRender() { diff --git a/game/src/GameLayer.h b/game/src/GameLayer.h index 5e1afb6..1196af5 100644 --- a/game/src/GameLayer.h +++ b/game/src/GameLayer.h @@ -6,6 +6,7 @@ #define COLORRACE_GAMELAYER_H #include +#include "core/inputsOutputs/controller/CameraController.h" #include "ecs/EntityRegistry.h" #include "layer/Layer.h" #include "renderer/MeshRenderer.h" @@ -15,12 +16,15 @@ class GameLayer: public engine::Layer { public: - GameLayer(engine::EntityRegistry& entityRegistry, std::shared_ptr cam, std::shared_ptr light) - : m_entityRegistry(entityRegistry), m_camera(std::move(cam)), m_renderer(std::make_unique()), m_pointLight(light) {} - void onAttach() override; - void onDetach() override; + GameLayer(engine::EntityRegistry& entityRegistry, std::shared_ptr cam, std::shared_ptr light, + engine::Keyboard& keyboard, engine::Mouse& mouse) + : Layer(keyboard, mouse), m_entityRegistry(entityRegistry), m_camera(std::move(cam)), m_renderer(std::make_unique()), m_pointLight(std::move(light)){} + void onUpdate() override; void onRender() override; +protected: + void onAttachImpl() override; + void onDetachImpl() override; private: engine::GLRenderState m_renderState; engine::RenderQueue m_renderQueue; @@ -28,6 +32,7 @@ private: std::shared_ptr m_pointLight; std::shared_ptr m_camera; std::unique_ptr m_renderer; + std::unique_ptr m_cameraController; }; #endif //COLORRACE_GAMELAYER_H diff --git a/game/src/GameScene.cpp b/game/src/GameScene.cpp index 1245821..64dddee 100644 --- a/game/src/GameScene.cpp +++ b/game/src/GameScene.cpp @@ -5,15 +5,16 @@ #include "GameScene.h" #include "GameLayer.h" +#include "core/inputsOutputs/inputs/Mouse.h" #include "ecs/standardComponents/MeshComponent.h" #include "ecs/standardComponents/TransformComponent.h" -GameScene::GameScene() : Scene(), m_camera(std::make_unique()) { +GameScene::GameScene(engine::InputContextStack& inputStack, engine::Keyboard& keyboard, engine::Mouse& mouse) : Scene(inputStack, keyboard, mouse), m_camera(std::make_unique()) { m_pointLight = std::make_shared(glm::vec3(.0f, .0f, -5.0f), glm::vec3(1.0f, 1.0f, 1.0f)); } void GameScene::onEnter() { - addLayer(std::make_unique(entityRegistry, m_camera, m_pointLight)); + addLayer(std::make_unique(entityRegistry, m_camera, m_pointLight, m_keyboard, m_mouse)); m_camera->setPosition({0.0f, 0.0f, 5.0f}); m_camera->setYaw(0.0f); diff --git a/game/src/GameScene.h b/game/src/GameScene.h index a9ddb08..da2f7dd 100644 --- a/game/src/GameScene.h +++ b/game/src/GameScene.h @@ -10,7 +10,7 @@ class GameScene : public engine::Scene { public: - GameScene(); + GameScene(engine::InputContextStack& inputContext, engine::Keyboard& keyboard, engine::Mouse& mouse); void onEnter() override; void onExit() override; std::vector getRequiredAssets() const override;