From e430d13c4a256ef380b2fe7057ed9bf472d9a953 Mon Sep 17 00:00:00 2001 From: Helium314 Date: Sat, 14 Jun 2025 12:53:46 +0200 Subject: [PATCH] improvements to hardware keyboard handling --- .../event/HardwareKeyboardEventDecoder.kt | 18 +++++++++++++++++- .../keyboard/latin/inputlogic/InputLogic.java | 9 +++++---- 2 files changed, 22 insertions(+), 5 deletions(-) diff --git a/app/src/main/java/helium314/keyboard/event/HardwareKeyboardEventDecoder.kt b/app/src/main/java/helium314/keyboard/event/HardwareKeyboardEventDecoder.kt index 45dcc27b4..0578a6ffb 100644 --- a/app/src/main/java/helium314/keyboard/event/HardwareKeyboardEventDecoder.kt +++ b/app/src/main/java/helium314/keyboard/event/HardwareKeyboardEventDecoder.kt @@ -10,6 +10,8 @@ import android.view.KeyCharacterMap import android.view.KeyEvent import helium314.keyboard.keyboard.internal.keyboard_parser.floris.KeyCode import helium314.keyboard.latin.common.Constants +import helium314.keyboard.latin.utils.Log +import helium314.keyboard.latin.utils.getCustomKeyCode /** * A hardware event decoder for a hardware qwerty-ish keyboard. @@ -24,7 +26,8 @@ class HardwareKeyboardEventDecoder(val mDeviceId: Int) : HardwareEventDecoder { // KeyEvent#getUnicodeChar() does not exactly returns a unicode char, but rather a value // that includes both the unicode char in the lower 21 bits and flags in the upper bits, // hence the name "codePointAndFlags". {@see KeyEvent#getUnicodeChar()} for more info. - val codePointAndFlags = keyEvent.unicodeChar + val codePointAndFlags = keyEvent.unicodeChar.takeIf { it != 0 } + ?: Event.NOT_A_CODE_POINT // KeyEvent has 0 if no codePoint, but that's actually valid so we convert it to -1 // The keyCode is the abstraction used by the KeyEvent to represent different keys that // do not necessarily map to a unicode character. This represents a physical key, like // the key for 'A' or Space, but also Backspace or Ctrl or Caps Lock. @@ -48,8 +51,21 @@ class HardwareKeyboardEventDecoder(val mDeviceId: Int) : HardwareEventDecoder { } else Event.createHardwareKeypressEvent(codePointAndFlags, keyCode, metaState, null, isKeyRepeat) // If not Enter, then this is just a regular keypress event for a normal character // that can be committed right away, taking into account the current state. + } else if (isDpadDirection(keyCode)) { + Event.createHardwareKeypressEvent(codePointAndFlags, keyCode, metaState, null, isKeyRepeat) +// } else if (KeyEvent.isModifierKey(keyCode)) { +// todo: we could synchronize meta state across HW and SW keyboard, but that's more work for little benefit (especially with shift & caps lock) } else { Event.notHandledEvent } } + + companion object { + private fun isDpadDirection(keyCode: Int) = when (keyCode) { + KeyEvent.KEYCODE_DPAD_UP, KeyEvent.KEYCODE_DPAD_DOWN, KeyEvent.KEYCODE_DPAD_LEFT, KeyEvent.KEYCODE_DPAD_RIGHT, + KeyEvent.KEYCODE_DPAD_DOWN_LEFT, KeyEvent.KEYCODE_DPAD_DOWN_RIGHT, KeyEvent.KEYCODE_DPAD_UP_RIGHT, + KeyEvent.KEYCODE_DPAD_UP_LEFT -> true + else -> false + } + } } diff --git a/app/src/main/java/helium314/keyboard/latin/inputlogic/InputLogic.java b/app/src/main/java/helium314/keyboard/latin/inputlogic/InputLogic.java index d34c276aa..63004024a 100644 --- a/app/src/main/java/helium314/keyboard/latin/inputlogic/InputLogic.java +++ b/app/src/main/java/helium314/keyboard/latin/inputlogic/InputLogic.java @@ -780,15 +780,16 @@ public final class InputLogic { default: if (KeyCode.INSTANCE.isModifier(keyCode)) return; // continuation of previous switch case above, but modifiers are held in a separate place - final int keyEventCode = event.getMCodePoint() <= 0 - ? KeyCode.keyCodeToKeyEventCode(keyCode) - : KeyCode.codePointToKeyEventCode(event.getMCodePoint()); + final int keyEventCode = keyCode > 0 + ? keyCode + : event.getMCodePoint() >= 0 ? KeyCode.codePointToKeyEventCode(event.getMCodePoint()) + : KeyCode.keyCodeToKeyEventCode(keyCode); if (keyEventCode != KeyEvent.KEYCODE_UNKNOWN) { sendDownUpKeyEventWithMetaState(keyEventCode, event.getMMetaState()); return; } // unknown event - Log.e(TAG, "unknown event, key code: "+keyCode+", functional: "+event.isFunctionalKeyEvent()+", meta: "+event.getMMetaState()); + Log.e(TAG, "unknown event, key code: "+keyCode+", meta: "+event.getMMetaState()); if (DebugFlags.DEBUG_ENABLED) throw new RuntimeException("Unknown event"); }