#ifndef KEY_ACTION_MAP_
#define KEY_ACTION_MAP_

#include <Utilities/Extern.hpp>
#include <optional>
#include <ostream>
#include <string>
#include <unordered_map>

/**
 * @brief Represents a map of scancodes to actions (and vice versa), which can be saved in the settings file.
 */
class KeyActionMap final
{
private:
    std::unordered_map<std::string, SDL_Scancode> defaultMappings;
    std::unordered_map<SDL_Scancode, std::string> scancodeToAction;
    std::unordered_map<std::string, SDL_Scancode> actionToScancode;

public:
    KeyActionMap();

    /**
     * @brief Set the scancode of a given action.
     */
    void setActionScancode(const std::string &action, SDL_Scancode scancode);

    /**
     * @brief Returns the scancode corresponding to an action.
     */
    std::optional<SDL_Scancode> getScancodeForAction(const std::string &action);

    /**
     * @brief Get the action corresponding to a scancode.
     */
    std::optional<std::string> getActionForScancode(SDL_Scancode scancode);

    /**
     * @brief Deserialize the map from a string of the form "action:scancode;action:scancode;"
     */
    void deserialize(const std::string &str);

    /**
     * @brief Reset the mapping for the specified action.
     */
    void resetActionMapping(const std::string &action);

    friend std::ostream& operator<<(std::ostream &os, const KeyActionMap &map);
};

std::ostream& operator<<(std::ostream &os, const KeyActionMap &map);

#endif