openMSX
Shortcuts.cc
Go to the documentation of this file.
1#include "Shortcuts.hh"
2
3#include "one_of.hh"
4
5#include "imgui_internal.h"
6
7#include <array>
8
9namespace openmsx {
10
11// When adding a new shortcut:
12// * Add a new value in 'enum Shortcuts::ID'
13// * Add a single line in this table
16 ImGuiKeyChord keyChord;
18 bool repeat;
19 zstring_view name; // used in settings.xml
20 zstring_view description; // shown in GUI
21};
22using enum Shortcuts::ID;
23using enum Shortcuts::Type;
24static constexpr auto allShortcutInfo = std::to_array<AllShortcutInfo>({
25 {HEX_GOTO_ADDR, ImGuiKey_G | ImGuiMod_Ctrl, ALWAYS_LOCAL, false, "hex_editor_goto_address", "Go to address in hex viewer"},
26 {DEBUGGER_STEP_IN, ImGuiKey_F7, LOCAL, true, "step-in", "Debugger: step-in"},
27 {DEBUGGER_STEP_OVER, ImGuiKey_F8, LOCAL, true, "step-over", "Debugger: step-over"},
28 {DEBUGGER_STEP_OUT, ImGuiKey_F7 | ImGuiMod_Shift, LOCAL, true, "step-out", "Debugger: step-out"},
29 {DEBUGGER_STEP_BACK, ImGuiKey_F8 | ImGuiMod_Shift, LOCAL, true, "step-back", "Debugger: step-back"},
30 {DEBUGGER_BREAK_CONTINUE, ImGuiKey_F5, LOCAL, false, "break-continue", "Debugger: toggle break / continue"},
31 {DISASM_GOTO_ADDR, ImGuiMod_Ctrl | ImGuiKey_G, ALWAYS_LOCAL, false, "disasm_goto_address", "Scroll to address in disassembler"},
32 {DISASM_RUN_TO_ADDR, ImGuiMod_Ctrl | ImGuiKey_R, ALWAYS_LOCAL, false, "disasm_run_to_address", "Debugger: run to a specific address"},
33});
34static_assert(allShortcutInfo.size() == to_underlying(Shortcuts::ID::NUM));
35
36static constexpr auto defaultShortcuts = []{
38 for (int i = 0; i < to_underlying(Shortcuts::ID::NUM); ++i) {
39 const auto& all = allShortcutInfo[i];
40 auto id = static_cast<Shortcuts::ID>(i);
41 assert(all.id == id); // verify that rows are in-order
42 result[id].keyChord = all.keyChord;
43 result[id].type = all.type;
44 }
45 return result;
46}();
47
48static constexpr auto shortcutRepeats = []{
50 for (int i = 0; i < to_underlying(Shortcuts::ID::NUM); ++i) {
51 auto id = static_cast<Shortcuts::ID>(i);
52 result[id] = allShortcutInfo[i].repeat;
53 }
54 return result;
55}();
56
57static constexpr auto shortcutNames = []{
59 for (int i = 0; i < to_underlying(Shortcuts::ID::NUM); ++i) {
60 auto id = static_cast<Shortcuts::ID>(i);
61 result[id] = allShortcutInfo[i].name;
62 }
63 return result;
64}();
65
66static constexpr auto shortcutDescriptions = []{
68 for (int i = 0; i < to_underlying(Shortcuts::ID::NUM); ++i) {
69 auto id = static_cast<Shortcuts::ID>(i);
70 result[id] = allShortcutInfo[i].description;
71 }
72 return result;
73}();
74
79
81{
82 shortcuts = defaultShortcuts; // this can overwrite the 'type' field
83}
84
86{
87 return defaultShortcuts[id];
88}
89
91{
92 return shortcuts[id];
93}
94
95void Shortcuts::setShortcut(ID id, const Shortcut& shortcut)
96{
97 auto oldType = shortcuts[id].type;
98 shortcuts[id] = shortcut;
100 // cannot change this
101 shortcuts[id].type = oldType;
102 }
103}
104
106{
107 return shortcutRepeats[id];
108}
109
111{
112 return shortcutNames[id];
113}
114
115std::optional<Shortcuts::ID> Shortcuts::parseShortcutName(std::string_view name)
116{
117 auto it = ranges::find(shortcutNames, name);
118 if (it == shortcutNames.end()) return {};
119 return static_cast<Shortcuts::ID>(std::distance(shortcutNames.begin(), it));
120}
121
122std::optional<Shortcuts::Type> Shortcuts::parseType(std::string_view name)
123{
124 if (name == "global") return GLOBAL;
125 if (name == "local") return LOCAL;
126 return {};
127}
128
130{
131 return shortcutDescriptions[id];
132}
133
135{
136 assert(shortcut.keyChord != ImGuiKey_None);
137 auto flags = (shortcut.type == one_of(GLOBAL, ALWAYS_GLOBAL) ? ImGuiInputFlags_RouteGlobalLow : 0)
138 | ImGuiInputFlags_RouteUnlessBgFocused
139 | (shortcut.repeat ? ImGuiInputFlags_Repeat : 0);
140 return ImGui::Shortcut(shortcut.keyChord, 0, flags);
141}
142
144{
145 const auto& shortcut = shortcuts[id];
146 if (shortcut.keyChord == ImGuiKey_None) return false;
147 return checkShortcut({shortcut.keyChord, shortcut.type, getShortcutRepeat(id)});
148}
149
150} // namespace openmsx
uintptr_t id
static zstring_view getShortcutName(ID id)
Definition Shortcuts.cc:110
void setDefaultShortcuts()
Definition Shortcuts.cc:80
static const Shortcut & getDefaultShortcut(ID id)
Definition Shortcuts.cc:85
static zstring_view getShortcutDescription(ID id)
Definition Shortcuts.cc:129
bool checkShortcut(const ShortcutWithRepeat &shortcut) const
Definition Shortcuts.cc:134
static std::optional< ID > parseShortcutName(std::string_view name)
Definition Shortcuts.cc:115
static std::optional< Type > parseType(std::string_view name)
Definition Shortcuts.cc:122
void setShortcut(ID id, const Shortcut &shortcut)
Definition Shortcuts.cc:95
const Shortcut & getShortcut(ID id) const
Definition Shortcuts.cc:90
static bool getShortcutRepeat(ID id)
Definition Shortcuts.cc:105
Like std::string_view, but with the extra guarantee that it refers to a zero-terminated string.
This file implemented 3 utility functions:
Definition Autofire.cc:11
auto find(InputRange &&range, const T &value)
Definition ranges.hh:162
constexpr auto to_underlying(E e) noexcept
Definition stl.hh:465
Shortcuts::Type type
Definition Shortcuts.cc:17
zstring_view description
Definition Shortcuts.cc:20
ImGuiKeyChord keyChord
Definition Shortcuts.cc:16