#pragma once #include #include // Para string, basic_string #include // Para vector // Definiciones de repetición constexpr bool INPUT_ALLOW_REPEAT = true; constexpr bool INPUT_DO_NOT_ALLOW_REPEAT = false; // Tipos de entrada enum class InputDeviceToUse : int { KEYBOARD = 0, CONTROLLER = 1, ANY = 2, }; enum class InputAction { // Inputs obligatorios UP, DOWN, LEFT, RIGHT, PAUSE, EXIT, ACCEPT, CANCEL, // Inputs personalizados JUMP, WINDOW_INC_ZOOM, WINDOW_DEC_ZOOM, TOGGLE_VIDEOMODE, TOGGLE_INTEGER_SCALE, TOGGLE_BORDER, TOGGLE_MUSIC, NEXT_PALETTE, PREVIOUS_PALETTE, TOGGLE_SHADERS, SHOW_DEBUG_INFO, // Input obligatorio NONE, SIZE }; class Input { private: // [SINGLETON] Objeto privado static Input* input; struct KeyBindings { Uint8 scancode; // Scancode asociado bool active; // Indica si está activo // Constructor explicit KeyBindings(Uint8 sc = 0, bool act = false) : scancode(sc), active(act) {} }; struct ControllerBindings { SDL_GamepadButton button; // GameControllerButton asociado bool active; // Indica si está activo bool axis_active; // Estado del eje // Constructor explicit ControllerBindings(SDL_GamepadButton btn = SDL_GAMEPAD_BUTTON_INVALID, bool act = false, bool axis_act = false) : button(btn), active(act), axis_active(axis_act) {} }; // Variables std::vector connected_controllers_; // Vector con todos los mandos conectados std::vector joysticks_; // Vector con todos los joysticks conectados std::vector key_bindings_; // Vector con las teclas asociadas a los inputs predefinidos std::vector> controller_bindings_; // Vector con los botones asociadas a los inputs predefinidos para cada mando std::vector controller_names_; // Vector con los nombres de los mandos std::vector button_inputs_; // Inputs asignados al jugador y a botones, excluyendo direcciones int num_joysticks_ = 0; // Número de joysticks conectados int num_gamepads_ = 0; // Número de mandos conectados std::string game_controller_db_path_; // Ruta al archivo gamecontrollerdb.txt // Comprueba el eje del mando auto checkAxisInput(InputAction input, int controller_index, bool repeat) -> bool; // Constructor explicit Input(const std::string& game_controller_db_path); // Destructor ~Input() = default; public: // [SINGLETON] Crearemos el objeto con esta función estática static void init(const std::string& game_controller_db_path); // [SINGLETON] Destruiremos el objeto con esta función estática static void destroy(); // [SINGLETON] Con este método obtenemos el objeto y podemos trabajar con él static auto get() -> Input*; // Asigna inputs a teclas void bindKey(InputAction input, SDL_Scancode code); // Asigna inputs a botones del mando void bindGameControllerButton(int controller_index, InputAction input, SDL_GamepadButton button); void bindGameControllerButton(int controller_index, InputAction input_target, InputAction input_source); // Comprueba si un input esta activo auto checkInput(InputAction input, bool repeat = true, InputDeviceToUse device = InputDeviceToUse::ANY, int controller_index = 0) -> bool; // Comprueba si hay almenos un input activo auto checkAnyInput(InputDeviceToUse device = InputDeviceToUse::ANY, int controller_index = 0) -> bool; // Busca si hay mandos conectados auto discoverGameControllers() -> bool; // Comprueba si hay algun mando conectado [[nodiscard]] auto gameControllerFound() const -> bool; // Obten el número de mandos conectados [[nodiscard]] auto getNumControllers() const -> int; // Obten el nombre de un mando de juego [[nodiscard]] auto getControllerName(int controller_index) const -> std::string; // Obtiene el indice del controlador a partir de un event.id [[nodiscard]] auto getJoyIndex(SDL_JoystickID id) const -> int; // Obtiene el SDL_GamepadButton asignado a un input [[nodiscard]] auto getControllerBinding(int controller_index, InputAction input) const -> SDL_GamepadButton; // Obtiene el indice a partir del nombre del mando [[nodiscard]] auto getIndexByName(const std::string& name) const -> int; };