FifeGUI 0.3.0
A C++ GUI library designed for games.
input.cpp
1// SPDX-License-Identifier: LGPL-2.1-or-later OR BSD-3-Clause
2// SPDX-FileCopyrightText: 2004 - 2008 Olof Naessén and Per Larsson
3// SPDX-FileCopyrightText: 2013 - 2026 Fifengine contributors
4
5// Corresponding header include
6#include "fifechan/backends/sdl3/input.hpp"
7
8// Standard library includes
9#include <string>
10#include <utility>
11#include <vector>
12
13// Third-party library includes
14#include <utf8cpp/utf8.h>
15
16// Project headers (subdirs before local)
17#include "fifechan/exception.hpp"
18
19namespace fcn::sdl3
20{
22 {
23 }
24
26 {
27 return mKeyInputQueue.empty();
28 }
29
31 {
32 KeyInput keyInput;
33
34 if (mKeyInputQueue.empty()) {
35 throwException("The queue is empty.");
36 }
37
38 keyInput = mKeyInputQueue.front();
39 mKeyInputQueue.pop();
40
41 return keyInput;
42 }
43
45 {
46 return mMouseInputQueue.empty();
47 }
48
50 {
51 MouseInput mouseInput{};
52
53 if (mMouseInputQueue.empty()) {
54 throwException("The queue is empty.");
55 }
56
57 mouseInput = mMouseInputQueue.front();
58 mMouseInputQueue.pop();
59
60 return mouseInput;
61 }
62
64 {
65 return mTextInputQueue.empty();
66 }
67
69 {
70 if (mTextInputQueue.empty()) {
71 return {};
72 }
73 std::string text = mTextInputQueue.front();
74 mTextInputQueue.pop();
75 return text;
76 }
77
78 void Input::pushInput(SDL_Event event)
79 {
80 KeyInput keyInput{};
81 MouseInput mouseInput{};
82
83 switch (event.type) {
84 case SDL_EVENT_KEY_DOWN:
85 case SDL_EVENT_KEY_UP: {
86 // KeyType mirrors SDL_Keycode 1:1 use the SDL keycode directly.
87 keyInput.setKey(Key(static_cast<int>(event.key.key)));
88 keyInput.setType(event.type == SDL_EVENT_KEY_DOWN ? KeyInput::Type::Pressed : KeyInput::Type::Released);
89 keyInput.setShiftPressed((event.key.mod & SDL_KMOD_SHIFT) != 0);
90 keyInput.setControlPressed((event.key.mod & SDL_KMOD_CTRL) != 0);
91 keyInput.setAltPressed((event.key.mod & SDL_KMOD_ALT) != 0);
92 keyInput.setMetaPressed((event.key.mod & SDL_KMOD_GUI) != 0);
93 keyInput.setNumericPad((event.key.mod & SDL_KMOD_NUM) != 0);
94 mKeyInputQueue.push(keyInput);
95 break;
96 }
97
98 case SDL_EVENT_MOUSE_BUTTON_DOWN: {
99 mMouseDown = true;
100 mouseInput.setX(static_cast<int>(event.button.x));
101 mouseInput.setY(static_cast<int>(event.button.y));
102 mouseInput.setButton(convertMouseButton(event.button.button));
103 mouseInput.setType(MouseInput::Type::Pressed);
104 mouseInput.setTimeStamp(SDL_GetTicks());
105 mMouseInputQueue.push(mouseInput);
106 break;
107 }
108
109 case SDL_EVENT_MOUSE_BUTTON_UP: {
110 mMouseDown = false;
111 mouseInput.setX(static_cast<int>(event.button.x));
112 mouseInput.setY(static_cast<int>(event.button.y));
113 mouseInput.setButton(convertMouseButton(event.button.button));
114 mouseInput.setType(MouseInput::Type::Released);
115 mouseInput.setTimeStamp(SDL_GetTicks());
116 mMouseInputQueue.push(mouseInput);
117 break;
118 }
119
120 case SDL_EVENT_MOUSE_MOTION: {
121 mouseInput.setX(static_cast<int>(event.motion.x));
122 mouseInput.setY(static_cast<int>(event.motion.y));
123 mouseInput.setButton(MouseInput::Button::Empty);
124 mouseInput.setType(MouseInput::Type::Moved);
125 mouseInput.setTimeStamp(SDL_GetTicks());
126 mMouseInputQueue.push(mouseInput);
127 break;
128 }
129
130 case SDL_EVENT_MOUSE_WHEEL: {
131 if (event.wheel.y > 0) {
132 mouseInput.setType(MouseInput::Type::WheelMovedUp);
133 } else if (event.wheel.y < 0) {
134 mouseInput.setType(MouseInput::Type::WheelMovedDown);
135 }
136 if (event.wheel.x > 0) {
137 mouseInput.setType(MouseInput::Type::WheelMovedRight);
138 } else if (event.wheel.x < 0) {
139 mouseInput.setType(MouseInput::Type::WheelMovedLeft);
140 }
141 float x = 0;
142 float y = 0;
143 SDL_GetMouseState(&x, &y);
144 mouseInput.setX(static_cast<int>(x));
145 mouseInput.setY(static_cast<int>(y));
146 mouseInput.setButton(convertMouseButton(SDL_BUTTON_LEFT));
147 mouseInput.setTimeStamp(SDL_GetTicks());
148 mMouseInputQueue.push(mouseInput);
149 break;
150 }
151
152 // case SDL_EVENT_TEXT_EDITING:
153 case SDL_EVENT_TEXT_INPUT: {
154 std::string text(event.text.text);
155 if (!text.empty()) {
156 mTextInputQueue.push(std::move(text));
157 }
158 break;
159 }
160
161 case SDL_EVENT_WINDOW_MOUSE_ENTER: {
162 mMouseInWindow = true;
163 break;
164 }
165 case SDL_EVENT_WINDOW_MOUSE_LEAVE: {
166 mMouseInWindow = false;
167 break;
168 }
169
170 default:
171 break;
172 }
173
174 } // end switch
175
177 {
178 switch (button) {
179 case SDL_BUTTON_LEFT:
180 return MouseInput::Button::Left;
181 break;
182 case SDL_BUTTON_RIGHT:
183 return MouseInput::Button::Right;
184 break;
185 case SDL_BUTTON_MIDDLE:
186 return MouseInput::Button::Middle;
187 break;
188 case SDL_BUTTON_X1:
189 return MouseInput::Button::X1;
190 break;
191 case SDL_BUTTON_X2:
192 return MouseInput::Button::X2;
193 break;
194 default:
195 return MouseInput::Button::Empty;
196 }
197 }
198
199} // namespace fcn::sdl3
Internal class representing raw keyboard input data.
Definition keyinput.hpp:32
void setType(Type type)
Sets the type of the key input.
Definition keyinput.cpp:22
void setAltPressed(bool pressed)
Sets the alt to be pressed at the same time as the key, or not.
Definition keyinput.cpp:71
void setNumericPad(bool numpad)
Sets the key to be pressed at the numeric pad.
Definition keyinput.cpp:91
void setControlPressed(bool pressed)
Sets control to be pressed at the same time as the key, or not.
Definition keyinput.cpp:61
void setKey(Key const &key)
Sets the key of the key input.
Definition keyinput.cpp:34
void setMetaPressed(bool pressed)
Sets meta to be pressed at the same time as the key, or not.
Definition keyinput.cpp:81
void setShiftPressed(bool pressed)
Sets shift to be pressed at the same time as the key, or not.
Definition keyinput.cpp:51
Internal class representing raw mouse input data.
void setX(int x)
Sets the x coordinate of the mouse input.
void setTimeStamp(int timeStamp)
Sets the timestamp for the mouse input.
void setY(int y)
Sets the y coordinate of the mouse input.
Button
Mouse button.
void setType(Type type)
Sets the type of the mouse input.
void setButton(Button button)
Sets the button pressed.
std::queue< std::string > mTextInputQueue
Queue of text input strings waiting to be processed.
bool mMouseDown
True if a mouse button is currently held down.
bool isTextQueueEmpty() override
Checks if the text input queue is empty.
Definition input.cpp:63
Input()
Constructor.
Definition input.cpp:21
bool isKeyQueueEmpty() override
Checks if the key queue is empty, or not.
Definition input.cpp:25
std::string dequeueTextInput() override
Dequeues a UTF-8 text string from the text input queue.
Definition input.cpp:68
std::queue< MouseInput > mMouseInputQueue
Queue of mouse inputs waiting to be processed.
MouseInput dequeueMouseInput() override
Dequeues the mouse input queue.
Definition input.cpp:49
KeyInput dequeueKeyInput() override
Dequeues the key input queue.
Definition input.cpp:30
static MouseInput::Button convertMouseButton(int button)
Converts a mouse button from SDL to a FifeGUI mouse button.
Definition input.cpp:176
virtual void pushInput(SDL_Event event)
Pushes an SDL event.
Definition input.cpp:78
std::queue< KeyInput > mKeyInputQueue
Queue of key inputs waiting to be processed.
bool mMouseInWindow
True if the mouse cursor is currently within the application window.
bool isMouseQueueEmpty() override
Checks if the mouse queue is empyt, or not.
Definition input.cpp:44
void throwException(std::string const &message, std::source_location location=std::source_location::current())
Throw an Exception capturing the current source location.