Skip to content

Commit

Permalink
Improve key code to key name mapping. (#784)
Browse files Browse the repository at this point in the history
Use the key detected by WebUI and our mapping only for from_settings call.
Replace the old Win + ~ with the correct value
  • Loading branch information
bzoz committed Nov 26, 2019
1 parent 51b791f commit ae4413d
Show file tree
Hide file tree
Showing 3 changed files with 26 additions and 20 deletions.
36 changes: 24 additions & 12 deletions src/common/settings_objects.h
Original file line number Diff line number Diff line change
Expand Up @@ -132,9 +132,7 @@ namespace PowerToysSettings {
}
const web::json::value& get_json() const { return m_json; }

std::wstring get_key() {
return key_from_code(get_code());
}
std::wstring get_key() { return m_json[L"key"].as_string(); }
UINT get_code() { return m_json[L"code"].as_integer(); }
bool win_pressed() { return m_json[L"win"].as_bool(); }
bool ctrl_pressed() { return m_json[L"ctrl"].as_bool(); }
Expand All @@ -151,23 +149,37 @@ namespace PowerToysSettings {
}
protected:
static std::wstring key_from_code(UINT key_code) {
auto scan_code = MapVirtualKeyW(key_code, MAPVK_VK_TO_VSC);
auto layout = GetKeyboardLayout(0);
std::array<BYTE, 256> key_states{}; // zero-initialize, no key pressed
auto scan_code = MapVirtualKeyExW(key_code, MAPVK_VK_TO_VSC_EX, layout);
// Determinate if vk is an extended key. Unfortunatly MAPVK_VK_TO_VSC_EX
// does not return correct values.
static std::vector<UINT> extended_keys = {
VK_APPS, VK_CANCEL, VK_SNAPSHOT, VK_DIVIDE, VK_NUMLOCK, VK_LWIN, VK_RWIN, VK_RMENU,
VK_RCONTROL, VK_RSHIFT, VK_RETURN, VK_INSERT, VK_DELETE, VK_PRIOR, VK_NEXT,
VK_HOME, VK_END, VK_UP, VK_DOWN, VK_LEFT, VK_RIGHT,
};
if (find(begin(extended_keys), end(extended_keys), key_code) != end(extended_keys)) {
scan_code |= 0x100;
}
std::array<BYTE, 256> key_states{}; // Zero-initialize
std::array<wchar_t, 256> output;
auto output_bytes = ToUnicodeEx(key_code, scan_code, key_states.data(), output.data(), (int)output.size() - 1, 0, layout);
if (output_bytes == 0) {
return L"(unknown)";
} else {
if (output_bytes == -1) {
output_bytes = 1;
}
if (output_bytes <= 0) {
// If ToUnicodeEx fails (e.g. for F1-F12 keys) use GetKeyNameTextW
output_bytes = GetKeyNameTextW(scan_code << 16, output.data(), static_cast<int>(output.size()));
}
if (output_bytes > 0) {
output[output_bytes] = 0;
if (output_bytes == 1 && output[0] >= 'a' && output[0] <= 'z') {
// Make Latin letters keys capital, as it looks better
output[0] = toupper(output[0]);
}
return output.data();
}
return L"(Key " + std::to_wstring(key_code) + L")";
}
HotkeyObject(web::json::value hotkey_json) : m_json(hotkey_json) {
if (m_json.has_number_field(L"code")) {
if (get_key() == L"~" && get_modifiers_repeat() == MOD_WIN) {
m_json.as_object()[L"key"] = web::json::value::string(key_from_code(get_code()));
}
};
Expand Down
8 changes: 1 addition & 7 deletions src/settings-web/src/components/HotkeySettingsControl.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -78,13 +78,7 @@ export class HotkeySettingsControl extends BaseSettingsControl {
new_value.key = '~';
}
if (!new_value.key || new_value.key === 'Unidentified') {
switch (new_value.code) {
case 192:
new_value.key = '~';
break;
default:
new_value.key = `(Key ${new_value.code})`;
}
new_value.key = `(Key ${new_value.code})`;
}
if (new_value.key.length === 1) {
new_value.key = new_value.key.toLocaleUpperCase();
Expand Down
2 changes: 1 addition & 1 deletion src/settings/settings-html/dist/bundle.js

Large diffs are not rendered by default.

0 comments on commit ae4413d

Please sign in to comment.