diff options
author | Clyne Sullivan <clyne@bitgloo.com> | 2022-11-17 13:47:16 -0500 |
---|---|---|
committer | Clyne Sullivan <clyne@bitgloo.com> | 2022-11-17 13:47:16 -0500 |
commit | 72603f1641bb400be6c9b0604273a4bd38932136 (patch) | |
tree | 50188f29a1af54d25c8fab91b3cc1ce170ca09aa | |
parent | 0c535a1526d725fbd242c5ce348a7f2252d1fd34 (diff) |
ui-coord mouse interacts with world-coord entity
-rw-r--r-- | Scripts/init.lua | 12 | ||||
-rw-r--r-- | src/engine.cpp | 3 | ||||
-rw-r--r-- | src/render.cpp | 36 | ||||
-rw-r--r-- | src/render.hpp | 22 | ||||
-rw-r--r-- | src/script.hpp | 19 |
5 files changed, 78 insertions, 14 deletions
diff --git a/Scripts/init.lua b/Scripts/init.lua index fde6c86..1ae2efc 100644 --- a/Scripts/init.lua +++ b/Scripts/init.lua @@ -24,12 +24,16 @@ player = { end end, JumpKeyReleased = function(self) - game.dialog(30, 50, 400, 100) - game.puts("dialog", 36, 52, "Hey. Hag?") end, MousePressed = function(self, mx, my) - if mx > 30 and mx < 430 and my > 50 and my < 150 then - game.dialogClear() + mp = game.uiToWorldCoord(mx, my) + if math.abs(mp.x - self.Position.x) < 1 and math.abs(mp.y - self.Position.y) < 1 then + game.dialog(30, 50, 400, 100) + game.puts("dialog", 36, 52, "What do you think you're doing?") + else + if mx > 30 and mx < 430 and my > 50 and my < 150 then + game.dialogClear() + end end end }, diff --git a/src/engine.cpp b/src/engine.cpp index 25e3cd3..a80dfe3 100644 --- a/src/engine.cpp +++ b/src/engine.cpp @@ -76,6 +76,9 @@ int Engine::init(void) systems.system<UISystem>().get())); script->addToGameNamespace("dialogClear", [this] { events.emit<HideDialog>(); }); + script->addToGameNamespace("uiToWorldCoord", + bindInstance(&RenderSystem::uiToWorldCoord, + systems.system<RenderSystem>().get())); script->init(); diff --git a/src/render.cpp b/src/render.cpp index 5ae2c15..9965b8f 100644 --- a/src/render.cpp +++ b/src/render.cpp @@ -25,8 +25,8 @@ #include <components/Light.hpp> #include <components/Script.hpp> -void RenderSystem::configure([[maybe_unused]] entityx::EntityManager& entities, - [[maybe_unused]] entityx::EventManager& events) +void RenderSystem::configure(entityx::EntityManager&, + entityx::EventManager& events) { events.subscribe<NewRenderEvent>(*this); events.subscribe<DelRenderEvent>(*this); @@ -40,9 +40,33 @@ void RenderSystem::configure([[maybe_unused]] entityx::EntityManager& entities, init(); } -void RenderSystem::update([[maybe_unused]] entityx::EntityManager& entities, - [[maybe_unused]] entityx::EventManager& events, - [[maybe_unused]] entityx::TimeDelta dt) +float RenderSystem::getWorldViewWidth() const +{ + return camPos.z * height / width * 2.0; +} + +float RenderSystem::getWorldViewHeight() const +{ + return getWorldViewWidth() * height / width; +} + +Position RenderSystem::uiToWorldCoord(float x, float y) const +{ + glm::vec2 scaled; + scaled.x = x / width - 0.5; + scaled.y = y / height - 0.5; + + Position world; + world.x = scaled.x * getWorldViewWidth() + camPos.x; + world.y = scaled.y * getWorldViewHeight() + camPos.y; + world.z = camPos.z; + + return world; +} + +void RenderSystem::update(entityx::EntityManager& entities, + entityx::EventManager&, + entityx::TimeDelta) { // TODO move these to only happen once to speed up rendering static GLuint s = worldShader.getProgram(); @@ -309,7 +333,7 @@ void RenderSystem::update([[maybe_unused]] entityx::EntityManager& entities, SDL_GL_SwapWindow(window.get()); } -int RenderSystem::init(void) +int RenderSystem::init() { if (SDL_InitSubSystem(SDL_INIT_VIDEO) != 0) { diff --git a/src/render.hpp b/src/render.hpp index ede3f88..786954e 100644 --- a/src/render.hpp +++ b/src/render.hpp @@ -82,11 +82,12 @@ private: std::map<GLuint, WorldRenderData> worldRenders; entityx::Entity player; // Save the player so we can track the camera + public: RenderSystem() : window(nullptr, SDL_DestroyWindow) {} - ~RenderSystem(void) + ~RenderSystem() { SDL_GL_DeleteContext(context); SDL_Quit(); @@ -109,7 +110,24 @@ public: * Initializes the rendering system * @return Zero on success, non-zero on error */ - int init(void); + int init(); + + glm::vec3 getCameraPosition() const { + return camPos; + } + + Position uiToWorldCoord(float x, float y) const; + + /** + * Returns the width of the camera's view in world coordinates. + */ + float getWorldViewWidth() const; + + /** + * Returns the height of the camera's view in world coordinates. + */ + float getWorldViewHeight() const; + /************ * EVENTS * diff --git a/src/script.hpp b/src/script.hpp index 24cc142..dadddfa 100644 --- a/src/script.hpp +++ b/src/script.hpp @@ -21,15 +21,19 @@ #ifndef SYSTEM_SCRIPT_HPP_ #define SYSTEM_SCRIPT_HPP_ +#include "world.hpp" + #include <entityx/entityx.h> #include <sol/sol.hpp> -#include "world.hpp" +#include <concepts> /** * Utility for pairing class instances to their member function calls. * This is useful for adding functions to the Lua game namespace. * + * TODO I am certain that this can be done better. -clyne + * * @param func The member function to call * @param instance The instance to bind to * @return A function that calls the member function using the given instance @@ -37,7 +41,18 @@ template<class C, typename R, typename... Args> auto bindInstance(R (C::* func)(Args...), C *instance) { - return [instance, func](Args... args) { (instance->*func)(args...); }; + if constexpr (std::same_as<R, void>) + return [instance, func](Args... args) { (instance->*func)(args...); }; + else + return [instance, func](Args... args) { return (instance->*func)(args...); }; +} +template<class C, typename R, typename... Args> +auto bindInstance(R (C::* func)(Args...) const, const C *instance) +{ + if constexpr (std::same_as<R, void>) + return [instance, func](Args... args) { (instance->*func)(args...); }; + else + return [instance, func](Args... args) { return (instance->*func)(args...); }; } |