Files
eink-dairy/keyboard_input.cpp
T

143 lines
4.6 KiB
C++

#include "keyboard_input.h"
#include <stdio.h>
static const uint8_t keycode2ascii[128][2] = {
{0, 0}, /* 0x00 */
{0, 0}, /* 0x01 */
{0, 0}, /* 0x02 */
{0, 0}, /* 0x03 */
{'a', 'A'}, /* 0x04 */
{'b', 'B'}, /* 0x05 */
{'c', 'C'}, /* 0x06 */
{'d', 'D'}, /* 0x07 */
{'e', 'E'}, /* 0x08 */
{'f', 'F'}, /* 0x09 */
{'g', 'G'}, /* 0x0a */
{'h', 'H'}, /* 0x0b */
{'i', 'I'}, /* 0x0c */
{'j', 'J'}, /* 0x0d */
{'k', 'K'}, /* 0x0e */
{'l', 'L'}, /* 0x0f */
{'m', 'M'}, /* 0x10 */
{'n', 'N'}, /* 0x11 */
{'o', 'O'}, /* 0x12 */
{'p', 'P'}, /* 0x13 */
{'q', 'Q'}, /* 0x14 */
{'r', 'R'}, /* 0x15 */
{'s', 'S'}, /* 0x16 */
{'t', 'T'}, /* 0x17 */
{'u', 'U'}, /* 0x18 */
{'v', 'V'}, /* 0x19 */
{'w', 'W'}, /* 0x1a */
{'x', 'X'}, /* 0x1b */
{'y', 'Y'}, /* 0x1c */
{'z', 'Z'}, /* 0x1d */
{'1', '!'}, /* 0x1e */
{'2', '@'}, /* 0x1f */
{'3', '#'}, /* 0x20 */
{'4', '$'}, /* 0x21 */
{'5', '%'}, /* 0x22 */
{'6', '^'}, /* 0x23 */
{'7', '&'}, /* 0x24 */
{'8', '*'}, /* 0x25 */
{'9', '('}, /* 0x26 */
{'0', ')'}, /* 0x27 */
{'\r', '\r'}, /* 0x28 ENTER */
{'\x1b', '\x1b'}, /* 0x29 ESCAPE */
{'\b', '\b'}, /* 0x2a BACKSPACE */
{'\t', '\t'}, /* 0x2b TAB */
{' ', ' '}, /* 0x2c SPACE */
{'-', '_'}, /* 0x2d MINUS */
{'=', '+'}, /* 0x2e EQUAL */
{'[', '{'}, /* 0x2f BRACKET_LEFT */
{']', '}'}, /* 0x30 BRACKET_RIGHT */
{'\\', '|'}, /* 0x31 BACKSLASH */
{'#', '~'}, /* 0x32 EUROPE_1 */
{';', ':'}, /* 0x33 SEMICOLON */
{'\'', '\"'}, /* 0x34 APOSTROPHE */
{'`', '~'}, /* 0x35 GRAVE */
{',', '<'}, /* 0x36 COMMA */
{'.', '>'}, /* 0x37 PERIOD */
{'/', '?'}, /* 0x38 SLASH */
{0, 0}, /* 0x39 CAPS_LOCK */
{0, 0}, /* 0x3a F1 */
{0, 0}, /* 0x3b F2 */
{0, 0}, /* 0x3c F3 */
{0, 0}, /* 0x3d F4 */
{0, 0}, /* 0x3e F5 */
{0, 0}, /* 0x3f F6 */
{0, 0}, /* 0x40 F7 */
{0, 0}, /* 0x41 F8 */
{0, 0}, /* 0x42 F9 */
{0, 0}, /* 0x43 F10 */
{0, 0}, /* 0x44 F11 */
{0, 0}, /* 0x45 F12 */
{0, 0}, /* 0x46 PRINT_SCREEN */
{0, 0}, /* 0x47 SCROLL_LOCK */
{0, 0}, /* 0x48 PAUSE */
{0, 0}, /* 0x49 INSERT */
{0, 0}, /* 0x4a HOME */
{0, 0}, /* 0x4b PAGE_UP */
{0, 0}, /* 0x4c DELETE */
{0, 0}, /* 0x4d END */
{0, 0}, /* 0x4e PAGE_DOWN */
{0, 0}, /* 0x4f RIGHT_ARROW */
{0, 0}, /* 0x50 LEFT_ARROW */
{0, 0}, /* 0x51 DOWN_ARROW */
{0, 0}, /* 0x52 UP_ARROW */
{0, 0}, /* 0x53 NUM_LOCK */
{'/', '/'}, /* 0x54 KP_DIVIDE */
{'*', '*'}, /* 0x55 KP_MULTIPLY */
{'-', '-'}, /* 0x56 KP_MINUS */
{'+', '+'}, /* 0x57 KP_PLUS */
{'\r', '\r'}, /* 0x58 KP_ENTER */
{'1', '1'}, /* 0x59 KP_1 */
{'2', '2'}, /* 0x5a KP_2 */
{'3', '3'}, /* 0x5b KP_3 */
{'4', '4'}, /* 0x5c KP_4 */
{'5', '5'}, /* 0x5d KP_5 */
{'6', '6'}, /* 0x5e KP_6 */
{'7', '7'}, /* 0x5f KP_7 */
{'8', '8'}, /* 0x60 KP_8 */
{'9', '9'}, /* 0x61 KP_9 */
{'0', '0'}, /* 0x62 KP_0 */
{'.', '.'}, /* 0x63 KP_DECIMAL */
};
static inline bool find_key_in_report(hid_keyboard_report_t const *report, uint8_t keycode) {
for(uint8_t i=0; i<6; i++) {
if (report->keycode[i] == keycode) return true;
}
return false;
}
bool parse_keyboard_report(hid_keyboard_report_t const *report, KeyEvent* result) {
static hid_keyboard_report_t prev_report = { 0, 0, {0} };
bool event_found = false;
for(uint8_t i=0; i<6; i++) {
if (report->keycode[i]) {
if (find_key_in_report(&prev_report, report->keycode[i])) {
// exist in previous report means the current key is holding
} else {
// not existed in previous report means the current key is pressed
bool const is_shift = report->modifier & (KEYBOARD_MODIFIER_LEFTSHIFT | KEYBOARD_MODIFIER_RIGHTSHIFT);
uint8_t ch = keycode2ascii[report->keycode[i]][is_shift ? 1 : 0];
if (ch) {
result->ascii = ch;
result->is_enter = (ch == '\r' || ch == '\n');
result->is_backspace = (ch == '\b' || ch == 127);
result->is_printable = !result->is_enter && !result->is_backspace;
event_found = true;
// We only process one key event per report for simplicity in this refactor
// Ideally we might want to queue them if multiple keys are pressed at once
break;
}
}
}
}
prev_report = *report;
return event_found;
}