diff options
author | Robert Griebl <rgriebl@trolltech.com> | 2009-03-03 17:36:58 (GMT) |
---|---|---|
committer | Robert Griebl <rgriebl@trolltech.com> | 2009-04-02 19:21:57 (GMT) |
commit | 3f51c30f030a5517273a62bdd48dfe96c98852ee (patch) | |
tree | aa40f43a4d2d0b8e68b8b4ebbd86113bc8bc4f60 /src/gui/embedded | |
parent | 86723ca856dbd07bc7809ed9c3f9a219a99e67bd (diff) | |
download | Qt-3f51c30f030a5517273a62bdd48dfe96c98852ee.zip Qt-3f51c30f030a5517273a62bdd48dfe96c98852ee.tar.gz Qt-3f51c30f030a5517273a62bdd48dfe96c98852ee.tar.bz2 |
Keymap support for QWS.
This patch adds support for keymaps to the QWSKeyboardHandler. The keymaps
can be generated by the kmap2qmap tool (see tools/ directory). The source
keymaps can be standard Linux .kmap files.
Changes to Qt:
* completely refactored the Tty and Usb (now known as LinuxInput) handlers
* removed the LinuxIS plugin (handled by LinuxInput now)
* removed support for iPAQ, EBX and Zylonite keypads (obsolete hardware)
* removed support for RAW tty mode. This could be re-added, for non-Linux
systems by implementing a PC/AT scan-code to Linux keycode converter.
New features for Tty and LinuxInput (ex Usb) handlers:
* support for keymaps
QWS_KEYBOARD=..:keymap=/path/to/x.qmap:..
* support for dead keys and the compose key
* support for lock LEDs
* support for key repeat rates (in ms):
QWS_KEYBOARD=..:repeat-delay=x:repear-rate=y:..
* the default keymap supports latin1 composing via AltGr:
QWS_KEYBOARD=..:enable-compose:..
* ctrl+alt+backspace application zapping can be disabled:
QWS_KEYBOARD=..:disable-zap:..
* added virtual filter functions to both the Tty and the LinuxInput
handlers. (QWSKeyboardHandler::processKeycode should be virtual in the
first place, but that would be BIC)
Still missing:
* extended documentation for QWS_KEYBOARD
Reviewed-By: Paul Olav Tvete
Reviewed-By: Harald Fernengel
Diffstat (limited to 'src/gui/embedded')
-rw-r--r-- | src/gui/embedded/embedded.pri | 19 | ||||
-rw-r--r-- | src/gui/embedded/qkbd_defaultmap_qws_p.h | 744 | ||||
-rw-r--r-- | src/gui/embedded/qkbd_qws.cpp | 480 | ||||
-rw-r--r-- | src/gui/embedded/qkbd_qws.h | 22 | ||||
-rw-r--r-- | src/gui/embedded/qkbd_qws_p.h | 77 | ||||
-rw-r--r-- | src/gui/embedded/qkbddriverfactory_qws.cpp | 14 | ||||
-rw-r--r-- | src/gui/embedded/qkbdlinuxinput_qws.cpp | 241 | ||||
-rw-r--r-- | src/gui/embedded/qkbdlinuxinput_qws.h (renamed from src/gui/embedded/qkbdusb_qws.h) | 24 | ||||
-rw-r--r-- | src/gui/embedded/qkbdsl5000_qws.cpp | 25 | ||||
-rw-r--r-- | src/gui/embedded/qkbdsl5000_qws.h | 19 | ||||
-rw-r--r-- | src/gui/embedded/qkbdtty_qws.cpp | 301 | ||||
-rw-r--r-- | src/gui/embedded/qkbdtty_qws.h | 8 | ||||
-rw-r--r-- | src/gui/embedded/qkbdusb_qws.cpp | 401 |
13 files changed, 1791 insertions, 584 deletions
diff --git a/src/gui/embedded/embedded.pri b/src/gui/embedded/embedded.pri index 95c4132..4a9aa3f 100644 --- a/src/gui/embedded/embedded.pri +++ b/src/gui/embedded/embedded.pri @@ -89,6 +89,8 @@ embedded { HEADERS += embedded/qscreendriverplugin_qws.h \ embedded/qscreendriverfactory_qws.h \ embedded/qkbd_qws.h \ + embedded/qkbd_qws_p.h \ + embedded/qkbd_defaultmap_qws_p.h \ embedded/qkbddriverplugin_qws.h \ embedded/qkbddriverfactory_qws.h \ embedded/qmouse_qws.h \ @@ -152,17 +154,11 @@ embedded { contains( kbd-drivers, tty ) { HEADERS +=embedded/qkbdtty_qws.h SOURCES +=embedded/qkbdtty_qws.cpp - !contains( kbd-drivers, pc101 ) { - kbd-drivers += pc101 - } } - contains( kbd-drivers, usb ) { - HEADERS +=embedded/qkbdusb_qws.h - SOURCES +=embedded/qkbdusb_qws.cpp - !contains( kbd-drivers, pc101 ) { - kbd-drivers += pc101 - } + contains( kbd-drivers, linuxinput ) { + HEADERS +=embedded/qkbdlinuxinput_qws.h + SOURCES +=embedded/qkbdlinuxinput_qws.cpp } contains( kbd-drivers, um ) { @@ -170,11 +166,6 @@ embedded { SOURCES +=embedded/qkbdum_qws.cpp } - contains( kbd-drivers, pc101 ) { - HEADERS +=embedded/qkbdpc101_qws.h - SOURCES +=embedded/qkbdpc101_qws.cpp - } - contains( kbd-drivers, yopy ) { HEADERS +=embedded/qkbdyopy_qws.h SOURCES +=embedded/qkbdyopy_qws.cpp diff --git a/src/gui/embedded/qkbd_defaultmap_qws_p.h b/src/gui/embedded/qkbd_defaultmap_qws_p.h new file mode 100644 index 0000000..34ce69e --- /dev/null +++ b/src/gui/embedded/qkbd_defaultmap_qws_p.h @@ -0,0 +1,744 @@ +#ifndef QWSKEYBOARDHANDLER_DEFAULTMAP_H +#define QWSKEYBOARDHANDLER_DEFAULTMAP_H + +const QWSKeyboard::Mapping QWSKbPrivate::s_keymap_default[] = { + { 1, 0xffff, 0x01000000, 0x00, 0x00, 0x0000 }, + { 2, 0x0031, 0x00000031, 0x00, 0x00, 0x0000 }, + { 2, 0x0021, 0x00000021, 0x01, 0x00, 0x0000 }, + { 3, 0x0032, 0x00000032, 0x00, 0x00, 0x0000 }, + { 3, 0x0040, 0x00000040, 0x01, 0x00, 0x0000 }, + { 3, 0x0040, 0x00000040, 0x02, 0x00, 0x0000 }, + { 4, 0x0033, 0x00000033, 0x00, 0x00, 0x0000 }, + { 4, 0x0023, 0x00000023, 0x01, 0x00, 0x0000 }, + { 4, 0xffff, 0x01000000, 0x04, 0x00, 0x0000 }, + { 5, 0x0034, 0x00000034, 0x00, 0x00, 0x0000 }, + { 5, 0x0024, 0x00000024, 0x01, 0x00, 0x0000 }, + { 5, 0x0024, 0x00000024, 0x02, 0x00, 0x0000 }, + { 5, 0x005c, 0x0400005c, 0x04, 0x00, 0x0000 }, + { 6, 0x0035, 0x00000035, 0x00, 0x00, 0x0000 }, + { 6, 0x0025, 0x00000025, 0x01, 0x00, 0x0000 }, + { 6, 0x005d, 0x0400005d, 0x04, 0x00, 0x0000 }, + { 7, 0x0036, 0x00000036, 0x00, 0x00, 0x0000 }, + { 7, 0x005e, 0x0000005e, 0x01, 0x00, 0x0000 }, + { 7, 0x005e, 0x01001252, 0x02, 0x01, 0x0000 }, + { 7, 0x005e, 0x0400005e, 0x04, 0x00, 0x0000 }, + { 8, 0x0037, 0x00000037, 0x00, 0x00, 0x0000 }, + { 8, 0x0026, 0x00000026, 0x01, 0x00, 0x0000 }, + { 8, 0x007b, 0x0000007b, 0x02, 0x00, 0x0000 }, + { 8, 0x005f, 0x0400005f, 0x04, 0x00, 0x0000 }, + { 9, 0x0038, 0x00000038, 0x00, 0x00, 0x0000 }, + { 9, 0x002a, 0x0000002a, 0x01, 0x00, 0x0000 }, + { 9, 0x005b, 0x0000005b, 0x02, 0x00, 0x0000 }, + { 9, 0xffff, 0x01000003, 0x04, 0x00, 0x0000 }, + { 10, 0x0039, 0x00000039, 0x00, 0x00, 0x0000 }, + { 10, 0x0028, 0x00000028, 0x01, 0x00, 0x0000 }, + { 10, 0x005d, 0x0000005d, 0x02, 0x00, 0x0000 }, + { 11, 0x0030, 0x00000030, 0x00, 0x00, 0x0000 }, + { 11, 0x0029, 0x00000029, 0x01, 0x00, 0x0000 }, + { 11, 0x007d, 0x0000007d, 0x02, 0x00, 0x0000 }, + { 12, 0x002d, 0x0000002d, 0x00, 0x00, 0x0000 }, + { 12, 0x005f, 0x0000005f, 0x01, 0x00, 0x0000 }, + { 12, 0x005c, 0x0000005c, 0x02, 0x00, 0x0000 }, + { 12, 0x005f, 0x0400005f, 0x04, 0x00, 0x0000 }, + { 12, 0x005f, 0x0400005f, 0x05, 0x00, 0x0000 }, + { 13, 0x003d, 0x0000003d, 0x00, 0x00, 0x0000 }, + { 13, 0x002b, 0x0000002b, 0x01, 0x00, 0x0000 }, + { 14, 0xffff, 0x01000003, 0x00, 0x00, 0x0000 }, + { 14, 0xffff, 0x01000000, 0x0c, 0x08, 0x0300 }, + { 15, 0xffff, 0x01000001, 0x00, 0x00, 0x0000 }, + { 16, 0x0071, 0x00000051, 0x00, 0x00, 0x0000 }, + { 16, 0x0051, 0x00000051, 0x01, 0x00, 0x0000 }, + { 16, 0x0071, 0x00000051, 0x02, 0x00, 0x0000 }, + { 16, 0x0051, 0x00000051, 0x03, 0x00, 0x0000 }, + { 16, 0x0071, 0x04000051, 0x04, 0x00, 0x0000 }, + { 16, 0x0071, 0x04000051, 0x05, 0x00, 0x0000 }, + { 16, 0x0071, 0x04000051, 0x06, 0x00, 0x0000 }, + { 16, 0x0071, 0x04000051, 0x07, 0x00, 0x0000 }, + { 16, 0x0071, 0x08000051, 0x08, 0x00, 0x0000 }, + { 16, 0x0071, 0x08000051, 0x09, 0x00, 0x0000 }, + { 16, 0x0071, 0x08000051, 0x0a, 0x00, 0x0000 }, + { 16, 0x0071, 0x08000051, 0x0b, 0x00, 0x0000 }, + { 16, 0x0071, 0x0c000051, 0x0c, 0x00, 0x0000 }, + { 16, 0x0071, 0x0c000051, 0x0d, 0x00, 0x0000 }, + { 16, 0x0071, 0x0c000051, 0x0e, 0x00, 0x0000 }, + { 16, 0x0071, 0x0c000051, 0x0f, 0x00, 0x0000 }, + { 17, 0x0077, 0x00000057, 0x00, 0x00, 0x0000 }, + { 17, 0x0057, 0x00000057, 0x01, 0x00, 0x0000 }, + { 17, 0x0077, 0x00000057, 0x02, 0x00, 0x0000 }, + { 17, 0x0057, 0x00000057, 0x03, 0x00, 0x0000 }, + { 17, 0x0077, 0x04000057, 0x04, 0x00, 0x0000 }, + { 17, 0x0077, 0x04000057, 0x05, 0x00, 0x0000 }, + { 17, 0x0077, 0x04000057, 0x06, 0x00, 0x0000 }, + { 17, 0x0077, 0x04000057, 0x07, 0x00, 0x0000 }, + { 17, 0x0077, 0x08000057, 0x08, 0x00, 0x0000 }, + { 17, 0x0077, 0x08000057, 0x09, 0x00, 0x0000 }, + { 17, 0x0077, 0x08000057, 0x0a, 0x00, 0x0000 }, + { 17, 0x0077, 0x08000057, 0x0b, 0x00, 0x0000 }, + { 17, 0x0077, 0x0c000057, 0x0c, 0x00, 0x0000 }, + { 17, 0x0077, 0x0c000057, 0x0d, 0x00, 0x0000 }, + { 17, 0x0077, 0x0c000057, 0x0e, 0x00, 0x0000 }, + { 17, 0x0077, 0x0c000057, 0x0f, 0x00, 0x0000 }, + { 18, 0x0065, 0x00000045, 0x00, 0x00, 0x0000 }, + { 18, 0x0045, 0x00000045, 0x01, 0x00, 0x0000 }, + { 18, 0x0065, 0x00000045, 0x02, 0x00, 0x0000 }, + { 18, 0x0045, 0x00000045, 0x03, 0x00, 0x0000 }, + { 18, 0x0065, 0x04000045, 0x04, 0x00, 0x0000 }, + { 18, 0x0065, 0x04000045, 0x05, 0x00, 0x0000 }, + { 18, 0x0065, 0x04000045, 0x06, 0x00, 0x0000 }, + { 18, 0x0065, 0x04000045, 0x07, 0x00, 0x0000 }, + { 18, 0x0065, 0x08000045, 0x08, 0x00, 0x0000 }, + { 18, 0x0065, 0x08000045, 0x09, 0x00, 0x0000 }, + { 18, 0x0065, 0x08000045, 0x0a, 0x00, 0x0000 }, + { 18, 0x0065, 0x08000045, 0x0b, 0x00, 0x0000 }, + { 18, 0x0065, 0x0c000045, 0x0c, 0x00, 0x0000 }, + { 18, 0x0065, 0x0c000045, 0x0d, 0x00, 0x0000 }, + { 18, 0x0065, 0x0c000045, 0x0e, 0x00, 0x0000 }, + { 18, 0x0065, 0x0c000045, 0x0f, 0x00, 0x0000 }, + { 19, 0x0072, 0x00000052, 0x00, 0x00, 0x0000 }, + { 19, 0x0052, 0x00000052, 0x01, 0x00, 0x0000 }, + { 19, 0x0072, 0x00000052, 0x02, 0x00, 0x0000 }, + { 19, 0x0052, 0x00000052, 0x03, 0x00, 0x0000 }, + { 19, 0x0072, 0x04000052, 0x04, 0x00, 0x0000 }, + { 19, 0x0072, 0x04000052, 0x05, 0x00, 0x0000 }, + { 19, 0x0072, 0x04000052, 0x06, 0x00, 0x0000 }, + { 19, 0x0072, 0x04000052, 0x07, 0x00, 0x0000 }, + { 19, 0x0072, 0x08000052, 0x08, 0x00, 0x0000 }, + { 19, 0x0072, 0x08000052, 0x09, 0x00, 0x0000 }, + { 19, 0x0072, 0x08000052, 0x0a, 0x00, 0x0000 }, + { 19, 0x0072, 0x08000052, 0x0b, 0x00, 0x0000 }, + { 19, 0x0072, 0x0c000052, 0x0c, 0x00, 0x0000 }, + { 19, 0x0072, 0x0c000052, 0x0d, 0x00, 0x0000 }, + { 19, 0x0072, 0x0c000052, 0x0e, 0x00, 0x0000 }, + { 19, 0x0072, 0x0c000052, 0x0f, 0x00, 0x0000 }, + { 20, 0x0074, 0x00000054, 0x00, 0x00, 0x0000 }, + { 20, 0x0054, 0x00000054, 0x01, 0x00, 0x0000 }, + { 20, 0x0074, 0x00000054, 0x02, 0x00, 0x0000 }, + { 20, 0x0054, 0x00000054, 0x03, 0x00, 0x0000 }, + { 20, 0x0074, 0x04000054, 0x04, 0x00, 0x0000 }, + { 20, 0x0074, 0x04000054, 0x05, 0x00, 0x0000 }, + { 20, 0x0074, 0x04000054, 0x06, 0x00, 0x0000 }, + { 20, 0x0074, 0x04000054, 0x07, 0x00, 0x0000 }, + { 20, 0x0074, 0x08000054, 0x08, 0x00, 0x0000 }, + { 20, 0x0074, 0x08000054, 0x09, 0x00, 0x0000 }, + { 20, 0x0074, 0x08000054, 0x0a, 0x00, 0x0000 }, + { 20, 0x0074, 0x08000054, 0x0b, 0x00, 0x0000 }, + { 20, 0x0074, 0x0c000054, 0x0c, 0x00, 0x0000 }, + { 20, 0x0074, 0x0c000054, 0x0d, 0x00, 0x0000 }, + { 20, 0x0074, 0x0c000054, 0x0e, 0x00, 0x0000 }, + { 20, 0x0074, 0x0c000054, 0x0f, 0x00, 0x0000 }, + { 21, 0x0079, 0x00000059, 0x00, 0x00, 0x0000 }, + { 21, 0x0059, 0x00000059, 0x01, 0x00, 0x0000 }, + { 21, 0x0079, 0x00000059, 0x02, 0x00, 0x0000 }, + { 21, 0x0059, 0x00000059, 0x03, 0x00, 0x0000 }, + { 21, 0x0079, 0x04000059, 0x04, 0x00, 0x0000 }, + { 21, 0x0079, 0x04000059, 0x05, 0x00, 0x0000 }, + { 21, 0x0079, 0x04000059, 0x06, 0x00, 0x0000 }, + { 21, 0x0079, 0x04000059, 0x07, 0x00, 0x0000 }, + { 21, 0x0079, 0x08000059, 0x08, 0x00, 0x0000 }, + { 21, 0x0079, 0x08000059, 0x09, 0x00, 0x0000 }, + { 21, 0x0079, 0x08000059, 0x0a, 0x00, 0x0000 }, + { 21, 0x0079, 0x08000059, 0x0b, 0x00, 0x0000 }, + { 21, 0x0079, 0x0c000059, 0x0c, 0x00, 0x0000 }, + { 21, 0x0079, 0x0c000059, 0x0d, 0x00, 0x0000 }, + { 21, 0x0079, 0x0c000059, 0x0e, 0x00, 0x0000 }, + { 21, 0x0079, 0x0c000059, 0x0f, 0x00, 0x0000 }, + { 22, 0x0075, 0x00000055, 0x00, 0x00, 0x0000 }, + { 22, 0x0055, 0x00000055, 0x01, 0x00, 0x0000 }, + { 22, 0x0075, 0x00000055, 0x02, 0x00, 0x0000 }, + { 22, 0x0055, 0x00000055, 0x03, 0x00, 0x0000 }, + { 22, 0x0075, 0x04000055, 0x04, 0x00, 0x0000 }, + { 22, 0x0075, 0x04000055, 0x05, 0x00, 0x0000 }, + { 22, 0x0075, 0x04000055, 0x06, 0x00, 0x0000 }, + { 22, 0x0075, 0x04000055, 0x07, 0x00, 0x0000 }, + { 22, 0x0075, 0x08000055, 0x08, 0x00, 0x0000 }, + { 22, 0x0075, 0x08000055, 0x09, 0x00, 0x0000 }, + { 22, 0x0075, 0x08000055, 0x0a, 0x00, 0x0000 }, + { 22, 0x0075, 0x08000055, 0x0b, 0x00, 0x0000 }, + { 22, 0x0075, 0x0c000055, 0x0c, 0x00, 0x0000 }, + { 22, 0x0075, 0x0c000055, 0x0d, 0x00, 0x0000 }, + { 22, 0x0075, 0x0c000055, 0x0e, 0x00, 0x0000 }, + { 22, 0x0075, 0x0c000055, 0x0f, 0x00, 0x0000 }, + { 23, 0x0069, 0x00000049, 0x00, 0x00, 0x0000 }, + { 23, 0x0049, 0x00000049, 0x01, 0x00, 0x0000 }, + { 23, 0x0069, 0x00000049, 0x02, 0x00, 0x0000 }, + { 23, 0x0049, 0x00000049, 0x03, 0x00, 0x0000 }, + { 23, 0x0069, 0x04000049, 0x04, 0x00, 0x0000 }, + { 23, 0x0069, 0x04000049, 0x05, 0x00, 0x0000 }, + { 23, 0x0069, 0x04000049, 0x06, 0x00, 0x0000 }, + { 23, 0x0069, 0x04000049, 0x07, 0x00, 0x0000 }, + { 23, 0x0069, 0x08000049, 0x08, 0x00, 0x0000 }, + { 23, 0x0069, 0x08000049, 0x09, 0x00, 0x0000 }, + { 23, 0x0069, 0x08000049, 0x0a, 0x00, 0x0000 }, + { 23, 0x0069, 0x08000049, 0x0b, 0x00, 0x0000 }, + { 23, 0x0069, 0x0c000049, 0x0c, 0x00, 0x0000 }, + { 23, 0x0069, 0x0c000049, 0x0d, 0x00, 0x0000 }, + { 23, 0x0069, 0x0c000049, 0x0e, 0x00, 0x0000 }, + { 23, 0x0069, 0x0c000049, 0x0f, 0x00, 0x0000 }, + { 24, 0x006f, 0x0000004f, 0x00, 0x00, 0x0000 }, + { 24, 0x004f, 0x0000004f, 0x01, 0x00, 0x0000 }, + { 24, 0x006f, 0x0000004f, 0x02, 0x00, 0x0000 }, + { 24, 0x004f, 0x0000004f, 0x03, 0x00, 0x0000 }, + { 24, 0x006f, 0x0400004f, 0x04, 0x00, 0x0000 }, + { 24, 0x006f, 0x0400004f, 0x05, 0x00, 0x0000 }, + { 24, 0x006f, 0x0400004f, 0x06, 0x00, 0x0000 }, + { 24, 0x006f, 0x0400004f, 0x07, 0x00, 0x0000 }, + { 24, 0x006f, 0x0800004f, 0x08, 0x00, 0x0000 }, + { 24, 0x006f, 0x0800004f, 0x09, 0x00, 0x0000 }, + { 24, 0x006f, 0x0800004f, 0x0a, 0x00, 0x0000 }, + { 24, 0x006f, 0x0800004f, 0x0b, 0x00, 0x0000 }, + { 24, 0x006f, 0x0c00004f, 0x0c, 0x00, 0x0000 }, + { 24, 0x006f, 0x0c00004f, 0x0d, 0x00, 0x0000 }, + { 24, 0x006f, 0x0c00004f, 0x0e, 0x00, 0x0000 }, + { 24, 0x006f, 0x0c00004f, 0x0f, 0x00, 0x0000 }, + { 25, 0x0070, 0x00000050, 0x00, 0x00, 0x0000 }, + { 25, 0x0050, 0x00000050, 0x01, 0x00, 0x0000 }, + { 25, 0x0070, 0x00000050, 0x02, 0x00, 0x0000 }, + { 25, 0x0050, 0x00000050, 0x03, 0x00, 0x0000 }, + { 25, 0x0070, 0x04000050, 0x04, 0x00, 0x0000 }, + { 25, 0x0070, 0x04000050, 0x05, 0x00, 0x0000 }, + { 25, 0x0070, 0x04000050, 0x06, 0x00, 0x0000 }, + { 25, 0x0070, 0x04000050, 0x07, 0x00, 0x0000 }, + { 25, 0x0070, 0x08000050, 0x08, 0x00, 0x0000 }, + { 25, 0x0070, 0x08000050, 0x09, 0x00, 0x0000 }, + { 25, 0x0070, 0x08000050, 0x0a, 0x00, 0x0000 }, + { 25, 0x0070, 0x08000050, 0x0b, 0x00, 0x0000 }, + { 25, 0x0070, 0x0c000050, 0x0c, 0x00, 0x0000 }, + { 25, 0x0070, 0x0c000050, 0x0d, 0x00, 0x0000 }, + { 25, 0x0070, 0x0c000050, 0x0e, 0x00, 0x0000 }, + { 25, 0x0070, 0x0c000050, 0x0f, 0x00, 0x0000 }, + { 26, 0x005b, 0x0000005b, 0x00, 0x00, 0x0000 }, + { 26, 0x007b, 0x0000007b, 0x01, 0x00, 0x0000 }, + { 26, 0xffff, 0x01000000, 0x04, 0x00, 0x0000 }, + { 27, 0x005d, 0x0000005d, 0x00, 0x00, 0x0000 }, + { 27, 0x007d, 0x0000007d, 0x01, 0x00, 0x0000 }, + { 27, 0x007e, 0x0000007e, 0x02, 0x00, 0x0000 }, + { 27, 0x005d, 0x0400005d, 0x04, 0x00, 0x0000 }, + { 28, 0xffff, 0x01000004, 0x00, 0x00, 0x0000 }, + { 28, 0x006d, 0x0c00004d, 0x08, 0x00, 0x0000 }, + { 29, 0xffff, 0x01000021, 0x00, 0x04, 0x0004 }, + { 30, 0x0061, 0x00000041, 0x00, 0x00, 0x0000 }, + { 30, 0x0041, 0x00000041, 0x01, 0x00, 0x0000 }, + { 30, 0x0061, 0x00000041, 0x02, 0x00, 0x0000 }, + { 30, 0x0041, 0x00000041, 0x03, 0x00, 0x0000 }, + { 30, 0x0061, 0x04000041, 0x04, 0x00, 0x0000 }, + { 30, 0x0061, 0x04000041, 0x05, 0x00, 0x0000 }, + { 30, 0x0061, 0x04000041, 0x06, 0x00, 0x0000 }, + { 30, 0x0061, 0x04000041, 0x07, 0x00, 0x0000 }, + { 30, 0x0061, 0x08000041, 0x08, 0x00, 0x0000 }, + { 30, 0x0061, 0x08000041, 0x09, 0x00, 0x0000 }, + { 30, 0x0061, 0x08000041, 0x0a, 0x00, 0x0000 }, + { 30, 0x0061, 0x08000041, 0x0b, 0x00, 0x0000 }, + { 30, 0x0061, 0x0c000041, 0x0c, 0x00, 0x0000 }, + { 30, 0x0061, 0x0c000041, 0x0d, 0x00, 0x0000 }, + { 30, 0x0061, 0x0c000041, 0x0e, 0x00, 0x0000 }, + { 30, 0x0061, 0x0c000041, 0x0f, 0x00, 0x0000 }, + { 31, 0x0073, 0x00000053, 0x00, 0x00, 0x0000 }, + { 31, 0x0053, 0x00000053, 0x01, 0x00, 0x0000 }, + { 31, 0x0073, 0x00000053, 0x02, 0x00, 0x0000 }, + { 31, 0x0053, 0x00000053, 0x03, 0x00, 0x0000 }, + { 31, 0x0073, 0x04000053, 0x04, 0x00, 0x0000 }, + { 31, 0x0073, 0x04000053, 0x05, 0x00, 0x0000 }, + { 31, 0x0073, 0x04000053, 0x06, 0x00, 0x0000 }, + { 31, 0x0073, 0x04000053, 0x07, 0x00, 0x0000 }, + { 31, 0x0073, 0x08000053, 0x08, 0x00, 0x0000 }, + { 31, 0x0073, 0x08000053, 0x09, 0x00, 0x0000 }, + { 31, 0x0073, 0x08000053, 0x0a, 0x00, 0x0000 }, + { 31, 0x0073, 0x08000053, 0x0b, 0x00, 0x0000 }, + { 31, 0x0073, 0x0c000053, 0x0c, 0x00, 0x0000 }, + { 31, 0x0073, 0x0c000053, 0x0d, 0x00, 0x0000 }, + { 31, 0x0073, 0x0c000053, 0x0e, 0x00, 0x0000 }, + { 31, 0x0073, 0x0c000053, 0x0f, 0x00, 0x0000 }, + { 32, 0x0064, 0x00000044, 0x00, 0x00, 0x0000 }, + { 32, 0x0044, 0x00000044, 0x01, 0x00, 0x0000 }, + { 32, 0x0064, 0x00000044, 0x02, 0x00, 0x0000 }, + { 32, 0x0044, 0x00000044, 0x03, 0x00, 0x0000 }, + { 32, 0x0064, 0x04000044, 0x04, 0x00, 0x0000 }, + { 32, 0x0064, 0x04000044, 0x05, 0x00, 0x0000 }, + { 32, 0x0064, 0x04000044, 0x06, 0x00, 0x0000 }, + { 32, 0x0064, 0x04000044, 0x07, 0x00, 0x0000 }, + { 32, 0x0064, 0x08000044, 0x08, 0x00, 0x0000 }, + { 32, 0x0064, 0x08000044, 0x09, 0x00, 0x0000 }, + { 32, 0x0064, 0x08000044, 0x0a, 0x00, 0x0000 }, + { 32, 0x0064, 0x08000044, 0x0b, 0x00, 0x0000 }, + { 32, 0x0064, 0x0c000044, 0x0c, 0x00, 0x0000 }, + { 32, 0x0064, 0x0c000044, 0x0d, 0x00, 0x0000 }, + { 32, 0x0064, 0x0c000044, 0x0e, 0x00, 0x0000 }, + { 32, 0x0064, 0x0c000044, 0x0f, 0x00, 0x0000 }, + { 33, 0x0066, 0x00000046, 0x00, 0x00, 0x0000 }, + { 33, 0x0046, 0x00000046, 0x01, 0x00, 0x0000 }, + { 33, 0x0066, 0x00000046, 0x02, 0x00, 0x0000 }, + { 33, 0x0046, 0x00000046, 0x03, 0x00, 0x0000 }, + { 33, 0x0066, 0x04000046, 0x04, 0x00, 0x0000 }, + { 33, 0x0066, 0x04000046, 0x05, 0x00, 0x0000 }, + { 33, 0x0066, 0x04000046, 0x06, 0x00, 0x0000 }, + { 33, 0x0066, 0x04000046, 0x07, 0x00, 0x0000 }, + { 33, 0x0066, 0x08000046, 0x08, 0x00, 0x0000 }, + { 33, 0x0066, 0x08000046, 0x09, 0x00, 0x0000 }, + { 33, 0x0066, 0x08000046, 0x0a, 0x00, 0x0000 }, + { 33, 0x0066, 0x08000046, 0x0b, 0x00, 0x0000 }, + { 33, 0x0066, 0x0c000046, 0x0c, 0x00, 0x0000 }, + { 33, 0x0066, 0x0c000046, 0x0d, 0x00, 0x0000 }, + { 33, 0x0066, 0x0c000046, 0x0e, 0x00, 0x0000 }, + { 33, 0x0066, 0x0c000046, 0x0f, 0x00, 0x0000 }, + { 34, 0x0067, 0x00000047, 0x00, 0x00, 0x0000 }, + { 34, 0x0047, 0x00000047, 0x01, 0x00, 0x0000 }, + { 34, 0x0067, 0x00000047, 0x02, 0x00, 0x0000 }, + { 34, 0x0047, 0x00000047, 0x03, 0x00, 0x0000 }, + { 34, 0x0067, 0x04000047, 0x04, 0x00, 0x0000 }, + { 34, 0x0067, 0x04000047, 0x05, 0x00, 0x0000 }, + { 34, 0x0067, 0x04000047, 0x06, 0x00, 0x0000 }, + { 34, 0x0067, 0x04000047, 0x07, 0x00, 0x0000 }, + { 34, 0x0067, 0x08000047, 0x08, 0x00, 0x0000 }, + { 34, 0x0067, 0x08000047, 0x09, 0x00, 0x0000 }, + { 34, 0x0067, 0x08000047, 0x0a, 0x00, 0x0000 }, + { 34, 0x0067, 0x08000047, 0x0b, 0x00, 0x0000 }, + { 34, 0x0067, 0x0c000047, 0x0c, 0x00, 0x0000 }, + { 34, 0x0067, 0x0c000047, 0x0d, 0x00, 0x0000 }, + { 34, 0x0067, 0x0c000047, 0x0e, 0x00, 0x0000 }, + { 34, 0x0067, 0x0c000047, 0x0f, 0x00, 0x0000 }, + { 35, 0x0068, 0x00000048, 0x00, 0x00, 0x0000 }, + { 35, 0x0048, 0x00000048, 0x01, 0x00, 0x0000 }, + { 35, 0x0068, 0x00000048, 0x02, 0x00, 0x0000 }, + { 35, 0x0048, 0x00000048, 0x03, 0x00, 0x0000 }, + { 35, 0x0068, 0x04000048, 0x04, 0x00, 0x0000 }, + { 35, 0x0068, 0x04000048, 0x05, 0x00, 0x0000 }, + { 35, 0x0068, 0x04000048, 0x06, 0x00, 0x0000 }, + { 35, 0x0068, 0x04000048, 0x07, 0x00, 0x0000 }, + { 35, 0x0068, 0x08000048, 0x08, 0x00, 0x0000 }, + { 35, 0x0068, 0x08000048, 0x09, 0x00, 0x0000 }, + { 35, 0x0068, 0x08000048, 0x0a, 0x00, 0x0000 }, + { 35, 0x0068, 0x08000048, 0x0b, 0x00, 0x0000 }, + { 35, 0x0068, 0x0c000048, 0x0c, 0x00, 0x0000 }, + { 35, 0x0068, 0x0c000048, 0x0d, 0x00, 0x0000 }, + { 35, 0x0068, 0x0c000048, 0x0e, 0x00, 0x0000 }, + { 35, 0x0068, 0x0c000048, 0x0f, 0x00, 0x0000 }, + { 36, 0x006a, 0x0000004a, 0x00, 0x00, 0x0000 }, + { 36, 0x004a, 0x0000004a, 0x01, 0x00, 0x0000 }, + { 36, 0x006a, 0x0000004a, 0x02, 0x00, 0x0000 }, + { 36, 0x004a, 0x0000004a, 0x03, 0x00, 0x0000 }, + { 36, 0x006a, 0x0400004a, 0x04, 0x00, 0x0000 }, + { 36, 0x006a, 0x0400004a, 0x05, 0x00, 0x0000 }, + { 36, 0x006a, 0x0400004a, 0x06, 0x00, 0x0000 }, + { 36, 0x006a, 0x0400004a, 0x07, 0x00, 0x0000 }, + { 36, 0x006a, 0x0800004a, 0x08, 0x00, 0x0000 }, + { 36, 0x006a, 0x0800004a, 0x09, 0x00, 0x0000 }, + { 36, 0x006a, 0x0800004a, 0x0a, 0x00, 0x0000 }, + { 36, 0x006a, 0x0800004a, 0x0b, 0x00, 0x0000 }, + { 36, 0x006a, 0x0c00004a, 0x0c, 0x00, 0x0000 }, + { 36, 0x006a, 0x0c00004a, 0x0d, 0x00, 0x0000 }, + { 36, 0x006a, 0x0c00004a, 0x0e, 0x00, 0x0000 }, + { 36, 0x006a, 0x0c00004a, 0x0f, 0x00, 0x0000 }, + { 37, 0x006b, 0x0000004b, 0x00, 0x00, 0x0000 }, + { 37, 0x004b, 0x0000004b, 0x01, 0x00, 0x0000 }, + { 37, 0x006b, 0x0000004b, 0x02, 0x00, 0x0000 }, + { 37, 0x004b, 0x0000004b, 0x03, 0x00, 0x0000 }, + { 37, 0x006b, 0x0400004b, 0x04, 0x00, 0x0000 }, + { 37, 0x006b, 0x0400004b, 0x05, 0x00, 0x0000 }, + { 37, 0x006b, 0x0400004b, 0x06, 0x00, 0x0000 }, + { 37, 0x006b, 0x0400004b, 0x07, 0x00, 0x0000 }, + { 37, 0x006b, 0x0800004b, 0x08, 0x00, 0x0000 }, + { 37, 0x006b, 0x0800004b, 0x09, 0x00, 0x0000 }, + { 37, 0x006b, 0x0800004b, 0x0a, 0x00, 0x0000 }, + { 37, 0x006b, 0x0800004b, 0x0b, 0x00, 0x0000 }, + { 37, 0x006b, 0x0c00004b, 0x0c, 0x00, 0x0000 }, + { 37, 0x006b, 0x0c00004b, 0x0d, 0x00, 0x0000 }, + { 37, 0x006b, 0x0c00004b, 0x0e, 0x00, 0x0000 }, + { 37, 0x006b, 0x0c00004b, 0x0f, 0x00, 0x0000 }, + { 38, 0x006c, 0x0000004c, 0x00, 0x00, 0x0000 }, + { 38, 0x004c, 0x0000004c, 0x01, 0x00, 0x0000 }, + { 38, 0x006c, 0x0000004c, 0x02, 0x00, 0x0000 }, + { 38, 0x004c, 0x0000004c, 0x03, 0x00, 0x0000 }, + { 38, 0x006c, 0x0400004c, 0x04, 0x00, 0x0000 }, + { 38, 0x006c, 0x0400004c, 0x05, 0x00, 0x0000 }, + { 38, 0x006c, 0x0400004c, 0x06, 0x00, 0x0000 }, + { 38, 0x006c, 0x0400004c, 0x07, 0x00, 0x0000 }, + { 38, 0x006c, 0x0800004c, 0x08, 0x00, 0x0000 }, + { 38, 0x006c, 0x0800004c, 0x09, 0x00, 0x0000 }, + { 38, 0x006c, 0x0800004c, 0x0a, 0x00, 0x0000 }, + { 38, 0x006c, 0x0800004c, 0x0b, 0x00, 0x0000 }, + { 38, 0x006c, 0x0c00004c, 0x0c, 0x00, 0x0000 }, + { 38, 0x006c, 0x0c00004c, 0x0d, 0x00, 0x0000 }, + { 38, 0x006c, 0x0c00004c, 0x0e, 0x00, 0x0000 }, + { 38, 0x006c, 0x0c00004c, 0x0f, 0x00, 0x0000 }, + { 39, 0x003b, 0x0000003b, 0x00, 0x00, 0x0000 }, + { 39, 0x003a, 0x0000003a, 0x01, 0x00, 0x0000 }, + { 40, 0x0027, 0x00000027, 0x00, 0x00, 0x0000 }, + { 40, 0x0022, 0x00000022, 0x01, 0x00, 0x0000 }, + { 40, 0x0027, 0x01001251, 0x02, 0x01, 0x0000 }, + { 40, 0x0022, 0x01001257, 0x03, 0x01, 0x0000 }, + { 40, 0x0067, 0x04000047, 0x04, 0x00, 0x0000 }, + { 41, 0x0060, 0x00000060, 0x00, 0x00, 0x0000 }, + { 41, 0x007e, 0x0000007e, 0x01, 0x00, 0x0000 }, + { 41, 0x0060, 0x01001250, 0x02, 0x01, 0x0000 }, + { 41, 0x007e, 0x01001253, 0x03, 0x01, 0x0000 }, + { 42, 0xffff, 0x01000020, 0x00, 0x04, 0x0001 }, + { 43, 0x005c, 0x0000005c, 0x00, 0x00, 0x0000 }, + { 43, 0x007c, 0x0000007c, 0x01, 0x00, 0x0000 }, + { 43, 0x005c, 0x0400005c, 0x04, 0x00, 0x0000 }, + { 44, 0x007a, 0x0000005a, 0x00, 0x00, 0x0000 }, + { 44, 0x005a, 0x0000005a, 0x01, 0x00, 0x0000 }, + { 44, 0x007a, 0x0000005a, 0x02, 0x00, 0x0000 }, + { 44, 0x005a, 0x0000005a, 0x03, 0x00, 0x0000 }, + { 44, 0x007a, 0x0400005a, 0x04, 0x00, 0x0000 }, + { 44, 0x007a, 0x0400005a, 0x05, 0x00, 0x0000 }, + { 44, 0x007a, 0x0400005a, 0x06, 0x00, 0x0000 }, + { 44, 0x007a, 0x0400005a, 0x07, 0x00, 0x0000 }, + { 44, 0x007a, 0x0800005a, 0x08, 0x00, 0x0000 }, + { 44, 0x007a, 0x0800005a, 0x09, 0x00, 0x0000 }, + { 44, 0x007a, 0x0800005a, 0x0a, 0x00, 0x0000 }, + { 44, 0x007a, 0x0800005a, 0x0b, 0x00, 0x0000 }, + { 44, 0x007a, 0x0c00005a, 0x0c, 0x00, 0x0000 }, + { 44, 0x007a, 0x0c00005a, 0x0d, 0x00, 0x0000 }, + { 44, 0x007a, 0x0c00005a, 0x0e, 0x00, 0x0000 }, + { 44, 0x007a, 0x0c00005a, 0x0f, 0x00, 0x0000 }, + { 45, 0x0078, 0x00000058, 0x00, 0x00, 0x0000 }, + { 45, 0x0058, 0x00000058, 0x01, 0x00, 0x0000 }, + { 45, 0x0078, 0x00000058, 0x02, 0x00, 0x0000 }, + { 45, 0x0058, 0x00000058, 0x03, 0x00, 0x0000 }, + { 45, 0x0078, 0x04000058, 0x04, 0x00, 0x0000 }, + { 45, 0x0078, 0x04000058, 0x05, 0x00, 0x0000 }, + { 45, 0x0078, 0x04000058, 0x06, 0x00, 0x0000 }, + { 45, 0x0078, 0x04000058, 0x07, 0x00, 0x0000 }, + { 45, 0x0078, 0x08000058, 0x08, 0x00, 0x0000 }, + { 45, 0x0078, 0x08000058, 0x09, 0x00, 0x0000 }, + { 45, 0x0078, 0x08000058, 0x0a, 0x00, 0x0000 }, + { 45, 0x0078, 0x08000058, 0x0b, 0x00, 0x0000 }, + { 45, 0x0078, 0x0c000058, 0x0c, 0x00, 0x0000 }, + { 45, 0x0078, 0x0c000058, 0x0d, 0x00, 0x0000 }, + { 45, 0x0078, 0x0c000058, 0x0e, 0x00, 0x0000 }, + { 45, 0x0078, 0x0c000058, 0x0f, 0x00, 0x0000 }, + { 46, 0x0063, 0x00000043, 0x00, 0x00, 0x0000 }, + { 46, 0x0043, 0x00000043, 0x01, 0x00, 0x0000 }, + { 46, 0x0063, 0x00000043, 0x02, 0x00, 0x0000 }, + { 46, 0x0043, 0x00000043, 0x03, 0x00, 0x0000 }, + { 46, 0x0063, 0x04000043, 0x04, 0x00, 0x0000 }, + { 46, 0x0063, 0x04000043, 0x05, 0x00, 0x0000 }, + { 46, 0x0063, 0x04000043, 0x06, 0x00, 0x0000 }, + { 46, 0x0063, 0x04000043, 0x07, 0x00, 0x0000 }, + { 46, 0x0063, 0x08000043, 0x08, 0x00, 0x0000 }, + { 46, 0x0063, 0x08000043, 0x09, 0x00, 0x0000 }, + { 46, 0x0063, 0x08000043, 0x0a, 0x00, 0x0000 }, + { 46, 0x0063, 0x08000043, 0x0b, 0x00, 0x0000 }, + { 46, 0x0063, 0x0c000043, 0x0c, 0x00, 0x0000 }, + { 46, 0x0063, 0x0c000043, 0x0d, 0x00, 0x0000 }, + { 46, 0x0063, 0x0c000043, 0x0e, 0x00, 0x0000 }, + { 46, 0x0063, 0x0c000043, 0x0f, 0x00, 0x0000 }, + { 47, 0x0076, 0x00000056, 0x00, 0x00, 0x0000 }, + { 47, 0x0056, 0x00000056, 0x01, 0x00, 0x0000 }, + { 47, 0x0076, 0x00000056, 0x02, 0x00, 0x0000 }, + { 47, 0x0056, 0x00000056, 0x03, 0x00, 0x0000 }, + { 47, 0x0076, 0x04000056, 0x04, 0x00, 0x0000 }, + { 47, 0x0076, 0x04000056, 0x05, 0x00, 0x0000 }, + { 47, 0x0076, 0x04000056, 0x06, 0x00, 0x0000 }, + { 47, 0x0076, 0x04000056, 0x07, 0x00, 0x0000 }, + { 47, 0x0076, 0x08000056, 0x08, 0x00, 0x0000 }, + { 47, 0x0076, 0x08000056, 0x09, 0x00, 0x0000 }, + { 47, 0x0076, 0x08000056, 0x0a, 0x00, 0x0000 }, + { 47, 0x0076, 0x08000056, 0x0b, 0x00, 0x0000 }, + { 47, 0x0076, 0x0c000056, 0x0c, 0x00, 0x0000 }, + { 47, 0x0076, 0x0c000056, 0x0d, 0x00, 0x0000 }, + { 47, 0x0076, 0x0c000056, 0x0e, 0x00, 0x0000 }, + { 47, 0x0076, 0x0c000056, 0x0f, 0x00, 0x0000 }, + { 48, 0x0062, 0x00000042, 0x00, 0x00, 0x0000 }, + { 48, 0x0042, 0x00000042, 0x01, 0x00, 0x0000 }, + { 48, 0x0062, 0x00000042, 0x02, 0x00, 0x0000 }, + { 48, 0x0042, 0x00000042, 0x03, 0x00, 0x0000 }, + { 48, 0x0062, 0x04000042, 0x04, 0x00, 0x0000 }, + { 48, 0x0062, 0x04000042, 0x05, 0x00, 0x0000 }, + { 48, 0x0062, 0x04000042, 0x06, 0x00, 0x0000 }, + { 48, 0x0062, 0x04000042, 0x07, 0x00, 0x0000 }, + { 48, 0x0062, 0x08000042, 0x08, 0x00, 0x0000 }, + { 48, 0x0062, 0x08000042, 0x09, 0x00, 0x0000 }, + { 48, 0x0062, 0x08000042, 0x0a, 0x00, 0x0000 }, + { 48, 0x0062, 0x08000042, 0x0b, 0x00, 0x0000 }, + { 48, 0x0062, 0x0c000042, 0x0c, 0x00, 0x0000 }, + { 48, 0x0062, 0x0c000042, 0x0d, 0x00, 0x0000 }, + { 48, 0x0062, 0x0c000042, 0x0e, 0x00, 0x0000 }, + { 48, 0x0062, 0x0c000042, 0x0f, 0x00, 0x0000 }, + { 49, 0x006e, 0x0000004e, 0x00, 0x00, 0x0000 }, + { 49, 0x004e, 0x0000004e, 0x01, 0x00, 0x0000 }, + { 49, 0x006e, 0x0000004e, 0x02, 0x00, 0x0000 }, + { 49, 0x004e, 0x0000004e, 0x03, 0x00, 0x0000 }, + { 49, 0x006e, 0x0400004e, 0x04, 0x00, 0x0000 }, + { 49, 0x006e, 0x0400004e, 0x05, 0x00, 0x0000 }, + { 49, 0x006e, 0x0400004e, 0x06, 0x00, 0x0000 }, + { 49, 0x006e, 0x0400004e, 0x07, 0x00, 0x0000 }, + { 49, 0x006e, 0x0800004e, 0x08, 0x00, 0x0000 }, + { 49, 0x006e, 0x0800004e, 0x09, 0x00, 0x0000 }, + { 49, 0x006e, 0x0800004e, 0x0a, 0x00, 0x0000 }, + { 49, 0x006e, 0x0800004e, 0x0b, 0x00, 0x0000 }, + { 49, 0x006e, 0x0c00004e, 0x0c, 0x00, 0x0000 }, + { 49, 0x006e, 0x0c00004e, 0x0d, 0x00, 0x0000 }, + { 49, 0x006e, 0x0c00004e, 0x0e, 0x00, 0x0000 }, + { 49, 0x006e, 0x0c00004e, 0x0f, 0x00, 0x0000 }, + { 50, 0x006d, 0x0000004d, 0x00, 0x00, 0x0000 }, + { 50, 0x004d, 0x0000004d, 0x01, 0x00, 0x0000 }, + { 50, 0x006d, 0x0000004d, 0x02, 0x00, 0x0000 }, + { 50, 0x004d, 0x0000004d, 0x03, 0x00, 0x0000 }, + { 50, 0x006d, 0x0400004d, 0x04, 0x00, 0x0000 }, + { 50, 0x006d, 0x0400004d, 0x05, 0x00, 0x0000 }, + { 50, 0x006d, 0x0400004d, 0x06, 0x00, 0x0000 }, + { 50, 0x006d, 0x0400004d, 0x07, 0x00, 0x0000 }, + { 50, 0x006d, 0x0800004d, 0x08, 0x00, 0x0000 }, + { 50, 0x006d, 0x0800004d, 0x09, 0x00, 0x0000 }, + { 50, 0x006d, 0x0800004d, 0x0a, 0x00, 0x0000 }, + { 50, 0x006d, 0x0800004d, 0x0b, 0x00, 0x0000 }, + { 50, 0x006d, 0x0c00004d, 0x0c, 0x00, 0x0000 }, + { 50, 0x006d, 0x0c00004d, 0x0d, 0x00, 0x0000 }, + { 50, 0x006d, 0x0c00004d, 0x0e, 0x00, 0x0000 }, + { 50, 0x006d, 0x0c00004d, 0x0f, 0x00, 0x0000 }, + { 51, 0x002c, 0x0000002c, 0x00, 0x00, 0x0000 }, + { 51, 0x003c, 0x0000003c, 0x01, 0x00, 0x0000 }, + { 51, 0x002c, 0x0100125b, 0x02, 0x01, 0x0000 }, + { 52, 0x002e, 0x0000002e, 0x00, 0x00, 0x0000 }, + { 52, 0x003e, 0x0000003e, 0x01, 0x00, 0x0000 }, + { 52, 0xffff, 0x01001120, 0x02, 0x00, 0x0000 }, + { 53, 0x002f, 0x0000002f, 0x00, 0x00, 0x0000 }, + { 53, 0x003f, 0x0000003f, 0x01, 0x00, 0x0000 }, + { 53, 0xffff, 0x01000003, 0x04, 0x00, 0x0000 }, + { 54, 0xffff, 0x01000020, 0x00, 0x04, 0x0001 }, + { 55, 0x002a, 0x2000002a, 0x00, 0x00, 0x0000 }, + { 56, 0xffff, 0x01000023, 0x00, 0x04, 0x0008 }, + { 57, 0x0020, 0x00000020, 0x00, 0x00, 0x0000 }, + { 58, 0xffff, 0x01000024, 0x00, 0x00, 0x0000 }, + { 59, 0xffff, 0x01000030, 0x00, 0x00, 0x0000 }, + { 59, 0xffff, 0x0100003c, 0x01, 0x00, 0x0000 }, + { 59, 0xffff, 0x01000048, 0x04, 0x00, 0x0000 }, + { 59, 0xffff, 0x01000000, 0x0c, 0x08, 0x0100 }, + { 60, 0xffff, 0x01000031, 0x00, 0x00, 0x0000 }, + { 60, 0xffff, 0x0100003d, 0x01, 0x00, 0x0000 }, + { 60, 0xffff, 0x01000049, 0x04, 0x00, 0x0000 }, + { 60, 0xffff, 0x01000000, 0x0c, 0x08, 0x0101 }, + { 61, 0xffff, 0x01000032, 0x00, 0x00, 0x0000 }, + { 61, 0xffff, 0x0100003e, 0x01, 0x00, 0x0000 }, + { 61, 0xffff, 0x0100004a, 0x04, 0x00, 0x0000 }, + { 61, 0xffff, 0x01000000, 0x0c, 0x08, 0x0102 }, + { 62, 0xffff, 0x01000033, 0x00, 0x00, 0x0000 }, + { 62, 0xffff, 0x0100003f, 0x01, 0x00, 0x0000 }, + { 62, 0xffff, 0x0100004b, 0x04, 0x00, 0x0000 }, + { 62, 0xffff, 0x01000000, 0x0c, 0x08, 0x0103 }, + { 63, 0xffff, 0x01000034, 0x00, 0x00, 0x0000 }, + { 63, 0xffff, 0x01000040, 0x01, 0x00, 0x0000 }, + { 63, 0xffff, 0x0100004c, 0x04, 0x00, 0x0000 }, + { 63, 0xffff, 0x01000000, 0x0c, 0x08, 0x0104 }, + { 64, 0xffff, 0x01000035, 0x00, 0x00, 0x0000 }, + { 64, 0xffff, 0x01000041, 0x01, 0x00, 0x0000 }, + { 64, 0xffff, 0x0100004d, 0x04, 0x00, 0x0000 }, + { 64, 0xffff, 0x01000000, 0x0c, 0x08, 0x0105 }, + { 65, 0xffff, 0x01000036, 0x00, 0x00, 0x0000 }, + { 65, 0xffff, 0x01000042, 0x01, 0x00, 0x0000 }, + { 65, 0xffff, 0x0100004e, 0x04, 0x00, 0x0000 }, + { 65, 0xffff, 0x01000000, 0x0c, 0x08, 0x0106 }, + { 66, 0xffff, 0x01000037, 0x00, 0x00, 0x0000 }, + { 66, 0xffff, 0x01000043, 0x01, 0x00, 0x0000 }, + { 66, 0xffff, 0x0100004f, 0x04, 0x00, 0x0000 }, + { 66, 0xffff, 0x01000000, 0x0c, 0x08, 0x0107 }, + { 67, 0xffff, 0x01000038, 0x00, 0x00, 0x0000 }, + { 67, 0xffff, 0x01000044, 0x01, 0x00, 0x0000 }, + { 67, 0xffff, 0x01000050, 0x04, 0x00, 0x0000 }, + { 67, 0xffff, 0x01000000, 0x0c, 0x08, 0x0108 }, + { 68, 0xffff, 0x01000039, 0x00, 0x00, 0x0000 }, + { 68, 0xffff, 0x01000045, 0x01, 0x00, 0x0000 }, + { 68, 0xffff, 0x01000051, 0x04, 0x00, 0x0000 }, + { 68, 0xffff, 0x01000000, 0x0c, 0x08, 0x0109 }, + { 69, 0xffff, 0x01000025, 0x00, 0x00, 0x0000 }, + { 70, 0xffff, 0x01000026, 0x00, 0x00, 0x0000 }, + { 70, 0xffff, 0x01000026, 0x08, 0x00, 0x0000 }, + { 71, 0x0037, 0x20000037, 0x00, 0x00, 0x0000 }, + { 72, 0x0038, 0x20000038, 0x00, 0x00, 0x0000 }, + { 73, 0x0039, 0x20000039, 0x00, 0x00, 0x0000 }, + { 74, 0x002d, 0x2000002d, 0x00, 0x00, 0x0000 }, + { 75, 0x0034, 0x20000034, 0x00, 0x00, 0x0000 }, + { 76, 0x0035, 0x20000035, 0x00, 0x00, 0x0000 }, + { 77, 0x0036, 0x20000036, 0x00, 0x00, 0x0000 }, + { 78, 0x002b, 0x2000002b, 0x00, 0x00, 0x0000 }, + { 79, 0x0031, 0x20000031, 0x00, 0x00, 0x0000 }, + { 80, 0x0032, 0x20000032, 0x00, 0x00, 0x0000 }, + { 81, 0x0033, 0x20000033, 0x00, 0x00, 0x0000 }, + { 82, 0x0030, 0x20000030, 0x00, 0x00, 0x0000 }, + { 83, 0x002e, 0x2000002e, 0x00, 0x00, 0x0000 }, + { 83, 0xffff, 0x01000000, 0x06, 0x08, 0x0200 }, + { 83, 0xffff, 0x01000000, 0x0c, 0x08, 0x0200 }, + { 86, 0x003c, 0x0000003c, 0x00, 0x00, 0x0000 }, + { 86, 0x003e, 0x0000003e, 0x01, 0x00, 0x0000 }, + { 86, 0x007c, 0x0000007c, 0x02, 0x00, 0x0000 }, + { 87, 0xffff, 0x0100003a, 0x00, 0x00, 0x0000 }, + { 87, 0xffff, 0x01000046, 0x01, 0x00, 0x0000 }, + { 87, 0xffff, 0x01000052, 0x04, 0x00, 0x0000 }, + { 87, 0xffff, 0x01000000, 0x0c, 0x08, 0x010a }, + { 88, 0xffff, 0x0100003b, 0x00, 0x00, 0x0000 }, + { 88, 0xffff, 0x01000047, 0x01, 0x00, 0x0000 }, + { 88, 0xffff, 0x01000000, 0x0c, 0x08, 0x010b }, + { 96, 0xffff, 0x21000005, 0x00, 0x00, 0x0000 }, + { 97, 0xffff, 0x01000021, 0x00, 0x04, 0x0004 }, + { 98, 0x002f, 0x2000002f, 0x00, 0x00, 0x0000 }, + { 99, 0x005c, 0x0400005c, 0x00, 0x00, 0x0000 }, + { 100, 0xffff, 0x01001103, 0x00, 0x04, 0x0002 }, + { 102, 0xffff, 0x01000010, 0x00, 0x00, 0x0000 }, + { 103, 0xffff, 0x01000013, 0x00, 0x00, 0x0000 }, + { 104, 0xffff, 0x01000016, 0x00, 0x00, 0x0000 }, + { 105, 0xffff, 0x01000012, 0x00, 0x00, 0x0000 }, + { 105, 0xffff, 0x01000000, 0x0c, 0x08, 0x0180 }, + { 106, 0xffff, 0x01000014, 0x00, 0x00, 0x0000 }, + { 106, 0xffff, 0x01000000, 0x0c, 0x08, 0x0181 }, + { 107, 0xffff, 0x01000011, 0x00, 0x00, 0x0000 }, + { 108, 0xffff, 0x01000015, 0x00, 0x00, 0x0000 }, + { 109, 0xffff, 0x01000017, 0x00, 0x00, 0x0000 }, + { 110, 0xffff, 0x01000006, 0x00, 0x00, 0x0000 }, + { 111, 0xffff, 0x01000007, 0x00, 0x00, 0x0000 }, + { 111, 0xffff, 0x01000000, 0x06, 0x08, 0x0200 }, + { 111, 0xffff, 0x01000000, 0x0c, 0x08, 0x0200 }, + { 119, 0xffff, 0x01000008, 0x00, 0x00, 0x0000 }, +}; + +const QWSKeyboard::Composing QWSKbPrivate::s_keycompose_default[] = { + { 0x0060, 0x0041, 0x00c0 }, + { 0x0060, 0x0061, 0x00e0 }, + { 0x0027, 0x0041, 0x00c1 }, + { 0x0027, 0x0061, 0x00e1 }, + { 0x005e, 0x0041, 0x00c2 }, + { 0x005e, 0x0061, 0x00e2 }, + { 0x007e, 0x0041, 0x00c3 }, + { 0x007e, 0x0061, 0x00e3 }, + { 0x0022, 0x0041, 0x00c4 }, + { 0x0022, 0x0061, 0x00e4 }, + { 0x002d, 0x0061, 0x00aa }, + { 0x002d, 0x0041, 0x00aa }, + { 0x004f, 0x0041, 0x00c5 }, + { 0x006f, 0x0061, 0x00e5 }, + { 0x0030, 0x0041, 0x00c5 }, + { 0x0030, 0x0061, 0x00e5 }, + { 0x0041, 0x0041, 0x00c5 }, + { 0x0061, 0x0061, 0x00e5 }, + { 0x00b0, 0x0041, 0x00c5 }, + { 0x00b0, 0x0061, 0x00e5 }, + { 0x0041, 0x0045, 0x00c6 }, + { 0x0061, 0x0065, 0x00e6 }, + { 0x002c, 0x0043, 0x00c7 }, + { 0x002c, 0x0063, 0x00e7 }, + { 0x005e, 0x0043, 0x00c7 }, + { 0x005e, 0x0063, 0x00e7 }, + { 0x0060, 0x0045, 0x00c8 }, + { 0x0060, 0x0065, 0x00e8 }, + { 0x0027, 0x0045, 0x00c9 }, + { 0x0027, 0x0065, 0x00e9 }, + { 0x005e, 0x0045, 0x00ca }, + { 0x005e, 0x0065, 0x00ea }, + { 0x0022, 0x0045, 0x00cb }, + { 0x0022, 0x0065, 0x00eb }, + { 0x0060, 0x0049, 0x00cc }, + { 0x0060, 0x0069, 0x00ec }, + { 0x0027, 0x0049, 0x00cd }, + { 0x0027, 0x0069, 0x00ed }, + { 0x005e, 0x0049, 0x00ce }, + { 0x005e, 0x0069, 0x00ee }, + { 0x0022, 0x0049, 0x00cf }, + { 0x0022, 0x0069, 0x00ef }, + { 0x002d, 0x0044, 0x00d0 }, + { 0x002d, 0x0064, 0x00f0 }, + { 0x005e, 0x0044, 0x00d0 }, + { 0x005e, 0x0064, 0x00f0 }, + { 0x007e, 0x004e, 0x00d1 }, + { 0x007e, 0x006e, 0x00f1 }, + { 0x005e, 0x004e, 0x00d1 }, + { 0x005e, 0x006e, 0x00f1 }, + { 0x0060, 0x004f, 0x00d2 }, + { 0x0060, 0x006f, 0x00f2 }, + { 0x0027, 0x004f, 0x00d3 }, + { 0x0027, 0x006f, 0x00f3 }, + { 0x005e, 0x004f, 0x00d4 }, + { 0x005e, 0x006f, 0x00f4 }, + { 0x007e, 0x004f, 0x00d5 }, + { 0x007e, 0x006f, 0x00f5 }, + { 0x0022, 0x004f, 0x00d6 }, + { 0x0022, 0x006f, 0x00f6 }, + { 0x002f, 0x004f, 0x00d8 }, + { 0x002f, 0x006f, 0x00f8 }, + { 0x002d, 0x006f, 0x00ba }, + { 0x002d, 0x004f, 0x00ba }, + { 0x0060, 0x0055, 0x00d9 }, + { 0x0060, 0x0075, 0x00f9 }, + { 0x0027, 0x0055, 0x00da }, + { 0x0027, 0x0075, 0x00fa }, + { 0x005e, 0x0055, 0x00db }, + { 0x005e, 0x0075, 0x00fb }, + { 0x0022, 0x0055, 0x00dc }, + { 0x0022, 0x0075, 0x00fc }, + { 0x0027, 0x0059, 0x00dd }, + { 0x0027, 0x0079, 0x00fd }, + { 0x0054, 0x0048, 0x00de }, + { 0x0074, 0x0068, 0x00fe }, + { 0x0073, 0x0073, 0x00df }, + { 0x0022, 0x0079, 0x00ff }, + { 0x0073, 0x007a, 0x00df }, + { 0x006e, 0x006e, 0x00f1 }, + { 0x006e, 0x0068, 0x00f1 }, + { 0x004e, 0x0059, 0x00d1 }, + { 0x004e, 0x004e, 0x00d1 }, + { 0x004e, 0x0048, 0x00d1 }, + { 0x004e, 0x0079, 0x00d1 }, + { 0x004e, 0x006e, 0x00d1 }, + { 0x004e, 0x0068, 0x00d1 }, + { 0x002d, 0x004c, 0x00a3 }, + { 0x003c, 0x003c, 0x00ab }, + { 0x003e, 0x003e, 0x00bb }, + { 0x003f, 0x003f, 0x00bf }, + { 0x005e, 0x003f, 0x00bf }, + { 0x0021, 0x0021, 0x00a1 }, + { 0x005e, 0x0021, 0x00a1 }, + { 0x005e, 0x0031, 0x00b9 }, + { 0x005e, 0x0032, 0x00b2 }, + { 0x005e, 0x0033, 0x00b3 }, + { 0x002b, 0x002d, 0x00b1 }, + { 0x0063, 0x003d, 0x00a2 }, + { 0x0063, 0x002f, 0x00a2 }, + { 0x002f, 0x0063, 0x00a2 }, + { 0x002d, 0x0063, 0x00a2 }, + { 0x002d, 0x0043, 0x00a2 }, + { 0x004c, 0x003d, 0x00a3 }, + { 0x002d, 0x004c, 0x00a3 }, + { 0x002d, 0x006c, 0x00a3 }, + { 0x005e, 0x002a, 0x00d7 }, + { 0x005e, 0x0078, 0x00d7 }, + { 0x0078, 0x0078, 0x00d7 }, + { 0x005e, 0x002e, 0x00b7 }, + { 0x002e, 0x002e, 0x00b7 }, + { 0x005e, 0x002f, 0x00f7 }, + { 0x005e, 0x003a, 0x00f7 }, + { 0x002d, 0x003a, 0x00f7 }, + { 0x003a, 0x002d, 0x00f7 }, + { 0x0059, 0x003d, 0x00a5 }, + { 0x002d, 0x0059, 0x00a5 }, + { 0x002d, 0x006c, 0x00a5 }, + { 0x0028, 0x0063, 0x00a9 }, + { 0x0022, 0x0063, 0x00a9 }, + { 0x002d, 0x0061, 0x00aa }, + { 0x002d, 0x0041, 0x00aa }, + { 0x002d, 0x006f, 0x00ba }, + { 0x002d, 0x004f, 0x00ba }, + { 0x0028, 0x0072, 0x00ae }, + { 0x0022, 0x0072, 0x00ae }, + { 0x006d, 0x0075, 0x00b5 }, + { 0x0031, 0x0034, 0x0152 }, + { 0x0031, 0x0032, 0x0153 }, + { 0x0033, 0x0034, 0x0178 }, + { 0x0065, 0x003d, 0x20ac }, + { 0x002d, 0x0065, 0x20ac }, + { 0x002d, 0x0045, 0x20ac }, + { 0x0076, 0x0053, 0x0160 }, + { 0x005e, 0x0053, 0x0160 }, + { 0x0076, 0x0073, 0x0161 }, + { 0x005e, 0x0073, 0x0161 }, + { 0x0076, 0x005a, 0x017d }, + { 0x005e, 0x005a, 0x017d }, + { 0x0076, 0x007a, 0x017e }, + { 0x005e, 0x007a, 0x017e }, + { 0x004f, 0x0045, 0x0152 }, + { 0x004f, 0x0065, 0x0152 }, + { 0x006f, 0x0065, 0x0153 }, + { 0x0022, 0x0059, 0x0178 }, + { 0x0069, 0x006a, 0x00ff }, + { 0x0049, 0x004a, 0x0178 }, +}; + +#endif diff --git a/src/gui/embedded/qkbd_qws.cpp b/src/gui/embedded/qkbd_qws.cpp index 8cf87db..120d2a1 100644 --- a/src/gui/embedded/qkbd_qws.cpp +++ b/src/gui/embedded/qkbd_qws.cpp @@ -40,56 +40,216 @@ ****************************************************************************/ #include "qkbd_qws.h" +#include "qkbd_qws_p.h" #ifndef QT_NO_QWS_KEYBOARD +#include <QFile> +#include <QDataStream> + #include "qwindowsystem_qws.h" #include "qscreen_qws.h" #include "qtimer.h" #include <stdlib.h> +//#define QT_DEBUG_KEYMAP + + QT_BEGIN_NAMESPACE class QWSKbPrivate : public QObject { Q_OBJECT public: - QWSKbPrivate(QWSKeyboardHandler *h) { - handler = h; - arTimer = new QTimer(this); - arTimer->setSingleShot(true); - connect(arTimer, SIGNAL(timeout()), SLOT(autoRepeat())); - repeatdelay = 400; - repeatperiod = 80; + QWSKbPrivate(QWSKeyboardHandler *h, const QString &device) + : m_handler(h), m_modifiers(0), m_composing(0), m_dead_unicode(0xffff), + m_no_zap(false), m_do_compose(false), + m_keymap(0), m_keymap_size(0), m_keycompose(0), m_keycompose_size(0) + { + m_ar_timer = new QTimer(this); + m_ar_timer->setSingleShot(true); + connect(m_ar_timer, SIGNAL(timeout()), SLOT(autoRepeat())); + m_ar_delay = 400; + m_ar_period = 80; + + memset(m_locks, 0, sizeof(m_locks)); + + QString keymap; + QStringList args = device.split(QLatin1Char(':')); + foreach (const QString &arg, args) { + if (arg.startsWith(QLatin1String("keymap="))) + keymap = arg.mid(7); + else if (arg == QLatin1String("disable-zap")) + m_no_zap = true; + else if (arg == QLatin1String("enable-compose")) + m_do_compose = true; + else if (arg.startsWith(QLatin1String("repeat-delay="))) + m_ar_delay = arg.mid(13).toInt(); + else if (arg.startsWith(QLatin1String("repeat-rate="))) + m_ar_period = arg.mid(12).toInt(); + } + + if (keymap.isEmpty() || !loadKeymap(keymap)) + unloadKeymap(); } - void beginAutoRepeat(int uni, int code, Qt::KeyboardModifiers mod) { - unicode = uni; - keycode = code; - modifier = mod; - arTimer->start(repeatdelay); + ~QWSKbPrivate() + { + unloadKeymap(); } - void endAutoRepeat() { - arTimer->stop(); + + void beginAutoRepeat(int uni, int code, Qt::KeyboardModifiers mod) + { + m_ar_unicode = uni; + m_ar_keycode = code; + m_ar_modifier = mod; + m_ar_timer->start(m_ar_delay); } + void endAutoRepeat() + { + m_ar_timer->stop(); + } + + static Qt::KeyboardModifiers toQtModifiers(quint8 mod) + { + Qt::KeyboardModifiers qtmod = Qt::NoModifier; + + if (mod & (QWSKeyboard::ModShift | QWSKeyboard::ModShiftL | QWSKeyboard::ModShiftR)) + qtmod |= Qt::ShiftModifier; + if (mod & (QWSKeyboard::ModControl | QWSKeyboard::ModCtrlL | QWSKeyboard::ModCtrlR)) + qtmod |= Qt::ControlModifier; + if (mod & QWSKeyboard::ModAlt) + qtmod |= Qt::AltModifier; + + return qtmod; + } + + void unloadKeymap(); + bool loadKeymap(const QString &file); + private slots: - void autoRepeat() { - handler->processKeyEvent(unicode, keycode, modifier, false, true); - handler->processKeyEvent(unicode, keycode, modifier, true, true); - arTimer->start(repeatperiod); + void autoRepeat() + { + m_handler->processKeyEvent(m_ar_unicode, m_ar_keycode, m_ar_modifier, false, true); + m_handler->processKeyEvent(m_ar_unicode, m_ar_keycode, m_ar_modifier, true, true); + m_ar_timer->start(m_ar_period); } private: - QWSKeyboardHandler *handler; - int unicode; - int keycode; - Qt::KeyboardModifiers modifier; - int repeatdelay; - int repeatperiod; - QTimer *arTimer; + QWSKeyboardHandler *m_handler; + + // auto repeat simulation + int m_ar_unicode; + int m_ar_keycode; + Qt::KeyboardModifiers m_ar_modifier; + int m_ar_delay; + int m_ar_period; + QTimer *m_ar_timer; + + // keymap handling + quint8 m_modifiers; + quint8 m_locks[3]; + int m_composing; + quint16 m_dead_unicode; + + bool m_no_zap; + bool m_do_compose; + + const QWSKeyboard::Mapping *m_keymap; + int m_keymap_size; + const QWSKeyboard::Composing *m_keycompose; + int m_keycompose_size; + + static const QWSKeyboard::Mapping s_keymap_default[]; + static const QWSKeyboard::Composing s_keycompose_default[]; + + friend class QWSKeyboardHandler; }; +// simple builtin US keymap +#include "qkbd_defaultmap_qws_p.h" + +// the unloadKeymap() function needs to be AFTER the defaultmap include, +// since the sizeof(s_keymap_default) wouldn't work otherwise. + +void QWSKbPrivate::unloadKeymap() +{ + if (m_keymap && m_keymap != s_keymap_default) + delete [] m_keymap; + if (m_keycompose && m_keycompose != s_keycompose_default) + delete [] m_keycompose; + + m_keymap = s_keymap_default; + m_keymap_size = sizeof(s_keymap_default) / sizeof(s_keymap_default[0]); + m_keycompose = s_keycompose_default; + m_keycompose_size = sizeof(s_keycompose_default) / sizeof(s_keycompose_default[0]); + + // reset state, so we could switch keymaps at runtime + m_modifiers = 0; + memset(m_locks, 0, sizeof(m_locks)); + m_composing = 0; + m_dead_unicode = 0xffff; +} + +bool QWSKbPrivate::loadKeymap(const QString &file) +{ + QFile f(file); + + if (!f.open(QIODevice::ReadOnly)) { + qWarning("Could not open keymap file '%s'", qPrintable(file)); + return false; + } + + // .qmap files have a very simple structure: + // quint32 magic (QWSKeyboard::FileMagic) + // quint32 version (1) + // quint32 keymap_size (# of struct QWSKeyboard::Mappings) + // quint32 keycompose_size (# of struct QWSKeyboard::Composings) + // all QWSKeyboard::Mappings via QDataStream::operator(<<|>>) + // all QWSKeyboard::Composings via QDataStream::operator(<<|>>) + + quint32 qmap_magic, qmap_version, qmap_keymap_size, qmap_keycompose_size; + + QDataStream ds(&f); + + ds >> qmap_magic >> qmap_version >> qmap_keymap_size >> qmap_keycompose_size; + + if (ds.status() != QDataStream::Ok || qmap_magic != QWSKeyboard::FileMagic || qmap_version != 1 || qmap_keymap_size == 0) { + qWarning("'%s' is ot a valid.qmap keymap file.", qPrintable(file)); + return false; + } + + QWSKeyboard::Mapping *qmap_keymap = new QWSKeyboard::Mapping[qmap_keymap_size]; + QWSKeyboard::Composing *qmap_keycompose = qmap_keycompose_size ? new QWSKeyboard::Composing[qmap_keycompose_size] : 0; + + for (quint32 i = 0; i < qmap_keymap_size; ++i) + ds >> qmap_keymap[i]; + for (quint32 i = 0; i < qmap_keycompose_size; ++i) + ds >> qmap_keycompose[i]; + + if (ds.status() != QDataStream::Ok) { + delete [] qmap_keymap; + delete [] qmap_keycompose; + + qWarning("Keymap file '%s' can not be loaded.", qPrintable(file)); + return false; + } + + // unload currently active and clear state + unloadKeymap(); + + m_keymap = qmap_keymap; + m_keymap_size = qmap_keymap_size; + m_keycompose = qmap_keycompose; + m_keycompose_size = qmap_keycompose_size; + + m_do_compose = true; + + return true; +} + + /*! \class QWSKeyboardHandler \ingroup qws @@ -132,18 +292,29 @@ private: /*! - Constructs a keyboard driver. + Constructs a keyboard driver. The \a device argument is passed by the + QWS_KEYBOARD environment variable. Call the QWSServer::setKeyboardHandler() function to make the newly created keyboard driver, the primary driver. Note that the primary driver is controlled by the system, i.e., the system will delete it upon exit. */ +QWSKeyboardHandler::QWSKeyboardHandler(const QString &device) +{ + d = new QWSKbPrivate(this, device); +} + +/*! + \overload +*/ QWSKeyboardHandler::QWSKeyboardHandler() { - d = new QWSKbPrivate(this); + d = new QWSKbPrivate(this, QString()); } + + /*! Destroys this keyboard driver. @@ -172,7 +343,10 @@ QWSKeyboardHandler::~QWSKeyboardHandler() event is caused by an auto-repeat mechanism and not an actual key press. - \sa beginAutoRepeat(), endAutoRepeat(), transformDirKey() + Note that this function does not handle key mapping. Please use + processKeycode() if you need that functionality. + + \sa processKeycode(), beginAutoRepeat(), endAutoRepeat(), transformDirKey() */ void QWSKeyboardHandler::processKeyEvent(int unicode, int keycode, Qt::KeyboardModifiers modifiers, bool isPress, bool autoRepeat) @@ -241,6 +415,256 @@ void QWSKeyboardHandler::endAutoRepeat() d->endAutoRepeat(); } +/*! + \enum QWSKeyboardHandler::KeycodeAction + + This enum describes the various special actions that actual + QWSKeyboardHandler implementations have to take care of. + + \value None No further action required. + + \value CapsLockOn Set the state of the Caps lock LED to on. + \value CapsLockOff Set the state of the Caps lock LED to off. + \value NumLockOn Set the state of the Num lock LED to on. + \value NumLockOff Set the state of the Num lock LED to off. + \value ScrollLockOn Set the state of the Scroll lock LED to on. + \value ScrollLockOff Set the state of the Scroll lock LED to off. + + \value PreviousConsole Switch to the previous virtual console (by + default Ctrl+Alt+Left on Linux). + \value NextConsole Switch to the next virtual console (by default + Ctrl+Alt+Right on Linux). + \value SwitchConsoleFirst Switch to the first virtual console (0). + \value SwitchConsoleLast Switch to the last virtual console (255). + \value SwitchConsoleMask If the KeyAction value is between SwitchConsoleFirst + and SwitchConsoleLast, you can use this mask to get + the specific virtual console number to switch to. + + \value Reboot Reboot the machine - this is ignored in both the TTY and + LinuxInput handlers though (by default Ctrl+Alt+Del on Linux). + + \sa processKeycode() +*/ + +/*! + \fn QWSKeyboardHandler::KeycodeAction QWSKeyboardHandler::processKeycode(quint16 keycode, bool isPress, bool autoRepeat) + + Maps \a keycode according to a keymap and sends that key event to the + \l{Qt for Embedded Linux} server application. + + Please see the QWS_KEYBOARD documentation for a description on how to + create and use keymap files. + + The key event is identified by its \a keycode value and the \a isPress + and \a autoRepeat parameters. + + The \a keycode parameter is \bold NOT the Qt keycode value as defined by + the Qt::Key enum. This functions expects a standard Linux 16 bit kernel + keycode as it is used in the Linux Input Event sub-system. This + \a keycode is transformed to a Qt::Key code by using either a + compiled-in US keyboard layout or by dynamically loading a keymap at + startup which can be specified via the QWS_KEYBOARD environment + variable. + + The \a isPress parameter is true if the event is a key press event and + \a autoRepeat is true if the event is caused by an auto-repeat mechanism + and not an actual key press. + + The return value indicates if the actual QWSKeyboardHandler + implementation needs to take care of a special action, like console + switching or LED handling. + + Standard Linux console keymaps can be found at the + \l {http://lct.sourceforege.net}{LCT project} + + If standard Linux console keymaps are used, \a keycode must be one of the + standardized values defined in \c /usr/include/linux/input.h + + \sa processKeyEvent(), KeycodeAction +*/ + +QWSKeyboardHandler::KeycodeAction QWSKeyboardHandler::processKeycode(quint16 keycode, bool pressed, bool autorepeat) +{ + KeycodeAction result = None; + bool first_press = pressed && !autorepeat; + + const QWSKeyboard::Mapping *map_plain = 0; + const QWSKeyboard::Mapping *map_withmod = 0; + + // get a specific and plain mapping for the keycode and the current modifiers + for (int i = 0; i < d->m_keymap_size && !(map_plain && map_withmod); ++i) { + const QWSKeyboard::Mapping *m = d->m_keymap + i; + if (m->keycode == keycode) { + if (m->modifiers == 0) + map_plain = m; + + quint8 testmods = d->m_modifiers; + if (d->m_locks[0] /*CapsLock*/ && (m->flags & QWSKeyboard::IsLetter)) + testmods ^= QWSKeyboard::ModShift; + if (m->modifiers == testmods) + map_withmod = m; + } + } + +#ifdef QT_DEBUG_KEYMAP + qWarning("Processing key event: keycode=%3d, modifiers=%02x pressed=%d, autorepeat=%d | plain=%d, withmod=%d, size=%d", \ + keycode, d->m_modifiers, pressed ? 1 : 0, autorepeat ? 1 : 0, \ + map_plain ? map_plain - d->m_keymap : -1, \ + map_withmod ? map_withmod - d->m_keymap : -1, \ + d->m_keymap_size); +#endif + + const QWSKeyboard::Mapping *it = map_withmod ? map_withmod : map_plain; + + if (!it) { +#ifdef QT_DEBUG_KEYMAP + // we couldn't even find a plain mapping + qWarning("Could not find a suitable mapping for keycode: %3d, modifiers: %02x", keycode, d->m_modifiers); +#endif + return result; + } + + bool skip = false; + quint16 unicode = it->unicode; + quint32 qtcode = it->qtcode; + + if ((it->flags & QWSKeyboard::IsModifier) && it->special) { + // this is a modifier, i.e. Shift, Alt, ... + if (pressed) + d->m_modifiers |= quint8(it->special); + else + d->m_modifiers &= ~quint8(it->special); + } else if (qtcode >= Qt::Key_CapsLock && qtcode <= Qt::Key_ScrollLock) { + // (Caps|Num|Scroll)Lock + if (first_press) { + quint8 &lock = d->m_locks[qtcode - Qt::Key_CapsLock]; + lock ^= 1; + + switch (qtcode) { + case Qt::Key_CapsLock : result = lock ? CapsLockOn : CapsLockOff; break; + case Qt::Key_NumLock : result = lock ? NumLockOn : NumLockOff; break; + case Qt::Key_ScrollLock: result = lock ? ScrollLockOn : ScrollLockOff; break; + default : break; + } + } + } else if ((it->flags & QWSKeyboard::IsSystem) && it->special && first_press) { + switch (it->special) { + case QWSKeyboard::SystemReboot: + result = Reboot; + break; + + case QWSKeyboard::SystemZap: + if (!d->m_no_zap) + qApp->quit(); + break; + + case QWSKeyboard::SystemConsolePrevious: + result = PreviousConsole; + break; + + case QWSKeyboard::SystemConsoleNext: + result = NextConsole; + break; + + default: + if (it->special >= QWSKeyboard::SystemConsoleFirst && + it->special <= QWSKeyboard::SystemConsoleLast) { + result = KeycodeAction(SwitchConsoleFirst + ((it->special & QWSKeyboard::SystemConsoleMask) & SwitchConsoleMask)); + } + break; + } + + skip = true; // no need to tell QWS about it + } else if ((qtcode == Qt::Key_Multi_key) && d->m_do_compose) { + // the Compose key was pressed + if (first_press) + d->m_composing = 2; + skip = true; + } else if ((it->flags & QWSKeyboard::IsDead) && d->m_do_compose) { + // a Dead key was pressed + if (first_press && d->m_composing == 1 && d->m_dead_unicode == unicode) { // twice + d->m_composing = 0; + qtcode = Qt::Key_unknown; // otherwise it would be Qt::Key_Dead... + } else if (first_press && unicode != 0xffff) { + d->m_dead_unicode = unicode; + d->m_composing = 1; + skip = true; + } else { + skip = true; + } + } + + if (!skip) { + // a normal key was pressed + const int modmask = Qt::ShiftModifier | Qt::ControlModifier | Qt::AltModifier | Qt::MetaModifier | Qt::KeypadModifier; + + // we couldn't find a specific mapping for the current modifiers, + // or that mapping didn't have special modifiers: + // so just report the plain mapping with additional modifiers. + if ((it == map_plain && it != map_withmod) || + (map_withmod && !(map_withmod->qtcode & modmask))) { + qtcode |= QWSKbPrivate::toQtModifiers(d->m_modifiers); + } + + if (d->m_composing == 2 && first_press && !(it->flags & QWSKeyboard::IsModifier)) { + // the last key press was the Compose key + if (unicode != 0xffff) { + int idx = 0; + // check if this code is in the compose table at all + for ( ; idx < d->m_keycompose_size; ++idx) { + if (d->m_keycompose[idx].first == unicode) + break; + } + if (idx < d->m_keycompose_size) { + // found it -> simulate a Dead key press + d->m_dead_unicode = unicode; + unicode = 0xffff; + d->m_composing = 1; + skip = true; + } else { + d->m_composing = 0; + } + } else { + d->m_composing = 0; + } + } else if (d->m_composing == 1 && first_press && !(it->flags & QWSKeyboard::IsModifier)) { + // the last key press was a Dead key + bool valid = false; + if (unicode != 0xffff) { + int idx = 0; + // check if this code is in the compose table at all + for ( ; idx < d->m_keycompose_size; ++idx) { + if (d->m_keycompose[idx].first == d->m_dead_unicode && d->m_keycompose[idx].second == unicode) + break; + } + if (idx < d->m_keycompose_size) { + quint16 composed = d->m_keycompose[idx].result; + if (composed != 0xffff) { + unicode = composed; + qtcode = Qt::Key_unknown; + valid = true; + } + } + } + if (!valid) { + unicode = d->m_dead_unicode; + qtcode = Qt::Key_unknown; + } + d->m_composing = 0; + } + + if (!skip) { +#ifdef QT_DEBUG_KEYMAP + qWarning("Processing: uni=%04x, qt=%08x, qtmod=%08x", unicode, qtcode & ~modmask, (qtcode & modmask)); +#endif + + // send the result to the QWS server + processKeyEvent(unicode, qtcode & ~modmask, Qt::KeyboardModifiers(qtcode & modmask), pressed, autorepeat); + } + } + return result; +} + QT_END_NAMESPACE #include "qkbd_qws.moc" diff --git a/src/gui/embedded/qkbd_qws.h b/src/gui/embedded/qkbd_qws.h index 8809f0a..171adc0 100644 --- a/src/gui/embedded/qkbd_qws.h +++ b/src/gui/embedded/qkbd_qws.h @@ -58,11 +58,33 @@ class Q_GUI_EXPORT QWSKeyboardHandler { public: QWSKeyboardHandler(); + QWSKeyboardHandler(const QString &device); virtual ~QWSKeyboardHandler(); virtual void processKeyEvent(int unicode, int keycode, Qt::KeyboardModifiers modifiers, bool isPress, bool autoRepeat); + enum KeycodeAction { + None = 0, + + CapsLockOff = 0x01000000, + CapsLockOn = 0x01000001, + NumLockOff = 0x02000000, + NumLockOn = 0x02000001, + ScrollLockOff = 0x03000000, + ScrollLockOn = 0x03000001, + + Reboot = 0x04000000, + + PreviousConsole = 0x05000000, + NextConsole = 0x05000001, + SwitchConsoleFirst = 0x06000000, + SwitchConsoleLast = 0x0600007f, + SwitchConsoleMask = 0x0000007f, + }; + + KeycodeAction processKeycode(quint16 keycode, bool pressed, bool autorepeat); + protected: int transformDirKey(int key); void beginAutoRepeat(int uni, int code, Qt::KeyboardModifiers mod); diff --git a/src/gui/embedded/qkbd_qws_p.h b/src/gui/embedded/qkbd_qws_p.h new file mode 100644 index 0000000..f7dcdaf --- /dev/null +++ b/src/gui/embedded/qkbd_qws_p.h @@ -0,0 +1,77 @@ +#ifndef QWSKEYBOARD_P_H +#define QWSKEYBOARD_P_H + +#include <QDataStream> + +namespace QWSKeyboard { + const quint32 FileMagic = 0x514d4150; // 'QMAP' + + struct Mapping { + quint16 keycode; + quint16 unicode; + quint32 qtcode; + quint8 modifiers; + quint8 flags; + quint16 special; + + }; + + enum Flags { + IsDead = 0x01, + IsLetter = 0x02, + IsModifier = 0x04, + IsSystem = 0x08, + }; + + enum System { + SystemConsoleFirst = 0x0100, + SystemConsoleMask = 0x007f, + SystemConsoleLast = 0x017f, + SystemConsolePrevious = 0x0180, + SystemConsoleNext = 0x0181, + SystemReboot = 0x0200, + SystemZap = 0x0300, + }; + + struct Composing { + quint16 first; + quint16 second; + quint16 result; + }; + + enum Modifiers { + ModPlain = 0x00, + ModShift = 0x01, + ModAltGr = 0x02, + ModControl = 0x04, + ModAlt = 0x08, + ModShiftL = 0x10, + ModShiftR = 0x20, + ModCtrlL = 0x40, + ModCtrlR = 0x80, + // ModCapsShift = 0x100, // not supported! + }; +}; + +inline QDataStream &operator>>(QDataStream &ds, QWSKeyboard::Mapping &m) +{ + return ds >> m.keycode >> m.unicode >> m.qtcode >> m.modifiers >> m.flags >> m.special; +} + +inline QDataStream &operator<<(QDataStream &ds, const QWSKeyboard::Mapping &m) +{ + return ds << m.keycode << m.unicode << m.qtcode << m.modifiers << m.flags << m.special; +} + +inline QDataStream &operator>>(QDataStream &ds, QWSKeyboard::Composing &c) +{ + return ds >> c.first >> c.second >> c.result; +} + +inline QDataStream &operator<<(QDataStream &ds, const QWSKeyboard::Composing &c) +{ + return ds << c.first << c.second << c.result; +} + + +#endif // QWSKEYBOARD_H diff --git a/src/gui/embedded/qkbddriverfactory_qws.cpp b/src/gui/embedded/qkbddriverfactory_qws.cpp index 1ade652..dbfac5c 100644 --- a/src/gui/embedded/qkbddriverfactory_qws.cpp +++ b/src/gui/embedded/qkbddriverfactory_qws.cpp @@ -45,7 +45,7 @@ #include "qapplication.h" #include "qkbdtty_qws.h" -#include "qkbdusb_qws.h" +#include "qkbdlinuxinput_qws.h" #include "qkbdum_qws.h" #include "qkbdsl5000_qws.h" #include "qkbdvfb_qws.h" @@ -121,9 +121,11 @@ QWSKeyboardHandler *QKbdDriverFactory::create(const QString& key, const QString& if (driver == QLatin1String("tty") || driver.isEmpty()) return new QWSTtyKeyboardHandler(device); # endif -# ifndef QT_NO_QWS_KBD_USB - if (driver == QLatin1String("usb")) - return new QWSUsbKeyboardHandler(device); +# ifndef QT_NO_QWS_KBD_LINUXINPUT + if (driver == QLatin1String("linuxinput") || \ + driver == QLatin1String("usb") || \ + driver == QLatin1String("linuxis")) + return new QWSLinuxInputKeyboardHandler(device); # endif # ifndef QT_NO_QWS_KBD_UM if (driver == QLatin1String("um") || driver == QLatin1String("qvfbkeyboard")) @@ -168,8 +170,8 @@ QStringList QKbdDriverFactory::keys() #ifndef QT_NO_QWS_KBD_TTY list << QLatin1String("TTY"); #endif -#ifndef QT_NO_QWS_KBD_USB - list << QLatin1String("USB"); +#ifndef QT_NO_QWS_KBD_LINUXINPUT + list << QLatin1String("LinuxInput"); #endif #ifndef QT_NO_QWS_KBD_UM list << QLatin1String("UM"); diff --git a/src/gui/embedded/qkbdlinuxinput_qws.cpp b/src/gui/embedded/qkbdlinuxinput_qws.cpp new file mode 100644 index 0000000..d04b09f --- /dev/null +++ b/src/gui/embedded/qkbdlinuxinput_qws.cpp @@ -0,0 +1,241 @@ +/**************************************************************************** +** +** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). +** Contact: Qt Software Information (qt-info@nokia.com) +** +** This file is part of the QtGui module of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** No Commercial Usage +** This file contains pre-release code and may not be distributed. +** You may use this file in accordance with the terms and conditions +** contained in the either Technology Preview License Agreement or the +** Beta Release License Agreement. +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 2.1 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 2.1 requirements +** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain +** additional rights. These rights are described in the Nokia Qt LGPL +** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this +** package. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU +** General Public License version 3.0 as published by the Free Software +** Foundation and appearing in the file LICENSE.GPL included in the +** packaging of this file. Please review the following information to +** ensure the GNU General Public License version 3.0 requirements will be +** met: http://www.gnu.org/copyleft/gpl.html. +** +** If you are unsure which license is appropriate for your use, please +** contact the sales department at qt-sales@nokia.com. +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#include "qkbdlinuxinput_qws.h" + +#ifndef QT_NO_QWS_KEYBOARD + +#include <QSocketNotifier> +#include <QStringList> + +#include <qplatformdefs.h> + +#include <errno.h> +#include <termios.h> + +#include <linux/kd.h> +#include <linux/input.h> + +QT_BEGIN_NAMESPACE + + +class QWSLinuxInputKbPrivate : public QObject +{ + Q_OBJECT +public: + QWSLinuxInputKbPrivate(QWSLinuxInputKeyboardHandler *, const QString &); + ~QWSLinuxInputKbPrivate(); + +private: + void switchLed(int, bool); + +private Q_SLOTS: + void readKeycode(); + +private: + QWSLinuxInputKeyboardHandler *m_handler; + int m_fd; + int m_tty_fd; + struct termios m_tty_attr; +}; + +QWSLinuxInputKeyboardHandler::QWSLinuxInputKeyboardHandler(const QString &device) + : QWSKeyboardHandler(device) +{ + d = new QWSLinuxInputKbPrivate(this, device); +} + +QWSLinuxInputKeyboardHandler::~QWSLinuxInputKeyboardHandler() +{ + delete d; +} + +bool QWSLinuxInputKeyboardHandler::filterInputEvent(quint16 &, qint32 &) +{ + return false; +} + +QWSLinuxInputKbPrivate::QWSLinuxInputKbPrivate(QWSLinuxInputKeyboardHandler *h, const QString &device) + : m_handler(h), m_fd(-1), m_tty_fd(-1) + +{ + setObjectName(QLatin1String("LinuxInputSubsystem Keyboard Handler")); + + QString dev = QLatin1String("/dev/input/event1"); + int repeat_delay = -1; + int repeat_rate = -1; + + QStringList args = device.split(QLatin1Char(':')); + foreach (const QString &arg, args) { + if (arg.startsWith(QLatin1String("repeat_delay="))) + repeat_delay = arg.mid(13).toInt(); + else if (arg.startsWith(QLatin1String("repeat_rate="))) + repeat_rate = arg.mid(12).toInt(); + else if (arg.startsWith(QLatin1String("/dev/"))) + dev = arg; + } + + m_fd = QT_OPEN(dev.toLocal8Bit().constData(), O_RDWR, 0); + if (m_fd >= 0) { + if (repeat_delay > 0 && repeat_rate > 0) { + int kbdrep[2] = { repeat_delay, repeat_rate }; + ::ioctl(m_fd, EVIOCSREP, kbdrep); + } + + QSocketNotifier *notifier; + notifier = new QSocketNotifier(m_fd, QSocketNotifier::Read, this); + connect(notifier, SIGNAL(activated(int)), this, SLOT(readKeycode())); + + // play nice in case we are started from a shell (e.g. for debugging) + m_tty_fd = isatty(0) ? 0 : -1; + + if (m_tty_fd >= 0) { + // save tty config for restore. + tcgetattr(m_tty_fd, &m_tty_attr); + + struct ::termios termdata; + tcgetattr(m_tty_fd, &termdata); + + // setting this tranlation mode is also needed in INPUT mode to prevent + // the shell from also interpreting codes, if the process has a tty + // attached: e.g. Ctrl+C wouldn't copy, but kill the application. + ::ioctl(m_tty_fd, KDSKBMODE, K_MEDIUMRAW); + + // set the tty layer to pass-through + termdata.c_iflag = (IGNPAR | IGNBRK) & (~PARMRK) & (~ISTRIP); + termdata.c_oflag = 0; + termdata.c_cflag = CREAD | CS8; + termdata.c_lflag = 0; + termdata.c_cc[VTIME]=0; + termdata.c_cc[VMIN]=1; + cfsetispeed(&termdata, 9600); + cfsetospeed(&termdata, 9600); + tcsetattr(m_tty_fd, TCSANOW, &termdata); + } + } else { + qWarning("Cannot open input device '%s': %s", qPrintable(dev), strerror(errno)); + return; + } +} + +QWSLinuxInputKbPrivate::~QWSLinuxInputKbPrivate() +{ + if (m_tty_fd >= 0) { + ::ioctl(m_tty_fd, KDSKBMODE, K_XLATE); + tcsetattr(m_tty_fd, TCSANOW, &m_tty_attr); + } + if (m_fd >= 0) + QT_CLOSE(m_fd); +} + +void QWSLinuxInputKbPrivate::switchLed(int led, bool state) +{ + struct ::input_event led_ie; + ::gettimeofday(&led_ie.time, 0); + led_ie.type = EV_LED; + led_ie.code = led; + led_ie.value = state; + + QT_WRITE(m_fd, &led_ie, sizeof(led_ie)); +} + +void QWSLinuxInputKbPrivate::readKeycode() +{ + struct ::input_event buffer[32]; + int n = 0; + + forever { + n = QT_READ(m_fd, reinterpret_cast<char *>(buffer) + n, sizeof(buffer) - n); + + if (n == 0) { + qWarning("Got EOF from the input device."); + return; + } else if (n < 0 && (errno != EINTR && errno != EAGAIN)) { + qWarning("Could not read from input device: %s", strerror(errno)); + return; + } else if (n % sizeof(buffer[0]) == 0) { + break; + } + } + + n /= sizeof(buffer[0]); + + for (int i = 0; i < n; ++i) { + if (buffer[i].type != EV_KEY) + continue; + + quint16 code = buffer[i].code; + qint32 value = buffer[i].value; + + if (m_handler->filterInputEvent(code, value)) + continue; + + QWSKeyboardHandler::KeycodeAction ka; + ka = m_handler->processKeycode(code, value != 0, value == 2); + + switch (ka) { + case QWSKeyboardHandler::CapsLockOn: + case QWSKeyboardHandler::CapsLockOff: + switchLed(LED_CAPSL, ka == QWSKeyboardHandler::CapsLockOn); + break; + + case QWSKeyboardHandler::NumLockOn: + case QWSKeyboardHandler::NumLockOff: + switchLed(LED_NUML, ka == QWSKeyboardHandler::NumLockOn); + break; + + case QWSKeyboardHandler::ScrollLockOn: + case QWSKeyboardHandler::ScrollLockOff: + switchLed(LED_SCROLLL, ka == QWSKeyboardHandler::ScrollLockOn); + break; + + default: + // ignore console switching and reboot + break; + } + } +} + +QT_END_NAMESPACE + +#include "qkbdlinuxinput_qws.moc" + +#endif // QT_NO_QWS_KEYBOARD diff --git a/src/gui/embedded/qkbdusb_qws.h b/src/gui/embedded/qkbdlinuxinput_qws.h index 81d0103..5fa8214 100644 --- a/src/gui/embedded/qkbdusb_qws.h +++ b/src/gui/embedded/qkbdlinuxinput_qws.h @@ -39,10 +39,10 @@ ** ****************************************************************************/ -#ifndef QKBDUSB_QWS_H -#define QKBDUSB_QWS_H +#ifndef QKBDLINUXINPUT_QWS_H +#define QKBDLINUXINPUT_QWS_H -#include <QtGui/qkbdpc101_qws.h> +#include <QtGui/qkbd_qws.h> QT_BEGIN_HEADER @@ -52,21 +52,23 @@ QT_MODULE(Gui) #ifndef QT_NO_QWS_KEYBOARD -#ifndef QT_NO_QWS_KBD_USB +#ifndef QT_NO_QWS_KBD_LINUXINPUT -class QWSUsbKbPrivate; +class QWSLinuxInputKbPrivate; -class QWSUsbKeyboardHandler : public QWSPC101KeyboardHandler +class QWSLinuxInputKeyboardHandler : public QWSKeyboardHandler { public: - QWSUsbKeyboardHandler(const QString&); - virtual ~QWSUsbKeyboardHandler(); + QWSLinuxInputKeyboardHandler(const QString&); + virtual ~QWSLinuxInputKeyboardHandler(); + + virtual bool filterInputEvent(quint16 &input_code, qint32 &input_value); private: - QWSUsbKbPrivate *d; + QWSLinuxInputKbPrivate *d; }; -#endif // QT_NO_QWS_KBD_USB +#endif // QT_NO_QWS_KBD_LINUXINPUT #endif // QT_NO_QWS_KEYBOARD @@ -74,4 +76,4 @@ QT_END_NAMESPACE QT_END_HEADER -#endif // QKBDUSB_QWS_H +#endif // QKBDLINUXINPUT_QWS_H diff --git a/src/gui/embedded/qkbdsl5000_qws.cpp b/src/gui/embedded/qkbdsl5000_qws.cpp index bc412b6..1e8095e 100644 --- a/src/gui/embedded/qkbdsl5000_qws.cpp +++ b/src/gui/embedded/qkbdsl5000_qws.cpp @@ -195,6 +195,13 @@ static const int keyMSize = sizeof(sl5000KeyMap)/sizeof(QWSKeyMap)-1; QWSSL5000KeyboardHandler::QWSSL5000KeyboardHandler(const QString &device) : QWSTtyKeyboardHandler(device) { + shift = false; + alt = false; + ctrl = false; + extended = 0; + prevuni = 0; + prevkey = 0; + caps = false; meta = false; fn = false; numLock = false; @@ -220,7 +227,7 @@ const QWSKeyMap *QWSSL5000KeyboardHandler::keyMap() const return sl5000KeyMap; } -void QWSSL5000KeyboardHandler::doKey(uchar code) +bool QWSSL5000KeyboardHandler::filterKeycode(char &code) { int keyCode = Qt::Key_unknown; bool release = false; @@ -239,19 +246,19 @@ void QWSSL5000KeyboardHandler::doKey(uchar code) else if (code == 0x52) { unicode='Z'-'@'; scan=Qt::Key_Z; } // Undo if (scan) { processKeyEvent(unicode, scan, Qt::ControlModifier, !release, false); - return; + return true; } } if (code < keyMSize) { - keyCode = keyMap()[code].key_code; + keyCode = keyMap()[int(code)].key_code; } bool repeatable = true; if (release && (keyCode == Qt::Key_F34 || keyCode == Qt::Key_F35)) - return; // no release for power and light keys - if (keyCode >= Qt::Key_F1 && keyCode <= Qt::Key_F35 + return true; // no release for power and light keys + if ((keyCode >= Qt::Key_F1 && keyCode <= Qt::Key_F35) || keyCode == Qt::Key_Escape || keyCode == Qt::Key_Home || keyCode == Qt::Key_Shift || keyCode == Qt::Key_Meta) repeatable = false; @@ -318,11 +325,11 @@ void QWSSL5000KeyboardHandler::doKey(uchar code) keyCode = Qt::Key_QuoteLeft; unicode = '`'; } else if (bCtrl) - unicode = keyMap()[code].ctrl_unicode ? keyMap()[code].ctrl_unicode : 0xffff; + unicode = keyMap()[int(code)].ctrl_unicode ? keyMap()[int(code)].ctrl_unicode : 0xffff; else if (bCaps) - unicode = keyMap()[code].shift_unicode ? keyMap()[code].shift_unicode : 0xffff; + unicode = keyMap()[int(code)].shift_unicode ? keyMap()[int(code)].shift_unicode : 0xffff; else - unicode = keyMap()[code].unicode ? keyMap()[code].unicode : 0xffff; + unicode = keyMap()[int(code)].unicode ? keyMap()[int(code)].unicode : 0xffff; } modifiers = 0; @@ -349,6 +356,8 @@ void QWSSL5000KeyboardHandler::doKey(uchar code) beginAutoRepeat(prevuni, prevkey, modifiers); else endAutoRepeat(); + + return true; } QT_END_NAMESPACE diff --git a/src/gui/embedded/qkbdsl5000_qws.h b/src/gui/embedded/qkbdsl5000_qws.h index 514d602..a96e038 100644 --- a/src/gui/embedded/qkbdsl5000_qws.h +++ b/src/gui/embedded/qkbdsl5000_qws.h @@ -52,7 +52,13 @@ QT_MODULE(Gui) #ifndef QT_NO_QWS_KBD_SL5000 -class QWSSL5000KbPrivate; +struct QWSKeyMap { + uint key_code; + ushort unicode; + ushort shift_unicode; + ushort ctrl_unicode; +}; + class QWSSL5000KeyboardHandler : public QWSTtyKeyboardHandler { @@ -60,14 +66,21 @@ public: explicit QWSSL5000KeyboardHandler(const QString&); virtual ~QWSSL5000KeyboardHandler(); - virtual void doKey(uchar scancode); + bool filterKeycode(char &keycode); virtual const QWSKeyMap *keyMap() const; private: + bool shift; + bool alt; + bool ctrl; + bool caps; + uint extended:2; + Qt::KeyboardModifiers modifiers; + int prevuni; + int prevkey; bool meta; bool fn; bool numLock; - QWSSL5000KbPrivate *d; }; #endif // QT_NO_QWS_KBD_SL5000 diff --git a/src/gui/embedded/qkbdtty_qws.cpp b/src/gui/embedded/qkbdtty_qws.cpp index b588e55..37ed510 100644 --- a/src/gui/embedded/qkbdtty_qws.cpp +++ b/src/gui/embedded/qkbdtty_qws.cpp @@ -43,64 +43,57 @@ #if !defined(QT_NO_QWS_KEYBOARD) && !defined(QT_NO_QWS_KBD_TTY) -#include "qscreen_qws.h" - -#include "qwindowsystem_qws.h" -#include "qapplication.h" -#include "qsocketnotifier.h" -#include "qnamespace.h" -#include "qtimer.h" -#include <private/qwssignalhandler_p.h> -#include <private/qwindowsurface_qws_p.h> - -#include <unistd.h> -#include <sys/ioctl.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <fcntl.h> -#include <errno.h> -#include <signal.h> -#include <termios.h> +#include <QSocketNotifier> +#include <QStringList> -#include <qeventloop.h> +#include <qplatformdefs.h> -#ifdef Q_OS_LINUX -#include <sys/kd.h> -#include <sys/vt.h> -#endif +#include <errno.h> +#include <termios.h> -QT_BEGIN_NAMESPACE +#if defined Q_OS_LINUX +# include <linux/kd.h> +# include <linux/vt.h> //TODO: move vt handling somewhere else (QLinuxFbScreen?) -#define VTACQSIG SIGUSR1 -#define VTRELSIG SIGUSR2 +# include "qscreen_qws.h" +# include "qwindowsystem_qws.h" +# include "qapplication.h" +# include "private/qwindowsurface_qws_p.h" +# include "private/qwssignalhandler_p.h" -static int vtQws = 0; -static int kbdFD = -1; +# define VTACQSIG SIGUSR1 +# define VTRELSIG SIGUSR2 +#endif -//=========================================================================== -// -// Tty keyboard -// +QT_BEGIN_NAMESPACE class QWSTtyKbPrivate : public QObject { Q_OBJECT public: - QWSTtyKbPrivate(QWSPC101KeyboardHandler *, const QString &device); + QWSTtyKbPrivate(QWSTtyKeyboardHandler *handler, const QString &device); ~QWSTtyKbPrivate(); -private slots: - void readKeyboardData(); - void handleTtySwitch(int); +private: + void switchLed(char, bool); + void switchConsole(int vt); + +private Q_SLOTS: + void readKeycode(); + void handleConsoleSwitch(int sig); private: - QWSPC101KeyboardHandler *handler; - struct termios origTermData; + QWSTtyKeyboardHandler *m_handler; + int m_tty_fd; + struct termios m_tty_attr; + char m_last_keycode; + int m_vt_qws; }; + QWSTtyKeyboardHandler::QWSTtyKeyboardHandler(const QString &device) - : QWSPC101KeyboardHandler(device) + : QWSKeyboardHandler(device) { d = new QWSTtyKbPrivate(this, device); } @@ -110,59 +103,63 @@ QWSTtyKeyboardHandler::~QWSTtyKeyboardHandler() delete d; } -void QWSTtyKeyboardHandler::processKeyEvent(int unicode, int keycode, - Qt::KeyboardModifiers modifiers, bool isPress, - bool autoRepeat) +bool QWSTtyKeyboardHandler::filterKeycode(char &) { -#if defined(Q_OS_LINUX) - // Virtual console switching - int term = 0; - bool ctrl = modifiers & Qt::ControlModifier; - bool alt = modifiers & Qt::AltModifier; - if (ctrl && alt && keycode >= Qt::Key_F1 && keycode <= Qt::Key_F10) - term = keycode - Qt::Key_F1 + 1; - else if (ctrl && alt && keycode == Qt::Key_Left) - term = qMax(vtQws - 1, 1); - else if (ctrl && alt && keycode == Qt::Key_Right) - term = qMin(vtQws + 1, 10); - if (term && isPress) { - ioctl(kbdFD, VT_ACTIVATE, term); - return; - } -#endif - - QWSPC101KeyboardHandler::processKeyEvent(unicode, keycode, modifiers, - isPress, autoRepeat); + return false; } - -QWSTtyKbPrivate::QWSTtyKbPrivate(QWSPC101KeyboardHandler *h, const QString &device) : handler(h) +QWSTtyKbPrivate::QWSTtyKbPrivate(QWSTtyKeyboardHandler *h, const QString &device) + : m_handler(h), m_tty_fd(-1), m_last_keycode(0), m_vt_qws(0) { - kbdFD = ::open(device.isEmpty()?"/dev/tty0":device.toLatin1().constData(), O_RDWR|O_NDELAY, 0); + setObjectName(QLatin1String("TTY Keyboard Handler")); #ifndef QT_NO_QWS_SIGNALHANDLER QWSSignalHandler::instance()->addObject(this); #endif - if (kbdFD >= 0) { + QString dev = QLatin1String("/dev/tty0"); + int repeat_delay = -1; + int repeat_rate = -1; + + QStringList args = device.split(QLatin1Char(':')); + foreach (const QString &arg, args) { + if (arg.startsWith(QLatin1String("repeat_delay="))) + repeat_delay = arg.mid(13).toInt(); + else if (arg.startsWith(QLatin1String("repeat_rate="))) + repeat_rate = arg.mid(12).toInt(); + else if (arg.startsWith(QLatin1String("/dev/"))) + dev = arg; + } + + m_tty_fd = QT_OPEN(dev.toLocal8Bit().constData(), O_RDWR, 0); + if (m_tty_fd >= 0) { + if (repeat_delay > 0 && repeat_rate > 0) { +#if defined(Q_OS_LINUX) + struct ::kbd_repeat kbdrep = { repeat_delay, repeat_rate }; + ::ioctl(m_tty_fd, KDKBDREP, &kbdrep); +#endif + } + QSocketNotifier *notifier; - notifier = new QSocketNotifier(kbdFD, QSocketNotifier::Read, this); - connect(notifier, SIGNAL(activated(int)),this, - SLOT(readKeyboardData())); + notifier = new QSocketNotifier(m_tty_fd, QSocketNotifier::Read, this); + connect(notifier, SIGNAL(activated(int)), this, SLOT(readKeycode())); - // save for restore. - tcgetattr(kbdFD, &origTermData); + // save tty config for restore. + tcgetattr(m_tty_fd, &m_tty_attr); - struct termios termdata; - tcgetattr(kbdFD, &termdata); + struct ::termios termdata; + tcgetattr(m_tty_fd, &termdata); #if defined(Q_OS_LINUX) -# ifdef QT_QWS_USE_KEYCODES - ioctl(kbdFD, KDSKBMODE, K_MEDIUMRAW); -# else - ioctl(kbdFD, KDSKBMODE, K_RAW); -# endif + // PLEASE NOTE: + // The tty keycode interface can only report keycodes 0x01 .. 0x7f + // KEY_MAX is however defined to 0x1ff. In practice this is sufficient + // for a PC style keyboard though. + // we don't support K_RAW anymore - if you need, you habe to add a + // scan- to keycode converter. + ::ioctl(m_tty_fd, KDSKBMODE, K_MEDIUMRAW); #endif + // set the tty layer to pass-through termdata.c_iflag = (IGNPAR | IGNBRK) & (~PARMRK) & (~ISTRIP); termdata.c_oflag = 0; termdata.c_cflag = CREAD | CS8; @@ -171,50 +168,146 @@ QWSTtyKbPrivate::QWSTtyKbPrivate(QWSPC101KeyboardHandler *h, const QString &devi termdata.c_cc[VMIN]=1; cfsetispeed(&termdata, 9600); cfsetospeed(&termdata, 9600); - tcsetattr(kbdFD, TCSANOW, &termdata); + tcsetattr(m_tty_fd, TCSANOW, &termdata); #if defined(Q_OS_LINUX) - - connect(QApplication::instance(), SIGNAL(unixSignal(int)), this, SLOT(handleTtySwitch(int))); + // VT switching is handled via unix signals + connect(QApplication::instance(), SIGNAL(unixSignal(int)), this, SLOT(handleConsoleSwitch(int))); QApplication::instance()->watchUnixSignal(VTACQSIG, true); QApplication::instance()->watchUnixSignal(VTRELSIG, true); - struct vt_mode vtMode; - ioctl(kbdFD, VT_GETMODE, &vtMode); + struct ::vt_mode vtMode; + if (::ioctl(m_tty_fd, VT_GETMODE, &vtMode) == 0) { + vtMode.mode = VT_PROCESS; + vtMode.relsig = VTRELSIG; + vtMode.acqsig = VTACQSIG; - // let us control VT switching - vtMode.mode = VT_PROCESS; - vtMode.relsig = VTRELSIG; - vtMode.acqsig = VTACQSIG; - ioctl(kbdFD, VT_SETMODE, &vtMode); + if (::ioctl(m_tty_fd, VT_SETMODE, &vtMode) == 0) { + struct ::vt_stat vtStat; + ::memset(&vtStat, 0, sizeof(vtStat)); - struct vt_stat vtStat; - ioctl(kbdFD, VT_GETSTATE, &vtStat); - vtQws = vtStat.v_active; + if (::ioctl(m_tty_fd, VT_GETSTATE, &vtStat) == 0 ) { + m_vt_qws = vtStat.v_active; + } + } + } + + if (!m_vt_qws) + qWarning("Could not initialize virtual console switching"); #endif } else { - qCritical("Cannot open keyboard: %s", strerror(errno)); + qWarning("Cannot open input device '%s': %s", qPrintable(dev), strerror(errno)); + return; } } QWSTtyKbPrivate::~QWSTtyKbPrivate() { - if (kbdFD >= 0) { + if (m_tty_fd >= 0) { #if defined(Q_OS_LINUX) - ioctl(kbdFD, KDSKBMODE, K_XLATE); + ::ioctl(m_tty_fd, KDSKBMODE, K_XLATE); #endif - tcsetattr(kbdFD, TCSANOW, &origTermData); - ::close(kbdFD); - kbdFD = -1; + tcsetattr(m_tty_fd, TCSANOW, &m_tty_attr); } } -void QWSTtyKbPrivate::handleTtySwitch(int sig) + + +void QWSTtyKbPrivate::switchLed(char led, bool state) { #if defined(Q_OS_LINUX) + char ledstate; + + ::ioctl(m_tty_fd, KDGETLED, &ledstate); + if (state) + ledstate |= led; + else + ledstate &= ~led; + ::ioctl(m_tty_fd, KDSETLED, ledstate); +#endif +} + +void QWSTtyKbPrivate::readKeycode() +{ + char buffer[32]; + int n = 0; + + forever { + n = QT_READ(m_tty_fd, buffer + n, 32 - n); + + if (n == 0) { + qWarning("Got EOF from the input device."); + return; + } else if (n < 0 && (errno != EINTR && errno != EAGAIN)) { + qWarning("Could not read from input device: %s", strerror(errno)); + return; + } else { + break; + } + } + + for (int i = 0; i < n; ++i) { + if (m_handler->filterKeycode(buffer[i])) + continue; + + QWSKeyboardHandler::KeycodeAction ka; + ka = m_handler->processKeycode(buffer[i] & 0x7f, (buffer[i] & 0x80) == 0x00, buffer[i] == m_last_keycode); + m_last_keycode = buffer[i]; + +qWarning("Special: %08x", ka); + switch (ka) { + case QWSKeyboardHandler::CapsLockOn: + case QWSKeyboardHandler::CapsLockOff: + switchLed(LED_CAP, ka == QWSKeyboardHandler::CapsLockOn); + break; + + case QWSKeyboardHandler::NumLockOn: + case QWSKeyboardHandler::NumLockOff: + switchLed(LED_NUM, ka == QWSKeyboardHandler::NumLockOn); + break; + + case QWSKeyboardHandler::ScrollLockOn: + case QWSKeyboardHandler::ScrollLockOff: + switchLed(LED_SCR, ka == QWSKeyboardHandler::ScrollLockOn); + break; + + case QWSKeyboardHandler::PreviousConsole: + switchConsole(qBound(1, m_vt_qws - 1, 10)); + break; + + case QWSKeyboardHandler::NextConsole: + switchConsole(qBound(1, m_vt_qws + 1, 10)); + break; + + default: + if (ka >= QWSKeyboardHandler::SwitchConsoleFirst && + ka <= QWSKeyboardHandler::SwitchConsoleLast) { + switchConsole(1 + (ka & QWSKeyboardHandler::SwitchConsoleMask)); + } + //ignore reboot + break; + } + } +} + + +void QWSTtyKbPrivate::switchConsole(int vt) +{ +#if defined(Q_OS_LINUX) + if (m_vt_qws && vt && (m_tty_fd >= 0 )) + ::ioctl(m_tty_fd, VT_ACTIVATE, vt); +#endif +} + +void QWSTtyKbPrivate::handleConsoleSwitch(int sig) +{ +#if defined(Q_OS_LINUX) + // received a notification from the kernel that the current VT is + // changing: either enable or disable QWS painting accordingly. + if (sig == VTACQSIG) { - if (ioctl(kbdFD, VT_RELDISP, VT_ACKACQ) == 0) { + if (::ioctl(m_tty_fd, VT_RELDISP, VT_ACKACQ) == 0) { qwsServer->enablePainting(true); qt_screen->restore(); qwsServer->resumeMouse(); @@ -236,9 +329,9 @@ void QWSTtyKbPrivate::handleTtySwitch(int sig) } if (!allWindowsHidden) { - ioctl(kbdFD, VT_RELDISP, 0); // abort console switch + ::ioctl(m_tty_fd, VT_RELDISP, 0); // abort console switch qwsServer->enablePainting(true); - } else if (ioctl(kbdFD, VT_RELDISP, 1) == 0) { + } else if (::ioctl(m_tty_fd, VT_RELDISP, 1) == 0) { qt_screen->save(); qwsServer->suspendMouse(); } else { @@ -248,14 +341,6 @@ void QWSTtyKbPrivate::handleTtySwitch(int sig) #endif } -void QWSTtyKbPrivate::readKeyboardData() -{ - unsigned char buf[81]; - int n = read(kbdFD, buf, 80); - for (int loop = 0; loop < n; loop++) - handler->doKey(buf[loop]); -} - QT_END_NAMESPACE #include "qkbdtty_qws.moc" diff --git a/src/gui/embedded/qkbdtty_qws.h b/src/gui/embedded/qkbdtty_qws.h index 4f93d6c..fc3eaa1 100644 --- a/src/gui/embedded/qkbdtty_qws.h +++ b/src/gui/embedded/qkbdtty_qws.h @@ -42,7 +42,7 @@ #ifndef QKBDTTY_QWS_H #define QKBDTTY_QWS_H -#include <QtGui/qkbdpc101_qws.h> +#include <QtGui/qkbd_qws.h> QT_BEGIN_HEADER @@ -56,15 +56,13 @@ QT_MODULE(Gui) class QWSTtyKbPrivate; -class QWSTtyKeyboardHandler : public QWSPC101KeyboardHandler +class QWSTtyKeyboardHandler : public QWSKeyboardHandler { public: explicit QWSTtyKeyboardHandler(const QString&); virtual ~QWSTtyKeyboardHandler(); -protected: - virtual void processKeyEvent(int unicode, int keycode, Qt::KeyboardModifiers modifiers, - bool isPress, bool autoRepeat); + virtual bool filterKeycode(char &code); private: QWSTtyKbPrivate *d; diff --git a/src/gui/embedded/qkbdusb_qws.cpp b/src/gui/embedded/qkbdusb_qws.cpp deleted file mode 100644 index e35ac55..0000000 --- a/src/gui/embedded/qkbdusb_qws.cpp +++ /dev/null @@ -1,401 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). -** Contact: Qt Software Information (qt-info@nokia.com) -** -** This file is part of the QtGui module of the Qt Toolkit. -** -** $QT_BEGIN_LICENSE:LGPL$ -** No Commercial Usage -** This file contains pre-release code and may not be distributed. -** You may use this file in accordance with the terms and conditions -** contained in the either Technology Preview License Agreement or the -** Beta Release License Agreement. -** -** GNU Lesser General Public License Usage -** Alternatively, this file may be used under the terms of the GNU Lesser -** General Public License version 2.1 as published by the Free Software -** Foundation and appearing in the file LICENSE.LGPL included in the -** packaging of this file. Please review the following information to -** ensure the GNU Lesser General Public License version 2.1 requirements -** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. -** -** In addition, as a special exception, Nokia gives you certain -** additional rights. These rights are described in the Nokia Qt LGPL -** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this -** package. -** -** GNU General Public License Usage -** Alternatively, this file may be used under the terms of the GNU -** General Public License version 3.0 as published by the Free Software -** Foundation and appearing in the file LICENSE.GPL included in the -** packaging of this file. Please review the following information to -** ensure the GNU General Public License version 3.0 requirements will be -** met: http://www.gnu.org/copyleft/gpl.html. -** -** If you are unsure which license is appropriate for your use, please -** contact the sales department at qt-sales@nokia.com. -** $QT_END_LICENSE$ -** -****************************************************************************/ - -#include "qkbdusb_qws.h" - -#ifndef QT_NO_QWS_KEYBOARD - -#include "qscreen_qws.h" - -#include "qwindowsystem_qws.h" -#include "qapplication.h" -#include "qsocketnotifier.h" -#include "qnamespace.h" -#include "qtimer.h" - -#include <unistd.h> -#include <sys/ioctl.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <fcntl.h> -#include <errno.h> -#include <signal.h> - -#include <linux/input.h> - -#ifdef Q_OS_LINUX -#include <sys/kd.h> -#include <sys/vt.h> -#endif - -QT_BEGIN_NAMESPACE - -/* USB driver */ - - -class QWSUsbKbPrivate : public QObject -{ - Q_OBJECT -public: - QWSUsbKbPrivate(QWSPC101KeyboardHandler *, const QString &); - ~QWSUsbKbPrivate(); - -private slots: - void readKeyboardData(); - -private: - QWSPC101KeyboardHandler *handler; - int fd; -#ifdef QT_QWS_ZYLONITE - bool shift; -#endif -}; - -QWSUsbKeyboardHandler::QWSUsbKeyboardHandler(const QString &device) - : QWSPC101KeyboardHandler(device) -{ - d = new QWSUsbKbPrivate(this, device); -} - -QWSUsbKeyboardHandler::~QWSUsbKeyboardHandler() -{ - delete d; -} - -QWSUsbKbPrivate::QWSUsbKbPrivate(QWSPC101KeyboardHandler *h, const QString &device) : handler(h) -{ -#ifdef QT_QWS_ZYLONITE - shift = FALSE; -#endif - fd = ::open(device.isEmpty()?"/dev/input/event1":device.toLocal8Bit(),O_RDONLY, 0); - if (fd >= 0) { - QSocketNotifier *notifier; - notifier = new QSocketNotifier(fd, QSocketNotifier::Read, this); - connect(notifier, SIGNAL(activated(int)),this, - SLOT(readKeyboardData())); - } -} - -QWSUsbKbPrivate::~QWSUsbKbPrivate() -{ - ::close(fd); -} - -void QWSUsbKbPrivate::readKeyboardData() -{ - input_event event; - if (read(fd, &event, sizeof(input_event)) != sizeof(input_event)) - return; - - if (event.type != EV_KEY) - return; - -#ifdef QT_QWS_ZYLONITE - qDebug("keypressed: code=%03d (%s)\n",event.code,((event.value)!=0) ? "Down":"Up"); - int modifiers=0; - int unicode=0xffff; - int key_code=0; - - switch(event.code) - { - case 0xA2: - key_code = ((!shift) ? Qt::Key_0 : Qt::Key_Plus ); - unicode = ((!shift) ? 0x30 : 0x2B ); - break; - case 0x70: - key_code = ((!shift) ? Qt::Key_1 : Qt::Key_At ); - unicode = ((!shift) ? 0x31 : 0x40 ); - break; - case 0x72: - key_code = ((!shift) ? Qt::Key_2 : Qt::Key_Ampersand ); - unicode = ((!shift) ? 0x32 : 0x26 ); - break; - case 0x74: - key_code = ((!shift) ? Qt::Key_3 : Qt::Key_At ); - unicode = ((!shift) ? 0x33 : 0x3F ); - break; - case 0x80: - key_code = ((!shift) ? Qt::Key_4 : Qt::Key_Minus ); - unicode = ((!shift) ? 0x34 : 0x2D ); - break; - case 0x82: - key_code = ((!shift) ? Qt::Key_5 : Qt::Key_Apostrophe); - unicode = ((!shift) ? 0x35 : 0x27 ); - break; - case 0x84: - key_code = ((!shift) ? Qt::Key_6 : Qt::Key_Slash ); - unicode = ((!shift) ? 0x36 : 0x5C ); - break; - case 0x90: - key_code = ((!shift) ? Qt::Key_7 : Qt::Key_Colon ); - unicode = ((!shift) ? 0x37 : 0x3A ); - break; - case 0x92: - key_code = ((!shift) ? Qt::Key_8 : Qt::Key_Semicolon ); - unicode = ((!shift) ? 0x38 : 0x3B ); - break; - case 0x94: - key_code = ((!shift) ? Qt::Key_9 : Qt::Key_QuoteDbl ); - unicode = ((!shift) ? 0x39 : 0x22 ); - break; - case 0x0: - key_code = Qt::Key_A; - unicode = ((!shift) ? 0x61 : 0x41 ); - break; - case 0x10: - key_code = Qt::Key_B; - unicode = ((!shift) ? 0x62 : 0x42 ); - break; - case 0x20: - key_code = Qt::Key_C; - unicode = ((!shift) ? 0x63 : 0x43 ); - break; - case 0x30: - key_code = Qt::Key_D; - unicode = ((!shift) ? 0x64 : 0x44 ); - break; - case 0x40: - key_code = Qt::Key_E; - unicode = ((!shift) ? 0x65 : 0x45 ); - break; - case 0x50: - key_code = Qt::Key_F; - unicode = ((!shift) ? 0x66 : 0x46 ); - break; - case 0x01: - key_code = Qt::Key_G; - unicode = ((!shift) ? 0x67 : 0x47 ); - break; - case 0x11: - key_code = Qt::Key_H; - unicode = ((!shift) ? 0x68 : 0x48 ); - break; - case 0x21: - key_code = Qt::Key_I; - unicode = ((!shift) ? 0x69 : 0x49 ); - break; - case 0x31: - key_code = Qt::Key_J; - unicode = ((!shift) ? 0x6A : 0x4A ); - break; - case 0x41: - key_code = Qt::Key_K; - unicode = ((!shift) ? 0x6B : 0x4B ); - break; - case 0x51: - key_code = Qt::Key_L; - unicode = ((!shift) ? 0x6C : 0x4C ); - break; - case 0x02: - key_code = Qt::Key_M; - unicode = ((!shift) ? 0x6D : 0x4D ); - break; - case 0x12: - key_code = Qt::Key_N; - unicode = ((!shift) ? 0x6E : 0x4E ); - break; - case 0x22: - key_code = Qt::Key_O; - unicode = ((!shift) ? 0x6F : 0x4F ); - break; - case 0x32: - key_code = Qt::Key_P; - unicode = ((!shift) ? 0x70 : 0x50 ); - break; - case 0x42: - key_code = Qt::Key_Q; - unicode = ((!shift) ? 0x71 : 0x51 ); - break; - case 0x52: - key_code = Qt::Key_R; - unicode = ((!shift) ? 0x72 : 0x52 ); - break; - case 0x03: - key_code = Qt::Key_S; - unicode = ((!shift) ? 0x73 : 0x53 ); - break; - case 0x13: - key_code = Qt::Key_T; - unicode = ((!shift) ? 0x74 : 0x54 ); - break; - case 0x23: - key_code = Qt::Key_U; - unicode = ((!shift) ? 0x75 : 0x55 ); - break; - case 0x33: - key_code = Qt::Key_V; - unicode = ((!shift) ? 0x76 : 0x56 ); - break; - case 0x43: - key_code = Qt::Key_W; - unicode = ((!shift) ? 0x77 : 0x57 ); - break; - case 0x53: - key_code = Qt::Key_X; - unicode = ((!shift) ? 0x78 : 0x58 ); - break; - case 0x24: - key_code = Qt::Key_Y; - unicode = ((!shift) ? 0x79 : 0x59 ); - break; - case 0x34: - key_code = Qt::Key_Z; - unicode = ((!shift) ? 0x7A : 0x5A ); - break; - case 0xA4: - key_code = ((!shift) ? Qt::Key_NumberSign : Qt::Key_Period); - unicode = ((!shift) ? 0x23 : 0x2E ); - break; - case 0xA0: - key_code = ((!shift) ? Qt::Key_Asterisk : Qt::Key_NumberSign ); - unicode = ((!shift) ? 0x2A : 0x2C ); - break; - case 0x25: - key_code = Qt::Key_Space; - unicode = 0x20; - break; - case 0x06: - key_code = Qt::Key_Up; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x16: - key_code = Qt::Key_Down; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x26: - key_code = Qt::Key_Left; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x36: - key_code = Qt::Key_Right; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x46: - key_code = Qt::Key_Select; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x61: - key_code = Qt::Key_No; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x60: - key_code = Qt::Key_Call; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x55: - key_code = Qt::Key_Hangup; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x62: - key_code = Qt::Key_Context1; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x63: - key_code = Qt::Key_No; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x05: - key_code = Qt::Key_Home; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x15: - key_code = Qt::Key_Shift; - unicode = 0xffff; modifiers |= Qt::ShiftModifier; - if(event.value==0) break; - if(shift) { - shift = FALSE; - qWarning("Caps Off!"); - } else { - shift = TRUE; - qWarning("Caps On!"); - } - break; - case 0x1C: - key_code = ((!shift) ? Qt::Key_Back : Qt::Key_Enter ); - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x19: - key_code = Qt::Key_Context2; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x1A: - key_code = Qt::Key_Context3; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - case 0x1B: - key_code = Qt::Key_Context4; - unicode = 0xffff; modifiers |= Qt::KeypadModifier; - break; - } - if(shift) modifiers |= Qt::ShiftModifier; - handler->processKeyEvent(unicode, key_code, (Qt::KeyboardModifiers)modifiers, event.value!=0, false); -#else - - int key=event.code; -#ifndef QT_QWS_USE_KEYCODES - // Handle SOME keys, otherwise it's useless. - - if(key==103) { - handler->processKeyEvent(0, Qt::Key_Up, 0, event.value!=0, false); - } else if(key==106) { - handler->processKeyEvent(0, Qt::Key_Right, 0, event.value!=0, false ); - } else if(key==108) { - handler->processKeyEvent(0, Qt::Key_Down, 0, event.value!=0, false); - } else if(key==105) { - handler->processKeyEvent(0, Qt::Key_Left, 0, event.value!=0, false); - } else - -#endif - - { - if(event.value == 0) { - key=key | 0x80; - } - handler->doKey(key); - } -#endif -} - -QT_END_NAMESPACE - -#include "qkbdusb_qws.moc" - -#endif // QT_NO_QWS_KEYBOARD |