Input
- Added 'Input' - Added <InputCodes> - The 'MirrorLayer''s ImGuiWindow, "GameView" will not receive/react to input events if the window is not focused
This commit is contained in:
parent
43b2f72ded
commit
aac2c51bd5
8 changed files with 371 additions and 53 deletions
|
@ -11,7 +11,7 @@
|
|||
|
||||
|
||||
// version
|
||||
#define LT_VERSION "0.7.2"
|
||||
#define LT_VERSION "0.7.4"
|
||||
///*** [ CHANGE_LOG ] ***///
|
||||
// --------------------------------------------------------------------
|
||||
// Note: change log starts from 2021-07-21, the starting version is 0.7.0,
|
||||
|
@ -21,6 +21,7 @@
|
|||
// platforms: 'Windows', 'Linux' [+0.2]
|
||||
// --------------------------------------------------------------------
|
||||
//
|
||||
//
|
||||
// 0.7.0: started the change log
|
||||
//
|
||||
// 0.7.1: [ LT_BREAK ]
|
||||
|
@ -30,7 +31,7 @@
|
|||
// - Separated 'FailedAssertion' into 'FailedEngineAssertion' and 'FailedClientAssertion'
|
||||
// - Minor adjustment to the change log
|
||||
//
|
||||
// 0.7.3: [ Layer ]
|
||||
// 0.7.3: [ Layer Improvements ]
|
||||
// - Added 'Layer::OnEvent()', 'Layer' now handles an event by itself and doesn't need another class to determine the event's type
|
||||
//
|
||||
// - Added reverse iterators 'rend()' and 'rbegin()' to 'LayerStack'
|
||||
|
@ -43,9 +44,15 @@
|
|||
//
|
||||
// - Fixed a typo where in 'Mirror' where the name of the 'MirrorLayer' was "SandboxLayer" instead of "MirrorLayer"
|
||||
//
|
||||
// 0.7.4 [ Input ]
|
||||
// - Added 'Input'
|
||||
// - - Added <InputCodes>
|
||||
// - The 'MirrorLayer''s ImGuiWindow, "GameView" will not receive/react to input events if the window is not focused
|
||||
//
|
||||
//
|
||||
///*** [ CHANGE_LOG ] ***///
|
||||
|
||||
// platform
|
||||
// platform
|
||||
#define LT_WIN(x) // windows
|
||||
#define LT_LIN(x) // linux
|
||||
#define LT_MAC(x) // mac
|
||||
|
|
|
@ -110,14 +110,15 @@ namespace Light {
|
|||
m_Window->GetGfxContext()->GetRenderer()->OnWindowResize((const WindowResizedEvent&)event);
|
||||
}
|
||||
|
||||
// user interface
|
||||
// input
|
||||
if (event.HasCategory(InputEventCategory))
|
||||
m_Window->GetGfxContext()->GetUserInterface()->OnInput(event);
|
||||
|
||||
// #todo: add input manager
|
||||
// ...
|
||||
m_Input.OnEvent(event);
|
||||
|
||||
// layers
|
||||
// return if the event is an input event and 'Input' has disabled the game events
|
||||
if (event.HasCategory(InputEventCategory) && !m_Input.IsReceivingGameEvents())
|
||||
return;
|
||||
|
||||
for (auto it = m_LayerStack.rbegin(); it != m_LayerStack.rend(); it++)
|
||||
if ((*it)->OnEvent(event)) return;
|
||||
}
|
||||
|
|
|
@ -6,6 +6,8 @@
|
|||
|
||||
#include "Layer/LayerStack.h"
|
||||
|
||||
#include "Input/Input.h"
|
||||
|
||||
namespace Light {
|
||||
|
||||
class Window;
|
||||
|
@ -18,6 +20,7 @@ namespace Light {
|
|||
private:
|
||||
std::unique_ptr<Instrumentor> m_Instrumentor = nullptr;
|
||||
LayerStack m_LayerStack;
|
||||
Input m_Input;
|
||||
|
||||
protected:
|
||||
std::unique_ptr<Window> m_Window = nullptr;
|
||||
|
|
131
Engine/src/Engine/Input/Input.cpp
Normal file
131
Engine/src/Engine/Input/Input.cpp
Normal file
|
@ -0,0 +1,131 @@
|
|||
#include "ltpch.h"
|
||||
#include "Input.h"
|
||||
|
||||
#include "Events/Event.h"
|
||||
#include "Events/MouseEvents.h"
|
||||
#include "Events/KeyboardEvents.h"
|
||||
|
||||
#include <imgui.h>
|
||||
|
||||
namespace Light {
|
||||
|
||||
Input* Input::s_Context = nullptr;
|
||||
|
||||
Input::Input()
|
||||
{
|
||||
LT_ENGINE_ASSERT(!s_Context, "Input::Input: an instance of 'Input' already exists, do not construct this class!");
|
||||
s_Context = this;
|
||||
|
||||
RestartInputState();
|
||||
}
|
||||
|
||||
void Input::ReceiveUserInterfaceEventsImpl(bool receive, bool toggle /* = false */)
|
||||
{
|
||||
m_UserInterfaceEvents = toggle ? !m_UserInterfaceEvents : receive;
|
||||
}
|
||||
|
||||
void Input::ReceieveGameEventsImpl(bool receive, bool toggle /*= false*/)
|
||||
{
|
||||
bool prev = m_GameEvents;
|
||||
m_GameEvents = toggle ? !m_UserInterfaceEvents : receive;
|
||||
|
||||
if(m_GameEvents != prev)
|
||||
RestartInputState();
|
||||
}
|
||||
|
||||
void Input::RestartInputState()
|
||||
{
|
||||
m_KeyboadKeys.fill(false);
|
||||
m_MouseButtons.fill(false);
|
||||
|
||||
m_MousePosition = glm::vec2(0.0f);
|
||||
m_MouseDelta = glm::vec2(0.0f);
|
||||
m_MouseWheelDelta = 0.0f;
|
||||
}
|
||||
|
||||
void Input::OnEvent(const Event& inputEvent)
|
||||
{
|
||||
ImGuiIO& io = ImGui::GetIO();
|
||||
switch (inputEvent.GetEventType())
|
||||
{
|
||||
//** MOUSE_EVENTS **//
|
||||
case EventType::MouseMoved:
|
||||
{
|
||||
const MouseMovedEvent& event = (const MouseMovedEvent&)inputEvent;
|
||||
|
||||
if (m_GameEvents)
|
||||
{
|
||||
m_MouseDelta = event.GetPosition() - m_MousePosition;
|
||||
m_MousePosition = event.GetPosition();
|
||||
}
|
||||
|
||||
if(m_UserInterfaceEvents)
|
||||
ImGui::GetIO().MousePos = ImVec2(event.GetX(), event.GetY());
|
||||
|
||||
return;
|
||||
}
|
||||
case EventType::ButtonPressed:
|
||||
{
|
||||
const ButtonPressedEvent& event = (const ButtonPressedEvent&)inputEvent;
|
||||
|
||||
if(m_GameEvents)
|
||||
m_MouseButtons[event.GetButton()] = true;
|
||||
|
||||
if (m_UserInterfaceEvents)
|
||||
ImGui::GetIO().MouseDown[event.GetButton()] = true;
|
||||
|
||||
return;
|
||||
}
|
||||
case EventType::ButtonReleased:
|
||||
{
|
||||
const ButtonReleasedEvent& event = (const ButtonReleasedEvent&)inputEvent;
|
||||
|
||||
if (m_GameEvents)
|
||||
m_MouseButtons[event.GetButton()] = false;
|
||||
|
||||
if (m_UserInterfaceEvents)
|
||||
ImGui::GetIO().MouseDown[event.GetButton()] = false;
|
||||
|
||||
return;
|
||||
}
|
||||
case EventType::WheelScrolled:
|
||||
{
|
||||
const WheelScrolledEvent& event = (const WheelScrolledEvent&)inputEvent;
|
||||
|
||||
if (m_GameEvents)
|
||||
m_MouseWheelDelta = event.GetOffset();
|
||||
|
||||
if (m_UserInterfaceEvents)
|
||||
ImGui::GetIO().MouseWheel = event.GetOffset();
|
||||
|
||||
return;
|
||||
}
|
||||
//** MOUSE_EVENTS **//
|
||||
case EventType::KeyPressed:
|
||||
{
|
||||
const KeyPressedEvent& event = (const KeyPressedEvent&)inputEvent;
|
||||
|
||||
if (m_GameEvents)
|
||||
m_KeyboadKeys[event.GetKey()] = true;
|
||||
|
||||
if (m_UserInterfaceEvents)
|
||||
ImGui::GetIO().KeysDown[event.GetKey()] = true;
|
||||
|
||||
return;
|
||||
}
|
||||
case EventType::KeyReleased:
|
||||
{
|
||||
const KeyReleasedEvent& event = (const KeyReleasedEvent&)inputEvent;
|
||||
|
||||
if (m_GameEvents)
|
||||
m_KeyboadKeys[event.GetKey()] = false;
|
||||
|
||||
if (m_UserInterfaceEvents)
|
||||
ImGui::GetIO().KeysDown[event.GetKey()] = false;
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
48
Engine/src/Engine/Input/Input.h
Normal file
48
Engine/src/Engine/Input/Input.h
Normal file
|
@ -0,0 +1,48 @@
|
|||
#pragma once
|
||||
|
||||
#include "Base.h"
|
||||
|
||||
#include <glm/glm.hpp>
|
||||
|
||||
namespace Light {
|
||||
|
||||
class Event;
|
||||
|
||||
class Input
|
||||
{
|
||||
private:
|
||||
static Input* s_Context;
|
||||
|
||||
std::array<bool, 348> m_KeyboadKeys;
|
||||
std::array<bool, 8> m_MouseButtons;
|
||||
|
||||
glm::vec2 m_MousePosition;
|
||||
glm::vec2 m_MouseDelta;
|
||||
float m_MouseWheelDelta;
|
||||
|
||||
bool m_UserInterfaceEvents = true;
|
||||
bool m_GameEvents = true;
|
||||
public:
|
||||
Input();
|
||||
|
||||
static inline void ReceiveUserInterfaceEvents(bool receive, bool toggle = false) { s_Context->ReceiveUserInterfaceEventsImpl(receive, toggle); }
|
||||
static inline void ReceiveGameEvents(bool receive, bool toggle = false) { s_Context->ReceieveGameEventsImpl(receive, toggle); }
|
||||
|
||||
static inline bool GetKeyboardKey(int code) { return s_Context->m_KeyboadKeys[code]; }
|
||||
static inline bool GetMouseButton(int code) { return s_Context->m_MouseButtons[code]; }
|
||||
|
||||
static inline const glm::vec2& GetMousePosition(int code) { return s_Context->m_MousePosition; }
|
||||
|
||||
void OnEvent(const Event& inputEvent);
|
||||
|
||||
inline bool IsReceivingInputEvents() const { return m_UserInterfaceEvents; }
|
||||
inline bool IsReceivingGameEvents() const { return m_GameEvents; }
|
||||
|
||||
private:
|
||||
void ReceiveUserInterfaceEventsImpl(bool receive, bool toggle = false);
|
||||
void ReceieveGameEventsImpl(bool receive, bool toggle = false);
|
||||
|
||||
void RestartInputState();
|
||||
};
|
||||
|
||||
}
|
136
Engine/src/Engine/Input/InputCodes.h
Normal file
136
Engine/src/Engine/Input/InputCodes.h
Normal file
|
@ -0,0 +1,136 @@
|
|||
#pragma once
|
||||
|
||||
#define MOUSE_BUTTON_1 0
|
||||
#define MOUSE_BUTTON_2 1
|
||||
#define MOUSE_BUTTON_3 2
|
||||
#define MOUSE_BUTTON_4 3
|
||||
#define MOUSE_BUTTON_5 4
|
||||
#define MOUSE_BUTTON_6 5
|
||||
#define MOUSE_BUTTON_7 6
|
||||
#define MOUSE_BUTTON_8 7
|
||||
|
||||
#define MOUSE_BUTTON_LEFT MOUSE_BUTTON_1
|
||||
#define MOUSE_BUTTON_RIGHT MOUSE_BUTTON_2
|
||||
#define MOUSE_BUTTON_MIDDLE MOUSE_BUTTON_3
|
||||
|
||||
#define KEY_SPACE 32
|
||||
#define KEY_APOSTROPHE 39 /* ' */
|
||||
#define KEY_COMMA 44 /* , */
|
||||
#define KEY_MINUS 45 /* - */
|
||||
#define KEY_PERIOD 46 /* . */
|
||||
#define KEY_SLASH 47 /* / */
|
||||
#define KEY_0 48
|
||||
#define KEY_1 49
|
||||
#define KEY_2 50
|
||||
#define KEY_3 51
|
||||
#define KEY_4 52
|
||||
#define KEY_5 53
|
||||
#define KEY_6 54
|
||||
#define KEY_7 55
|
||||
#define KEY_8 56
|
||||
#define KEY_9 57
|
||||
#define KEY_SEMICOLON 59 /* ; */
|
||||
#define KEY_EQUAL 61 /* = */
|
||||
#define KEY_A 65
|
||||
#define KEY_B 66
|
||||
#define KEY_C 67
|
||||
#define KEY_D 68
|
||||
#define KEY_E 69
|
||||
#define KEY_F 70
|
||||
#define KEY_G 71
|
||||
#define KEY_H 72
|
||||
#define KEY_I 73
|
||||
#define KEY_J 74
|
||||
#define KEY_K 75
|
||||
#define KEY_L 76
|
||||
#define KEY_M 77
|
||||
#define KEY_N 78
|
||||
#define KEY_O 79
|
||||
#define KEY_P 80
|
||||
#define KEY_Q 81
|
||||
#define KEY_R 82
|
||||
#define KEY_S 83
|
||||
#define KEY_T 84
|
||||
#define KEY_U 85
|
||||
#define KEY_V 86
|
||||
#define KEY_W 87
|
||||
#define KEY_X 88
|
||||
#define KEY_Y 89
|
||||
#define KEY_Z 90
|
||||
#define KEY_LEFT_BRACKET 91 /* [ */
|
||||
#define KEY_BACKSLASH 92 /* \ */
|
||||
#define KEY_RIGHT_BRACKET 93 /* ] */
|
||||
#define KEY_GRAVE_ACCENT 96 /* ` */
|
||||
#define KEY_WORLD_1 161 /* non-US #1 */
|
||||
#define KEY_WORLD_2 162 /* non-US #2 */
|
||||
#define KEY_ESCAPE 256
|
||||
#define KEY_ESC KEY_ESCAPE
|
||||
#define KEY_ENTER 257
|
||||
#define KEY_TAB 258
|
||||
#define KEY_BACKSPACE 259
|
||||
#define KEY_INSERT 260
|
||||
#define KEY_DELETE 261
|
||||
#define KEY_RIGHT 262
|
||||
#define KEY_LEFT 263
|
||||
#define KEY_DOWN 264
|
||||
#define KEY_UP 265
|
||||
#define KEY_PAGE_UP 266
|
||||
#define KEY_PAGE_DOWN 267
|
||||
#define KEY_HOME 268
|
||||
#define KEY_END 269
|
||||
#define KEY_CAPS_LOCK 280
|
||||
#define KEY_SCROLL_LOCK 281
|
||||
#define KEY_NUM_LOCK 282
|
||||
#define KEY_PRINT_SCREEN 283
|
||||
#define KEY_PAUSE 284
|
||||
#define KEY_F1 290
|
||||
#define KEY_F2 291
|
||||
#define KEY_F3 292
|
||||
#define KEY_F4 293
|
||||
#define KEY_F5 294
|
||||
#define KEY_F6 295
|
||||
#define KEY_F7 296
|
||||
#define KEY_F8 297
|
||||
#define KEY_F9 298
|
||||
#define KEY_F10 299
|
||||
#define KEY_F11 300
|
||||
#define KEY_F12 301
|
||||
#define KEY_F13 302
|
||||
#define KEY_F14 303
|
||||
#define KEY_F15 304
|
||||
#define KEY_F16 305
|
||||
#define KEY_F17 306
|
||||
#define KEY_F18 307
|
||||
#define KEY_F19 308
|
||||
#define KEY_F20 309
|
||||
#define KEY_F21 310
|
||||
#define KEY_F22 311
|
||||
#define KEY_F23 312
|
||||
#define KEY_F24 313
|
||||
#define KEY_F25 314
|
||||
#define KEY_KP_0 320
|
||||
#define KEY_KP_1 321
|
||||
#define KEY_KP_2 322
|
||||
#define KEY_KP_3 323
|
||||
#define KEY_KP_4 324
|
||||
#define KEY_KP_5 325
|
||||
#define KEY_KP_6 326
|
||||
#define KEY_KP_7 327
|
||||
#define KEY_KP_8 328
|
||||
#define KEY_KP_9 329
|
||||
#define KEY_KP_DECIMAL 330
|
||||
#define KEY_KP_DIVIDE 331
|
||||
#define KEY_KP_MULTIPLY 332
|
||||
#define KEY_KP_SUBTRACT 333
|
||||
#define KEY_KP_ADD 334
|
||||
#define KEY_KP_ENTER 335
|
||||
#define KEY_KP_EQUAL 336
|
||||
#define KEY_LEFT_SHIFT 340
|
||||
#define KEY_LEFT_CONTROL 341
|
||||
#define KEY_LEFT_ALT 342
|
||||
#define KEY_LEFT_SUPER 343
|
||||
#define KEY_RIGHT_SHIFT 344
|
||||
#define KEY_RIGHT_CONTROL 345
|
||||
#define KEY_RIGHT_ALT 346
|
||||
#define KEY_RIGHT_SUPER 347
|
||||
#define KEY_MENU 348
|
|
@ -21,6 +21,10 @@
|
|||
#include "Graphics/Renderer.h"
|
||||
#include "Graphics/Framebuffer.h"
|
||||
|
||||
//** INPUT **//
|
||||
#include "Input/Input.h"
|
||||
#include "Input/InputCodes.h"
|
||||
|
||||
//** LAYER **//
|
||||
#include "Layer/Layer.h"
|
||||
#include "Layer/LayerStack.h"
|
||||
|
|
|
@ -15,6 +15,8 @@ private:
|
|||
|
||||
std::shared_ptr<Light::Framebuffer> m_Framebuffer;
|
||||
|
||||
bool m_GameSceneEvents = false;
|
||||
|
||||
public:
|
||||
MirrorLayer(const std::string& name)
|
||||
: Light::Layer(name), m_Direction(glm::vec2(0.0f, 0.0f))
|
||||
|
@ -51,59 +53,45 @@ public:
|
|||
|
||||
void OnUserInterfaceUpdate()
|
||||
{
|
||||
ImGui::Begin("GameView");
|
||||
|
||||
static ImVec2 regionAvailPrev = {0, 0};
|
||||
ImVec2 regionAvail = ImGui::GetContentRegionAvail();
|
||||
|
||||
if (regionAvail.x != regionAvailPrev.x || regionAvail.y != regionAvailPrev.y)
|
||||
if (ImGui::Begin("GameView"))
|
||||
{
|
||||
m_Framebuffer->Resize({ regionAvail.x, regionAvail.y });
|
||||
m_Camera->OnResize({ regionAvail.x, regionAvail.y });
|
||||
regionAvailPrev = regionAvail;
|
||||
}
|
||||
Light::Input::ReceiveGameEvents(ImGui::IsWindowFocused());
|
||||
|
||||
if(Light::GraphicsContext::GetGraphicsAPI() == Light::GraphicsAPI::DirectX)
|
||||
ImGui::Image(m_Framebuffer->GetColorAttachment(), regionAvail);
|
||||
else
|
||||
ImGui::Image(m_Framebuffer->GetColorAttachment(), regionAvail, ImVec2(0, 1), ImVec2(1, 0));
|
||||
static ImVec2 regionAvailPrev = { 0, 0 };
|
||||
ImVec2 regionAvail = ImGui::GetContentRegionAvail();
|
||||
|
||||
if (regionAvail.x != regionAvailPrev.x || regionAvail.y != regionAvailPrev.y)
|
||||
{
|
||||
m_Framebuffer->Resize({ regionAvail.x, regionAvail.y });
|
||||
m_Camera->OnResize({ regionAvail.x, regionAvail.y });
|
||||
regionAvailPrev = regionAvail;
|
||||
}
|
||||
|
||||
if (Light::GraphicsContext::GetGraphicsAPI() == Light::GraphicsAPI::DirectX)
|
||||
ImGui::Image(m_Framebuffer->GetColorAttachment(), regionAvail);
|
||||
else
|
||||
ImGui::Image(m_Framebuffer->GetColorAttachment(), regionAvail, ImVec2(0, 1), ImVec2(1, 0));
|
||||
}
|
||||
|
||||
ImGui::End();
|
||||
}
|
||||
|
||||
bool OnKeyPressed(const Light::KeyPressedEvent& event) override
|
||||
{
|
||||
if (event.GetKey() == 65) // GLFW_KEY_A
|
||||
m_Direction.x += -1.0f;
|
||||
if(event.GetKey() == 68) // GLFW_KEY_D
|
||||
m_Direction.x += 1.0f;
|
||||
|
||||
if (event.GetKey() == 87) // GLFW_KEY_W
|
||||
m_Direction.y += 1.0f;
|
||||
if (event.GetKey() == 83) // GLFW_KEY_S
|
||||
m_Direction.y += -1.0f;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool OnKeyReleased(const Light::KeyReleasedEvent& event) override
|
||||
{
|
||||
// #todo: add input class
|
||||
if (event.GetKey() == 65) // GLFW_KEY_A
|
||||
m_Direction.x -= -1.0f;
|
||||
if (event.GetKey() == 68) // GLFW_KEY_D
|
||||
m_Direction.x -= 1.0f;
|
||||
|
||||
if (event.GetKey() == 87) // GLFW_KEY_W
|
||||
m_Direction.y -= 1.0f;
|
||||
if (event.GetKey() == 83) // GLFW_KEY_S
|
||||
m_Direction.y -= -1.0f;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void OnUpdate(float deltaTime) override
|
||||
{
|
||||
if (Light::Input::GetKeyboardKey(KEY_A))
|
||||
m_Direction.x = -1.0f;
|
||||
else if (Light::Input::GetKeyboardKey(KEY_D))
|
||||
m_Direction.x = 1.0f;
|
||||
else
|
||||
m_Direction.x = 0.0f;
|
||||
|
||||
if (Light::Input::GetKeyboardKey(KEY_W))
|
||||
m_Direction.y = 1.0f;
|
||||
else if (Light::Input::GetKeyboardKey(KEY_S))
|
||||
m_Direction.y = -1.0f;
|
||||
else
|
||||
m_Direction.y = 0.0f;
|
||||
|
||||
m_Camera->Move(m_Direction * m_Speed * deltaTime);
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue