Qt
Internal/Contributor docs for the Qt SDK. Note: These are NOT official API docs; those are found at https://doc.qt.io/
Loading...
Searching...
No Matches
qintegrityhidmanager.cpp
Go to the documentation of this file.
1// Copyright (C) 2015 Green Hills Software
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3// Qt-Security score:significant reason:default
4
6#include <QList>
7#include <QPoint>
8#include <QGuiApplication>
9#include <qpa/qwindowsysteminterface.h>
10#include <device/hiddriver.h>
11
13
14class IntNotifier
15{
16 static const Value ActivityPriority = 2;
17protected:
19public:
21 {
22 CheckSuccess(CreateActivity(CurrentTask(), ActivityPriority, false, (Value)this, &act));
23 };
25 {
26 CheckSuccess(CloseActivity(act));
27 };
28 virtual void process_event() = 0;
29 virtual void async_wait() = 0;
30};
31
33{
34public:
35 HIDDeviceHandler(HIDDriver *hidd, HIDHandle hidh)
36 : driver(hidd), handle(hidh), currentPos(0, 0) { }
38 {
39 CheckSuccess(gh_hid_close(handle));
40 };
41 void process_event(void) override;
42 void async_wait(void) override;
43 HIDDriver *get_driver(void) { return driver; };
44 HIDHandle get_handle(void) { return handle; };
45private:
46 HIDDriver *driver;
47 HIDHandle handle;
48 QPoint currentPos;
49 Qt::MouseButtons buttons;
50};
51
53{
54public:
55 HIDDriverHandler(HIDDriver *hidd) : IntNotifier(), driver(hidd) { }
57 {
58 qDeleteAll(devices);
59 };
60 void process_event(void) override;
61 void async_wait(void) override;
62 void find_devices(void);
63private:
64 QHash<Value, HIDDeviceHandler *> devices;
65 HIDDriver *driver;
66};
67
69{
71}
72
74{
75 gh_hid_wait_for_new_device(driver, act);
76}
77
79{
80 Error err;
81 uintptr_t devicecontext;
82 uint32_t device_id;
83 HIDHandle handle;
84 HIDDeviceHandler *hidnot;
85
86 devicecontext = 0;
87 forever {
88 err = gh_hid_enum_devices(driver, &device_id, &devicecontext);
89 if (err == OperationNotImplemented)
90 break;
91 else if (err == Failure)
92 break;
93 if (!devices.contains(device_id)) {
94 err = gh_hid_init_device(driver, device_id, &handle);
95 if (err == Success) {
96 hidnot = new HIDDeviceHandler(driver, handle);
97 devices.insert(device_id, hidnot);
98 hidnot->async_wait();
99 }
100 }
101 }
102 if (err == OperationNotImplemented) {
103 /* fallback on legacy enumeration where we assume 0-based
104 * contiguous indexes */
105 device_id = 0;
106 err = Success;
107 do {
108 if (!devices.contains(device_id)) {
109 err = gh_hid_init_device(driver, device_id, &handle);
110 if (err != Success)
111 break;
112 hidnot = new HIDDeviceHandler(driver, handle);
113 devices.insert(device_id, hidnot);
114 hidnot->async_wait();
115 }
116 device_id++;
117 } while (err == Success);
118 }
119
120 async_wait();
121}
122
123
125{
126 HIDEvent event;
127 uint32_t num_events = 1;
128
129 while (gh_hid_get_event(handle, &event, &num_events) == Success) {
130 if (event.type == HID_TYPE_AXIS) {
131 switch (event.index) {
132 case HID_AXIS_ABSX:
133 currentPos.setX(event.value);
134 break;
135 case HID_AXIS_ABSY:
136 currentPos.setY(event.value);
137 break;
138 case HID_AXIS_RELX:
139 currentPos.setX(currentPos.x() + event.value);
140 break;
141 case HID_AXIS_RELY:
142 currentPos.setY(currentPos.y() + event.value);
143 break;
144 default:
145 /* ignore the rest for now */
146 break;
147 }
148 } else if (event.type == HID_TYPE_KEY) {
149 switch (event.index) {
150 case HID_BUTTON_LEFT:
151 if (event.value)
152 buttons |= Qt::LeftButton;
153 else
154 buttons &= ~Qt::LeftButton;
155 break;
156 case HID_BUTTON_MIDDLE:
157 if (event.value)
158 buttons |= Qt::MiddleButton;
159 else
160 buttons &= ~Qt::MiddleButton;
161 break;
162 case HID_BUTTON_RIGHT:
163 if (event.value)
164 buttons |= Qt::RightButton;
165 else
166 buttons &= ~Qt::RightButton;
167 break;
168 default:
169 /* ignore the rest for now */
170 break;
171 }
172 } else if (event.type == HID_TYPE_SYNC) {
173 QWindowSystemInterface::handleMouseEvent(0, currentPos, currentPos, buttons,
174 QGuiApplication::keyboardModifiers());
175 } else if (event.type == HID_TYPE_DISCONNECT) {
176 /* FIXME */
177 }
178 }
180}
181
183{
184 CheckSuccess(gh_hid_async_wait_for_event(handle, act));
185}
186
187void QIntegrityHIDManager::open_devices()
188{
189 HIDDriver *hidd;
190 uintptr_t context = 0;
191 HIDDriverHandler *hidnot;
192
193 while (gh_hid_enum_drivers(&hidd, &context) == Success) {
194 hidnot = new HIDDriverHandler(hidd);
195 m_drivers.append(hidnot);
196 hidnot->find_devices();
197 }
198}
199
201{
202 IntNotifier *notifier;
203 open_devices();
204 /* main loop */
205 forever {
206 WaitForActivity((Value *)&notifier);
207 notifier->process_event();
208 }
209}
210
211QIntegrityHIDManager::QIntegrityHIDManager(const QString &key, const QString &spec, QObject *parent)
212 : QThread(parent)
213{
214 start();
215}
216
218{
219 terminate();
220 qDeleteAll(m_drivers);
221}
222
223QT_END_NAMESPACE
void process_event(void) override
HIDDeviceHandler(HIDDriver *hidd, HIDHandle hidh)
HIDHandle get_handle(void)
HIDDriver * get_driver(void)
void async_wait(void) override
void process_event(void) override
HIDDriverHandler(HIDDriver *hidd)
void async_wait(void) override
virtual void process_event()=0
virtual void async_wait()=0
Combined button and popup list for selecting options.