Add default keys CTRL+q to post a "quit" command and listen for the command in the Game::respond function. When the SHIFT key is also pressed on Linux, run a system command that stops the daemon configured at "daemon service name". This is made for arcade cabinet builds which have a daemon service managing the game.
145 lines
4.7 KiB
C++
145 lines
4.7 KiB
C++
/* +=======================================================+
|
|
____/ \____ /: Open source game framework licensed to freely use, :
|
|
\ / / : copy, and modify - created for dank.game :
|
|
+==\ ^__^ /==+ : :
|
|
: ~/ \~ : : Download at https://open.shampoo.ooo/shampoo/spacebox :
|
|
: ~~~~~~~~~~~~ : +=======================================================+
|
|
: SPACE ~~~~~ : /
|
|
: ~~~~~~~ BOX :/
|
|
+=============*/
|
|
|
|
#include "Input.hpp"
|
|
|
|
Input::Input(Node *parent) : Node(parent)
|
|
{
|
|
get_delegate().subscribe(&Input::respond, this, SDL_KEYDOWN);
|
|
get_delegate().subscribe(&Input::respond, this, SDL_KEYUP);
|
|
for (KeyCombination& combination : key_map)
|
|
{
|
|
print_key_combination(combination);
|
|
}
|
|
}
|
|
|
|
void Input::print_key_combination(const KeyCombination &combination) const
|
|
{
|
|
std::cout << "<KeyCombination " << combination.command << ", " <<
|
|
combination.key << ", ctrl " << combination.ctrl << ", shift " <<
|
|
combination.shift << ", alt " << combination.alt << ">" << std::endl;
|
|
}
|
|
|
|
void Input::load_key_map()
|
|
{
|
|
const nlohmann::json& config = configuration()();
|
|
for (const auto& [command, input] : config.at("keys").items())
|
|
{
|
|
if (input.is_array() && input.size())
|
|
{
|
|
if (input[0].is_array())
|
|
{
|
|
for (nlohmann::json version : input)
|
|
{
|
|
key_map.push_back(parse_key(command, version));
|
|
}
|
|
}
|
|
else
|
|
{
|
|
key_map.push_back(parse_key(command, input));
|
|
}
|
|
}
|
|
else if (!input.is_array())
|
|
{
|
|
SDL_Keycode code = SDL_GetKeyFromName(input.get<std::string>().c_str());
|
|
if (code == SDLK_UNKNOWN)
|
|
{
|
|
sb::Log::Multi(sb::Log::WARN) << "Unknown key in config mapped to \"" << command << "\": " << input <<
|
|
sb::Log::end;
|
|
}
|
|
key_map.push_back((KeyCombination){command, code, false, false, false});
|
|
}
|
|
}
|
|
}
|
|
|
|
KeyCombination Input::parse_key(const std::string& command, const nlohmann::json& json) const
|
|
{
|
|
SDL_Keycode key_code;
|
|
bool ctrl = false, alt = false, shift = false;
|
|
for (const std::string component : json)
|
|
{
|
|
if (component == "CTRL")
|
|
{
|
|
ctrl = true;
|
|
}
|
|
else if (component == "SHIFT")
|
|
{
|
|
shift = true;
|
|
}
|
|
else if (component == "ALT")
|
|
{
|
|
alt = true;
|
|
}
|
|
else
|
|
{
|
|
key_code = SDL_GetKeyFromName(component.c_str());
|
|
}
|
|
}
|
|
return (KeyCombination){command, key_code, ctrl, shift, alt};
|
|
}
|
|
|
|
void Input::add_to_key_map(std::string command, SDL_Keycode key_code, bool ctrl, bool shift, bool alt)
|
|
{
|
|
key_map.push_back((KeyCombination){command, key_code, ctrl, shift, alt});
|
|
}
|
|
|
|
void Input::respond(SDL_Event &event)
|
|
{
|
|
if (!is_suppressed())
|
|
{
|
|
SDL_Keymod mod = SDL_GetModState();
|
|
SDL_Keycode sym = event.key.keysym.sym;
|
|
bool found_command = false, cancel = event.type != SDL_KEYDOWN, ctrl = mod & KMOD_CTRL,
|
|
shift = mod & KMOD_SHIFT, alt = mod & KMOD_ALT,
|
|
suppress_any_key = configuration()["input"]["suppress any key on mods"] && (ctrl || alt);
|
|
const std::vector<std::string>& system_any_key_ignore = configuration()["input"]["system any key ignore commands"];
|
|
const std::vector<std::string>& any_key_ignore = configuration()["input"]["any key ignore commands"];
|
|
bool ignore_repeat = configuration()["input"]["ignore repeat keypress"];
|
|
if (event.key.repeat == 0 || !ignore_repeat)
|
|
{
|
|
for (KeyCombination& combination : key_map)
|
|
{
|
|
if (sym == combination.key &&
|
|
(!combination.ctrl || ctrl) &&
|
|
(!combination.shift || shift) &&
|
|
(!combination.alt || alt))
|
|
{
|
|
sb::Delegate::post(combination.command, cancel);
|
|
if (!sb::contains(system_any_key_ignore, combination.command) && !found_command &&
|
|
!sb::contains(any_key_ignore, combination.command) && !suppress_any_key)
|
|
{
|
|
sb::Delegate::post(any, cancel);
|
|
}
|
|
found_command = true;
|
|
}
|
|
}
|
|
if (!found_command && !suppress_any_key)
|
|
{
|
|
sb::Delegate::post(any, cancel);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
void Input::suppress()
|
|
{
|
|
suppressed = true;
|
|
}
|
|
|
|
void Input::unsuppress()
|
|
{
|
|
suppressed = false;
|
|
}
|
|
|
|
bool Input::is_suppressed()
|
|
{
|
|
return suppressed;
|
|
}
|