mirror of
https://github.com/microsoft/PowerToys.git
synced 2024-12-05 04:39:08 +08:00
Added unique lock mutexes to KeyboardManagerState (dev/keyboardManager) (#1789)
* Added unique lock mutexes for thread safety * Fixed a bug in detect key logic * Added early unlock statements to fix issue with shortcut guide * Added comments for unlocks before SendInput and changed some unique_locks to lock_guards
This commit is contained in:
parent
467cf919be
commit
ac26818005
@ -3,15 +3,17 @@
|
||||
|
||||
// Constructor
|
||||
KeyboardManagerState::KeyboardManagerState() :
|
||||
uiState(KeyboardManagerUIState::Deactivated), currentUIWindow(nullptr), currentShortcutTextBlock(nullptr), currentSingleKeyRemapTextBlock(nullptr)
|
||||
uiState(KeyboardManagerUIState::Deactivated), currentUIWindow(nullptr), currentShortcutTextBlock(nullptr), currentSingleKeyRemapTextBlock(nullptr), detectedRemapKey(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
// Function to check the if the UI state matches the argument state. For states with activated windows it also checks if the window is in focus.
|
||||
bool KeyboardManagerState::CheckUIState(KeyboardManagerUIState state)
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(uiState_mutex);
|
||||
if (uiState == state)
|
||||
{
|
||||
std::unique_lock<std::mutex> lock(currentUIWindow_mutex);
|
||||
if (uiState == KeyboardManagerUIState::Deactivated)
|
||||
{
|
||||
return true;
|
||||
@ -30,73 +32,114 @@ bool KeyboardManagerState::CheckUIState(KeyboardManagerUIState state)
|
||||
// Function to set the window handle of the current UI window that is activated
|
||||
void KeyboardManagerState::SetCurrentUIWindow(HWND windowHandle)
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(currentUIWindow_mutex);
|
||||
currentUIWindow = windowHandle;
|
||||
}
|
||||
|
||||
// Function to set the UI state. When a window is activated, the handle to the window can be passed in the windowHandle argument.
|
||||
void KeyboardManagerState::SetUIState(KeyboardManagerUIState state, HWND windowHandle)
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(uiState_mutex);
|
||||
uiState = state;
|
||||
currentUIWindow = windowHandle;
|
||||
SetCurrentUIWindow(windowHandle);
|
||||
}
|
||||
|
||||
// Function to reset the UI state members
|
||||
void KeyboardManagerState::ResetUIState()
|
||||
{
|
||||
SetUIState(KeyboardManagerUIState::Deactivated);
|
||||
currentShortcutTextBlock = nullptr;
|
||||
detectedShortcut.clear();
|
||||
|
||||
// Reset all the single key remap stored variables.
|
||||
// Reset the shortcut UI stored variables
|
||||
std::unique_lock<std::mutex> currentShortcutTextBlock_lock(currentShortcutTextBlock_mutex);
|
||||
currentShortcutTextBlock = nullptr;
|
||||
currentShortcutTextBlock_lock.unlock();
|
||||
|
||||
std::unique_lock<std::mutex> detectedShortcut_lock(detectedShortcut_mutex);
|
||||
detectedShortcut.clear();
|
||||
detectedShortcut_lock.unlock();
|
||||
|
||||
// Reset all the single key remap UI stored variables.
|
||||
std::unique_lock<std::mutex> currentSingleKeyRemapTextBlock_lock(currentSingleKeyRemapTextBlock_mutex);
|
||||
currentSingleKeyRemapTextBlock = nullptr;
|
||||
currentSingleKeyRemapTextBlock_lock.unlock();
|
||||
|
||||
std::unique_lock<std::mutex> detectedRemapKey_lock(detectedRemapKey_mutex);
|
||||
detectedRemapKey = NULL;
|
||||
detectedRemapKey_lock.unlock();
|
||||
}
|
||||
|
||||
// Function to clear the OS Level shortcut remapping table
|
||||
void KeyboardManagerState::ClearOSLevelShortcuts()
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(osLevelShortcutReMap_mutex);
|
||||
osLevelShortcutReMap.clear();
|
||||
}
|
||||
|
||||
// Function to clear the Keys remapping table.
|
||||
void KeyboardManagerState::ClearSingleKeyRemaps()
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(singleKeyReMap_mutex);
|
||||
singleKeyReMap.clear();
|
||||
}
|
||||
|
||||
// Function to add a new OS level shortcut remapping
|
||||
void KeyboardManagerState::AddOSLevelShortcut(const std::vector<DWORD>& originalSC, const std::vector<WORD>& newSC)
|
||||
bool KeyboardManagerState::AddOSLevelShortcut(const std::vector<DWORD>& originalSC, const std::vector<WORD>& newSC)
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(osLevelShortcutReMap_mutex);
|
||||
|
||||
// Check if the shortcut is already remapped
|
||||
auto it = osLevelShortcutReMap.find(originalSC);
|
||||
if (it != osLevelShortcutReMap.end())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
osLevelShortcutReMap[originalSC] = std::make_pair(newSC, false);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Function to add a new OS level shortcut remapping
|
||||
void KeyboardManagerState::AddSingleKeyRemap(const DWORD& originalKey, const WORD& newRemapKey)
|
||||
bool KeyboardManagerState::AddSingleKeyRemap(const DWORD& originalKey, const WORD& newRemapKey)
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(singleKeyReMap_mutex);
|
||||
|
||||
// Check if the key is already remapped
|
||||
auto it = singleKeyReMap.find(originalKey);
|
||||
if (it != singleKeyReMap.end())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
singleKeyReMap[originalKey] = newRemapKey;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Function to set the textblock of the detect shortcut UI so that it can be accessed by the hook
|
||||
void KeyboardManagerState::ConfigureDetectShortcutUI(const TextBlock& textBlock)
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(currentShortcutTextBlock_mutex);
|
||||
currentShortcutTextBlock = textBlock;
|
||||
}
|
||||
|
||||
// Function to set the textblock of the detect remap key UI so that it can be accessed by the hook
|
||||
void KeyboardManagerState::ConfigureDetectSingleKeyRemapUI(const TextBlock& textBlock)
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(currentSingleKeyRemapTextBlock_mutex);
|
||||
currentSingleKeyRemapTextBlock = textBlock;
|
||||
}
|
||||
|
||||
// Function to update the detect shortcut UI based on the entered keys
|
||||
void KeyboardManagerState::UpdateDetectShortcutUI()
|
||||
{
|
||||
std::lock_guard<std::mutex> currentShortcutTextBlock_lock(currentShortcutTextBlock_mutex);
|
||||
if (currentShortcutTextBlock == nullptr)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
std::unique_lock<std::mutex> detectedShortcut_lock(detectedShortcut_mutex);
|
||||
hstring shortcutString = convertVectorToHstring<DWORD>(detectedShortcut);
|
||||
detectedShortcut_lock.unlock();
|
||||
|
||||
// Since this function is invoked from the back-end thread, in order to update the UI the dispatcher must be used.
|
||||
currentShortcutTextBlock.Dispatcher().RunAsync(Windows::UI::Core::CoreDispatcherPriority::Normal, [=]() {
|
||||
@ -107,12 +150,15 @@ void KeyboardManagerState::UpdateDetectShortcutUI()
|
||||
// Function to update the detect remap key UI based on the entered key.
|
||||
void KeyboardManagerState::UpdateDetectSingleKeyRemapUI()
|
||||
{
|
||||
std::lock_guard<std::mutex> currentSingleKeyRemapTextBlock_lock(currentSingleKeyRemapTextBlock_mutex);
|
||||
if (currentSingleKeyRemapTextBlock == nullptr)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
std::unique_lock<std::mutex> detectedRemapKey_lock(detectedRemapKey_mutex);
|
||||
hstring remapKeyString = winrt::to_hstring((unsigned int)detectedRemapKey);
|
||||
detectedRemapKey_lock.unlock();
|
||||
|
||||
// Since this function is invoked from the back-end thread, in order to update the UI the dispatcher must be used.
|
||||
currentSingleKeyRemapTextBlock.Dispatcher().RunAsync(Windows::UI::Core::CoreDispatcherPriority::Normal, [=]() {
|
||||
@ -123,16 +169,22 @@ void KeyboardManagerState::UpdateDetectSingleKeyRemapUI()
|
||||
// Function to return the currently detected shortcut which is displayed on the UI
|
||||
std::vector<DWORD> KeyboardManagerState::GetDetectedShortcut()
|
||||
{
|
||||
std::unique_lock<std::mutex> lock(currentShortcutTextBlock_mutex);
|
||||
hstring detectedShortcutString = currentShortcutTextBlock.Text();
|
||||
lock.unlock();
|
||||
|
||||
std::wstring detectedShortcutWstring = detectedShortcutString.c_str();
|
||||
std::vector<std::wstring> detectedShortcutVector = splitwstring(detectedShortcutWstring, L' ');
|
||||
return convertWStringVectorToIntegerVector<DWORD>(detectedShortcutVector);
|
||||
}
|
||||
|
||||
// Function to return the currently detected remap key which is displayed on the UI
|
||||
DWORD KeyboardManagerState::GetDetectedSingleRemapKey()
|
||||
DWORD KeyboardManagerState::GetDetectedSingleRemapKey()
|
||||
{
|
||||
std::unique_lock<std::mutex> lock(currentSingleKeyRemapTextBlock_mutex);
|
||||
hstring remapKeyString = currentSingleKeyRemapTextBlock.Text();
|
||||
lock.unlock();
|
||||
|
||||
std::wstring remapKeyWString = remapKeyString.c_str();
|
||||
DWORD remapKey = NULL;
|
||||
if (!remapKeyString.empty())
|
||||
@ -149,8 +201,16 @@ bool KeyboardManagerState::DetectSingleRemapKeyUIBackend(LowlevelKeyboardEvent*
|
||||
// Check if the detect key UI window has been activated
|
||||
if (CheckUIState(KeyboardManagerUIState::DetectSingleKeyRemapWindowActivated))
|
||||
{
|
||||
detectedRemapKey = data->lParam->vkCode;
|
||||
UpdateDetectSingleKeyRemapUI();
|
||||
// detect the key if it is pressed down
|
||||
if (data->wParam == WM_KEYDOWN || data->wParam == WM_SYSKEYDOWN)
|
||||
{
|
||||
std::unique_lock<std::mutex> detectedRemapKey_lock(detectedRemapKey_mutex);
|
||||
detectedRemapKey = data->lParam->vkCode;
|
||||
detectedRemapKey_lock.unlock();
|
||||
|
||||
UpdateDetectSingleKeyRemapUI();
|
||||
}
|
||||
|
||||
// Suppress the keyboard event
|
||||
return true;
|
||||
}
|
||||
@ -167,9 +227,12 @@ bool KeyboardManagerState::DetectShortcutUIBackend(LowlevelKeyboardEvent* data)
|
||||
// Add the key if it is pressed down
|
||||
if (data->wParam == WM_KEYDOWN || data->wParam == WM_SYSKEYDOWN)
|
||||
{
|
||||
std::unique_lock<std::mutex> lock(detectedShortcut_mutex);
|
||||
if (std::find(detectedShortcut.begin(), detectedShortcut.end(), data->lParam->vkCode) == detectedShortcut.end())
|
||||
{
|
||||
detectedShortcut.push_back(data->lParam->vkCode);
|
||||
lock.unlock();
|
||||
|
||||
// Update the UI. This function is called here because it should store the set of keys pressed till the last key which was pressed down.
|
||||
UpdateDetectShortcutUI();
|
||||
}
|
||||
@ -177,6 +240,7 @@ bool KeyboardManagerState::DetectShortcutUIBackend(LowlevelKeyboardEvent* data)
|
||||
// Remove the key if it has been released
|
||||
else if (data->wParam == WM_KEYUP || data->wParam == WM_SYSKEYUP)
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(detectedShortcut_mutex);
|
||||
detectedShortcut.erase(std::remove(detectedShortcut.begin(), detectedShortcut.end(), data->lParam->vkCode), detectedShortcut.end());
|
||||
}
|
||||
|
||||
@ -185,9 +249,13 @@ bool KeyboardManagerState::DetectShortcutUIBackend(LowlevelKeyboardEvent* data)
|
||||
}
|
||||
|
||||
// If the detect shortcut UI window is not activated, then clear the shortcut buffer if it isn't empty
|
||||
else if (!detectedShortcut.empty())
|
||||
else
|
||||
{
|
||||
detectedShortcut.clear();
|
||||
std::lock_guard<std::mutex> lock(detectedShortcut_mutex);
|
||||
if (!detectedShortcut.empty())
|
||||
{
|
||||
detectedShortcut.clear();
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
|
@ -1,6 +1,7 @@
|
||||
#pragma once
|
||||
#include "Helpers.h"
|
||||
#include <interface/lowlevel_keyboard_event_data.h>
|
||||
#include <mutex>
|
||||
#include <winrt/Windows.UI.Xaml.Controls.h>
|
||||
using namespace winrt::Windows::UI::Xaml::Controls;
|
||||
|
||||
@ -21,35 +22,46 @@ class KeyboardManagerState
|
||||
private:
|
||||
// State variable used to store which UI window is currently active that requires interaction with the hook
|
||||
KeyboardManagerUIState uiState;
|
||||
std::mutex uiState_mutex;
|
||||
|
||||
// Window handle for the current UI window which is active. Should be set to nullptr if UI is deactivated
|
||||
HWND currentUIWindow;
|
||||
std::mutex currentUIWindow_mutex;
|
||||
|
||||
// Vector to store the shortcut detected in the detect shortcut UI window. This is used in both the backend and the UI.
|
||||
std::vector<DWORD> detectedShortcut;
|
||||
std::mutex detectedShortcut_mutex;
|
||||
|
||||
// Store detected remap key in the remap UI window. This is used in both the backend and the UI.
|
||||
DWORD detectedRemapKey;
|
||||
std::mutex detectedRemapKey_mutex;
|
||||
|
||||
// Stores the UI element which is to be updated based on the remap key entered.
|
||||
TextBlock currentSingleKeyRemapTextBlock;
|
||||
std::mutex currentSingleKeyRemapTextBlock_mutex;
|
||||
|
||||
// Stores the UI element which is to be updated based on the shortcut entered
|
||||
TextBlock currentShortcutTextBlock;
|
||||
std::mutex currentShortcutTextBlock_mutex;
|
||||
|
||||
public:
|
||||
// The map members and their mutexes are left as public since the maps are used extensively in dllmain.cpp.
|
||||
// Maps which store the remappings for each of the features. The bool fields should be initalised to false. They are used to check the current state of the shortcut (i.e is that particular shortcut currently pressed down or not).
|
||||
// Stores single key remappings
|
||||
std::unordered_map<DWORD, WORD> singleKeyReMap;
|
||||
std::mutex singleKeyReMap_mutex;
|
||||
|
||||
// Stores keys which need to be changed from toggle behaviour to modifier behaviour. Eg. Caps Lock
|
||||
std::unordered_map<DWORD, bool> singleKeyToggleToMod;
|
||||
std::mutex singleKeyToggleToMod_mutex;
|
||||
|
||||
// Stores the os level shortcut remappings
|
||||
std::map<std::vector<DWORD>, std::pair<std::vector<WORD>, bool>> osLevelShortcutReMap;
|
||||
std::mutex osLevelShortcutReMap_mutex;
|
||||
|
||||
// Stores the app-specific shortcut remappings. Maps application name to the shortcut map
|
||||
std::map<std::wstring, std::map<std::vector<DWORD>, std::pair<std::vector<WORD>, bool>>> appSpecificShortcutReMap;
|
||||
std::mutex appSpecificShortcutReMap_mutex;
|
||||
|
||||
// Constructor
|
||||
KeyboardManagerState();
|
||||
@ -73,10 +85,10 @@ public:
|
||||
void ClearSingleKeyRemaps();
|
||||
|
||||
// Function to add a new single key remapping
|
||||
void AddSingleKeyRemap(const DWORD& originalKey, const WORD& newRemapKey);
|
||||
bool AddSingleKeyRemap(const DWORD& originalKey, const WORD& newRemapKey);
|
||||
|
||||
// Function to add a new OS level shortcut remapping
|
||||
void AddOSLevelShortcut(const std::vector<DWORD>& originalSC, const std::vector<WORD>& newSC);
|
||||
bool AddOSLevelShortcut(const std::vector<DWORD>& originalSC, const std::vector<WORD>& newSC);
|
||||
|
||||
// Function to set the textblock of the detect shortcut UI so that it can be accessed by the hook
|
||||
void ConfigureDetectShortcutUI(const TextBlock& textBlock);
|
||||
|
@ -313,6 +313,8 @@ public:
|
||||
// Check if the key event was generated by KeyboardManager to avoid remapping events generated by us.
|
||||
if (!(data->lParam->dwExtraInfo & KEYBOARDMANAGER_INJECTED_FLAG))
|
||||
{
|
||||
// The mutex should be unlocked before SendInput is called to avoid re-entry into the same mutex. More details can be found at https://github.com/microsoft/PowerToys/pull/1789#issuecomment-607555837
|
||||
std::unique_lock<std::mutex> lock(keyboardManagerState.singleKeyReMap_mutex);
|
||||
auto it = keyboardManagerState.singleKeyReMap.find(data->lParam->vkCode);
|
||||
if (it != keyboardManagerState.singleKeyReMap.end())
|
||||
{
|
||||
@ -334,6 +336,7 @@ public:
|
||||
keyEventList[0].ki.dwFlags = KEYEVENTF_KEYUP;
|
||||
}
|
||||
|
||||
lock.unlock();
|
||||
UINT res = SendInput(key_count, keyEventList, sizeof(INPUT));
|
||||
delete[] keyEventList;
|
||||
return 1;
|
||||
@ -349,6 +352,8 @@ public:
|
||||
// Check if the key event was generated by KeyboardManager to avoid remapping events generated by us.
|
||||
if (!(data->lParam->dwExtraInfo & KEYBOARDMANAGER_INJECTED_FLAG))
|
||||
{
|
||||
// The mutex should be unlocked before SendInput is called to avoid re-entry into the same mutex. More details can be found at https://github.com/microsoft/PowerToys/pull/1789#issuecomment-607555837
|
||||
std::unique_lock<std::mutex> lock(keyboardManagerState.singleKeyToggleToMod_mutex);
|
||||
auto it = keyboardManagerState.singleKeyToggleToMod.find(data->lParam->vkCode);
|
||||
if (it != keyboardManagerState.singleKeyToggleToMod.end())
|
||||
{
|
||||
@ -361,6 +366,7 @@ public:
|
||||
}
|
||||
else
|
||||
{
|
||||
lock.unlock();
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@ -376,14 +382,18 @@ public:
|
||||
keyEventList[1].ki.dwFlags = KEYEVENTF_KEYUP;
|
||||
keyEventList[1].ki.dwExtraInfo = KEYBOARDMANAGER_SINGLEKEY_FLAG;
|
||||
|
||||
lock.unlock();
|
||||
UINT res = SendInput(key_count, keyEventList, sizeof(INPUT));
|
||||
delete[] keyEventList;
|
||||
|
||||
// Reset the long press flag when the key has been lifted.
|
||||
if (data->wParam == WM_KEYUP || data->wParam == WM_SYSKEYUP)
|
||||
{
|
||||
lock.lock();
|
||||
keyboardManagerState.singleKeyToggleToMod[data->lParam->vkCode] = false;
|
||||
lock.unlock();
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@ -495,8 +505,10 @@ public:
|
||||
}
|
||||
|
||||
// Function to a handle a shortcut remap
|
||||
intptr_t HandleShortcutRemapEvent(LowlevelKeyboardEvent* data, std::map<std::vector<DWORD>, std::pair<std::vector<WORD>, bool>>& reMap) noexcept
|
||||
intptr_t HandleShortcutRemapEvent(LowlevelKeyboardEvent* data, std::map<std::vector<DWORD>, std::pair<std::vector<WORD>, bool>>& reMap, std::mutex& map_mutex) noexcept
|
||||
{
|
||||
// The mutex should be unlocked before SendInput is called to avoid re-entry into the same mutex. More details can be found at https://github.com/microsoft/PowerToys/pull/1789#issuecomment-607555837
|
||||
std::unique_lock<std::mutex> lock(map_mutex);
|
||||
for (auto& it : reMap)
|
||||
{
|
||||
const size_t src_size = it.first.size();
|
||||
@ -588,6 +600,7 @@ public:
|
||||
}
|
||||
|
||||
it.second.second = true;
|
||||
lock.unlock();
|
||||
UINT res = SendInput((UINT)key_count, keyEventList, sizeof(INPUT));
|
||||
delete[] keyEventList;
|
||||
return 1;
|
||||
@ -657,8 +670,8 @@ public:
|
||||
}
|
||||
|
||||
it.second.second = false;
|
||||
lock.unlock();
|
||||
UINT res = SendInput((UINT)key_count, keyEventList, sizeof(INPUT));
|
||||
|
||||
delete[] keyEventList;
|
||||
return 1;
|
||||
}
|
||||
@ -678,6 +691,7 @@ public:
|
||||
keyEventList[0].ki.dwExtraInfo = KEYBOARDMANAGER_SHORTCUT_FLAG;
|
||||
|
||||
it.second.second = true;
|
||||
lock.unlock();
|
||||
UINT res = SendInput((UINT)key_count, keyEventList, sizeof(INPUT));
|
||||
delete[] keyEventList;
|
||||
return 1;
|
||||
@ -758,6 +772,7 @@ public:
|
||||
}
|
||||
|
||||
it.second.second = false;
|
||||
lock.unlock();
|
||||
UINT res = SendInput((UINT)key_count, keyEventList, sizeof(INPUT));
|
||||
delete[] keyEventList;
|
||||
return 1;
|
||||
@ -775,7 +790,8 @@ public:
|
||||
// Check if the key event was generated by KeyboardManager to avoid remapping events generated by us.
|
||||
if (data->lParam->dwExtraInfo != KEYBOARDMANAGER_SHORTCUT_FLAG)
|
||||
{
|
||||
return HandleShortcutRemapEvent(data, keyboardManagerState.osLevelShortcutReMap);
|
||||
bool result = HandleShortcutRemapEvent(data, keyboardManagerState.osLevelShortcutReMap, keyboardManagerState.osLevelShortcutReMap_mutex);
|
||||
return result;
|
||||
}
|
||||
|
||||
return 0;
|
||||
@ -838,11 +854,13 @@ public:
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
std::unique_lock<std::mutex> lock(keyboardManagerState.appSpecificShortcutReMap_mutex);
|
||||
auto it = keyboardManagerState.appSpecificShortcutReMap.find(process_name);
|
||||
if (it != keyboardManagerState.appSpecificShortcutReMap.end())
|
||||
{
|
||||
return HandleShortcutRemapEvent(data, keyboardManagerState.appSpecificShortcutReMap[process_name]);
|
||||
lock.unlock();
|
||||
bool result = HandleShortcutRemapEvent(data, keyboardManagerState.appSpecificShortcutReMap[process_name], keyboardManagerState.appSpecificShortcutReMap_mutex);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -150,7 +150,12 @@ void createEditKeyboardWindow(HINSTANCE hInst, KeyboardManagerState& keyboardMan
|
||||
{
|
||||
DWORD originalKey = std::stoi(originalKeyString.c_str());
|
||||
DWORD newKey = std::stoi(newKeyString.c_str());
|
||||
keyboardManagerState.AddSingleKeyRemap(originalKey, newKey);
|
||||
|
||||
bool result = keyboardManagerState.AddSingleKeyRemap(originalKey, newKey);
|
||||
if (!result)
|
||||
{
|
||||
isSuccess = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -181,10 +186,12 @@ void createEditKeyboardWindow(HINSTANCE hInst, KeyboardManagerState& keyboardMan
|
||||
SingleKeyRemapControl::keyboardManagerState = &keyboardManagerState;
|
||||
|
||||
// Load existing remaps into UI
|
||||
std::unique_lock<std::mutex> lock(keyboardManagerState.singleKeyReMap_mutex);
|
||||
for (const auto& it : keyboardManagerState.singleKeyReMap)
|
||||
{
|
||||
SingleKeyRemapControl::AddNewControlKeyRemapRow(keyRemapTable, it.first, it.second);
|
||||
}
|
||||
lock.unlock();
|
||||
|
||||
// Add remap key button
|
||||
Windows::UI::Xaml::Controls::Button addRemapKey;
|
||||
|
@ -109,7 +109,7 @@ void createEditShortcutsWindow(HINSTANCE hInst, KeyboardManagerState& keyboardMa
|
||||
originalShortcutHeader.Margin({ 0, 0, 0, 10 });
|
||||
tableHeaderRow.Children().Append(originalShortcutHeader);
|
||||
|
||||
// Second header textblock in the header row of the shortcut table
|
||||
// Second header textblock in the header row of the shortcut table
|
||||
TextBlock newShortcutHeader;
|
||||
newShortcutHeader.Text(winrt::to_hstring("New Shortcut:"));
|
||||
newShortcutHeader.FontWeight(Text::FontWeights::Bold());
|
||||
@ -143,7 +143,11 @@ void createEditShortcutsWindow(HINSTANCE hInst, KeyboardManagerState& keyboardMa
|
||||
// Shortcut should consist of atleast two keys
|
||||
if (originalKeys.size() > 1 && newKeys.size() > 1)
|
||||
{
|
||||
keyboardManagerState.AddOSLevelShortcut(originalKeys, newKeys);
|
||||
bool result = keyboardManagerState.AddOSLevelShortcut(originalKeys, newKeys);
|
||||
if (!result)
|
||||
{
|
||||
isSuccess = false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -179,10 +183,12 @@ void createEditShortcutsWindow(HINSTANCE hInst, KeyboardManagerState& keyboardMa
|
||||
ShortcutControl::keyboardManagerState = &keyboardManagerState;
|
||||
|
||||
// Load existing shortcuts into UI
|
||||
for (const auto& it: keyboardManagerState.osLevelShortcutReMap)
|
||||
std::unique_lock<std::mutex> lock(keyboardManagerState.osLevelShortcutReMap_mutex);
|
||||
for (const auto& it : keyboardManagerState.osLevelShortcutReMap)
|
||||
{
|
||||
ShortcutControl::AddNewShortcutControlRow(shortcutTable, it.first, it.second.first);
|
||||
}
|
||||
lock.unlock();
|
||||
|
||||
// Add shortcut button
|
||||
Windows::UI::Xaml::Controls::Button addShortcut;
|
||||
|
@ -93,10 +93,8 @@ void createMainWindow(HINSTANCE hInstance, KeyboardManagerState& keyboardManager
|
||||
Windows::UI::Xaml::Controls::Button bt;
|
||||
bt.Content(winrt::box_value(winrt::to_hstring("Edit Keyboard")));
|
||||
bt.Click([&](IInspectable const& sender, RoutedEventArgs const&) {
|
||||
//keyboardManagerState.SetUIState(KeyboardManagerUIState::DetectKeyWindowActivated);
|
||||
std::thread th(createEditKeyboardWindow, _hInstance, std::ref(keyboardManagerState));
|
||||
th.join();
|
||||
//keyboardManagerState.ResetUIState();
|
||||
});
|
||||
|
||||
Windows::UI::Xaml::Controls::Button bt2;
|
||||
|
Loading…
Reference in New Issue
Block a user