From d6589a028919c671a3005d32202cdbbaf5caa010 Mon Sep 17 00:00:00 2001 From: Stanislaw Halik Date: Fri, 2 Oct 2015 08:09:14 +0200 Subject: shortcuts: rework KeybindingWorker for win32 The class is now usable outside of center/zero/toggle loop. --- opentrack/shortcuts.cpp | 96 +++++++++++++++++++++++++++---------------------- opentrack/shortcuts.h | 11 +++--- 2 files changed, 59 insertions(+), 48 deletions(-) diff --git a/opentrack/shortcuts.cpp b/opentrack/shortcuts.cpp index 63cd9088..e20fa1c0 100644 --- a/opentrack/shortcuts.cpp +++ b/opentrack/shortcuts.cpp @@ -10,18 +10,10 @@ #include #if defined(_WIN32) +#include #include #include "win32-shortcuts.h" -void KeybindingWorker::set_keys(Key kCenter_, Key kToggle_, Key kZero_) -{ - QMutexLocker l(&mtx); - - kCenter = kCenter_; - kToggle = kToggle_; - kZero = kZero_; -} - KeybindingWorker::~KeybindingWorker() { should_quit = true; wait(); @@ -33,9 +25,11 @@ KeybindingWorker::~KeybindingWorker() { din->Release(); } -KeybindingWorker::KeybindingWorker(Key keyCenter, Key keyToggle, Key keyZero, WId handle, Shortcuts& sc) : - sc(sc), din(0), dinkeyboard(0), kCenter(keyCenter), kToggle(keyToggle), kZero(keyZero), should_quit(true) +KeybindingWorker::KeybindingWorker(std::function receiver, WId h) : + should_quit(true), receiver(receiver) { + HWND handle = reinterpret_cast(h); + if (DirectInput8Create(GetModuleHandle(NULL), DIRECTINPUT_VERSION, IID_IDirectInput8, (void**)&din, NULL) != DI_OK) { qDebug() << "setup DirectInput8 Creation failed!" << GetLastError(); return; @@ -74,26 +68,6 @@ KeybindingWorker::KeybindingWorker(Key keyCenter, Key keyToggle, Key keyZero, WI should_quit = false; } -static bool isKeyPressed( const Key *key, const BYTE *keystate ) { - bool shift; - bool ctrl; - bool alt; - - if (key->keycode != 0 && keystate[key->keycode] & 0x80) - { - shift = ( (keystate[DIK_LSHIFT] & 0x80) || (keystate[DIK_RSHIFT] & 0x80) ); - ctrl = ( (keystate[DIK_LCONTROL] & 0x80) || (keystate[DIK_RCONTROL] & 0x80) ); - alt = ( (keystate[DIK_LALT] & 0x80) || (keystate[DIK_RALT] & 0x80) ); - - if (key->shift && !shift) return false; - if (key->ctrl && !ctrl) return false; - if (key->alt && !alt) return false; - - return true; - } - return false; -} - void KeybindingWorker::run() { BYTE keystate[256]; @@ -107,14 +81,30 @@ void KeybindingWorker::run() { QMutexLocker l(&mtx); - if (isKeyPressed(&kCenter, keystate) && kCenter.should_process()) - emit sc.center(); - - if (isKeyPressed(&kToggle, keystate) && kToggle.should_process()) - emit sc.toggle(); - - if (isKeyPressed(&kZero, keystate) && kZero.should_process()) - emit sc.zero(); + for (int i = 0; i < 256; i++) + { + Key k; + if (keystate[i] & 0x80) + { + switch (i) + { + case DIK_LCONTROL: + case DIK_LSHIFT: + case DIK_LALT: + case DIK_RCONTROL: + case DIK_RSHIFT: + case DIK_RALT: + break; + default: + k.shift = !!(keystate[DIK_LSHIFT] & 0x80); + k.alt = !!(keystate[DIK_LALT] & 0x80); + k.ctrl = !!(keystate[DIK_LCONTROL] & 0x80); + k.keycode = i; + receiver(k); + break; + } + } + } // keypresses get dropped with high values Sleep(15); @@ -158,6 +148,30 @@ void Shortcuts::bind_keyboard_shortcut(K &key, key_opts& k) } #endif +#ifdef _WIN32 +void Shortcuts::receiver(Key &k) +{ + std::vector ks { &keyCenter, &keyToggle, &keyZero }; + for (auto& k_ : ks) + { + if (k.keycode != k_->keycode) + continue; + if (!k_->should_process()) + return; + if (k_->alt && !k.alt) return; + if (k_->ctrl && !k.ctrl) return; + if (k_->shift && !k.shift) return; + + if (k.keycode == keyCenter.keycode) + emit center(); + else if (k.keycode == keyToggle.keycode) + emit toggle(); + else if (k.keycode == keyZero.keycode) + emit zero(); + } +} +#endif + void Shortcuts::reload() { bind_keyboard_shortcut(keyCenter, s.center); bind_keyboard_shortcut(keyToggle, s.toggle); @@ -166,10 +180,8 @@ void Shortcuts::reload() { bool is_new = keybindingWorker == nullptr; if (is_new) { - keybindingWorker = std::make_shared(keyCenter, keyToggle, keyZero, handle, *this); + keybindingWorker = std::make_shared([&](Key& k) { receiver(k); }, handle); keybindingWorker->start(); } - else - keybindingWorker->set_keys(keyCenter, keyToggle, keyZero); #endif } diff --git a/opentrack/shortcuts.h b/opentrack/shortcuts.h index 2d7fec54..8877b5bb 100644 --- a/opentrack/shortcuts.h +++ b/opentrack/shortcuts.h @@ -67,19 +67,15 @@ struct Shortcuts; struct KeybindingWorker : public QThread { #ifdef _WIN32 private: - Shortcuts& sc; LPDIRECTINPUT8 din; LPDIRECTINPUTDEVICE8 dinkeyboard; - Key kCenter; - Key kToggle; - Key kZero; QMutex mtx; public: volatile bool should_quit; + std::function receiver; ~KeybindingWorker(); - KeybindingWorker(Key keyCenter, Key keyToggle, Key keyZero, WId handle, Shortcuts& sc); + KeybindingWorker(std::function receiver, WId h); void run(); - void set_keys(Key kCenter, Key kToggle, Key kZero); #else public: KeybindingWorker(Key, Key, Key, WId) {} @@ -124,6 +120,9 @@ public: void reload(); private: void bind_keyboard_shortcut(K &key, key_opts& k); +#ifdef _WIN32 + void receiver(Key& k); +#endif signals: void center(); void toggle(); -- cgit v1.2.3