clang-format

This commit is contained in:
kalaposfos13 2024-11-14 14:44:34 +01:00
parent 1a8f177526
commit 9c81f8e2f2
4 changed files with 146 additions and 112 deletions

View File

@ -5,38 +5,38 @@
#include "fstream" #include "fstream"
#include "iostream" #include "iostream"
#include "map"
#include "unordered_map"
#include "list" #include "list"
#include "map"
#include "sstream" #include "sstream"
#include "string" #include "string"
#include "unordered_map"
#include "vector" #include "vector"
#include "SDL3/SDL_events.h" #include "SDL3/SDL_events.h"
#include "SDL3/SDL_timer.h" #include "SDL3/SDL_timer.h"
#include "common/config.h" #include "common/config.h"
#include "common/elf_info.h"
#include "common/io_file.h" #include "common/io_file.h"
#include "common/path_util.h" #include "common/path_util.h"
#include "common/version.h" #include "common/version.h"
#include "common/elf_info.h"
#include "input/controller.h" #include "input/controller.h"
namespace Input { namespace Input {
/* /*
Project structure: Project structure:
n to m connection between inputs and outputs n to m connection between inputs and outputs
Keyup and keydown events update a dynamic list* of u32 'flags' (what is currently in the list is 'pressed') Keyup and keydown events update a dynamic list* of u32 'flags' (what is currently in the list is
On every event, after flag updates, we check for every input binding -> controller output pair if all their flags are 'on' 'pressed') On every event, after flag updates, we check for every input binding -> controller output
If not, disable; if so, enable them. pair if all their flags are 'on' If not, disable; if so, enable them. For axes, we gather their data
For axes, we gather their data into a struct cumulatively from all inputs, into a struct cumulatively from all inputs, then after we checked all of those, we update them all
then after we checked all of those, we update them all at once. at once. Wheel inputs generate a timer that doesn't turn off their outputs automatically, but push a
Wheel inputs generate a timer that doesn't turn off their outputs automatically, but push a userevent to do so. userevent to do so.
What structs are needed? What structs are needed?
InputBinding(key1, key2, key3) InputBinding(key1, key2, key3)
ControllerOutput(button, axis) - we only need a const array of these, and one of the attr-s is always 0 ControllerOutput(button, axis) - we only need a const array of these, and one of the attr-s is
BindingConnection(inputBinding (member), controllerOutput (ref to the array element)) always 0 BindingConnection(inputBinding (member), controllerOutput (ref to the array element))
*/ */
// Flags and values for varying purposes // Flags and values for varying purposes
@ -50,7 +50,6 @@ std::list<std::pair<u32, bool>> pressed_keys;
std::list<u32> toggled_keys; std::list<u32> toggled_keys;
std::list<BindingConnection> connections = std::list<BindingConnection>(); std::list<BindingConnection> connections = std::list<BindingConnection>();
ControllerOutput output_array[] = { ControllerOutput output_array[] = {
// Button mappings // Button mappings
ControllerOutput(OrbisPadButtonDataOffset::ORBIS_PAD_BUTTON_TRIANGLE), ControllerOutput(OrbisPadButtonDataOffset::ORBIS_PAD_BUTTON_TRIANGLE),
@ -71,20 +70,15 @@ ControllerOutput output_array[] = {
ControllerOutput(OrbisPadButtonDataOffset::ORBIS_PAD_BUTTON_RIGHT), ControllerOutput(OrbisPadButtonDataOffset::ORBIS_PAD_BUTTON_RIGHT),
// Axis mappings // Axis mappings
ControllerOutput(0, Input::Axis::LeftX), ControllerOutput(0, Input::Axis::LeftX), ControllerOutput(0, Input::Axis::LeftY),
ControllerOutput(0, Input::Axis::LeftY), ControllerOutput(0, Input::Axis::RightX), ControllerOutput(0, Input::Axis::RightY),
ControllerOutput(0, Input::Axis::RightX), ControllerOutput(0, Input::Axis::TriggerLeft), ControllerOutput(0, Input::Axis::TriggerRight),
ControllerOutput(0, Input::Axis::RightY),
ControllerOutput(0, Input::Axis::TriggerLeft),
ControllerOutput(0, Input::Axis::TriggerRight),
ControllerOutput(LEFTJOYSTICK_HALFMODE), ControllerOutput(LEFTJOYSTICK_HALFMODE), ControllerOutput(RIGHTJOYSTICK_HALFMODE),
ControllerOutput(RIGHTJOYSTICK_HALFMODE),
ControllerOutput(KEY_TOGGLE), ControllerOutput(KEY_TOGGLE),
// End marker to signify the end of the array // End marker to signify the end of the array
ControllerOutput(0, Input::Axis::AxisMax) ControllerOutput(0, Input::Axis::AxisMax)};
};
// We had to go through 3 files of indirection just to update a flag // We had to go through 3 files of indirection just to update a flag
void toggleMouseEnabled() { void toggleMouseEnabled() {
@ -113,9 +107,12 @@ InputBinding getBindingFromString(std::string& line) {
} }
// Assign values to keys if all tokens were valid // Assign values to keys if all tokens were valid
if (tokens.size() > 0) key1 = string_to_keyboard_key_map.at(tokens[0]); if (tokens.size() > 0)
if (tokens.size() > 1) key2 = string_to_keyboard_key_map.at(tokens[1]); key1 = string_to_keyboard_key_map.at(tokens[0]);
if (tokens.size() > 2) key3 = string_to_keyboard_key_map.at(tokens[2]); if (tokens.size() > 1)
key2 = string_to_keyboard_key_map.at(tokens[1]);
if (tokens.size() > 2)
key3 = string_to_keyboard_key_map.at(tokens[2]);
return InputBinding(key1, key2, key3); return InputBinding(key1, key2, key3);
} }
@ -165,7 +162,8 @@ void parseInputConfig(const std::string game_id = "") {
// Split the line by '=' // Split the line by '='
std::size_t equal_pos = line.find('='); std::size_t equal_pos = line.find('=');
if (equal_pos == std::string::npos) { if (equal_pos == std::string::npos) {
LOG_ERROR(Input, "Invalid format at line: {}, data: \"{}\", skipping line.", lineCount, line); LOG_ERROR(Input, "Invalid format at line: {}, data: \"{}\", skipping line.", lineCount,
line);
continue; continue;
} }
@ -173,7 +171,6 @@ void parseInputConfig(const std::string game_id = "") {
std::string input_string = line.substr(equal_pos + 1); std::string input_string = line.substr(equal_pos + 1);
std::size_t comma_pos = input_string.find(','); std::size_t comma_pos = input_string.find(',');
// special check for mouse to joystick input // special check for mouse to joystick input
if (output_string == "mouse_to_joystick") { if (output_string == "mouse_to_joystick") {
if (input_string == "left") { if (input_string == "left") {
@ -191,30 +188,33 @@ void parseInputConfig(const std::string game_id = "") {
// handle key-to-key toggling (separate list?) // handle key-to-key toggling (separate list?)
InputBinding toggle_keys = getBindingFromString(input_string); InputBinding toggle_keys = getBindingFromString(input_string);
if (toggle_keys.keyCount() != 2) { if (toggle_keys.keyCount() != 2) {
LOG_ERROR(Input, "Syntax error: Please provide exactly 2 keys: " LOG_ERROR(Input,
"first is the toggler, the second is the key to toggle: {}", line); "Syntax error: Please provide exactly 2 keys: "
"first is the toggler, the second is the key to toggle: {}",
line);
continue; continue;
} }
ControllerOutput* toggle_out = getOutputPointer(ControllerOutput(KEY_TOGGLE)); ControllerOutput* toggle_out = getOutputPointer(ControllerOutput(KEY_TOGGLE));
BindingConnection toggle_connection = BindingConnection(InputBinding(toggle_keys.key2), toggle_out, toggle_keys.key3); BindingConnection toggle_connection =
BindingConnection(InputBinding(toggle_keys.key2), toggle_out, toggle_keys.key3);
connections.insert(connections.end(), toggle_connection); connections.insert(connections.end(), toggle_connection);
continue; continue;
} }
LOG_ERROR(Input, "Invalid format at line: {}, data: \"{}\", skipping line.", lineCount, line); LOG_ERROR(Input, "Invalid format at line: {}, data: \"{}\", skipping line.", lineCount,
line);
continue; continue;
} }
if (output_string == "mouse_movement_params") { if (output_string == "mouse_movement_params") {
std::stringstream ss(input_string); std::stringstream ss(input_string);
char comma; // To hold the comma separators between the floats char comma; // To hold the comma separators between the floats
ss >> mouse_deadzone_offset >> comma ss >> mouse_deadzone_offset >> comma >> mouse_speed >> comma >> mouse_speed_offset;
>> mouse_speed >> comma
>> mouse_speed_offset;
// Check for invalid input (in case there's an unexpected format) // Check for invalid input (in case there's an unexpected format)
if (ss.fail()) { if (ss.fail()) {
LOG_ERROR(Input, "Failed to parse mouse movement parameters from line: {}", line); LOG_ERROR(Input, "Failed to parse mouse movement parameters from line: {}", line);
} else { } else {
//LOG_DEBUG(Input, "Mouse movement parameters parsed: {} {} {}", mouse_deadzone_offset, mouse_speed, mouse_speed_offset); // LOG_DEBUG(Input, "Mouse movement parameters parsed: {} {} {}",
// mouse_deadzone_offset, mouse_speed, mouse_speed_offset);
} }
continue; continue;
@ -227,18 +227,23 @@ void parseInputConfig(const std::string game_id = "") {
auto axis_it = string_to_axis_map.find(output_string); auto axis_it = string_to_axis_map.find(output_string);
if (binding.isEmpty()) { if (binding.isEmpty()) {
LOG_DEBUG(Input, "Invalid format at line: {}, data: \"{}\", skipping line.", lineCount, line); LOG_DEBUG(Input, "Invalid format at line: {}, data: \"{}\", skipping line.", lineCount,
line);
continue; continue;
} }
if (button_it != string_to_cbutton_map.end()) { if (button_it != string_to_cbutton_map.end()) {
connection = BindingConnection(binding, getOutputPointer(ControllerOutput(button_it->second))); connection =
BindingConnection(binding, getOutputPointer(ControllerOutput(button_it->second)));
connections.insert(connections.end(), connection); connections.insert(connections.end(), connection);
} else if (axis_it != string_to_axis_map.end()) { } else if (axis_it != string_to_axis_map.end()) {
connection = BindingConnection(binding, getOutputPointer(ControllerOutput(0, axis_it->second.axis)), axis_it->second.value); connection = BindingConnection(
binding, getOutputPointer(ControllerOutput(0, axis_it->second.axis)),
axis_it->second.value);
connections.insert(connections.end(), connection); connections.insert(connections.end(), connection);
} else { } else {
LOG_DEBUG(Input, "Invalid format at line: {}, data: \"{}\", skipping line.", lineCount, line); LOG_DEBUG(Input, "Invalid format at line: {}, data: \"{}\", skipping line.", lineCount,
line);
continue; continue;
} }
// LOG_INFO(Input, "Succesfully parsed line {}", lineCount); // LOG_INFO(Input, "Succesfully parsed line {}", lineCount);
@ -403,7 +408,8 @@ void ControllerOutput::addUpdate(bool pressed, u32 param) {
} }
axis_value = SDL_clamp((pressed ? (int)param : 0) * multiplier + axis_value, -127, 127); axis_value = SDL_clamp((pressed ? (int)param : 0) * multiplier + axis_value, -127, 127);
controller->Axis(0, axis, GetAxis(-0x80, 0x80, axis_value)); controller->Axis(0, axis, GetAxis(-0x80, 0x80, axis_value));
//LOG_INFO(Input, "Axis value delta: {} final value: {}", (pressed ? a_value : 0), axis_value); // LOG_INFO(Input, "Axis value delta: {} final value: {}", (pressed ? a_value : 0),
// axis_value);
} else { } else {
LOG_DEBUG(Input, "Controller output with no values detected!"); LOG_DEBUG(Input, "Controller output with no values detected!");
} }
@ -412,7 +418,8 @@ void ControllerOutput::addUpdate(bool pressed, u32 param) {
void updatePressedKeys(u32 value, bool is_pressed) { void updatePressedKeys(u32 value, bool is_pressed) {
if (is_pressed) { if (is_pressed) {
// Find the correct position for insertion to maintain order // Find the correct position for insertion to maintain order
auto it = std::lower_bound(pressed_keys.begin(), pressed_keys.end(), value, auto it =
std::lower_bound(pressed_keys.begin(), pressed_keys.end(), value,
[](const std::pair<u32, bool>& pk, u32 v) { return pk.first < v; }); [](const std::pair<u32, bool>& pk, u32 v) { return pk.first < v; });
// Insert only if 'value' is not already in the list // Insert only if 'value' is not already in the list
@ -421,7 +428,8 @@ void updatePressedKeys(u32 value, bool is_pressed) {
} }
} else { } else {
// Remove 'value' from the list if it's not pressed // Remove 'value' from the list if it's not pressed
auto it = std::find_if(pressed_keys.begin(), pressed_keys.end(), auto it =
std::find_if(pressed_keys.begin(), pressed_keys.end(),
[value](const std::pair<u32, bool>& pk) { return pk.first == value; }); [value](const std::pair<u32, bool>& pk) { return pk.first == value; });
if (it != pressed_keys.end()) { if (it != pressed_keys.end()) {
pressed_keys.erase(it); // Remove the key entirely from the list pressed_keys.erase(it); // Remove the key entirely from the list
@ -435,9 +443,12 @@ bool isInputActive(const InputBinding& i) {
bool* flag2 = nullptr; bool* flag2 = nullptr;
bool* flag3 = nullptr; bool* flag3 = nullptr;
bool key1_pressed = std::find(toggled_keys.begin(), toggled_keys.end(), i.key1) != toggled_keys.end(); bool key1_pressed =
bool key2_pressed = std::find(toggled_keys.begin(), toggled_keys.end(), i.key2) != toggled_keys.end(); std::find(toggled_keys.begin(), toggled_keys.end(), i.key1) != toggled_keys.end();
bool key3_pressed = std::find(toggled_keys.begin(), toggled_keys.end(), i.key3) != toggled_keys.end(); bool key2_pressed =
std::find(toggled_keys.begin(), toggled_keys.end(), i.key2) != toggled_keys.end();
bool key3_pressed =
std::find(toggled_keys.begin(), toggled_keys.end(), i.key3) != toggled_keys.end();
// First pass: locate each key and save pointers to their flags if found // First pass: locate each key and save pointers to their flags if found
for (auto& entry : pressed_keys) { for (auto& entry : pressed_keys) {
@ -461,19 +472,23 @@ bool isInputActive(const InputBinding& i) {
return false; return false;
} }
// Check if all flags are already true, which indicates this input is overridden (only if the key is not 0) // Check if all flags are already true, which indicates this input is overridden (only if the
if ((i.key1 == 0 || (flag1 && *flag1)) && // key is not 0)
(i.key2 == 0 || (flag2 && *flag2)) && if ((i.key1 == 0 || (flag1 && *flag1)) && (i.key2 == 0 || (flag2 && *flag2)) &&
(i.key3 == 0 || (flag3 && *flag3))) { (i.key3 == 0 || (flag3 && *flag3))) {
return false; // This input is overridden by another input return false; // This input is overridden by another input
} }
// Set flags to true only after confirming all keys are present and not overridden // Set flags to true only after confirming all keys are present and not overridden
if (flag1 && !key1_pressed) *flag1 = true; if (flag1 && !key1_pressed)
if (flag2 && !key2_pressed) *flag2 = true; *flag1 = true;
if (flag3 && !key3_pressed) *flag3 = true; if (flag2 && !key2_pressed)
*flag2 = true;
if (flag3 && !key3_pressed)
*flag3 = true;
LOG_DEBUG(Input, "A valid held input is found: {}, flag ptrs: {} {} {}", i.toString(), fmt::ptr(flag1), fmt::ptr(flag2), fmt::ptr(flag3)); LOG_DEBUG(Input, "A valid held input is found: {}, flag ptrs: {} {} {}", i.toString(),
fmt::ptr(flag1), fmt::ptr(flag2), fmt::ptr(flag3));
return true; return true;
} }
@ -484,18 +499,21 @@ void activateOutputsFromInputs() {
if (it->output) { if (it->output) {
it->output->update(false, 0); it->output->update(false, 0);
} else { } else {
LOG_DEBUG(Input, "Null output in BindingConnection at position {}", std::distance(connections.begin(), it)); LOG_DEBUG(Input, "Null output in BindingConnection at position {}",
std::distance(connections.begin(), it));
} }
} }
for (auto it : pressed_keys) { for (auto it : pressed_keys) {
it.second = false; it.second = false;
} }
// iterates over the connections, and updates them depending on whether the corresponding input trio is found // iterates over the connections, and updates them depending on whether the corresponding input
// trio is found
for (auto it = connections.begin(); it != connections.end(); it++) { for (auto it = connections.begin(); it != connections.end(); it++) {
if (it->output) { if (it->output) {
it->output->addUpdate(isInputActive(it->binding), it->parameter); it->output->addUpdate(isInputActive(it->binding), it->parameter);
} else { } else {
//LOG_DEBUG(Input, "Null output in BindingConnection at position {}", std::distance(connections.begin(), it)); // LOG_DEBUG(Input, "Null output in BindingConnection at position {}",
// std::distance(connections.begin(), it));
} }
} }
} }
@ -543,4 +561,4 @@ Uint32 mousePolling(void* param, Uint32 id, Uint32 interval) {
return interval; return interval;
} }
} } // namespace Input

View File

@ -4,14 +4,14 @@
#pragma once #pragma once
#include "array" #include "array"
#include "map"
#include "unordered_set"
#include "string"
#include "common/types.h"
#include "common/logging/log.h" #include "common/logging/log.h"
#include "common/types.h"
#include "core/libraries/pad/pad.h" #include "core/libraries/pad/pad.h"
#include "fmt/format.h" #include "fmt/format.h"
#include "input/controller.h" #include "input/controller.h"
#include "map"
#include "string"
#include "unordered_set"
#include "SDL3/SDL_events.h" #include "SDL3/SDL_events.h"
#include "SDL3/SDL_timer.h" #include "SDL3/SDL_timer.h"
@ -186,26 +186,47 @@ class InputBinding {
public: public:
u32 key1, key2, key3; u32 key1, key2, key3;
InputBinding(u32 k1 = SDLK_UNKNOWN, u32 k2 = SDLK_UNKNOWN, u32 k3 = SDLK_UNKNOWN) { InputBinding(u32 k1 = SDLK_UNKNOWN, u32 k2 = SDLK_UNKNOWN, u32 k3 = SDLK_UNKNOWN) {
// we format the keys so comparing them will be very fast, because we will only have to compare 3 sorted elements, // we format the keys so comparing them will be very fast, because we will only have to
// where the only possible duplicate item is 0 // compare 3 sorted elements, where the only possible duplicate item is 0
// duplicate entries get changed to one original, one null // duplicate entries get changed to one original, one null
if(k1 == k2 && k1 != SDLK_UNKNOWN) { k2 = 0; } if (k1 == k2 && k1 != SDLK_UNKNOWN) {
if(k1 == k3 && k1 != SDLK_UNKNOWN) { k3 = 0; } k2 = 0;
if(k3 == k2 && k2 != SDLK_UNKNOWN) { k2 = 0; } }
if (k1 == k3 && k1 != SDLK_UNKNOWN) {
k3 = 0;
}
if (k3 == k2 && k2 != SDLK_UNKNOWN) {
k2 = 0;
}
// this sorts them // this sorts them
if (k1 <= k2 && k1 <= k3) { if (k1 <= k2 && k1 <= k3) {
key1 = k1; key1 = k1;
if (k2 <= k3) { key2 = k2; key3 = k3; } if (k2 <= k3) {
else { key2 = k3; key3 = k2; } key2 = k2;
key3 = k3;
} else {
key2 = k3;
key3 = k2;
}
} else if (k2 <= k1 && k2 <= k3) { } else if (k2 <= k1 && k2 <= k3) {
key1 = k2; key1 = k2;
if (k1 <= k3) { key2 = k1; key3 = k3; } if (k1 <= k3) {
else { key2 = k3; key3 = k1; } key2 = k1;
key3 = k3;
} else {
key2 = k3;
key3 = k1;
}
} else { } else {
key1 = k3; key1 = k3;
if (k1 <= k2) { key2 = k1; key3 = k2; } if (k1 <= k2) {
else { key2 = k2; key3 = k1; } key2 = k1;
key3 = k2;
} else {
key2 = k2;
key3 = k1;
}
} }
} }
// copy ctor // copy ctor
@ -236,10 +257,10 @@ public:
// returns a u32 based on the event type (keyboard, mouse buttons, or wheel) // returns a u32 based on the event type (keyboard, mouse buttons, or wheel)
static u32 getInputIDFromEvent(const SDL_Event& e); static u32 getInputIDFromEvent(const SDL_Event& e);
}; };
class ControllerOutput { class ControllerOutput {
static GameController* controller; static GameController* controller;
public: public:
static void setControllerOutputController(GameController* c); static void setControllerOutputController(GameController* c);
@ -291,13 +312,9 @@ void updatePressedKeys(u32 button, bool is_pressed);
void activateOutputsFromInputs(); void activateOutputsFromInputs();
void updateMouse(GameController* controller); void updateMouse(GameController* controller);
// Polls the mouse for changes, and simulates joystick movement from it. // Polls the mouse for changes, and simulates joystick movement from it.
Uint32 mousePolling(void* param, Uint32 id, Uint32 interval); Uint32 mousePolling(void* param, Uint32 id, Uint32 interval);
} // namespace Input
}

View File

@ -8,8 +8,8 @@
#include "SDL3/SDL_video.h" #include "SDL3/SDL_video.h"
#include "common/assert.h" #include "common/assert.h"
#include "common/config.h" #include "common/config.h"
#include "common/version.h"
#include "common/elf_info.h" #include "common/elf_info.h"
#include "common/version.h"
#include "core/libraries/pad/pad.h" #include "core/libraries/pad/pad.h"
#include "imgui/renderer/imgui_core.h" #include "imgui/renderer/imgui_core.h"
#include "input/controller.h" #include "input/controller.h"
@ -200,7 +200,6 @@ void WindowSDL::onKeyboardMouseInput(const SDL_Event* event) {
// update bindings // update bindings
Input::activateOutputsFromInputs(); Input::activateOutputsFromInputs();
} }
void WindowSDL::onGamepadEvent(const SDL_Event* event) { void WindowSDL::onGamepadEvent(const SDL_Event* event) {

View File

@ -3,8 +3,8 @@
#pragma once #pragma once
#include "string"
#include "common/types.h" #include "common/types.h"
#include "string"
struct SDL_Window; struct SDL_Window;
struct SDL_Gamepad; struct SDL_Gamepad;