x11/skia: Add basic KeyPress/Release handling

Unicode char still missing in the generated event.
This commit is contained in:
David Capello 2018-08-07 16:35:55 -03:00
parent 9e65ff9ad8
commit cb3b201734
6 changed files with 257 additions and 20 deletions

View File

@ -36,10 +36,6 @@ public:
std::string getLayout() { return ""; }
void setLayout(const std::string& layout) { }
void setTranslateDeadKeys(bool state) {
// Do nothing
}
private:
void queueEvent(Event& ev) override;
void paintGC(const gfx::Rect& rc) override;

View File

@ -1,5 +1,5 @@
// SHE library
// Copyright (C) 2016 David Capello
// Copyright (C) 2016-2018 David Capello
//
// This file is released under the terms of the MIT license.
// Read LICENSE.txt for more information.
@ -8,10 +8,160 @@
#include "config.h"
#endif
#include "she/keys.h"
#include "base/ints.h"
#include "she/x11/keys.h"
#include <X11/keysym.h>
namespace she {
KeyScancode x11_keysym_to_scancode(KeySym keysym)
{
switch (keysym) {
case XK_BackSpace: return kKeyBackspace;
case XK_Tab: return kKeyTab;
case XK_Linefeed: return kKeyEnter;
case XK_Clear: return kKeyDel;
case XK_Return: return kKeyEnter;
case XK_Pause:
case XK_Break: return kKeyPause;
case XK_Scroll_Lock: return kKeyScrLock;
case XK_Escape: return kKeyEsc;
case XK_Delete: return kKeyDel;
case XK_Home: return kKeyHome;
case XK_Left: return kKeyLeft;
case XK_Up: return kKeyUp;
case XK_Right: return kKeyRight;
case XK_Down: return kKeyDown;
case XK_Page_Up: return kKeyPageUp;
case XK_Page_Down: return kKeyPageDown;
case XK_End: return kKeyEnd;
case XK_Sys_Req:
case XK_Print: return kKeyPrtscr;
case XK_Insert: return kKeyInsert;
case XK_Menu: return kKeyMenu;
case XK_Num_Lock: return kKeyNumLock;
case XK_KP_Space: return kKeySpace;
case XK_KP_Tab: return kKeyTab;
case XK_KP_Enter: return kKeyEnterPad;
case XK_KP_0: case XK_KP_Insert: return kKey0Pad;
case XK_KP_1: case XK_KP_End: return kKey1Pad;
case XK_KP_2: case XK_KP_Down: return kKey2Pad;
case XK_KP_3: case XK_KP_Page_Down: return kKey3Pad;
case XK_KP_4: case XK_KP_Left: return kKey4Pad;
case XK_KP_5: case XK_KP_Begin: return kKey5Pad;
case XK_KP_6: case XK_KP_Right: return kKey6Pad;
case XK_KP_7: case XK_KP_Home: return kKey7Pad;
case XK_KP_8: case XK_KP_Up: return kKey8Pad;
case XK_KP_9: case XK_KP_Page_Up: return kKey9Pad;
case XK_KP_Decimal:
case XK_KP_Delete: return kKeyDelPad;
case XK_KP_Equal: return kKeyEqualsPad;
case XK_KP_Multiply: return kKeyAsterisk;
case XK_KP_Add: return kKeyPlusPad;
case XK_KP_Subtract: return kKeyMinusPad;
case XK_KP_Divide: return kKeySlashPad;
case XK_F1: return kKeyF1;
case XK_F2: return kKeyF2;
case XK_F3: return kKeyF3;
case XK_F4: return kKeyF4;
case XK_F5: return kKeyF5;
case XK_F6: return kKeyF6;
case XK_F7: return kKeyF7;
case XK_F8: return kKeyF8;
case XK_F9: return kKeyF9;
case XK_F10: return kKeyF10;
case XK_F11: return kKeyF11;
case XK_F12: return kKeyF12;
case XK_Shift_L: return kKeyLShift;
case XK_Shift_R: return kKeyRShift;
case XK_Control_L: return kKeyLControl;
case XK_Control_R: return kKeyRControl;
case XK_Caps_Lock: return kKeyCapsLock;
case XK_Alt_L: return kKeyAlt;
case XK_Alt_R: return kKeyAltGr;
case XK_Meta_L:
case XK_Super_L: return kKeyLWin;
case XK_Meta_R:
case XK_Super_R: return kKeyRWin;
case XK_space: return kKeySpace;
case XK_apostrophe: return kKeyQuote;
case XK_comma: return kKeyComma;
case XK_minus: return kKeyMinus;
case XK_period: return kKeyStop;
case XK_slash: return kKeySlash;
case XK_0: return kKey0;
case XK_1: return kKey1;
case XK_2: return kKey2;
case XK_3: return kKey3;
case XK_4: return kKey4;
case XK_5: return kKey5;
case XK_6: return kKey6;
case XK_7: return kKey7;
case XK_8: return kKey8;
case XK_9: return kKey9;
case XK_semicolon: return kKeyColon;
case XK_less: return kKeyBackslash2;
case XK_A: return kKeyA;
case XK_B: return kKeyB;
case XK_C: return kKeyC;
case XK_D: return kKeyD;
case XK_E: return kKeyE;
case XK_F: return kKeyF;
case XK_G: return kKeyG;
case XK_H: return kKeyH;
case XK_I: return kKeyI;
case XK_J: return kKeyJ;
case XK_K: return kKeyK;
case XK_L: return kKeyL;
case XK_M: return kKeyM;
case XK_N: return kKeyN;
case XK_O: return kKeyO;
case XK_P: return kKeyP;
case XK_Q: return kKeyQ;
case XK_R: return kKeyR;
case XK_S: return kKeyS;
case XK_T: return kKeyT;
case XK_U: return kKeyU;
case XK_V: return kKeyV;
case XK_W: return kKeyW;
case XK_X: return kKeyX;
case XK_Y: return kKeyY;
case XK_Z: return kKeyZ;
case XK_bracketleft: return kKeyOpenbrace;
case XK_backslash: return kKeyBackslash;
case XK_bracketright: return kKeyClosebrace;
case XK_grave: return kKeyTilde;
case XK_a: return kKeyA;
case XK_b: return kKeyB;
case XK_c: return kKeyC;
case XK_d: return kKeyD;
case XK_e: return kKeyE;
case XK_f: return kKeyF;
case XK_g: return kKeyG;
case XK_h: return kKeyH;
case XK_i: return kKeyI;
case XK_j: return kKeyJ;
case XK_k: return kKeyK;
case XK_l: return kKeyL;
case XK_m: return kKeyM;
case XK_n: return kKeyN;
case XK_o: return kKeyO;
case XK_p: return kKeyP;
case XK_q: return kKeyQ;
case XK_r: return kKeyR;
case XK_s: return kKeyS;
case XK_t: return kKeyT;
case XK_u: return kKeyU;
case XK_v: return kKeyV;
case XK_w: return kKeyW;
case XK_x: return kKeyX;
case XK_y: return kKeyY;
case XK_z: return kKeyZ;
}
return kKeyNil;
}
bool x11_is_key_pressed(KeyScancode scancode)
{
return false; // TODO

22
src/she/x11/keys.h Normal file
View File

@ -0,0 +1,22 @@
// SHE library
// Copyright (C) 2018 David Capello
//
// This file is released under the terms of the MIT license.
// Read LICENSE.txt for more information.
#ifndef SHE_X11_KEYS_INCLUDED
#define SHE_X11_KEYS_INCLUDED
#pragma once
#include "she/keys.h"
#include <X11/X.h>
namespace she {
KeyScancode x11_keysym_to_scancode(KeySym keysym);
bool x11_is_key_pressed(KeyScancode scancode);
int x11_get_unicode_from_scancode(KeyScancode scancode);
} // namespace she
#endif

View File

@ -9,12 +9,10 @@
#pragma once
#include "she/common/system.h"
#include "she/x11/keys.h"
namespace she {
bool x11_is_key_pressed(KeyScancode scancode);
int x11_get_unicode_from_scancode(KeyScancode scancode);
class X11System : public CommonSystem {
public:
bool isKeyPressed(KeyScancode scancode) override {

View File

@ -1,5 +1,5 @@
// SHE library
// Copyright (C) 2017 David Capello
// Copyright (C) 2017-2018 David Capello
//
// This file is released under the terms of the MIT license.
// Read LICENSE.txt for more information.
@ -12,10 +12,15 @@
#include "gfx/rect.h"
#include "she/event.h"
#include "she/x11/keys.h"
#include <X11/cursorfont.h>
#include <map>
#define KEY_TRACE(...)
#define MOUSE_TRACE(...)
#define EVENT_TRACE(...)
namespace she {
namespace {
@ -35,9 +40,24 @@ std::map<::Window, X11Window*> g_activeWindows;
KeyModifiers get_modifiers_from_x(int state)
{
int modifiers = kKeyNoneModifier;
if (state & ShiftMask) modifiers |= kKeyShiftModifier;
if (state & LockMask) modifiers |= kKeyAltModifier;
if (state & ControlMask) modifiers |= kKeyCtrlModifier;
if (state & ShiftMask) {
modifiers |= kKeyShiftModifier;
KEY_TRACE("+SHIFT\n");
}
if (state & ControlMask) {
modifiers |= kKeyCtrlModifier;
KEY_TRACE("+CTRL\n");
}
// Mod1Mask is Alt, and Mod5Mask is AltGr
if (state & (Mod1Mask | Mod5Mask)) {
modifiers |= kKeyAltModifier;
KEY_TRACE("+ALT\n");
}
// Mod4Mask is Windows key
if (state & Mod4Mask) {
modifiers |= kKeyWinModifier;
KEY_TRACE("+WIN\n");
}
return (KeyModifiers)modifiers;
}
@ -64,13 +84,13 @@ gfx::Point get_mouse_wheel_delta(int button)
Event::MouseButton get_mouse_button_from_x(int button)
{
switch (button) {
case Button1: TRACE("LeftButton\n"); return Event::LeftButton;
case Button2: TRACE("MiddleButton\n"); return Event::MiddleButton;
case Button3: TRACE("RightButton\n"); return Event::RightButton;
case 8: TRACE("X1Button\n"); return Event::X1Button;
case 9: TRACE("X2Button\n"); return Event::X2Button;
case Button1: MOUSE_TRACE("LeftButton\n"); return Event::LeftButton;
case Button2: MOUSE_TRACE("MiddleButton\n"); return Event::MiddleButton;
case Button3: MOUSE_TRACE("RightButton\n"); return Event::RightButton;
case 8: MOUSE_TRACE("X1Button\n"); return Event::X1Button;
case 9: MOUSE_TRACE("X2Button\n"); return Event::X2Button;
}
TRACE("Unknown Button %d\n", button);
MOUSE_TRACE("Unknown Button %d\n", button);
return Event::NoneButton;
}
@ -332,6 +352,53 @@ void X11Window::processX11Event(XEvent& event)
break;
}
case KeyPress:
case KeyRelease: {
Event ev;
ev.setType(event.type == KeyPress ? Event::KeyDown: Event::KeyUp);
KeySym keysym = XLookupKeysym(&event.xkey, 0);
ev.setScancode(x11_keysym_to_scancode(keysym));
int modifiers = (int)get_modifiers_from_x(event.xkey.state);
switch (keysym) {
case XK_Shift_L:
case XK_Shift_R:
modifiers |= kKeyShiftModifier;
break;
case XK_Control_L:
case XK_Control_R:
modifiers |= kKeyCtrlModifier;
break;
case XK_Alt_L:
case XK_Alt_R:
modifiers |= kKeyAltModifier;
break;
case XK_Meta_L:
case XK_Super_L:
case XK_Meta_R:
case XK_Super_R:
modifiers |= kKeyWinModifier;
break;
}
ev.setModifiers((KeyModifiers)modifiers);
KEY_TRACE("%s state=%04x keycode=%04x\n",
(event.type == KeyPress ? "KeyPress": "KeyRelease"),
event.xkey.state,
event.xkey.keycode);
#ifndef NDEBUG
{
char* str = XKeysymToString(keysym);
KEY_TRACE(" > %s\n", str);
}
#endif
queueEvent(ev);
break;
}
case ButtonPress:
case ButtonRelease: {
Event ev;

View File

@ -1,5 +1,5 @@
// SHE library
// Copyright (C) 2016-2017 David Capello
// Copyright (C) 2016-2018 David Capello
//
// This file is released under the terms of the MIT license.
// Read LICENSE.txt for more information.
@ -49,6 +49,10 @@ public:
::Window handle() const { return m_window; }
::GC gc() const { return m_gc; }
void setTranslateDeadKeys(bool state) {
// TODO
}
void processX11Event(XEvent& event);
static X11Window* getPointerFromHandle(Window handle);