Files
dusk/src/input/input.c
2025-11-03 09:22:18 -06:00

122 lines
3.1 KiB
C

/**
* Copyright (c) 2025 Dominic Masters
*
* This software is released under the MIT License.
* https://opensource.org/licenses/MIT
*/
#include "input.h"
#include "assert/assert.h"
#include "util/memory.h"
#include "util/string.h"
#include "util/math.h"
input_t INPUT;
void inputInit(void) {
memoryZero(&INPUT, sizeof(input_t));
for(uint8_t i = 0; i < INPUT_ACTION_COUNT; i++) {
INPUT.actions[i].action = (inputaction_t)i;
INPUT.actions[i].lastValue = 0.0f;
INPUT.actions[i].currentValue = 0.0f;
}
INPUT.deadzone = 0.1f;
}
void inputUpdate(void) {
#if INPUT_SDL2 == 1
#if INPUT_GAMEPAD == 1
INPUT.controller = NULL;
for(int32_t i = 0; i < SDL_NumJoysticks(); i++) {
if(!SDL_IsGameController(i)) continue;
INPUT.controller = SDL_GameControllerOpen(i);
if(INPUT.controller) break;
}
#endif
#if INPUT_KEYBOARD == 1
INPUT.keyboardState = SDL_GetKeyboardState(NULL);
#endif
#endif
// Reset all actions
inputactiondata_t *action = &INPUT.actions[0];
do {
action->lastValue = action->currentValue;
action->currentValue = 0.0f;
action++;
} while(action < &INPUT.actions[INPUT_ACTION_COUNT]);
// For each button...
inputbuttondata_t *cur = &INPUT_BUTTON_DATA[0];
do {
cur->lastVal = cur->curVal;
cur->curVal = inputButtonGetValue(cur->button);
if(cur->curVal == 0.0f) {
cur++;
continue;
}
INPUT.actions[cur->action].currentValue = mathMax(
cur->curVal, INPUT.actions[cur->action].currentValue
);
cur++;
} while(cur->name);
}
float_t inputGetCurrentValue(const inputaction_t action) {
assertTrue(action < INPUT_ACTION_COUNT, "Input action out of bounds");
return INPUT.actions[action].currentValue;
}
float_t inputGetLast(const inputaction_t action) {
assertTrue(action < INPUT_ACTION_COUNT, "Input action out of bounds");
return INPUT.actions[action].lastValue;
}
bool_t inputIsDown(const inputaction_t action) {
return inputGetCurrentValue(action) > 0.0f;
}
bool_t inputWasDown(const inputaction_t action) {
return inputGetLast(action) > 0.0f;
}
bool_t inputPressed(const inputaction_t action) {
return inputIsDown(action) && !inputWasDown(action);
}
bool_t inputReleased(const inputaction_t action) {
return !inputIsDown(action) && inputWasDown(action);
}
float_t inputAxis(const inputaction_t neg, const inputaction_t pos) {
assertTrue(neg < INPUT_ACTION_COUNT, "Negative input action out of bounds");
assertTrue(pos < INPUT_ACTION_COUNT, "Positive input action out of bounds");
return inputGetCurrentValue(pos) - inputGetCurrentValue(neg);
}
void inputBind(const inputbutton_t button, const inputaction_t act) {
assertTrue(
act < INPUT_ACTION_COUNT,
"Invalid input action"
);
// Get the button data for this button.
inputbuttondata_t *data = INPUT_BUTTON_DATA;
do {
if(memoryCompare(&data->button, &button, sizeof(inputbutton_t)) == 0) {
break;
}
data++;
} while(data->name != NULL);
assertNotNull(data->name, "Input button not found");
// Bind the action.
data->action = act;
}