forked from tas/major_tom
Initial commit
This commit is contained in:
99
src/engine/input.c
Normal file
99
src/engine/input.c
Normal file
@@ -0,0 +1,99 @@
|
||||
#include "engine/input.h"
|
||||
#include <string.h>
|
||||
|
||||
static bool s_current[ACTION_COUNT];
|
||||
static bool s_previous[ACTION_COUNT];
|
||||
|
||||
/*
|
||||
* Latched states: accumulate press/release events across frames
|
||||
* so that a press is never lost even if no update tick runs
|
||||
* during the frame it was detected.
|
||||
*/
|
||||
static bool s_latched_pressed[ACTION_COUNT];
|
||||
static bool s_latched_released[ACTION_COUNT];
|
||||
|
||||
static bool s_quit_requested;
|
||||
|
||||
/* Default key bindings (primary + alternate) */
|
||||
static SDL_Scancode s_bindings[ACTION_COUNT] = {
|
||||
[ACTION_LEFT] = SDL_SCANCODE_LEFT,
|
||||
[ACTION_RIGHT] = SDL_SCANCODE_RIGHT,
|
||||
[ACTION_UP] = SDL_SCANCODE_UP,
|
||||
[ACTION_DOWN] = SDL_SCANCODE_DOWN,
|
||||
[ACTION_JUMP] = SDL_SCANCODE_Z,
|
||||
[ACTION_SHOOT] = SDL_SCANCODE_X,
|
||||
[ACTION_DASH] = SDL_SCANCODE_C,
|
||||
[ACTION_PAUSE] = SDL_SCANCODE_ESCAPE,
|
||||
};
|
||||
|
||||
/* Alternate bindings (0 = no alternate) */
|
||||
static SDL_Scancode s_alt_bindings[ACTION_COUNT] = {
|
||||
[ACTION_SHOOT] = SDL_SCANCODE_SPACE,
|
||||
};
|
||||
|
||||
void input_init(void) {
|
||||
memset(s_current, 0, sizeof(s_current));
|
||||
memset(s_previous, 0, sizeof(s_previous));
|
||||
memset(s_latched_pressed, 0, sizeof(s_latched_pressed));
|
||||
memset(s_latched_released, 0, sizeof(s_latched_released));
|
||||
s_quit_requested = false;
|
||||
}
|
||||
|
||||
void input_poll(void) {
|
||||
/* Save previous state */
|
||||
memcpy(s_previous, s_current, sizeof(s_current));
|
||||
s_quit_requested = false;
|
||||
|
||||
/* Process SDL events */
|
||||
SDL_Event event;
|
||||
while (SDL_PollEvent(&event)) {
|
||||
switch (event.type) {
|
||||
case SDL_QUIT:
|
||||
s_quit_requested = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Read keyboard state */
|
||||
const Uint8 *keys = SDL_GetKeyboardState(NULL);
|
||||
for (int i = 0; i < ACTION_COUNT; i++) {
|
||||
s_current[i] = keys[s_bindings[i]];
|
||||
if (s_alt_bindings[i] && keys[s_alt_bindings[i]]) {
|
||||
s_current[i] = true;
|
||||
}
|
||||
|
||||
/* Latch edges: once set, stays true until consumed */
|
||||
if (s_current[i] && !s_previous[i]) {
|
||||
s_latched_pressed[i] = true;
|
||||
}
|
||||
if (!s_current[i] && s_previous[i]) {
|
||||
s_latched_released[i] = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void input_consume(void) {
|
||||
/* Clear latched states after an update tick has read them */
|
||||
memset(s_latched_pressed, 0, sizeof(s_latched_pressed));
|
||||
memset(s_latched_released, 0, sizeof(s_latched_released));
|
||||
}
|
||||
|
||||
bool input_pressed(Action a) {
|
||||
return s_latched_pressed[a];
|
||||
}
|
||||
|
||||
bool input_held(Action a) {
|
||||
return s_current[a];
|
||||
}
|
||||
|
||||
bool input_released(Action a) {
|
||||
return s_latched_released[a];
|
||||
}
|
||||
|
||||
bool input_quit_requested(void) {
|
||||
return s_quit_requested;
|
||||
}
|
||||
|
||||
void input_shutdown(void) {
|
||||
/* Nothing to clean up */
|
||||
}
|
||||
Reference in New Issue
Block a user