summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRoman Savochenko <roman@oscada.org>2019-08-04 16:38:55 +0300
committerMichele Calgaro <michele.calgaro@yahoo.it>2019-08-14 10:31:32 +0900
commit4bae06f5d5248e0cd001ef76ad884853a1705a91 (patch)
tree545fa5647161f1f9b53de965648ac7978f8e8506
parent50e63e8b7d1f355202bab4f900c8f4f5138245f7 (diff)
downloadtdenetwork-4bae06f5d5248e0cd001ef76ad884853a1705a91.tar.gz
tdenetwork-4bae06f5d5248e0cd001ef76ad884853a1705a91.zip
krfb: Add a function for appending new symbols to the actual X-server keymap
This resolves bug 3014 and issue #11 Signed-off-by: Roman Savochenko <roman@oscada.org> (cherry picked from commit b75ba2ef0d61d0d356a3a0fe9e581e5aaf29b7a4)
-rw-r--r--krfb/krfb/rfbcontroller.cc53
-rw-r--r--krfb/krfb/rfbcontroller.h1
2 files changed, 54 insertions, 0 deletions
diff --git a/krfb/krfb/rfbcontroller.cc b/krfb/krfb/rfbcontroller.cc
index 0db57514..4cd0f7fb 100644
--- a/krfb/krfb/rfbcontroller.cc
+++ b/krfb/krfb/rfbcontroller.cc
@@ -184,9 +184,13 @@ const int KeyboardEvent::RIGHTSHIFT = 2;
const int KeyboardEvent::ALTGR = 4;
char KeyboardEvent::ModifierState;
+static KeySym added_keysyms[0x100];
+
KeyboardEvent::KeyboardEvent(bool d, KeySym k) :
down(d),
keySym(k) {
+
+ if(k && !IsModifierKey(k)) add_keysym(k);
}
void KeyboardEvent::initKeycodes() {
@@ -221,6 +225,55 @@ void KeyboardEvent::initKeycodes() {
XFree ((char *)keymap);
}
+int KeyboardEvent::add_keysym( KeySym keysym )
+{
+ static int first = 1;
+ if(first) {
+ for(int n = 0; n < 0x100; n++)
+ added_keysyms[n] = NoSymbol;
+ first = 0;
+ }
+
+ if(keysym == NoSymbol) return 0;
+
+ /* there can be a race before MappingNotify */
+ for(int n = 0; n < 0x100; n++)
+ if(added_keysyms[n] == keysym) return n;
+
+ int minkey, maxkey, syms_per_keycode, kc, ret = 0;
+ XDisplayKeycodes(dpy, &minkey, &maxkey);
+ KeySym *keymap = XGetKeyboardMapping(dpy, minkey, (maxkey-minkey+1), &syms_per_keycode);
+
+ for(int kc = minkey+1; kc <= maxkey; kc++) {
+ int j, didmsg = 0, is_empty = 1;
+ char *str;
+ KeySym newks[8];
+
+ for(int n = 0; n < syms_per_keycode; n++) {
+ if(keymap[(kc-minkey)*syms_per_keycode+n] != NoSymbol)
+ { is_empty = 0; break; }
+ }
+ if(!is_empty) continue;
+
+ for(int i = 0; i < 8; i++) newks[i] = NoSymbol;
+ for(int i = 0; i < syms_per_keycode; i++) {
+ newks[i] = keysym;
+ if(i >= 7) break;
+ }
+
+ XChangeKeyboardMapping(dpy, kc, syms_per_keycode, newks, 1);
+
+ XFlush(dpy);
+ added_keysyms[kc] = keysym;
+ ret = kc;
+ break;
+ }
+
+ XFree(keymap);
+
+ return ret;
+}
+
/* this function adjusts the modifiers according to mod (as from modifiers) and ModifierState */
void KeyboardEvent::tweakModifiers(signed char mod, bool down) {
diff --git a/krfb/krfb/rfbcontroller.h b/krfb/krfb/rfbcontroller.h
index 223bbf5a..d8882b90 100644
--- a/krfb/krfb/rfbcontroller.h
+++ b/krfb/krfb/rfbcontroller.h
@@ -73,6 +73,7 @@ public:
static void initKeycodes();
KeyboardEvent(bool d, KeySym k);
+ int add_keysym( KeySym keysym );
virtual void exec();
};