From 7fc997cc18c52eaac16bff24233d324eda4da129 Mon Sep 17 00:00:00 2001 From: mrq Date: Sun, 27 Jun 2021 00:42:00 -0500 Subject: [PATCH] Commit for 2021.06.27 00-42-22.7z --- bin/data/entities/player.json | 3 +- client/client/ext.cpp | 28 +- engine/inc/uf/spec/window/universal.h | 63 +- engine/inc/uf/spec/window/universal.inl | 6 + .../inc/uf/utils/math/transform/transform.inl | 24 +- engine/inc/uf/utils/math/vector/pod.inl | 14 +- engine/inc/uf/utils/window/payloads.h | 67 ++ engine/inc/uf/utils/window/window.h | 54 +- engine/src/spec/window/dreamcast.cpp | 107 +-- engine/src/spec/window/windows.cpp | 780 ++++++++---------- ext/behaviors/player/behavior.cpp | 70 +- ext/behaviors/player/behavior.h | 9 + ext/gui/behavior.cpp | 65 +- 13 files changed, 593 insertions(+), 697 deletions(-) create mode 100644 engine/inc/uf/spec/window/universal.inl create mode 100644 engine/inc/uf/utils/window/payloads.h diff --git a/bin/data/entities/player.json b/bin/data/entities/player.json index 30ba57d5..a1a24bc4 100644 --- a/bin/data/entities/player.json +++ b/bin/data/entities/player.json @@ -84,8 +84,7 @@ "minima": [ null, -1.0, null ], "maxima": [ null, 1.0, null ], - - "current": [ null, 0, null ] + "current":[ null, 0, null ] }, "settings": { "fov" : 90, diff --git a/client/client/ext.cpp b/client/client/ext.cpp index 710f7e51..cd2d2298 100644 --- a/client/client/ext.cpp +++ b/client/client/ext.cpp @@ -8,24 +8,13 @@ #include #include #include +#include bool client::ready = false; bool client::terminated = false; uf::Window client::window; uf::Serializer client::config; -namespace pod { - namespace payloads { - struct windowMouseMoved { - std::string invoker = ""; - pod::Vector2i delta; - pod::Vector2ui position; - pod::Vector2ui size; - int_fast8_t state; - }; - } -} - void client::initialize() { uf::IoStream::ncurses = true; uf::renderer::device.window = &client::window; @@ -157,11 +146,16 @@ void client::tick() { } #endif uf::hooks.call("window:Mouse.Moved", pod::payloads::windowMouseMoved{ - .invoker = "client", - .delta = previous - current, - .position = current, - .size = size, - .state = 0 + "window:Mouse.Moved", + "client", + { + pod::Vector2ui{ size.x, size.y }, + }, + { + current, + previous - current, + 0 + } }); } } diff --git a/engine/inc/uf/spec/window/universal.h b/engine/inc/uf/spec/window/universal.h index 80423aa5..c58abdbe 100644 --- a/engine/inc/uf/spec/window/universal.h +++ b/engine/inc/uf/spec/window/universal.h @@ -25,42 +25,41 @@ namespace spec { std::queue m_events; public: // C-tors - /*virtual*/ void UF_API_CALL create( const spec::uni::Window::vector_t& size, const spec::uni::Window::title_t& title = L"Window" ) {} ;// = 0; + void create( const spec::uni::Window::vector_t& size, const spec::uni::Window::title_t& title = L"Window" ) {} ;// = 0; // D-tors - /*virtual*/ void UF_API_CALL terminate();/* = 0;*/ + void terminate();/* = 0;*/ // Gets - /*virtual*/ spec::uni::Window::vector_t UF_API_CALL getPosition() const;/* = 0;*/ - /*virtual*/ spec::uni::Window::vector_t UF_API_CALL getSize() const;/* = 0;*/ - /*virtual*/ size_t UF_API_CALL getRefreshRate() const;/* = 0;*/ + spec::uni::Window::vector_t getPosition() const;/* = 0;*/ + spec::uni::Window::vector_t getSize() const;/* = 0;*/ + size_t getRefreshRate() const;/* = 0;*/ // Attribute modifiers - /*virtual*/ void UF_API_CALL setPosition( const spec::uni::Window::vector_t& position );/* = 0;*/ - /*virtual*/ void UF_API_CALL centerWindow();/* = 0;*/ - /*virtual*/ void UF_API_CALL setMousePosition( const spec::uni::Window::vector_t& position );/* = 0;*/ - /*virtual*/ void UF_API_CALL setSize( const spec::uni::Window::vector_t& size );/* = 0;*/ - /*virtual*/ void UF_API_CALL setTitle( const spec::uni::Window::title_t& title );/* = 0;*/ - /*virtual*/ void UF_API_CALL setIcon( const spec::uni::Window::vector_t& size, uint8_t* pixels );/* = 0;*/ - /*virtual*/ void UF_API_CALL setVisible( bool visibility );/* = 0;*/ - /*virtual*/ void UF_API_CALL setCursorVisible( bool visibility );/* = 0;*/ - /*virtual*/ void UF_API_CALL setKeyRepeatEnabled( bool state );/* = 0;*/ - /*virtual*/ void UF_API_CALL setMouseGrabbed( bool state );/* = 0;*/ + void setPosition( const spec::uni::Window::vector_t& position );/* = 0;*/ + void centerWindow();/* = 0;*/ + void setMousePosition( const spec::uni::Window::vector_t& position );/* = 0;*/ + void setSize( const spec::uni::Window::vector_t& size );/* = 0;*/ + void setTitle( const spec::uni::Window::title_t& title );/* = 0;*/ + void setIcon( const spec::uni::Window::vector_t& size, uint8_t* pixels );/* = 0;*/ + void setVisible( bool visibility );/* = 0;*/ + void setCursorVisible( bool visibility );/* = 0;*/ + void setKeyRepeatEnabled( bool state );/* = 0;*/ + void setMouseGrabbed( bool state );/* = 0;*/ - /*virtual*/ void UF_API_CALL requestFocus();/* = 0;*/ - /*virtual*/ bool UF_API_CALL hasFocus() const;/* = 0;*/ + void requestFocus();/* = 0;*/ + bool hasFocus() const;/* = 0;*/ // Update - /*virtual*/ void UF_API_CALL processEvents();/* = 0;*/ - /* - void UF_API_CALL pushEvent( const uf::ReadableHook::name_t& name, const uf::ReadableHook::argument_t& argument ); - void UF_API_CALL pushEvent( const uf::OptimalHook::name_t& name, const uf::OptimalHook::argument_t& argument ); - void UF_API_CALL pushEvent( const uf::ReadableHook::argument_t& serialized ); - void UF_API_CALL pushEvent( const uf::OptimalHook::argument_t& userdata ); - */ - void UF_API_CALL pushEvent( const uf::Hooks::name_t& name, const std::string& payload ); - void UF_API_CALL pushEvent( const uf::Hooks::name_t& name, const ext::json::Value& payload ); - void UF_API_CALL pushEvent( const uf::Hooks::name_t& name, const uf::Serializer& payload ); - void UF_API_CALL pushEvent( const uf::Hooks::name_t& name, const uf::Hooks::argument_t& payload ); - void UF_API_CALL pushEvent( const uf::Hooks::argument_t& payload ); - bool UF_API_CALL pollEvents( bool block = false ); - static bool UF_API_CALL isKeyPressed( const std::string& ); + void processEvents();/* = 0;*/ + + void pushEvent( const uf::Hooks::name_t& name, const std::string& payload ); + void pushEvent( const uf::Hooks::name_t& name, const ext::json::Value& payload ); + void pushEvent( const uf::Hooks::name_t& name, const uf::Serializer& payload ); + void pushEvent( const uf::Hooks::name_t& name, const uf::Hooks::argument_t& payload ); + void pushEvent( const uf::Hooks::argument_t& payload ); + template void pushEvent( const uf::Hooks::name_t& name, const T& payload ); + + bool pollEvents( bool block = false ); + static bool isKeyPressed( const std::string& ); }; } -} \ No newline at end of file +} + +#include "universal.inl" \ No newline at end of file diff --git a/engine/inc/uf/spec/window/universal.inl b/engine/inc/uf/spec/window/universal.inl new file mode 100644 index 00000000..46375e0e --- /dev/null +++ b/engine/inc/uf/spec/window/universal.inl @@ -0,0 +1,6 @@ +template +void spec::uni::Window::pushEvent( const uf::Hooks::name_t& name, const T& payload ) { + pod::Hook::userdata_t userdata; + userdata.create( payload ); + this->pushEvent( name, userdata ); +} \ No newline at end of file diff --git a/engine/inc/uf/utils/math/transform/transform.inl b/engine/inc/uf/utils/math/transform/transform.inl index 81a86df9..3c049df2 100644 --- a/engine/inc/uf/utils/math/transform/transform.inl +++ b/engine/inc/uf/utils/math/transform/transform.inl @@ -169,15 +169,19 @@ pod::Transform& /*UF_API*/ uf::transform::decode( const ext::json::Value& _js // transform.position = uf::vector::decode(json["position"], transform.position); // transform.scale = uf::vector::decode(json["scale"], transform.scale); // transform.orientation = uf::vector::decode(json["orientation"], transform.orientation); - if ( ext::json::isArray(json["position"]) || ext::json::isObject(json["position"]) ) transform.position = uf::vector::decode(json["position"], transform.position); - if ( ext::json::isArray(json["scale"]) || ext::json::isObject(json["scale"]) ) transform.scale = uf::vector::decode(json["scale"], transform.scale); - if ( ext::json::isArray(json["orientation"]) || ext::json::isObject(json["orientation"]) ) transform.orientation = uf::vector::decode(json["orientation"], transform.orientation); +// if ( ext::json::isArray(json["position"]) || ext::json::isObject(json["position"]) ) + transform.position = uf::vector::decode(json["position"], transform.position); +// if ( ext::json::isArray(json["scale"]) || ext::json::isObject(json["scale"]) ) + transform.scale = uf::vector::decode(json["scale"], transform.scale); +// if ( ext::json::isArray(json["orientation"]) || ext::json::isObject(json["orientation"]) ) + transform.orientation = uf::vector::decode(json["orientation"], transform.orientation); if ( ext::json::isObject(json["rotation"]) && !ext::json::isNull(json["rotation"]["axis"]) && !ext::json::isNull(json["rotation"]["angle"]) ) { pod::Vector3t axis = uf::vector::decode(json["rotation"]["axis"]); T angle = json["rotation"]["angle"].as(); transform.orientation = uf::quaternion::axisAngle( axis, angle ); } - if ( ext::json::isArray(json["model"]) ) transform.model = uf::matrix::decode(json["model"]); +// if ( ext::json::isArray(json["model"]) ) + transform.model = uf::matrix::decode(json["model"], transform.model); return transform; } template @@ -187,14 +191,18 @@ pod::Transform /*UF_API*/ uf::transform::decode( const ext::json::Value& _jso // transform.position = uf::vector::decode(json["position"], transform.position); // transform.scale = uf::vector::decode(json["scale"], transform.scale); // transform.orientation = uf::vector::decode(json["orientation"], transform.orientation); - if ( ext::json::isArray(json["position"]) || ext::json::isObject(json["position"]) ) transform.position = uf::vector::decode(json["position"], transform.position); - if ( ext::json::isArray(json["scale"]) || ext::json::isObject(json["scale"]) ) transform.scale = uf::vector::decode(json["scale"], transform.scale); - if ( ext::json::isArray(json["orientation"]) || ext::json::isObject(json["orientation"]) ) transform.orientation = uf::vector::decode(json["orientation"], transform.orientation); +// if ( ext::json::isArray(json["position"]) || ext::json::isObject(json["position"]) ) + transform.position = uf::vector::decode(json["position"], transform.position); +// if ( ext::json::isArray(json["scale"]) || ext::json::isObject(json["scale"]) ) + transform.scale = uf::vector::decode(json["scale"], transform.scale); +// if ( ext::json::isArray(json["orientation"]) || ext::json::isObject(json["orientation"]) ) + transform.orientation = uf::vector::decode(json["orientation"], transform.orientation); if ( ext::json::isObject(json["rotation"]) && !ext::json::isNull(json["rotation"]["axis"]) && !ext::json::isNull(json["rotation"]["angle"]) ) { pod::Vector3t axis = uf::vector::decode(json["rotation"]["axis"]); T angle = json["rotation"]["angle"].as(); transform.orientation = uf::quaternion::axisAngle( axis, angle ); } - if ( ext::json::isArray(json["model"]) ) transform.model = uf::matrix::decode(json["model"]); +// if ( ext::json::isArray(json["model"]) ) + transform.model = uf::matrix::decode(json["model"], transform.model); return transform; } \ No newline at end of file diff --git a/engine/inc/uf/utils/math/vector/pod.inl b/engine/inc/uf/utils/math/vector/pod.inl index b0000eb4..b368dc6e 100644 --- a/engine/inc/uf/utils/math/vector/pod.inl +++ b/engine/inc/uf/utils/math/vector/pod.inl @@ -407,11 +407,14 @@ pod::Vector& /*UF_API*/ uf::vector::decode( const ext::json::Value& json, p if ( ext::json::isArray(json) ) #pragma unroll // GCC unroll T::size for ( uint_fast8_t i = 0; i < N; ++i ) - v[i] = json[i].as(); + v[i] = json[i].as(v[i]); else if ( ext::json::isObject(json) ) { uint_fast8_t i = 0; ext::json::forEach(json, [&](const ext::json::Value& c){ - if ( i < N ) v[i++] = uf::math::unquantize( c.as() ); + if ( i < N ) { + v[i] = uf::math::unquantize( c.as(v[i]) ); + ++i; + } }); } return v; @@ -422,11 +425,14 @@ pod::Vector /*UF_API*/ uf::vector::decode( const ext::json::Value& json, co if ( ext::json::isArray(json) ) #pragma unroll // GCC unroll T::size for ( uint_fast8_t i = 0; i < N; ++i ) - v[i] = json[i].as(); + v[i] = json[i].as(_v[i]); else if ( ext::json::isObject(json) ) { uint_fast8_t i = 0; ext::json::forEach(json, [&](const ext::json::Value& c){ - if ( i < N ) v[i++] = c.as(); + if ( i < N ) { + v[i] = c.as(_v[i]); + ++i; + } }); } return v; diff --git a/engine/inc/uf/utils/window/payloads.h b/engine/inc/uf/utils/window/payloads.h new file mode 100644 index 00000000..dd24f38b --- /dev/null +++ b/engine/inc/uf/utils/window/payloads.h @@ -0,0 +1,67 @@ +#pragma once + +#include + +#include +#include + +namespace pod { + namespace payloads { + struct windowEvent { + std::string type = ""; + std::string invoker = ""; + }; + struct windowResized : public windowEvent { + struct { + pod::Vector2ui size{}; + } window; + }; + struct windowFocusedChanged : public windowEvent { + struct { + int_fast8_t state{}; + } window; + }; + struct windowTextEntered : public windowEvent { + struct { + uint32_t utf32; + std::string unicode; + } text; + }; + struct windowKey : public windowEvent { + struct { + std::string code; + uint32_t raw; + + int_fast8_t state = -1; + bool async; + struct { + bool alt; + bool ctrl; + bool shift; + bool sys; + } modifier; + } key; + }; + struct windowMouseWheel : public windowEvent { + struct { + pod::Vector2ui position{}; + float delta = 0; + } mouse; + }; + struct windowMouseClick : public windowEvent { + struct { + pod::Vector2i position = {}; + pod::Vector2i delta = {}; + std::string button = ""; + int_fast8_t state = 0; + } mouse; + }; + struct windowMouseMoved : public windowResized { + struct { + pod::Vector2ui position{}; + pod::Vector2i delta{}; + int_fast8_t state{}; + } mouse; + }; + } +} \ No newline at end of file diff --git a/engine/inc/uf/utils/window/window.h b/engine/inc/uf/utils/window/window.h index d33e4c06..dd3fc96f 100644 --- a/engine/inc/uf/utils/window/window.h +++ b/engine/inc/uf/utils/window/window.h @@ -17,44 +17,44 @@ namespace uf { // C-tors UF_API_CALL Window(); UF_API_CALL Window( const spec::uni::Window::vector_t& size, const spec::uni::Window::title_t& title = L"Window", const spec::Context::Settings& settings = spec::Context::Settings() ); - /*virtual*/ void UF_API_CALL create( const spec::uni::Window::vector_t& size, const spec::uni::Window::title_t& title = L"Window", const spec::Context::Settings& settings = spec::Context::Settings() ); + void UF_API_CALL create( const spec::uni::Window::vector_t& size, const spec::uni::Window::title_t& title = L"Window", const spec::Context::Settings& settings = spec::Context::Settings() ); // D-tors - /*virtual*/ ~Window(); - /*virtual*/ void UF_API_CALL terminate(); + ~Window(); + void UF_API_CALL terminate(); // Gets - /*virtual*/ spec::uni::Window::vector_t UF_API_CALL getPosition() const; - /*virtual*/ spec::uni::Window::vector_t UF_API_CALL getSize() const; - /*virtual*/ size_t UF_API_CALL getRefreshRate() const; + spec::uni::Window::vector_t UF_API_CALL getPosition() const; + spec::uni::Window::vector_t UF_API_CALL getSize() const; + size_t UF_API_CALL getRefreshRate() const; // Attribute modifiers - /*virtual*/ void UF_API_CALL setPosition( const spec::uni::Window::vector_t& position ); - /*virtual*/ void UF_API_CALL centerWindow(); - /*virtual*/ void UF_API_CALL setMousePosition( const spec::uni::Window::vector_t& position ); - /*virtual*/ spec::uni::Window::vector_t UF_API_CALL getMousePosition(); - /*virtual*/ void UF_API_CALL setSize( const spec::uni::Window::vector_t& size ); - /*virtual*/ void UF_API_CALL setTitle( const spec::uni::Window::title_t& title ); - /*virtual*/ void UF_API_CALL setIcon( const spec::uni::Window::vector_t& size, uint8_t* pixels ); - /*virtual*/ void UF_API_CALL setVisible( bool visibility ); - /*virtual*/ void UF_API_CALL setCursorVisible( bool visibility ); - /*virtual*/ void UF_API_CALL setKeyRepeatEnabled( bool state ); - /*virtual*/ void UF_API_CALL setMouseGrabbed( bool state ); + void UF_API_CALL setPosition( const spec::uni::Window::vector_t& position ); + void UF_API_CALL centerWindow(); + void UF_API_CALL setMousePosition( const spec::uni::Window::vector_t& position ); + spec::uni::Window::vector_t UF_API_CALL getMousePosition(); + void UF_API_CALL setSize( const spec::uni::Window::vector_t& size ); + void UF_API_CALL setTitle( const spec::uni::Window::title_t& title ); + void UF_API_CALL setIcon( const spec::uni::Window::vector_t& size, uint8_t* pixels ); + void UF_API_CALL setVisible( bool visibility ); + void UF_API_CALL setCursorVisible( bool visibility ); + void UF_API_CALL setKeyRepeatEnabled( bool state ); + void UF_API_CALL setMouseGrabbed( bool state ); - /*virtual*/ void UF_API_CALL requestFocus(); - /*virtual*/ bool UF_API_CALL hasFocus() const; + void UF_API_CALL requestFocus(); + bool UF_API_CALL hasFocus() const; static pod::Vector2ui UF_API_CALL getResolution(); - /*virtual*/ void UF_API_CALL switchToFullscreen( bool borderless = false ); + void UF_API_CALL switchToFullscreen( bool borderless = false ); // Update #if defined(UF_USE_VULKAN) && UF_USE_VULKAN == 1 std::vector getExtensions( bool validationEnabled = true ); void createSurface( VkInstance instance, VkSurfaceKHR& surface ); #endif static bool focused; - static /*virtual*/ bool UF_API_CALL isKeyPressed(const std::string&); - /*virtual*/ void UF_API_CALL processEvents(); - /*virtual*/ bool UF_API_CALL pollEvents(bool block = false); - /*virtual*/ bool UF_API_CALL setActive( bool active = true ); - /*virtual*/ void UF_API_CALL display(); - /*virtual*/ Window::window_t* UF_API_CALL getHandle(); - /*virtual*/ const Window::window_t* UF_API_CALL getHandle() const; + static bool UF_API_CALL isKeyPressed(const std::string&); + void UF_API_CALL processEvents(); + bool UF_API_CALL pollEvents(bool block = false); + bool UF_API_CALL setActive( bool active = true ); + void UF_API_CALL display(); + Window::window_t* UF_API_CALL getHandle(); + const Window::window_t* UF_API_CALL getHandle() const; }; } #elif UF_USE_SFML diff --git a/engine/src/spec/window/dreamcast.cpp b/engine/src/spec/window/dreamcast.cpp index 8a70bf63..0dd3e98d 100644 --- a/engine/src/spec/window/dreamcast.cpp +++ b/engine/src/spec/window/dreamcast.cpp @@ -362,65 +362,52 @@ void UF_API_CALL spec::dreamcast::Window::processEvents() { if ( ::mouse.device ) ::mouse.state = (mouse_state_t*) maple_dev_status(::mouse.device); /* Key inputs */ if ( this->m_asyncParse ) { - std::vector keys = GetKeys(); + std::vector keys = GetKeys(); + pod::payloads::windowKey event{ + "window:Key", + "os", + { + "", + 0, - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; - - struct { - int state; - std::string code; - uint32_t raw; - bool async; - - struct { - bool alt; - bool ctrl; - bool shift; - bool sys; - } modifier; - } key; - }; - Event event; { - event.type = "window:Key"; - event.invoker = "window"; - event.key.state = -1; - event.key.code = "NULL"; - event.key.raw = 0; - event.key.async = true; - event.key.modifier = { - .alt = GetModifier(KBD_MOD_LALT) || GetModifier(KBD_MOD_RALT), - .ctrl = GetModifier(KBD_MOD_LCTRL) || GetModifier(KBD_MOD_RCTRL), - .shift = GetModifier(KBD_MOD_LSHIFT) || GetModifier(KBD_MOD_RSHIFT), - .sys = GetModifier(KBD_MOD_S1) || GetModifier(KBD_MOD_S2), - }; - } - /* Readable (JSON) + Optimal (Userdata) event */ { - uf::Serializer json; - /* Set up JSON data*/ { - json["type"] = event.type + "." + ((event.key.state == -1)?"Pressed":"Released"); - json["invoker"] = event.invoker; - json["key"]["state"] = (event.key.state == -1) ? "Down" : "Up"; - json["key"]["async"] = event.key.async; - json["key"]["modifier"]["alt"] = event.key.modifier.alt; - json["key"]["modifier"]["control"] = event.key.modifier.ctrl; - json["key"]["modifier"]["shift"] = event.key.modifier.shift; - json["key"]["modifier"]["system"] = event.key.modifier.sys; - } - /* Loop through key inputs */ { - for ( auto& key : keys ) { - auto code = GetKeyName(key); - event.key.code = code; - event.key.raw = key; - event.key.state = GetKeyState(key); - - json["key"]["code"] = code; - json["key"]["raw"] = key; - this->pushEvent(event.type, json); - this->pushEvent(event.type + "." + code, json); + -1, + true, + { + GetModifier(KBD_MOD_LALT) || GetModifier(KBD_MOD_RALT), + GetModifier(KBD_MOD_LCTRL) || GetModifier(KBD_MOD_RCTRL), + GetModifier(KBD_MOD_LSHIFT) || GetModifier(KBD_MOD_RSHIFT), + GetModifier(KBD_MOD_S1) || GetModifier(KBD_MOD_S2), } } + }; + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type + "." + ((event.key.state == -1)?"Pressed":"Released"); + json["invoker"] = event.invoker; + json["key"]["code"] = ""; + json["key"]["raw"] = 0; + json["key"]["state"] = (event.key.state == -1) ? "Down" : "Up"; + json["key"]["async"] = event.key.async; + json["key"]["modifier"]["alt"] = event.key.modifier.alt; + json["key"]["modifier"]["control"] = event.key.modifier.ctrl; + json["key"]["modifier"]["shift"] = event.key.modifier.shift; + json["key"]["modifier"]["system"] = event.key.modifier.sys; + #endif + for ( auto& key : keys ) { + const auto code = GetKeyName(key); + event.key.code = code; + event.key.raw = key; + + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + this->pushEvent(event.type + "." + code, event); + #endif + #if UF_USE_JSON + json["key"]["code"] = code; + json["key"]["raw"] = key; + this->pushEvent(event.type, json); + this->pushEvent(event.type + "." + code, json); + #endif } } } @@ -435,22 +422,14 @@ bool UF_API_CALL spec::dreamcast::Window::pollEvents( bool block ) { auto& event = this->m_events.front(); if ( event.payload.is() ) { ext::json::Value payload = uf::Serializer( event.payload.as() ); - // std::cout << event.name << " (string)\t" << payload << std::endl; - uf::hooks.call( "window:Event", payload ); uf::hooks.call( event.name, payload ); } else if ( event.payload.is() ) { uf::Serializer& payload = event.payload.as(); - // std::cout << event.name << " (serializer)\t" << payload << std::endl; - uf::hooks.call( "window:Event", payload ); uf::hooks.call( event.name, payload ); } else if ( event.payload.is() ) { ext::json::Value& payload = event.payload.as(); - // std::cout << event.name << " (json)\t" << payload << std::endl; - uf::hooks.call( "window:Event", payload ); uf::hooks.call( event.name, payload ); } else { - // std::cout << event.name << "(???)" << std::endl; - uf::hooks.call( "window:Event", event.payload ); uf::hooks.call( event.name, event.payload ); } /* diff --git a/engine/src/spec/window/windows.cpp b/engine/src/spec/window/windows.cpp index e2f6a6b4..1e2bfed2 100644 --- a/engine/src/spec/window/windows.cpp +++ b/engine/src/spec/window/windows.cpp @@ -2,8 +2,10 @@ #include #include #include +#include -#define USE_OPTIMAL 0 +#define UF_USE_USERDATA 1 +#define UF_USE_JSON 1 #if UF_ENV_WINDOWS && (!UF_USE_SFML || (UF_USE_SFML && UF_USE_SFML == 0)) namespace { @@ -772,39 +774,53 @@ void UF_API_CALL spec::win32::Window::processEvents() { } /* Key inputs */ if ( this->m_asyncParse ) { std::vector keys = GetKeys(); + pod::payloads::windowKey event{ + "window:Key", + "os", + { + "", + 0, - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; - - struct { - int state; - std::string code; - uint32_t raw; - bool async; - - struct { - bool alt; - bool ctrl; - bool shift; - bool sys; - } modifier; - } key; + -1, + true, + { + HIWORD(GetAsyncKeyState(VK_MENU)) != 0, + HIWORD(GetAsyncKeyState(VK_CONTROL)) != 0, + HIWORD(GetAsyncKeyState(VK_SHIFT)) != 0, + HIWORD(GetAsyncKeyState(VK_LWIN)) || HIWORD(GetAsyncKeyState(VK_RWIN)), + } + } }; - Event event; { - event.type = "window:Key"; - event.invoker = "window"; - event.key.state = -1; - event.key.code = "NULL"; - event.key.raw = 0; - event.key.async = true; - event.key.modifier = { - .alt = HIWORD(GetAsyncKeyState(VK_MENU)) != 0, - .ctrl = HIWORD(GetAsyncKeyState(VK_CONTROL)) != 0, - .shift = HIWORD(GetAsyncKeyState(VK_SHIFT)) != 0, - .sys = HIWORD(GetAsyncKeyState(VK_LWIN)) || HIWORD(GetAsyncKeyState(VK_RWIN)), - }; + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type + "." + ((event.key.state == -1)?"Pressed":"Released"); + json["invoker"] = event.invoker; + json["key"]["code"] = ""; + json["key"]["raw"] = 0; + json["key"]["state"] = (event.key.state == -1) ? "Down" : "Up"; + json["key"]["async"] = event.key.async; + json["key"]["modifier"]["alt"] = event.key.modifier.alt; + json["key"]["modifier"]["control"] = event.key.modifier.ctrl; + json["key"]["modifier"]["shift"] = event.key.modifier.shift; + json["key"]["modifier"]["system"] = event.key.modifier.sys; + #endif + for ( auto& key : keys ) { + const auto code = GetKeyName(key); + event.key.code = code; + event.key.raw = key; + + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + this->pushEvent(event.type + "." + code, event); + #endif + #if UF_USE_JSON + json["key"]["code"] = code; + json["key"]["raw"] = key; + this->pushEvent(event.type, json); + this->pushEvent(event.type + "." + code, json); + #endif } + #if 0 /* Readable (JSON) + Optimal (Userdata) event */ { uf::Serializer json; /* Set up JSON data*/ { @@ -830,6 +846,7 @@ void UF_API_CALL spec::win32::Window::processEvents() { } } } + #endif } } bool UF_API_CALL spec::win32::Window::pollEvents( bool block ) { @@ -843,32 +860,16 @@ bool UF_API_CALL spec::win32::Window::pollEvents( bool block ) { auto& event = this->m_events.front(); if ( event.payload.is() ) { ext::json::Value payload = uf::Serializer( event.payload.as() ); - // std::cout << event.name << " (string)\t" << payload << std::endl; - uf::hooks.call( "window:Event", payload ); uf::hooks.call( event.name, payload ); } else if ( event.payload.is() ) { uf::Serializer& payload = event.payload.as(); - // std::cout << event.name << " (serializer)\t" << payload << std::endl; - uf::hooks.call( "window:Event", payload ); uf::hooks.call( event.name, payload ); } else if ( event.payload.is() ) { ext::json::Value& payload = event.payload.as(); - // std::cout << event.name << " (json)\t" << payload << std::endl; - uf::hooks.call( "window:Event", payload ); uf::hooks.call( event.name, payload ); } else { - // std::cout << event.name << "(???)" << std::endl; - uf::hooks.call( "window:Event", event.payload ); uf::hooks.call( event.name, event.payload ); } - /* - try { - uf::hooks.call( "window:Event", payload ); - uf::hooks.call( event.name, payload ); - } catch ( ... ) { - // Let the hook handler handle the exceptions - } - */ this->m_events.pop(); } return true; @@ -938,12 +939,13 @@ void UF_API_CALL spec::win32::Window::registerWindowClass() { void UF_API_CALL spec::win32::Window::processEvent(UINT message, WPARAM wParam, LPARAM lParam) { if (!this->m_handle) return; - uf::Serializer json; std::string hook = "window:Unknown"; std::string serialized = ""; std::stringstream serializer; bool labelAsDelta = true; + uf::Serializer json; + switch (message) { case WM_DESTROY: this->terminate(); @@ -952,54 +954,40 @@ void UF_API_CALL spec::win32::Window::processEvent(UINT message, WPARAM wParam, if (LOWORD(lParam) == HTCLIENT) SetCursor(this->m_cursor); break; case WM_CLOSE: { - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; + pod::payloads::windowEvent event{ + "window:Closed", + "os", }; - Event event; { - event.type = "window:Closed"; - event.invoker = "os"; - }; - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + #endif + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type; + json["invoker"] = event.invoker; + this->pushEvent(event.type, json); #endif - { - json["type"] = event.type; - json["invoker"] = event.invoker; - this->pushEvent(event.type, json); - } } break; case WM_SIZE: { - if (wParam != SIZE_MINIMIZED && !this->m_resizing && this->m_lastSize != getSize()) { - this->m_lastSize = this->getSize(); + if (wParam == SIZE_MINIMIZED || this->m_resizing || this->m_lastSize == getSize()) break; + this->m_lastSize = this->getSize(); - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; - - struct { - pod::Vector2i size; - } window; - }; - Event event; { - event.type = "window:Resized"; - event.invoker = "os"; - event.window.size = this->m_lastSize; - }; - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); - #endif - { - json["type"] = event.type; - json["invoker"] = event.invoker; - json["window"]["size"] = uf::vector::encode(event.window.size); - // json["window"]["size"]["x"] = event.window.size.x; - // json["window"]["size"]["y"] = event.window.size.y; - this->pushEvent(event.type, json); - } - - this->grabMouse(this->m_mouseGrabbed); - } + pod::payloads::windowResized event{ + "window:Resized", + "os", + { this->m_lastSize }, + }; + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + #endif + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type; + json["invoker"] = event.invoker; + json["window"]["size"] = uf::vector::encode(event.window.size); + this->pushEvent(event.type, json); + #endif + this->grabMouse(this->m_mouseGrabbed); } break; case WM_ENTERSIZEMOVE: { this->m_resizing = true; @@ -1007,50 +995,38 @@ void UF_API_CALL spec::win32::Window::processEvent(UINT message, WPARAM wParam, } break; case WM_EXITSIZEMOVE:{ this->m_resizing = false; - if(this->m_lastSize != this->getSize()) { + if( this->m_lastSize != this->getSize() ) { this->m_lastSize = this->getSize(); - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; - - struct { - pod::Vector2i size; - } window; + pod::payloads::windowResized event = { + "window:Resized", + "os", + { this->m_lastSize }, }; - Event event; { - event.type = "window:Resized"; - event.invoker = "os"; - event.window.size = this->m_lastSize; - }; - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + #endif + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type; + json["invoker"] = event.invoker; + json["window"]["size"] = uf::vector::encode(event.window.size); + this->pushEvent(event.type, json); #endif - { - json["type"] = event.type; - json["invoker"] = event.invoker; - json["window"]["size"] = uf::vector::encode(event.window.size); - // json["window"]["size"]["x"] = event.window.size.x; - // json["window"]["size"]["y"] = event.window.size.y; - this->pushEvent(event.type, json); - } } else { - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; + pod::payloads::windowEvent event{ + "window:Moved", + "os", }; - Event event; { - event.type = "window:Moved"; - event.invoker = "os"; - }; - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + #endif + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type; + json["invoker"] = event.invoker; + this->pushEvent(event.type, json); #endif - { - json["type"] = event.type; - json["invoker"] = event.invoker; - this->pushEvent(event.type, json); - } } this->grabMouse(this->m_mouseGrabbed); } break; @@ -1069,35 +1045,27 @@ void UF_API_CALL spec::win32::Window::processEvent(UINT message, WPARAM wParam, this->grabMouse(this->m_mouseGrabbed); SetCursor(this->m_cursor); } - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; - - struct { - int state = 0; - } window; + pod::payloads::windowFocusedChanged event{ + "window:Focus.Changed", + "os", }; - Event event; { - event.type = "window:Focus.Changed"; - event.invoker = "os"; - - switch ( message ) { - case WM_SETFOCUS: event.window.state = 1; break; - case WM_KILLFOCUS: event.window.state = -1; break; - } - }; - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); - #endif - { - json["type"] = event.type; - json["invoker"] = event.invoker; - switch ( message ) { - case WM_SETFOCUS: json["window"]["state"] = "Gained"; break; - case WM_KILLFOCUS: json["window"]["state"] = "Lost"; break; - } - this->pushEvent(event.type, json); + switch ( message ) { + case WM_SETFOCUS: event.window.state = 1; break; + case WM_KILLFOCUS: event.window.state = -1; break; } + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + #endif + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type; + json["invoker"] = event.invoker; + switch ( message ) { + case WM_SETFOCUS: json["window"]["state"] = "Gained"; break; + case WM_KILLFOCUS: json["window"]["state"] = "Lost"; break; + } + this->pushEvent(event.type, json); + #endif } break; // Text event case WM_CHAR: if ( /*true ||*/ this->m_syncParse ) { @@ -1120,36 +1088,26 @@ void UF_API_CALL spec::win32::Window::processEvent(UINT message, WPARAM wParam, std::basic_string utf32; utf32+=character; std::basic_string utf8; utf8.reserve(utf32.length()); uf::Utf32::toUtf8(utf32.begin(), utf32.end(), std::back_inserter(utf8)); - - std::stringstream to_hex; - to_hex << std::hex << character; - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; - - struct { - uint32_t utf32; - std::string unicode; - } text; + pod::payloads::windowTextEntered event{ + "window:Text.Entered", + "os", + { + character, + std::string(utf8.begin(), utf8.end()), + } }; - Event event; { - event.type = "window:Text.Entered"; - event.invoker = "os"; - - event.text.utf32 = character; - event.text.unicode = std::string(utf8.begin(), utf8.end()); - }; - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); + #if UF_USE_USERDATA + this->pushEvent(event.type, event); #endif - + #if UF_USE_JSON + uf::Serializer json; json["type"] = event.type; json["invoker"] = event.invoker; - json["text"]["uint32_t"] = event.text.utf32; - json["text"]["unicode"] = std::string(utf8.begin(), utf8.end()); + json["text"]["unicode"] = event.text.unicode; this->pushEvent(event.type, json); + #endif } } } break; @@ -1158,71 +1116,51 @@ void UF_API_CALL spec::win32::Window::processEvent(UINT message, WPARAM wParam, case WM_KEYUP: case WM_SYSKEYUP: if ( /*true ||*/ this->m_syncParse ) { if (this->m_keyRepeatEnabled || ((HIWORD(lParam) & KF_REPEAT) == 0)) { - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; + int_fast8_t state = 0; + switch ( message ) { + case WM_KEYDOWN: + case WM_SYSKEYDOWN: state = -1; break; - struct { - int state = -1; - std::string code; - uint32_t raw; - bool async; - - struct { - bool alt; - bool ctrl; - bool shift; - bool sys; - } modifier; - } key; - }; - Event event; { - event.type = "window:Key", - event.invoker = "window", - event.key.code = this->getKey(wParam, lParam), - event.key.raw = wParam, - event.key.async = false, - event.key.modifier = { - .alt = HIWORD(GetAsyncKeyState(VK_MENU)) != 0, - .ctrl = HIWORD(GetAsyncKeyState(VK_CONTROL)) != 0, - .shift = HIWORD(GetAsyncKeyState(VK_SHIFT)) != 0, - .sys = HIWORD(GetAsyncKeyState(VK_LWIN)) || HIWORD(GetAsyncKeyState(VK_RWIN)), - }; - switch ( message ) { - case WM_KEYDOWN: - case WM_SYSKEYDOWN: event.key.state = -1; break; - - case WM_KEYUP: - case WM_SYSKEYUP: event.key.state = 1; break; - } + case WM_KEYUP: + case WM_SYSKEYUP: state = 1; break; } - // if ( USE_OPTIMAL ) this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); - // if ( USE_OPTIMAL ) this->pushEvent(event.type + "." + event.key.code, uf::Userdata(uf::userdata::create(event))); - json["type"] = event.type + "." + ((event.key.state == -1)?"Pressed":"Released"); - json["invoker"] = event.invoker; - json["key"]["state"] = (event.key.state == -1) ? "Down" : "Up"; - json["key"]["async"] = event.key.async; - json["key"]["modifier"]["alt"] = event.key.modifier.alt; - json["key"]["modifier"]["control"] = event.key.modifier.ctrl; - json["key"]["modifier"]["shift"] = event.key.modifier.shift; - json["key"]["modifier"]["system"] = event.key.modifier.sys; - - json["key"]["code"] = event.key.code; - json["key"]["raw"] = event.key.raw; - json["key"]["lparam"] = lParam; - - // don't know why things dont like things - /* - if (event.key.state == -1) { - uf::hooks.call(event.type, json); - uf::hooks.call(event.type + "." + event.key.code, json); - } else { + pod::payloads::windowKey event{ + "window:Key", + "os", + { + this->getKey(wParam, lParam), + wParam, + state, + false, + { + .alt = HIWORD(GetAsyncKeyState(VK_MENU)) != 0, + .ctrl = HIWORD(GetAsyncKeyState(VK_CONTROL)) != 0, + .shift = HIWORD(GetAsyncKeyState(VK_SHIFT)) != 0, + .sys = HIWORD(GetAsyncKeyState(VK_LWIN)) || HIWORD(GetAsyncKeyState(VK_RWIN)), + } + } + }; + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + this->pushEvent(event.type + "." + event.key.code, event); + #endif + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type + "." + ((event.key.state == -1)?"Pressed":"Released"); + json["invoker"] = event.invoker; + json["key"]["state"] = (event.key.state == -1) ? "Down" : "Up"; + json["key"]["async"] = event.key.async; + json["key"]["modifier"]["alt"] = event.key.modifier.alt; + json["key"]["modifier"]["control"] = event.key.modifier.ctrl; + json["key"]["modifier"]["shift"] = event.key.modifier.shift; + json["key"]["modifier"]["system"] = event.key.modifier.sys; + + json["key"]["code"] = event.key.code; + json["key"]["raw"] = event.key.raw; + json["key"]["lparam"] = lParam; this->pushEvent(event.type, json); this->pushEvent(event.type + "." + event.key.code, json); - } - */ - this->pushEvent(event.type, json); - this->pushEvent(event.type + "." + event.key.code, json); + #endif } } break; case WM_MOUSEWHEEL: { @@ -1232,38 +1170,25 @@ void UF_API_CALL spec::win32::Window::processEvent(UINT message, WPARAM wParam, ScreenToClient(this->m_handle, &position); int16_t delta = static_cast(HIWORD(wParam)); - - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; - - struct { - pod::Vector2ui position = {}; - float delta = 0; - } mouse; + pod::payloads::windowMouseWheel event{ + "window:Mouse.Wheel", + "os", + { + pod::Vector2ui{ position.x, position.y }, + delta, + } }; - Event event; { - event.type = "window:Mouse.Wheel"; - event.invoker = "os"; - - event.mouse.position.x = position.x; - event.mouse.position.y = position.y; - event.mouse.delta = delta; // 120.0f; - }; - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + #endif + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type; + json["invoker"] = event.invoker; + json["mouse"]["position"] = uf::vector::encode(event.mouse.position); + json["mouse"]["delta"] = event.mouse.delta; + this->pushEvent(event.type, json); #endif - { - json["type"] = event.type; - json["invoker"] = event.invoker; - - json["mouse"]["position"] = uf::vector::encode(event.mouse.position); - // json["mouse"]["position"]["x"] = event.mouse.position.x; - // json["mouse"]["position"]["y"] = event.mouse.position.y; - json["mouse"]["delta"] = event.mouse.delta; - - this->pushEvent(event.type, json); - } } break; case WM_LBUTTONDOWN: case WM_LBUTTONUP: @@ -1274,187 +1199,90 @@ void UF_API_CALL spec::win32::Window::processEvent(UINT message, WPARAM wParam, case WM_XBUTTONDOWN: case WM_XBUTTONUP: if ( true || this->m_syncParse ) { static pod::Vector2i lastPosition = {}; - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; + + const pod::Vector2i currentPosition = pod::Vector2ui{ static_cast(LOWORD(lParam)), static_cast(HIWORD(lParam)) }; + std::string button = ""; + int_fast8_t state = 0; - struct { - pod::Vector2i position = {}; - pod::Vector2i delta = lastPosition; - std::string button = "???"; - int state = 0; - } mouse; - }; - Event event; { - event.type = "window:Mouse.Click"; - event.invoker = "os"; + switch ( message ) { + case WM_LBUTTONDOWN: + case WM_LBUTTONUP: button = "Left"; break; + + case WM_RBUTTONDOWN: + case WM_RBUTTONUP: button = "Right"; break; + + case WM_MBUTTONDOWN: + case WM_MBUTTONUP: button = "Middle"; break; + + case WM_XBUTTONDOWN: + case WM_XBUTTONUP: button = "Aux"; break; - // event.mouse.position = this->getMousePosition(); - event.mouse.position.x = static_cast(LOWORD(lParam)); - event.mouse.position.y = static_cast(HIWORD(lParam)); - event.mouse.delta = event.mouse.position - lastPosition; - switch ( message ) { - case WM_LBUTTONDOWN: - case WM_LBUTTONUP: event.mouse.button = "Left"; break; - - case WM_RBUTTONDOWN: - case WM_RBUTTONUP: event.mouse.button = "Right"; break; - - case WM_MBUTTONDOWN: - case WM_MBUTTONUP: event.mouse.button = "Middle"; break; - - case WM_XBUTTONDOWN: - case WM_XBUTTONUP: event.mouse.button = "Aux"; break; - - default: event.mouse.button = "???"; break; - } - switch ( message ) { - case WM_LBUTTONUP: - case WM_RBUTTONUP: - case WM_MBUTTONUP: - case WM_XBUTTONUP: event.mouse.state = 1; break; - - case WM_LBUTTONDOWN: - case WM_RBUTTONDOWN: - case WM_MBUTTONDOWN: - case WM_XBUTTONDOWN: event.mouse.state = -1; break; - default: event.mouse.state = 0; break; - } - }; - if ( true || this->m_syncParse ){ - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); - #endif - json["type"] = event.type; - json["invoker"] = event.invoker; - - json["mouse"]["position"] = uf::vector::encode(event.mouse.position); - json["mouse"]["delta"] = uf::vector::encode(event.mouse.delta); - // json["mouse"]["position"]["x"] = event.mouse.position.x; - // json["mouse"]["position"]["y"] = event.mouse.position.y; - // json["mouse"]["delta"]["x"] = event.mouse.delta.x; - // json["mouse"]["delta"]["y"] = event.mouse.delta.y; - json["mouse"]["button"] = event.mouse.button; - switch (event.mouse.state) { - case 1: - json["mouse"]["state"] = "Up"; - break; - case -1: - json["mouse"]["state"] = "Down"; - break; - default: - json["mouse"]["state"] = "???"; - break; - } - - this->pushEvent(event.type, json); + default: button = "???"; break; } - lastPosition = event.mouse.position; //this->getMousePosition(); + switch ( message ) { + case WM_LBUTTONUP: + case WM_RBUTTONUP: + case WM_MBUTTONUP: + case WM_XBUTTONUP: state = 1; break; + + case WM_LBUTTONDOWN: + case WM_RBUTTONDOWN: + case WM_MBUTTONDOWN: + case WM_XBUTTONDOWN: state = -1; break; + default: state = 0; break; + } + pod::payloads::windowMouseClick event{ + "window:Mouse.Click", + "os", + { + currentPosition, + currentPosition - lastPosition, + button, + state + } + }; + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + #endif + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type; + json["invoker"] = event.invoker; + json["mouse"]["position"] = uf::vector::encode(event.mouse.position); + json["mouse"]["delta"] = uf::vector::encode(event.mouse.delta); + json["mouse"]["button"] = event.mouse.button; + switch (event.mouse.state) { + case 1: json["mouse"]["state"] = "Up"; break; + case -1: json["mouse"]["state"] = "Down"; break; + } + this->pushEvent(event.type, json); + #endif + + lastPosition = currentPosition; } break; case WM_MOUSELEAVE: - if (this->m_mouseInside) { + if ( this->m_mouseInside ) { this->m_mouseInside = false; - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; - - struct { - int state = 0; - } mouse; - }; - Event event; { - event.type = "window:Mouse.Moved"; - event.invoker = "os"; - - event.mouse.state = -1; - }; - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); - #endif - { - json["type"] = event.type; - json["invoker"] = event.invoker; - - switch (event.mouse.state) { - case 1: - json["mouse"]["state"] = "Entered"; - break; - case -1: - json["mouse"]["state"] = "Left"; - break; - default: - json["mouse"]["state"] = "???"; - break; + pod::payloads::windowMouseMoved event{ + "window:Mouse.Moved", + "os", + { + {} + }, + { + {}, + {}, + -1 } - this->pushEvent(event.type, json); - } - } - break; - case WM_MOUSEMOVE: { - static pod::Vector2i lastPosition = {}; - struct Event { - std::string type = "unknown"; - std::string invoker = "???"; - - struct { - int state = 0; - pod::Vector2i position; - pod::Vector2i delta; - pod::Vector2i size; - } mouse; - }; - Event event; { - event.type = "window:Mouse.Moved"; - event.invoker = "os"; - }; - - int x = static_cast(LOWORD(lParam)); - int y = static_cast(HIWORD(lParam)); - RECT area; - GetClientRect(this->m_handle, &area); - if ((wParam & (MK_LBUTTON | MK_MBUTTON | MK_RBUTTON | MK_XBUTTON1 | MK_XBUTTON2)) == 0) { - if (GetCapture() == this->m_handle) ReleaseCapture(); - } - else if (GetCapture() != this->m_handle) { - SetCapture(this->m_handle); - } - - if ((x < area.left) || (x > area.right) || (y < area.top) || (y > area.bottom)) { - if (this->m_mouseInside) { - this->m_mouseInside = false; - this->setTracking(false); - event.mouse.state = -1; - } - } else { - if (!this->m_mouseInside) { - this->m_mouseInside = true; - this->setTracking(true); - event.mouse.state = 1; - } - } - { - event.mouse.position.x = x; - event.mouse.position.y = y; - event.mouse.size = {area.right, area.bottom}; - event.mouse.delta = event.mouse.position - lastPosition; - } - #if USE_OPTIMAL - this->pushEvent(event.type, uf::Userdata(uf::userdata::create(event))); - #endif - { + }; + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + #endif + #if UF_USE_JSON + uf::Serializer json; json["type"] = event.type; json["invoker"] = event.invoker; - - // json["mouse"]["position"]["x"] = event.mouse.position.x; - // json["mouse"]["position"]["y"] = event.mouse.position.y; - // json["mouse"]["delta"]["x"] = event.mouse.delta.x; - // json["mouse"]["delta"]["y"] = event.mouse.delta.y; - // json["mouse"]["size"]["x"] = event.mouse.size.x; - // json["mouse"]["size"]["y"] = event.mouse.size.y; - json["mouse"]["position"] = uf::vector::encode(event.mouse.position); - json["mouse"]["delta"] = uf::vector::encode(event.mouse.delta); - json["mouse"]["size"] = uf::vector::encode(event.mouse.size); switch (event.mouse.state) { case 1: json["mouse"]["state"] = "Entered"; @@ -1467,8 +1295,78 @@ void UF_API_CALL spec::win32::Window::processEvent(UINT message, WPARAM wParam, break; } this->pushEvent(event.type, json); + #endif } - lastPosition = event.mouse.position; //this->getMousePosition(); + break; + case WM_MOUSEMOVE: { + static pod::Vector2i lastPosition = {}; + const pod::Vector2i currentPosition = { + static_cast(LOWORD(lParam)), + static_cast(HIWORD(lParam)), + }; + RECT area; + GetClientRect(this->m_handle, &area); + if ((wParam & (MK_LBUTTON | MK_MBUTTON | MK_RBUTTON | MK_XBUTTON1 | MK_XBUTTON2)) == 0) { + if (GetCapture() == this->m_handle) ReleaseCapture(); + } + else if (GetCapture() != this->m_handle) { + SetCapture(this->m_handle); + } + + int_fast8_t state{}; + if ((currentPosition.x < area.left) || (currentPosition.x > area.right) || (currentPosition.y < area.top) || (currentPosition.y > area.bottom)) { + if ( this->m_mouseInside ) { + this->m_mouseInside = false; + this->setTracking(false); + state = -1; + } + } else { + if ( !this->m_mouseInside ) { + this->m_mouseInside = true; + this->setTracking(true); + state = 1; + } + } + + pod::payloads::windowMouseMoved event{ + "window:Mouse.Moved", + "os", + { + pod::Vector2ui{ area.right, area.bottom }, + }, + { + currentPosition, + currentPosition - lastPosition, + state + } + }; + #if UF_USE_USERDATA + this->pushEvent(event.type, event); + #endif + #if UF_USE_JSON + uf::Serializer json; + json["type"] = event.type; + json["invoker"] = event.invoker; + + json["window"]["size"] = uf::vector::encode(event.window.size); + + json["mouse"]["position"] = uf::vector::encode(event.mouse.position); + json["mouse"]["delta"] = uf::vector::encode(event.mouse.delta); + switch (event.mouse.state) { + case 1: + json["mouse"]["state"] = "Entered"; + break; + case -1: + json["mouse"]["state"] = "Left"; + break; + default: + json["mouse"]["state"] = "???"; + break; + } + this->pushEvent(event.type, json); + #endif + + lastPosition = currentPosition; break; } } diff --git a/ext/behaviors/player/behavior.cpp b/ext/behaviors/player/behavior.cpp index 1225030e..63ee5232 100644 --- a/ext/behaviors/player/behavior.cpp +++ b/ext/behaviors/player/behavior.cpp @@ -5,6 +5,7 @@ #include #include #include +#include #include #include #include @@ -13,18 +14,6 @@ #include #include -namespace pod { - namespace payloads { - struct windowMouseMoved { - std::string invoker = ""; - pod::Vector2i delta; - pod::Vector2ui position; - pod::Vector2ui size; - int_fast8_t state; - }; - } -} - #include UF_BEHAVIOR_REGISTER_CPP(ext::PlayerBehavior) #define this (&self) @@ -111,26 +100,20 @@ void ext::PlayerBehavior::initialize( uf::Object& self ) { } metadataJson["system"]["control"] = true; this->addHook( "window:Mouse.CursorVisibility", [&](ext::json::Value& json){ - // metadataJson["system"]["control"] = !json["state"].as(); metadata.system.control = !json["state"].as(); }); // Rotate Camera this->addHook( "window:Mouse.Moved", [&](pod::payloads::windowMouseMoved& payload ){ - pod::Vector2 relta = { (float) payload.delta.x / payload.size.x, (float) payload.delta.y / payload.size.y }; - relta *= 2; - if ( (payload.delta.x == 0 && payload.delta.y == 0) || !metadata.system.control ) return; + float sensitivity = 2; + pod::Vector2 relta = { (float) sensitivity * payload.mouse.delta.x / payload.window.size.x, (float) sensitivity * payload.mouse.delta.y / payload.window.size.y }; + if ( (payload.mouse.delta.x == 0 && payload.mouse.delta.y == 0) || !metadata.system.control ) return; bool updateCamera = false; - if ( payload.delta.x != 0 ) { - double current, minima, maxima; { - current = !ext::json::isNull( metadataJson["camera"]["limit"]["current"][0] ) ? metadataJson["camera"]["limit"]["current"][0].as() : NAN; - minima = !ext::json::isNull( metadataJson["camera"]["limit"]["minima"][0] ) ? metadataJson["camera"]["limit"]["minima"][0].as() : NAN; - maxima = !ext::json::isNull( metadataJson["camera"]["limit"]["maxima"][0] ) ? metadataJson["camera"]["limit"]["maxima"][0].as() : NAN; - } - if ( metadataJson["camera"]["invert"][0].as() ) relta.x *= -1; - current += relta.x; - if ( current != current || ( current < maxima && current > minima ) ) { + if ( payload.mouse.delta.x != 0 ) { + if ( metadata.camera.invert.x ) relta.x *= -1; + metadata.camera.limit.current.x += relta.x; + if ( metadata.camera.limit.current.x != metadata.camera.limit.current.x || ( metadata.camera.limit.current.x < metadata.camera.limit.max.x && metadata.camera.limit.current.x > metadata.camera.limit.min.x ) ) { if ( collider.body && !collider.shared ) { #if UF_USE_BULLET ext::bullet::applyRotation( collider, transform.up, relta.x ); @@ -138,27 +121,19 @@ void ext::PlayerBehavior::initialize( uf::Object& self ) { } else { uf::transform::rotate( transform, transform.up, relta.x ), updateCamera = true; } - } else current -= relta.x; - - if ( !ext::json::isNull( metadataJson["camera"]["limit"]["current"][0] ) ) metadataJson["camera"]["limit"]["current"][0] = current; + } else metadata.camera.limit.current.x -= relta.x; } - if ( payload.delta.y != 0 ) { - double current, minima, maxima; { - current = !ext::json::isNull( metadataJson["camera"]["limit"]["current"][1] ) ? metadataJson["camera"]["limit"]["current"][1].as() : NAN; - minima = !ext::json::isNull( metadataJson["camera"]["limit"]["minima"][1] ) ? metadataJson["camera"]["limit"]["minima"][1].as() : NAN; - maxima = !ext::json::isNull( metadataJson["camera"]["limit"]["maxima"][1] ) ? metadataJson["camera"]["limit"]["maxima"][1].as() : NAN; - } - if ( metadataJson["camera"]["invert"][1].as() ) relta.y *= -1; - current += relta.y; - if ( current != current || ( current < maxima && current > minima ) ) { + if ( payload.mouse.delta.y != 0 ) { + if ( metadata.camera.invert.y ) relta.y *= -1; + metadata.camera.limit.current.y += relta.y; + if ( metadata.camera.limit.current.y != metadata.camera.limit.current.y || ( metadata.camera.limit.current.y < metadata.camera.limit.max.y && metadata.camera.limit.current.y > metadata.camera.limit.min.y ) ) { // if ( collider.body && !collider.shared ) { // ext::bullet::applyRotation( collider, cameraTransform.right, relta.y ); // } else { uf::transform::rotate( cameraTransform, cameraTransform.right, relta.y ); // } updateCamera = true; - } else current -= relta.y; - if ( !ext::json::isNull( metadataJson["camera"]["limit"]["current"][1] ) ) metadataJson["camera"]["limit"]["current"][1] = current; + } else metadata.camera.limit.current.y -= relta.y; } if ( updateCamera ) camera.updateView(); }); @@ -259,6 +234,8 @@ void ext::PlayerBehavior::initialize( uf::Object& self ) { auto& metadataSystem = metadataJson["system"]; auto& metadataSystemPhysics = metadataSystem["physics"]; auto& metadataAudioFootstep = metadataJson["audio"]["footstep"]; + auto& metadataCamera = metadataJson["camera"]; + auto& metadataCameraLimit = metadataCamera["limit"]; metadataSystem["menu"] = metadata.system.menu; metadataSystem["control"] = metadata.system.control; @@ -274,11 +251,17 @@ void ext::PlayerBehavior::initialize( uf::Object& self ) { metadataSystemPhysics["crouch"] = metadata.system.physics.crouch; metadataAudioFootstep["list"] = metadata.audio.footstep.list; metadataAudioFootstep["volume"] = metadata.audio.footstep.volume; + metadataCamera["invert"] = uf::vector::encode(metadata.camera.invert); + metadataCameraLimit["current"] = uf::vector::encode(metadata.camera.limit.current); + metadataCameraLimit["minima"] = uf::vector::encode(metadata.camera.limit.min); + metadataCameraLimit["maxima"] = uf::vector::encode(metadata.camera.limit.max); }; metadata.deserialize = [&](){ auto& metadataSystem = metadataJson["system"]; auto& metadataAudioFootstep = metadataJson["audio"]["footstep"]; auto& metadataSystemPhysics = metadataSystem["physics"]; + auto& metadataCamera = metadataJson["camera"]; + auto& metadataCameraLimit = metadataCamera["limit"]; metadata.system.menu = metadataSystem["menu"].as(); metadata.system.control = metadataSystem["control"].as(); @@ -296,6 +279,15 @@ void ext::PlayerBehavior::initialize( uf::Object& self ) { metadata.audio.footstep.list.emplace_back(value); }); metadata.audio.footstep.volume = metadataAudioFootstep["volume"].as(); + + metadata.camera.invert = uf::vector::decode( metadataCamera["invert"], pod::Vector3t{false, false, false} ); + metadata.camera.limit.current = uf::vector::decode( metadataCameraLimit["current"], pod::Vector3f{NAN, NAN, NAN} ); + metadata.camera.limit.min = uf::vector::decode( metadataCameraLimit["minima"], pod::Vector3f{NAN, NAN, NAN} ); + metadata.camera.limit.max = uf::vector::decode( metadataCameraLimit["maxima"], pod::Vector3f{NAN, NAN, NAN} ); + + // for ( uint_fast8_t i = 0; i < 3; ++i ) metadata.camera.limit.current[i] = metadataCameraLimit["current"][i].as(NAN); + // for ( uint_fast8_t i = 0; i < 3; ++i ) metadata.camera.limit.min[i] = metadataCameraLimit["minima"][i].as(NAN); + // for ( uint_fast8_t i = 0; i < 3; ++i ) metadata.camera.limit.max[i] = metadataCameraLimit["maxima"][i].as(NAN); }; this->addHook( "object:UpdateMetadata.%UID%", metadata.deserialize); metadata.deserialize(); diff --git a/ext/behaviors/player/behavior.h b/ext/behaviors/player/behavior.h index 855dc357..cfcacaec 100644 --- a/ext/behaviors/player/behavior.h +++ b/ext/behaviors/player/behavior.h @@ -26,11 +26,20 @@ namespace ext { float walk = 1.0f; pod::Vector3f jump = {0,8,0}; } physics; + bool control = true; std::string menu = ""; bool crouching = false; bool noclipped = false; } system; + struct { + struct { + pod::Vector3f current = {NAN, NAN, NAN}; + pod::Vector3f min = {NAN, NAN, NAN}; + pod::Vector3f max = {NAN, NAN, NAN}; + } limit; + pod::Vector3t invert; + } camera; struct { struct { std::vector list; diff --git a/ext/gui/behavior.cpp b/ext/gui/behavior.cpp index ddf3e0f3..c18f0dab 100644 --- a/ext/gui/behavior.cpp +++ b/ext/gui/behavior.cpp @@ -31,18 +31,6 @@ #include -namespace pod { - namespace payloads { - struct windowMouseMoved { - std::string invoker = ""; - pod::Vector2i delta; - pod::Vector2ui position; - pod::Vector2ui size; - int_fast8_t state; - }; - } -} - namespace { #if UF_USE_FREETYPE struct { @@ -555,51 +543,6 @@ void ext::GuiBehavior::initialize( uf::Object& self ) { if ( metadataJson["system"]["hoverable"].as() ) { uf::Timer hoverTimer(false); hoverTimer.start( uf::Time<>(-1000000) ); - #if 1 - this->addHook( "window:Mouse.Moved", [&]( pod::payloads::windowMouseMoved& payload ){ - if ( ext::json::isObject( metadataJson["events"]["hover"] ) ) { - uf::Serializer event = metadataJson["events"]["hover"]; - metadataJson["events"]["hover"] = ext::json::array(); //Json::arrayValue; - metadataJson["events"]["hover"][0] = event; - } else if ( !ext::json::isArray( metadataJson["events"]["hover"] ) ) { - this->getParent().as().callHook("gui:Clicked.%UID%", payload ); - return; - } - for ( int i = 0; i < metadataJson["events"]["hover"].size(); ++i ) { - uf::Serializer event = metadataJson["events"]["hover"][i]; - uf::Serializer payload = event["payload"]; - float delay = event["delay"].as(); - if ( event["delay"].is() ) this->queueHook(event["name"].as(), payload, event["delay"].as()); - else this->callHook(event["name"].as(), payload ); - } - return; - }); - this->addHook( "window:Mouse.Moved", [&]( pod::payloads::windowMouseMoved& payload ){ - if ( this->getUid() == 0 || !this->hasComponent() || metadata.world || (!metadata.box.min && !metadata.box.max) ) return; - - bool clicked = false; - bool down = payload.state < 0; - pod::Vector2f click; { - click.x = (float) payload.position.x / (float) ext::gui::size.current.x; - click.y = (float) payload.position.y / (float) ext::gui::size.current.y; - - click.x = (click.x * 2.0f) - 1.0f; - click.y = (click.y * 2.0f) - 1.0f; - float x = click.x; - float y = click.y; - - clicked = ( metadata.box.min.x <= x && metadata.box.min.y <= y && metadata.box.max.x >= x && metadata.box.max.y >= y ); - } - metadata.hovered = clicked; - metadataJson["hovered"] = clicked; - - if ( clicked && hoverTimer.elapsed().asDouble() >= 1 ) { - hoverTimer.reset(); - this->callHook("gui:Hovered.%UID%", payload); - } - this->callHook("gui:Mouse.Moved.%UID%", payload); - }); - #else this->addHook( "gui:Hovered.%UID%", [&](ext::json::Value& json){ if ( ext::json::isObject( metadataJson["events"]["hover"] ) ) { uf::Serializer event = metadataJson["events"]["hover"]; @@ -628,12 +571,9 @@ void ext::GuiBehavior::initialize( uf::Object& self ) { if ( metadata.world ) return; if ( !metadata.box.min && !metadata.box.max ) return; - bool down = json["mouse"]["state"].as() == "Down"; bool clicked = false; - pod::Vector2ui position = uf::vector::decode( json["mouse"]["position"], pod::Vector2ui{} ); { - // position.x = json["mouse"]["position"]["x"].as() > 0 ? json["mouse"]["position"]["x"].as() : 0; - // position.y = json["mouse"]["position"]["y"].as() > 0 ? json["mouse"]["position"]["y"].as() : 0; - } + bool down = json["mouse"]["state"].as() == "Down"; + pod::Vector2ui position = uf::vector::decode( json["mouse"]["position"], pod::Vector2ui{} ); pod::Vector2f click; { click.x = (float) position.x / (float) ext::gui::size.current.x; click.y = (float) position.y / (float) ext::gui::size.current.y; @@ -654,7 +594,6 @@ void ext::GuiBehavior::initialize( uf::Object& self ) { } this->callHook("gui:Mouse.Moved.%UID%", json); } ); - #endif } #if UF_USE_FREETYPE if ( metadataJson["text settings"]["string"].is() ) {