Page MenuHomePhabricator (Chris)

No OneTemporary

Size
7 KB
Referenced Files
None
Subscribers
None
diff --git a/uglobalhotkeys.cpp b/uglobalhotkeys.cpp
index cefdde0..6f071a0 100644
--- a/uglobalhotkeys.cpp
+++ b/uglobalhotkeys.cpp
@@ -1,148 +1,154 @@
#include <QtCore>
#if defined(Q_OS_WIN)
#include <windows.h>
#elif defined(Q_OS_LINUX)
#include <QWindow>
#include <qpa/qplatformnativeinterface.h>
#include <QApplication>
#endif
#include "hotkeymap.h"
#include "uglobalhotkeys.h"
UGlobalHotkeys::UGlobalHotkeys(QWidget *parent)
: QWidget(parent)
{
#if defined(Q_OS_LINUX)
qApp->installNativeEventFilter(this);
QWindow wndw;
void* v = qApp->platformNativeInterface()->nativeResourceForWindow("connection", &wndw);
X11Connection = (xcb_connection_t*)v;
X11Wid = xcb_setup_roots_iterator(xcb_get_setup(X11Connection)).data->root;
X11KeySymbs = xcb_key_symbols_alloc(X11Connection);
#endif
}
-void UGlobalHotkeys::RegisterHotkey(const QString& keySeq, size_t id) {
- RegisterHotkey(UKeySequence(keySeq), id);
+void UGlobalHotkeys::registerHotkey(const QString& keySeq, size_t id) {
+ registerHotkey(UKeySequence(keySeq), id);
}
-void UGlobalHotkeys::RegisterHotkey(const UKeySequence& keySeq, size_t id) {
+void UGlobalHotkeys::registerHotkey(const UKeySequence& keySeq, size_t id) {
if (keySeq.Size() == 0) {
throw UException("Empty hotkeys");
}
if (Registered.find(id) != Registered.end()) {
- UnregisterHotkey(id);
+ unregisterHotkey(id);
}
#if defined(Q_OS_WIN)
size_t winMod = 0;
size_t key = VK_F2;
for (size_t i = 0; i != keySeq.Size(); i++) {
if (keySeq[i] == Qt::Key_Control) {
winMod |= MOD_CONTROL;
} else if (keySeq[i] == Qt::Key_Alt) {
winMod |= MOD_ALT;
} else if (keySeq[i] == Qt::Key_Shift) {
winMod |= MOD_SHIFT;
} else if (keySeq[i] == Qt::Key_Meta) {
winMod |= MOD_WIN;
} else {
key = QtKeyToWin(keySeq[i]);
}
}
if (!RegisterHotKey((HWND)winId(), id, winMod, key)) {
qDebug() << "Error activating hotkey!";
} else {
Registered.insert(id);
}
#elif defined(Q_OS_LINUX)
regLinuxHotkey(keySeq, id);
#endif
}
-void UGlobalHotkeys::UnregisterHotkey(size_t id) {
+void UGlobalHotkeys::unregisterHotkey(size_t id) {
Q_ASSERT(Registered.find(id) != Registered.end() && "Unregistered hotkey");
#if defined(Q_OS_WIN)
UnregisterHotKey((HWND)winId(), id);
#elif defined(Q_OS_LINUX)
unregLinuxHotkey(id);
#endif
Registered.remove(id);
}
+void UGlobalHotkeys::unregisterAllHotkeys()
+{
+ for (size_t id : Registered)
+ this->unregisterHotkey(id);
+}
+
UGlobalHotkeys::~UGlobalHotkeys() {
#if defined(Q_OS_WIN)
for (QSet<size_t>::iterator i = Registered.begin(); i != Registered.end(); i++) {
UnregisterHotKey((HWND)winId(), *i);
}
#elif defined(Q_OS_LINUX)
xcb_key_symbols_free(X11KeySymbs);
#endif
}
#if defined(Q_OS_WIN)
bool UGlobalHotkeys::winEvent(MSG * message, long * result) {
Q_UNUSED(result);
if (message->message == WM_HOTKEY) {
size_t id = message->wParam;
Q_ASSERT(Registered.find(id) != Registered.end() && "Unregistered hotkey");
- emit Activated(id);
+ emit activated(id);
}
return false;
}
bool UGlobalHotkeys::nativeEvent(const QByteArray &eventType,
void *message, long *result)
{
Q_UNUSED(eventType);
return winEvent((MSG*)message, result);
}
#elif defined(Q_OS_LINUX)
bool UGlobalHotkeys::nativeEventFilter(const QByteArray &eventType, void *message, long *result) {
Q_UNUSED(eventType);
Q_UNUSED(result);
return linuxEvent(static_cast<xcb_generic_event_t*>(message));
}
bool UGlobalHotkeys::linuxEvent(xcb_generic_event_t *message)
{
if ( (message->response_type & ~0x80) == XCB_KEY_PRESS ) {
xcb_key_press_event_t *ev = (xcb_key_press_event_t*)message;
auto ind = Registered.key( {ev->detail, (ev->state & ~XCB_MOD_MASK_2)} );
if (ind == 0) // this is not hotkeys
return false;
- emit Activated(ind);
+ emit activated(ind);
return true;
}
return false;
}
void UGlobalHotkeys::regLinuxHotkey(const UKeySequence &keySeq, size_t id)
{
UHotkeyData data;
UKeyData keyData = QtKeyToLinux(keySeq);
xcb_keycode_t *keyC = xcb_key_symbols_get_keycode(X11KeySymbs, keyData.key);
data.keyCode = *keyC;
data.mods = keyData.mods;
xcb_grab_key(X11Connection, 1, X11Wid, data.mods, data.keyCode, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC);
// NumLk
xcb_grab_key(X11Connection, 1, X11Wid, data.mods | XCB_MOD_MASK_2, data.keyCode,XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC);
Registered.insert(id, data);
}
void UGlobalHotkeys::unregLinuxHotkey(size_t id)
{
UHotkeyData data = Registered.take(id);
xcb_ungrab_key(X11Connection, data.keyCode, X11Wid, data.mods);
xcb_ungrab_key(X11Connection, data.keyCode, X11Wid, data.mods | XCB_MOD_MASK_2);
}
#endif
diff --git a/uglobalhotkeys.h b/uglobalhotkeys.h
index eb699a4..d7a0e32 100644
--- a/uglobalhotkeys.h
+++ b/uglobalhotkeys.h
@@ -1,59 +1,60 @@
#pragma once
#include <QWidget>
#include <QAbstractNativeEventFilter>
#include <QSet>
#if defined(Q_OS_LINUX)
#include "xcb/xcb.h"
#include "xcb/xcb_keysyms.h"
#endif
#include "ukeysequence.h"
#include "uexception.h"
#include "uglobal.h"
#if defined(Q_OS_LINUX)
struct UHotkeyData {
xcb_keycode_t keyCode;
int mods;
bool operator ==(const UHotkeyData& data) const {
return data.keyCode == this->keyCode && data.mods == this->mods;
}
};
#endif
class UGLOBALHOTKEY_EXPORT UGlobalHotkeys : public QWidget
#if defined(Q_OS_LINUX)
, public QAbstractNativeEventFilter
#endif
{
Q_OBJECT
public:
explicit UGlobalHotkeys(QWidget *parent = 0);
- void RegisterHotkey(const QString& keySeq, size_t id = 1);
- void RegisterHotkey(const UKeySequence& keySeq, size_t id = 1);
- void UnregisterHotkey(size_t id = 1);
+ void registerHotkey(const QString& keySeq, size_t id = 1);
+ void registerHotkey(const UKeySequence& keySeq, size_t id = 1);
+ void unregisterHotkey(size_t id = 1);
+ void unregisterAllHotkeys();
~UGlobalHotkeys();
protected:
#if defined(Q_OS_WIN)
bool winEvent (MSG * message, long * result);
bool nativeEvent(const QByteArray &eventType, void *message, long *result);
#elif defined(Q_OS_LINUX)
bool nativeEventFilter(const QByteArray &eventType, void *message, long *result);
bool linuxEvent(xcb_generic_event_t *message);
void regLinuxHotkey(const UKeySequence& keySeq, size_t id);
void unregLinuxHotkey(size_t id);
#endif
signals:
- void Activated(size_t id);
+ void activated(size_t id);
private:
#if defined(Q_OS_WIN)
QSet<size_t> Registered;
#elif defined(Q_OS_LINUX)
QHash<size_t, UHotkeyData> Registered;
xcb_connection_t* X11Connection;
xcb_window_t X11Wid;
xcb_key_symbols_t* X11KeySymbs;
#endif
};

File Metadata

Mime Type
text/x-diff
Expires
Fri, Jan 30, 3:17 PM (5 d, 15 h ago)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
55457
Default Alt Text
(7 KB)

Event Timeline