forked from electronicarts/CnC_Generals_Zero_Hour
-
Notifications
You must be signed in to change notification settings - Fork 199
Expand file tree
/
Copy pathSDL3Input.h
More file actions
211 lines (167 loc) · 5.79 KB
/
SDL3Input.h
File metadata and controls
211 lines (167 loc) · 5.79 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
/*
** Command & Conquer Generals Zero Hour(tm)
** Copyright 2026 TheSuperHackers
**
** This program is free software: you can redistribute it and/or modify
** it under the terms of the GNU General Public License as published by
** the Free Software Foundation, either version 3 of the License, or
** (at your option) any later version.
**
** This program is distributed in the hope that it will be useful,
** but WITHOUT ANY WARRANTY; without even the implied warranty of
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
** GNU General Public License for more details.
**
** You should have received a copy of the GNU General Public License
** along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
/*
** Derived from the GeneralsX branch by fbraz3
*/
#pragma once
#include "Lib/BaseType.h"
// SYSTEM INCLUDES
#include <SDL3/SDL.h>
#include <SDL3_image/SDL_image.h>
#include <array>
#include <functional>
// USER INCLUDES
#include "GameClient/Mouse.h"
#include "GameClient/Keyboard.h"
#include "GameClient/KeyDefs.h"
// FORWARD REFERENCES
struct AnimatedCursor;
class SDL3InputManager;
// GLOBALS ---------------------------------------------------------------------
extern SDL3InputManager* TheSDL3InputManager;
// TYPE DEFINES ----------------------------------------------------------------
typedef KeyDefType KeyVal;
// SDL3Mouse ------------------------------------------------------------------
/** Mouse interface using SDL3 APIs */
//-----------------------------------------------------------------------------
class SDL3Mouse : public Mouse
{
public:
SDL3Mouse(SDL_Window* window);
virtual ~SDL3Mouse(void);
// SubsystemInterface
virtual void init(void) override;
virtual void reset(void) override;
virtual void update(void) override;
virtual void initCursorResources(void) override;
static void freeCursorResources(void);
// Mouse interface
virtual void setCursor(MouseCursor cursor) override;
virtual void setVisibility(Bool visible) override;
virtual void loseFocus() override;
virtual void regainFocus() override;
// SDL3-specific methods
void addSDLEvent(SDL_Event *event);
protected:
virtual void capture(void) override;
virtual void releaseCapture(void) override;
virtual UnsignedByte getMouseEvent(MouseIO *result, Bool flush) override;
private:
// Event translation from SDL_Event (Clean Slate implementation)
void translateEvent(const SDL_Event& event, MouseIO *result);
// Scale raw SDL window coordinates to game internal resolution
void scaleMouseCoordinates(int rawX, int rawY, Uint32 windowID, int& scaledX, int& scaledY);
// Load cursor from ANI file (fighter19 pattern)
AnimatedCursor* loadCursorFromFile(const char* filepath);
SDL_Window* m_Window;
Bool m_IsCaptured;
Bool m_IsVisible;
Bool m_LostFocus;
Uint32 m_LeftButtonDownTime;
Uint32 m_RightButtonDownTime;
Uint32 m_MiddleButtonDownTime;
UnsignedInt m_LastFrameNumber;
ICoord2D m_LeftButtonDownPos;
ICoord2D m_RightButtonDownPos;
ICoord2D m_MiddleButtonDownPos;
Int m_directionFrame;
UnsignedInt m_inputFrame;
float m_accumulatedDeltaX;
float m_accumulatedDeltaY;
SDL_Cursor* m_activeSDLCursor;
Bool m_cursorDirty;
};
// SDL3Keyboard ---------------------------------------------------------------
/** Keyboard interface using SDL3 APIs */
//-----------------------------------------------------------------------------
class SDL3Keyboard : public Keyboard
{
public:
SDL3Keyboard(void);
virtual ~SDL3Keyboard(void);
// SubsystemInterface
virtual void init(void) override;
virtual void reset(void) override;
virtual void update(void) override;
// Keyboard interface
virtual Bool getCapsState(void) override;
// SDL3-specific methods
void addSDLEvent(SDL_Event *event);
protected:
virtual void getKey(KeyboardIO *key) override;
virtual KeyVal translateScanCodeToKeyVal(unsigned char scan);
private:
void translateKeyEvent(const SDL_KeyboardEvent& event);
};
// SDL3InputManager -----------------------------------------------------------
/** Unified manager for SDL3 input events */
//-----------------------------------------------------------------------------
class SDL3InputManager
{
public:
SDL3InputManager(SDL_Window* window);
virtual ~SDL3InputManager();
void update();
// Buffer access
Bool getNextMouseEvent(SDL_Event& outEvent);
Bool getNextKeyboardEvent(SDL_Event& outEvent);
void addMouseSDLEvent(const SDL_Event& event);
void addKeyboardSDLEvent(const SDL_Event& event);
Bool isQuitting() const { return m_isQuitting; }
// Constants
static constexpr float AXIS_MAX = 32767.0f;
static constexpr int TRIGGER_THRESHOLD = 16384;
static constexpr float DEFAULT_DEADZONE = 0.15f;
static constexpr float DEFAULT_CURSOR_SPEED = 800.0f;
private:
struct GamepadState {
bool buttonState[SDL_GAMEPAD_BUTTON_COUNT];
bool stickLeft, stickRight, stickUp, stickDown;
bool ltDown, rtDown;
GamepadState() {
memset(buttonState, 0, sizeof(buttonState));
stickLeft = stickRight = stickUp = stickDown = false;
ltDown = rtDown = false;
}
};
private:
// Gamepad management
void openFirstGamepad();
void closeGamepad();
SDL_Window* m_window;
SDL_Gamepad* m_gamepad;
void processGamepadInput();
void handleGamepadButton(SDL_GamepadButton button, bool& currentState, bool isDown, std::function<void(bool)> action);
// Virtual event injection
void virtualPulseKey(SDL_Scancode scancode, bool down);
void virtualPulseMouse(Uint8 button, bool down);
// Event buffers
static const UnsignedInt MAX_MOUSE_EVENTS = 256;
static const UnsignedInt MAX_KEY_EVENTS = 256;
SDL_Event m_mouseEvents[MAX_MOUSE_EVENTS];
UnsignedInt m_mouseNextFree;
UnsignedInt m_mouseNextGet;
SDL_Event m_keyEvents[MAX_KEY_EVENTS];
UnsignedInt m_keyNextFree;
UnsignedInt m_keyNextGet;
// Gamepad state
GamepadState m_state;
Bool m_precisionMode;
Uint64 m_lastUpdateTime;
Bool m_isQuitting;
};