1 /* antimicro Gamepad to KB+M event mapper
2 * Copyright (C) 2015 Travis Nickles <nickles.travis@gmail.com>
3 *
4 * This program is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation, either version 3 of the License, or
7 * (at your option) any later version.
8
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18 #include "xtesteventhandler.h"
19
20 #include <QApplication>
21
22 #include <X11/Xlib.h>
23 #include <X11/Xutil.h>
24 #include <X11/XKBlib.h>
25 #include <X11/extensions/XTest.h>
26 #include <x11extras.h>
27 #include <antkeymapper.h>
28
XTestEventHandler(QObject * parent)29 XTestEventHandler::XTestEventHandler(QObject *parent) :
30 BaseEventHandler(parent)
31 {
32 }
33
init()34 bool XTestEventHandler::init()
35 {
36 X11Extras *instance = X11Extras::getInstance();
37 if (instance)
38 {
39 instance->x11ResetMouseAccelerationChange(X11Extras::xtestMouseDeviceName);
40 }
41
42 return true;
43 }
44
cleanup()45 bool XTestEventHandler::cleanup()
46 {
47 return true;
48 }
49
sendKeyboardEvent(JoyButtonSlot * slot,bool pressed)50 void XTestEventHandler::sendKeyboardEvent(JoyButtonSlot *slot, bool pressed)
51 {
52 Display* display = X11Extras::getInstance()->display();
53 JoyButtonSlot::JoySlotInputAction device = slot->getSlotMode();
54 int code = slot->getSlotCode();
55
56 if (device == JoyButtonSlot::JoyKeyboard)
57 {
58 unsigned int tempcode = XKeysymToKeycode(display, code);
59 if (tempcode > 0)
60 {
61 XTestFakeKeyEvent(display, tempcode, pressed, 0);
62 XFlush(display);
63 }
64 }
65 }
66
sendMouseButtonEvent(JoyButtonSlot * slot,bool pressed)67 void XTestEventHandler::sendMouseButtonEvent(JoyButtonSlot *slot, bool pressed)
68 {
69 Display* display = X11Extras::getInstance()->display();
70 JoyButtonSlot::JoySlotInputAction device = slot->getSlotMode();
71 int code = slot->getSlotCode();
72
73 if (device == JoyButtonSlot::JoyMouseButton)
74 {
75 XTestFakeButtonEvent(display, code, pressed, 0);
76 XFlush(display);
77 }
78 }
79
sendMouseEvent(int xDis,int yDis)80 void XTestEventHandler::sendMouseEvent(int xDis, int yDis)
81 {
82 Display* display = X11Extras::getInstance()->display();
83 XTestFakeRelativeMotionEvent(display, xDis, yDis, 0);
84 XFlush(display);
85 }
86
sendMouseAbsEvent(int xDis,int yDis,int screen)87 void XTestEventHandler::sendMouseAbsEvent(int xDis, int yDis, int screen)
88 {
89 Display* display = X11Extras::getInstance()->display();
90 XTestFakeMotionEvent(display, screen, xDis, yDis, 0);
91 XFlush(display);
92 }
93
getName()94 QString XTestEventHandler::getName()
95 {
96 return QString("XTest");
97 }
98
getIdentifier()99 QString XTestEventHandler::getIdentifier()
100 {
101 return QString("xtest");
102 }
103
sendTextEntryEvent(QString maintext)104 void XTestEventHandler::sendTextEntryEvent(QString maintext)
105 {
106 AntKeyMapper *mapper = AntKeyMapper::getInstance();
107
108 // Populated as needed.
109 unsigned int shiftcode = 0;
110 unsigned int controlcode = 0;
111 unsigned int metacode = 0;
112 unsigned int altcode = 0;
113
114 if (mapper && mapper->getKeyMapper())
115 {
116 //Qt::KeyboardModifiers originalModifiers = Qt::KeyboardModifiers(QApplication::keyboardModifiers());
117 //Qt::KeyboardModifiers currentModifiers = Qt::KeyboardModifiers(QApplication::keyboardModifiers());
118 Display* display = X11Extras::getInstance()->display();
119 QtX11KeyMapper *keymapper = static_cast<QtX11KeyMapper*>(mapper->getKeyMapper());
120
121 for (int i=0; i < maintext.size(); i++)
122 {
123 QtX11KeyMapper::charKeyInformation temp = keymapper->getCharKeyInformation(maintext.at(i));
124 unsigned int tempcode = XKeysymToKeycode(display, temp.virtualkey);
125 if (tempcode > 0)
126 {
127 QList<unsigned int> tempList;
128
129 if (temp.modifiers != Qt::NoModifier)
130 {
131 if (temp.modifiers.testFlag(Qt::ShiftModifier))
132 {
133 if (shiftcode == 0)
134 {
135 shiftcode = XKeysymToKeycode(display, XK_Shift_L);
136 }
137
138 unsigned int modifiercode = shiftcode;
139 XTestFakeKeyEvent(display, modifiercode, 1, 0);
140 //currentModifiers |= Qt::ShiftModifier;
141 tempList.append(modifiercode);
142 }
143
144 if (temp.modifiers.testFlag(Qt::ControlModifier))
145 {
146 if (controlcode == 0)
147 {
148 controlcode = XKeysymToKeycode(display, XK_Control_L);
149 }
150
151 unsigned int modifiercode = controlcode;
152 XTestFakeKeyEvent(display, modifiercode, 1, 0);
153 //currentModifiers |= Qt::ControlModifier;
154 tempList.append(modifiercode);
155 }
156
157 if (temp.modifiers.testFlag(Qt::AltModifier))
158 {
159 if (altcode == 0)
160 {
161 altcode = XKeysymToKeycode(display, XK_Alt_L);
162 }
163
164 unsigned int modifiercode = altcode;
165 XTestFakeKeyEvent(display, modifiercode, 1, 0);
166 //currentModifiers |= Qt::AltModifier;
167 tempList.append(modifiercode);
168 }
169
170 if (temp.modifiers.testFlag(Qt::MetaModifier))
171 {
172 if (metacode == 0)
173 {
174 metacode = XKeysymToKeycode(display, XK_Meta_L);
175 }
176
177 unsigned int modifiercode = metacode;
178 XTestFakeKeyEvent(display, modifiercode, 1, 0);
179 //currentModifiers |= Qt::MetaModifier;
180 tempList.append(modifiercode);
181 }
182 }
183
184 XTestFakeKeyEvent(display, tempcode, 1, 0);
185 tempList.append(tempcode);
186
187 XFlush(display);
188
189 if (tempList.size() > 0)
190 {
191 QListIterator<unsigned int> tempiter(tempList);
192 tempiter.toBack();
193 while (tempiter.hasPrevious())
194 {
195 unsigned int currentcode = tempiter.previous();
196 XTestFakeKeyEvent(display, currentcode, 0, 0);
197 }
198
199 XFlush(display);
200 }
201 }
202 }
203
204 // Perform a flush at the end.
205 //XFlush(display);
206
207 // Restore modifiers in place
208 /*if (originalModifiers != currentModifiers)
209 {
210
211 }
212 */
213 }
214 }
215