mini-arcade-native-backend 0.4.0__tar.gz → 0.4.2__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/CHANGELOG.md +29 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/PKG-INFO +2 -2
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/cpp/bindings.cpp +20 -1
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/cpp/engine.cpp +57 -5
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/cpp/engine.h +34 -3
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/pyproject.toml +2 -2
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/src/mini_arcade_native_backend/__init__.py +83 -5
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/tests/test_init.py +94 -16
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/.github/workflows/ci.yml +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/.github/workflows/create-release-branch.yml +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/.github/workflows/release-finalize.yml +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/.github/workflows/release-publish.yml +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/.gitignore +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/.vscode/settings.json +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/CMakeLists.txt +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/LICENSE +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/README.md +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/examples/native_backend_demo.py +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/poetry.lock +0 -0
- {mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/poetry.toml +0 -0
|
@@ -6,6 +6,35 @@ This project adheres to [Semantic Versioning](https://semver.org/).
|
|
|
6
6
|
|
|
7
7
|
## [Unreleased]
|
|
8
8
|
|
|
9
|
+
## [0.4.2] - 2025-12-16
|
|
10
|
+
|
|
11
|
+
### Added
|
|
12
|
+
- enhance event handling by adding key_code to event mapping in NativeBackend
|
|
13
|
+
|
|
14
|
+
## [0.4.1] - 2025-12-15
|
|
15
|
+
|
|
16
|
+
### Added
|
|
17
|
+
- extend event handling with additional mouse and window events in engine and bindings
|
|
18
|
+
- enhance font handling by returning font ID and updating draw_text signature
|
|
19
|
+
|
|
20
|
+
### Fixed
|
|
21
|
+
- update mini-arcade-core dependency version to ensure compatibility
|
|
22
|
+
|
|
23
|
+
### Other
|
|
24
|
+
- Merge release/0.3 into develop
|
|
25
|
+
|
|
26
|
+
## [0.4.0] - 2025-12-15
|
|
27
|
+
|
|
28
|
+
### Added
|
|
29
|
+
- extend event handling with additional mouse and window events in engine and bindings
|
|
30
|
+
- enhance font handling by returning font ID and updating draw_text signature
|
|
31
|
+
|
|
32
|
+
### Fixed
|
|
33
|
+
- update mini-arcade-core dependency version to ensure compatibility
|
|
34
|
+
|
|
35
|
+
### Other
|
|
36
|
+
- Merge release/0.3 into develop
|
|
37
|
+
|
|
9
38
|
## [0.3.3] - 2025-12-05
|
|
10
39
|
|
|
11
40
|
### Other
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.2
|
|
2
2
|
Name: mini-arcade-native-backend
|
|
3
|
-
Version: 0.4.
|
|
3
|
+
Version: 0.4.2
|
|
4
4
|
Summary: Native SDL2 backend for mini-arcade-core using SDL2 + pybind11.
|
|
5
5
|
Author-Email: Santiago Rincon <rincores@gmail.com>
|
|
6
6
|
License: Copyright (c) 2025 Santiago Rincón
|
|
@@ -24,7 +24,7 @@ License: Copyright (c) 2025 Santiago Rincón
|
|
|
24
24
|
SOFTWARE.
|
|
25
25
|
|
|
26
26
|
Requires-Python: <3.12,>=3.9
|
|
27
|
-
Requires-Dist: mini-arcade-core
|
|
27
|
+
Requires-Dist: mini-arcade-core~=0.9
|
|
28
28
|
Provides-Extra: dev
|
|
29
29
|
Requires-Dist: pytest~=8.3; extra == "dev"
|
|
30
30
|
Requires-Dist: pytest-cov~=6.0; extra == "dev"
|
|
@@ -14,12 +14,31 @@ PYBIND11_MODULE(_native, m) {
|
|
|
14
14
|
.value("Quit", mini::EventType::Quit)
|
|
15
15
|
.value("KeyDown", mini::EventType::KeyDown)
|
|
16
16
|
.value("KeyUp", mini::EventType::KeyUp)
|
|
17
|
+
.value("MouseMotion", mini::EventType::MouseMotion)
|
|
18
|
+
.value("MouseButtonDown", mini::EventType::MouseButtonDown)
|
|
19
|
+
.value("MouseButtonUp", mini::EventType::MouseButtonUp)
|
|
20
|
+
.value("MouseWheel", mini::EventType::MouseWheel)
|
|
21
|
+
.value("WindowResized", mini::EventType::WindowResized)
|
|
22
|
+
.value("TextInput", mini::EventType::TextInput)
|
|
17
23
|
.export_values();
|
|
18
24
|
|
|
19
25
|
// Bind the Event struct
|
|
20
26
|
py::class_<mini::Event>(m, "Event")
|
|
21
27
|
.def_readonly("type", &mini::Event::type)
|
|
22
|
-
.def_readonly("key", &mini::Event::key)
|
|
28
|
+
.def_readonly("key", &mini::Event::key)
|
|
29
|
+
.def_readonly("scancode", &mini::Event::scancode)
|
|
30
|
+
.def_readonly("mod", &mini::Event::mod)
|
|
31
|
+
.def_readonly("repeat", &mini::Event::repeat)
|
|
32
|
+
.def_readonly("x", &mini::Event::x)
|
|
33
|
+
.def_readonly("y", &mini::Event::y)
|
|
34
|
+
.def_readonly("dx", &mini::Event::dx)
|
|
35
|
+
.def_readonly("dy", &mini::Event::dy)
|
|
36
|
+
.def_readonly("button", &mini::Event::button)
|
|
37
|
+
.def_readonly("wheel_x", &mini::Event::wheel_x)
|
|
38
|
+
.def_readonly("wheel_y", &mini::Event::wheel_y)
|
|
39
|
+
.def_readonly("width", &mini::Event::width)
|
|
40
|
+
.def_readonly("height", &mini::Event::height)
|
|
41
|
+
.def_readonly("text", &mini::Event::text);
|
|
23
42
|
|
|
24
43
|
// Bind the Engine class
|
|
25
44
|
py::class_<mini::Engine>(m, "Engine")
|
|
@@ -10,7 +10,8 @@ namespace mini {
|
|
|
10
10
|
renderer_(nullptr),
|
|
11
11
|
initialized_(false),
|
|
12
12
|
font_(nullptr),
|
|
13
|
-
clear_color_{0, 0, 0, 255}
|
|
13
|
+
clear_color_{0, 0, 0, 255},
|
|
14
|
+
default_font_id_(-1)
|
|
14
15
|
{
|
|
15
16
|
}
|
|
16
17
|
|
|
@@ -87,6 +88,8 @@ namespace mini {
|
|
|
87
88
|
// Enable alpha blending for RGBA drawing
|
|
88
89
|
SDL_SetRenderDrawBlendMode(renderer_, SDL_BLENDMODE_BLEND);
|
|
89
90
|
|
|
91
|
+
SDL_StartTextInput(); // <--- needed for SDL_TEXTINPUT
|
|
92
|
+
|
|
90
93
|
initialized_ = true;
|
|
91
94
|
}
|
|
92
95
|
|
|
@@ -245,7 +248,6 @@ namespace mini {
|
|
|
245
248
|
SDL_RenderFillRect(renderer_, &rect);
|
|
246
249
|
}
|
|
247
250
|
|
|
248
|
-
|
|
249
251
|
bool Engine::capture_frame(const char* path)
|
|
250
252
|
{
|
|
251
253
|
if (!initialized_ || renderer_ == nullptr) {
|
|
@@ -305,8 +307,6 @@ namespace mini {
|
|
|
305
307
|
|
|
306
308
|
while (SDL_PollEvent(&sdl_event)) {
|
|
307
309
|
Event ev;
|
|
308
|
-
ev.type = EventType::Unknown;
|
|
309
|
-
ev.key = 0;
|
|
310
310
|
|
|
311
311
|
switch (sdl_event.type) {
|
|
312
312
|
case SDL_QUIT:
|
|
@@ -316,11 +316,63 @@ namespace mini {
|
|
|
316
316
|
case SDL_KEYDOWN:
|
|
317
317
|
ev.type = EventType::KeyDown;
|
|
318
318
|
ev.key = sdl_event.key.keysym.sym;
|
|
319
|
+
ev.scancode = (int)sdl_event.key.keysym.scancode;
|
|
320
|
+
ev.mod = (int)sdl_event.key.keysym.mod;
|
|
321
|
+
ev.repeat = (int)sdl_event.key.repeat;
|
|
319
322
|
break;
|
|
320
323
|
|
|
321
324
|
case SDL_KEYUP:
|
|
322
325
|
ev.type = EventType::KeyUp;
|
|
323
326
|
ev.key = sdl_event.key.keysym.sym;
|
|
327
|
+
ev.scancode = (int)sdl_event.key.keysym.scancode;
|
|
328
|
+
ev.mod = (int)sdl_event.key.keysym.mod;
|
|
329
|
+
ev.repeat = 0;
|
|
330
|
+
break;
|
|
331
|
+
|
|
332
|
+
case SDL_MOUSEMOTION:
|
|
333
|
+
ev.type = EventType::MouseMotion;
|
|
334
|
+
ev.x = sdl_event.motion.x;
|
|
335
|
+
ev.y = sdl_event.motion.y;
|
|
336
|
+
ev.dx = sdl_event.motion.xrel;
|
|
337
|
+
ev.dy = sdl_event.motion.yrel;
|
|
338
|
+
break;
|
|
339
|
+
|
|
340
|
+
case SDL_MOUSEBUTTONDOWN:
|
|
341
|
+
ev.type = EventType::MouseButtonDown;
|
|
342
|
+
ev.button = (int)sdl_event.button.button;
|
|
343
|
+
ev.x = sdl_event.button.x;
|
|
344
|
+
ev.y = sdl_event.button.y;
|
|
345
|
+
break;
|
|
346
|
+
|
|
347
|
+
case SDL_MOUSEBUTTONUP:
|
|
348
|
+
ev.type = EventType::MouseButtonUp;
|
|
349
|
+
ev.button = (int)sdl_event.button.button;
|
|
350
|
+
ev.x = sdl_event.button.x;
|
|
351
|
+
ev.y = sdl_event.button.y;
|
|
352
|
+
break;
|
|
353
|
+
|
|
354
|
+
case SDL_MOUSEWHEEL:
|
|
355
|
+
ev.type = EventType::MouseWheel;
|
|
356
|
+
ev.wheel_x = sdl_event.wheel.x;
|
|
357
|
+
ev.wheel_y = sdl_event.wheel.y;
|
|
358
|
+
// If you want "natural" direction handling, you can flip based on sdl_event.wheel.direction
|
|
359
|
+
break;
|
|
360
|
+
|
|
361
|
+
case SDL_TEXTINPUT:
|
|
362
|
+
ev.type = EventType::TextInput;
|
|
363
|
+
ev.text = sdl_event.text.text; // UTF-8
|
|
364
|
+
break;
|
|
365
|
+
|
|
366
|
+
case SDL_WINDOWEVENT:
|
|
367
|
+
if (sdl_event.window.event == SDL_WINDOWEVENT_RESIZED ||
|
|
368
|
+
sdl_event.window.event == SDL_WINDOWEVENT_SIZE_CHANGED)
|
|
369
|
+
{
|
|
370
|
+
ev.type = EventType::WindowResized;
|
|
371
|
+
ev.width = sdl_event.window.data1;
|
|
372
|
+
ev.height = sdl_event.window.data2;
|
|
373
|
+
} else {
|
|
374
|
+
continue; // ignore other window events
|
|
375
|
+
}
|
|
324
376
|
break;
|
|
325
377
|
|
|
326
378
|
default:
|
|
@@ -328,7 +380,7 @@ namespace mini {
|
|
|
328
380
|
break;
|
|
329
381
|
}
|
|
330
382
|
|
|
331
|
-
events.push_back(ev);
|
|
383
|
+
events.push_back(std::move(ev));
|
|
332
384
|
}
|
|
333
385
|
|
|
334
386
|
return events;
|
|
@@ -3,6 +3,7 @@
|
|
|
3
3
|
#include <SDL.h>
|
|
4
4
|
#include <SDL_ttf.h>
|
|
5
5
|
#include <vector>
|
|
6
|
+
#include <string>
|
|
6
7
|
|
|
7
8
|
// A minimal 2D graphics engine binding for Python using SDL.
|
|
8
9
|
namespace mini {
|
|
@@ -11,14 +12,44 @@ namespace mini {
|
|
|
11
12
|
enum class EventType {
|
|
12
13
|
Unknown = 0,
|
|
13
14
|
Quit,
|
|
15
|
+
|
|
14
16
|
KeyDown,
|
|
15
|
-
KeyUp
|
|
17
|
+
KeyUp,
|
|
18
|
+
|
|
19
|
+
MouseMotion,
|
|
20
|
+
MouseButtonDown,
|
|
21
|
+
MouseButtonUp,
|
|
22
|
+
MouseWheel,
|
|
23
|
+
|
|
24
|
+
WindowResized,
|
|
25
|
+
TextInput
|
|
16
26
|
};
|
|
17
27
|
|
|
18
28
|
// A simple event structure to pass events to Python.
|
|
19
29
|
struct Event {
|
|
20
|
-
EventType type;
|
|
21
|
-
|
|
30
|
+
EventType type = EventType::Unknown;
|
|
31
|
+
|
|
32
|
+
// Keyboard
|
|
33
|
+
int key = 0; // SDL_Keycode
|
|
34
|
+
int scancode = 0; // SDL_Scancode
|
|
35
|
+
int mod = 0; // SDL_Keymod bitmask
|
|
36
|
+
int repeat = 0; // 1 if key repeat, else 0
|
|
37
|
+
|
|
38
|
+
// Mouse
|
|
39
|
+
int x = 0;
|
|
40
|
+
int y = 0;
|
|
41
|
+
int dx = 0; // motion relative
|
|
42
|
+
int dy = 0;
|
|
43
|
+
int button = 0; // SDL_BUTTON_LEFT etc.
|
|
44
|
+
int wheel_x = 0;
|
|
45
|
+
int wheel_y = 0;
|
|
46
|
+
|
|
47
|
+
// Window
|
|
48
|
+
int width = 0;
|
|
49
|
+
int height = 0;
|
|
50
|
+
|
|
51
|
+
// Text input
|
|
52
|
+
std::string text;
|
|
22
53
|
};
|
|
23
54
|
|
|
24
55
|
// The main engine class that wraps SDL functionality.
|
|
@@ -8,7 +8,7 @@ build-backend = "scikit_build_core.build"
|
|
|
8
8
|
|
|
9
9
|
[project]
|
|
10
10
|
name = "mini-arcade-native-backend"
|
|
11
|
-
version = "0.4.
|
|
11
|
+
version = "0.4.2"
|
|
12
12
|
description = "Native SDL2 backend for mini-arcade-core using SDL2 + pybind11."
|
|
13
13
|
authors = [
|
|
14
14
|
{ name = "Santiago Rincon", email = "rincores@gmail.com" },
|
|
@@ -17,7 +17,7 @@ readme = "README.md"
|
|
|
17
17
|
requires-python = ">=3.9,<3.12"
|
|
18
18
|
license = { file = "LICENSE" }
|
|
19
19
|
dependencies = [
|
|
20
|
-
"mini-arcade-core
|
|
20
|
+
"mini-arcade-core~=0.9",
|
|
21
21
|
]
|
|
22
22
|
|
|
23
23
|
[project.optional-dependencies]
|
|
@@ -37,6 +37,7 @@ if sys.platform == "win32":
|
|
|
37
37
|
# Justification: Need to import core after setting DLL path on Windows
|
|
38
38
|
# pylint: disable=wrong-import-position
|
|
39
39
|
from mini_arcade_core import Backend, Event, EventType
|
|
40
|
+
from mini_arcade_core.keymaps.sdl import SDL_KEYCODE_TO_KEY
|
|
40
41
|
|
|
41
42
|
# Justification: Importing the native extension module
|
|
42
43
|
# pylint: disable=import-self,no-name-in-module
|
|
@@ -53,6 +54,12 @@ _NATIVE_TO_CORE = {
|
|
|
53
54
|
native.EventType.Quit: EventType.QUIT,
|
|
54
55
|
native.EventType.KeyDown: EventType.KEYDOWN,
|
|
55
56
|
native.EventType.KeyUp: EventType.KEYUP,
|
|
57
|
+
native.EventType.MouseMotion: EventType.MOUSEMOTION,
|
|
58
|
+
native.EventType.MouseButtonDown: EventType.MOUSEBUTTONDOWN,
|
|
59
|
+
native.EventType.MouseButtonUp: EventType.MOUSEBUTTONUP,
|
|
60
|
+
native.EventType.MouseWheel: EventType.MOUSEWHEEL,
|
|
61
|
+
native.EventType.WindowResized: EventType.WINDOWRESIZED,
|
|
62
|
+
native.EventType.TextInput: EventType.TEXTINPUT,
|
|
56
63
|
}
|
|
57
64
|
|
|
58
65
|
|
|
@@ -108,6 +115,8 @@ class NativeBackend(Backend):
|
|
|
108
115
|
"""
|
|
109
116
|
self._engine.set_clear_color(int(r), int(g), int(b))
|
|
110
117
|
|
|
118
|
+
# Justification: Many local variables needed for event mapping
|
|
119
|
+
# pylint: disable=too-many-locals
|
|
111
120
|
def poll_events(self) -> list[Event]:
|
|
112
121
|
"""
|
|
113
122
|
Poll for events from the backend and return them as a list of Event objects.
|
|
@@ -115,12 +124,81 @@ class NativeBackend(Backend):
|
|
|
115
124
|
:return: List of Event objects representing the polled events.
|
|
116
125
|
:rtype: list[Event]
|
|
117
126
|
"""
|
|
118
|
-
|
|
127
|
+
out: list[Event] = []
|
|
119
128
|
for ev in self._engine.poll_events():
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
129
|
+
etype = _NATIVE_TO_CORE.get(ev.type, EventType.UNKNOWN)
|
|
130
|
+
|
|
131
|
+
key = None
|
|
132
|
+
key_code = None
|
|
133
|
+
scancode = None
|
|
134
|
+
mod = None
|
|
135
|
+
repeat = None
|
|
136
|
+
|
|
137
|
+
x = y = dx = dy = None
|
|
138
|
+
button = None
|
|
139
|
+
wheel = None
|
|
140
|
+
size = None
|
|
141
|
+
text = None
|
|
142
|
+
|
|
143
|
+
if etype in (EventType.KEYDOWN, EventType.KEYUP):
|
|
144
|
+
raw_key = int(getattr(ev, "key", 0) or 0)
|
|
145
|
+
key_code = raw_key if raw_key != 0 else None
|
|
146
|
+
key = SDL_KEYCODE_TO_KEY.get(raw_key) if raw_key != 0 else None
|
|
147
|
+
|
|
148
|
+
scancode = (
|
|
149
|
+
int(ev.scancode) if getattr(ev, "scancode", 0) else None
|
|
150
|
+
)
|
|
151
|
+
mod = int(ev.mod) if getattr(ev, "mod", 0) else None
|
|
152
|
+
|
|
153
|
+
rep = int(getattr(ev, "repeat", 0) or 0)
|
|
154
|
+
repeat = bool(rep) if etype == EventType.KEYDOWN else None
|
|
155
|
+
|
|
156
|
+
elif etype == EventType.MOUSEMOTION:
|
|
157
|
+
x = int(ev.x)
|
|
158
|
+
y = int(ev.y)
|
|
159
|
+
dx = int(ev.dx)
|
|
160
|
+
dy = int(ev.dy)
|
|
161
|
+
|
|
162
|
+
elif etype in (EventType.MOUSEBUTTONDOWN, EventType.MOUSEBUTTONUP):
|
|
163
|
+
button = int(ev.button) if ev.button else None
|
|
164
|
+
x = int(ev.x)
|
|
165
|
+
y = int(ev.y)
|
|
166
|
+
|
|
167
|
+
elif etype == EventType.MOUSEWHEEL:
|
|
168
|
+
wx = int(ev.wheel_x)
|
|
169
|
+
wy = int(ev.wheel_y)
|
|
170
|
+
wheel = (wx, wy) if (wx or wy) else None
|
|
171
|
+
|
|
172
|
+
elif etype == EventType.WINDOWRESIZED:
|
|
173
|
+
w = int(ev.width)
|
|
174
|
+
h = int(ev.height)
|
|
175
|
+
size = (w, h) if (w and h) else None
|
|
176
|
+
|
|
177
|
+
elif etype == EventType.TEXTINPUT:
|
|
178
|
+
t = getattr(ev, "text", "")
|
|
179
|
+
text = t if t else None
|
|
180
|
+
|
|
181
|
+
out.append(
|
|
182
|
+
Event(
|
|
183
|
+
type=etype,
|
|
184
|
+
key=key,
|
|
185
|
+
key_code=key_code,
|
|
186
|
+
scancode=scancode,
|
|
187
|
+
mod=mod,
|
|
188
|
+
repeat=repeat,
|
|
189
|
+
x=x,
|
|
190
|
+
y=y,
|
|
191
|
+
dx=dx,
|
|
192
|
+
dy=dy,
|
|
193
|
+
button=button,
|
|
194
|
+
wheel=wheel,
|
|
195
|
+
size=size,
|
|
196
|
+
text=text,
|
|
197
|
+
)
|
|
198
|
+
)
|
|
199
|
+
return out
|
|
200
|
+
|
|
201
|
+
# pylint: enable=too-many-locals
|
|
124
202
|
|
|
125
203
|
def begin_frame(self):
|
|
126
204
|
"""Begin a new frame for rendering."""
|
|
@@ -18,18 +18,34 @@ def setup_fake_core_and_native(monkeypatch):
|
|
|
18
18
|
class FakeBackend:
|
|
19
19
|
"""Minimal base class just to satisfy inheritance."""
|
|
20
20
|
|
|
21
|
-
pass
|
|
22
|
-
|
|
23
21
|
class FakeCoreEventType:
|
|
24
22
|
UNKNOWN = "core_unknown"
|
|
25
23
|
QUIT = "core_quit"
|
|
26
24
|
KEYDOWN = "core_keydown"
|
|
27
25
|
KEYUP = "core_keyup"
|
|
26
|
+
MOUSEMOTION = "core_mousemotion"
|
|
27
|
+
MOUSEBUTTONDOWN = "core_mousebuttondown"
|
|
28
|
+
MOUSEBUTTONUP = "core_mousebuttonup"
|
|
29
|
+
MOUSEWHEEL = "core_mousewheel"
|
|
30
|
+
WINDOWRESIZED = "core_windowresized"
|
|
31
|
+
TEXTINPUT = "core_textinput"
|
|
28
32
|
|
|
29
33
|
@dataclass
|
|
30
34
|
class FakeEvent:
|
|
31
35
|
type: object
|
|
32
36
|
key: object = None
|
|
37
|
+
key_code: object = None
|
|
38
|
+
x: object = None
|
|
39
|
+
y: object = None
|
|
40
|
+
dx: object = None
|
|
41
|
+
dy: object = None
|
|
42
|
+
button: object = None
|
|
43
|
+
wheel: object = None
|
|
44
|
+
size: object = None
|
|
45
|
+
text: object = None
|
|
46
|
+
scancode: object = None
|
|
47
|
+
mod: object = None
|
|
48
|
+
repeat: object = None
|
|
33
49
|
|
|
34
50
|
fake_core.Backend = FakeBackend
|
|
35
51
|
fake_core.Event = FakeEvent
|
|
@@ -37,6 +53,13 @@ def setup_fake_core_and_native(monkeypatch):
|
|
|
37
53
|
|
|
38
54
|
sys.modules["mini_arcade_core"] = fake_core
|
|
39
55
|
|
|
56
|
+
fake_keymaps = types.ModuleType("mini_arcade_core.keymaps")
|
|
57
|
+
fake_sdl = types.ModuleType("mini_arcade_core.keymaps.sdl")
|
|
58
|
+
fake_sdl.SDL_KEYCODE_TO_KEY = {} # or mapping your test expects
|
|
59
|
+
|
|
60
|
+
sys.modules["mini_arcade_core.keymaps"] = fake_keymaps
|
|
61
|
+
sys.modules["mini_arcade_core.keymaps.sdl"] = fake_sdl
|
|
62
|
+
|
|
40
63
|
# --- Fake native extension: mini_arcade_native_backend._native -------------
|
|
41
64
|
fake_native = types.ModuleType("mini_arcade_native_backend._native")
|
|
42
65
|
|
|
@@ -45,6 +68,12 @@ def setup_fake_core_and_native(monkeypatch):
|
|
|
45
68
|
Quit = "native_quit"
|
|
46
69
|
KeyDown = "native_keydown"
|
|
47
70
|
KeyUp = "native_keyup"
|
|
71
|
+
MouseMotion = "native_mousemotion"
|
|
72
|
+
MouseButtonDown = "native_mousebuttondown"
|
|
73
|
+
MouseButtonUp = "native_mousebuttonup"
|
|
74
|
+
MouseWheel = "native_mousewheel"
|
|
75
|
+
WindowResized = "native_windowresized"
|
|
76
|
+
TextInput = "native_textinput"
|
|
48
77
|
|
|
49
78
|
class FakeEngine:
|
|
50
79
|
def __init__(self):
|
|
@@ -226,36 +255,85 @@ def test_poll_events_maps_native_events_to_core_events_and_keys(
|
|
|
226
255
|
backend_module,
|
|
227
256
|
):
|
|
228
257
|
pkg, fake_core, fake_native = backend_module
|
|
229
|
-
|
|
230
258
|
backend = pkg.NativeBackend()
|
|
231
259
|
|
|
232
|
-
# Create fake native events
|
|
233
260
|
@dataclass
|
|
234
261
|
class FakeNativeEvent:
|
|
235
262
|
type: object
|
|
236
263
|
key: int = 0
|
|
264
|
+
key_code: int = 0
|
|
265
|
+
x: int = 0
|
|
266
|
+
y: int = 0
|
|
267
|
+
dx: int = 0
|
|
268
|
+
dy: int = 0
|
|
269
|
+
button: int = 0
|
|
270
|
+
wheel_x: int = 0
|
|
271
|
+
wheel_y: int = 0
|
|
272
|
+
width: int = 0
|
|
273
|
+
height: int = 0
|
|
274
|
+
text: str = ""
|
|
275
|
+
scancode: int = 0
|
|
276
|
+
mod: int = 0
|
|
277
|
+
repeat: int = 0
|
|
237
278
|
|
|
238
279
|
engine = backend._engine
|
|
239
280
|
engine._events_to_return = [
|
|
240
|
-
FakeNativeEvent(fake_native.EventType.Quit
|
|
281
|
+
FakeNativeEvent(fake_native.EventType.Quit), # -> QUIT
|
|
241
282
|
FakeNativeEvent(
|
|
242
|
-
fake_native.EventType.KeyDown, 32
|
|
283
|
+
fake_native.EventType.KeyDown, key=32
|
|
243
284
|
), # -> KEYDOWN, key=32
|
|
244
|
-
FakeNativeEvent(
|
|
285
|
+
FakeNativeEvent(
|
|
286
|
+
fake_native.EventType.MouseMotion, x=10, y=20, dx=1, dy=-2
|
|
287
|
+
),
|
|
288
|
+
FakeNativeEvent(
|
|
289
|
+
fake_native.EventType.MouseButtonDown, x=5, y=6, button=1
|
|
290
|
+
),
|
|
291
|
+
FakeNativeEvent(
|
|
292
|
+
fake_native.EventType.MouseWheel, wheel_x=0, wheel_y=-1
|
|
293
|
+
),
|
|
294
|
+
FakeNativeEvent(
|
|
295
|
+
fake_native.EventType.WindowResized, width=800, height=600
|
|
296
|
+
),
|
|
297
|
+
FakeNativeEvent(fake_native.EventType.TextInput, text="á"),
|
|
298
|
+
FakeNativeEvent("something_unknown", key=10), # -> UNKNOWN, key=10
|
|
245
299
|
]
|
|
246
300
|
|
|
247
301
|
events = backend.poll_events()
|
|
302
|
+
assert len(events) == 8
|
|
248
303
|
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
# 1) Quit event, key==0 -> key should become None
|
|
304
|
+
# Quit: key 0 -> None
|
|
252
305
|
assert events[0].type == fake_core.EventType.QUIT
|
|
253
306
|
assert events[0].key is None
|
|
254
307
|
|
|
255
|
-
#
|
|
308
|
+
# KeyDown: key passes through
|
|
256
309
|
assert events[1].type == fake_core.EventType.KEYDOWN
|
|
257
|
-
assert events[1].
|
|
258
|
-
|
|
259
|
-
#
|
|
260
|
-
assert events[2].type == fake_core.EventType.
|
|
261
|
-
assert events[2].
|
|
310
|
+
assert events[1].key_code == 32
|
|
311
|
+
|
|
312
|
+
# MouseMotion: x/y/dx/dy mapped (0 becomes None; here non-zero)
|
|
313
|
+
assert events[2].type == fake_core.EventType.MOUSEMOTION
|
|
314
|
+
assert events[2].x == 10
|
|
315
|
+
assert events[2].y == 20
|
|
316
|
+
assert events[2].dx == 1
|
|
317
|
+
assert events[2].dy == -2
|
|
318
|
+
|
|
319
|
+
# MouseButtonDown
|
|
320
|
+
assert events[3].type == fake_core.EventType.MOUSEBUTTONDOWN
|
|
321
|
+
assert events[3].x == 5
|
|
322
|
+
assert events[3].y == 6
|
|
323
|
+
assert events[3].button == 1
|
|
324
|
+
|
|
325
|
+
# MouseWheel -> wheel tuple
|
|
326
|
+
assert events[4].type == fake_core.EventType.MOUSEWHEEL
|
|
327
|
+
assert events[4].wheel == (0, -1)
|
|
328
|
+
|
|
329
|
+
# WindowResized -> size tuple
|
|
330
|
+
assert events[5].type == fake_core.EventType.WINDOWRESIZED
|
|
331
|
+
assert events[5].size == (800, 600)
|
|
332
|
+
|
|
333
|
+
# TextInput -> text
|
|
334
|
+
assert events[6].type == fake_core.EventType.TEXTINPUT
|
|
335
|
+
assert events[6].text == "á"
|
|
336
|
+
|
|
337
|
+
# Unknown
|
|
338
|
+
assert events[7].type == fake_core.EventType.UNKNOWN
|
|
339
|
+
assert events[7].key_code is None
|
{mini_arcade_native_backend-0.4.0 → mini_arcade_native_backend-0.4.2}/.github/workflows/ci.yml
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|