From f7d6c33313a85397cf534ccddb2cc94d5dd78ab3 Mon Sep 17 00:00:00 2001 From: Darcy Wong Date: Mon, 20 Mar 2023 11:08:42 +0700 Subject: [PATCH 01/20] refactor(android/engine): Move dispatchKey --- .../keyman/engine/KMKeyboardJSHandler.java | 38 +++++++++++++++++- .../java/com/keyman/engine/KMManager.java | 39 ------------------- 2 files changed, 37 insertions(+), 40 deletions(-) diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java index 7098f2c3dc..c40a04b39e 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java @@ -205,7 +205,43 @@ public abstract class KMKeyboardJSHandler { } @JavascriptInterface - public abstract boolean dispatchKey(final int code, final int eventModifiers); + public boolean dispatchKey(final int code, final int eventModifiers) { + Handler mainLoop = new Handler(Looper.getMainLooper()); + mainLoop.post(new Runnable() { + public void run() { + if (SystemKeyboard == null) { + KMLog.LogError(TAG, "dispatchKey failed: SystemKeyboard is null"); + return; + } + + if (SystemKeyboard.subKeysWindow != null) { + return; + } + + InputConnection ic = IMService.getCurrentInputConnection(); + if (ic == null) { + if (isDebugMode()) { + Log.w(HANDLER_TAG, "insertText failed: InputConnection is null"); + } + return; + } + + SystemKeyboard.dismissHelpBubble(); + SystemKeyboard.setShouldShowHelpBubble(false); + + // Handle tab or enter since KMW didn't process it + Log.d(HANDLER_TAG, "dispatchKey called with code: " + code + ", eventModifiers: " + eventModifiers); + if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_TAB]) { + KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_TAB, 0, eventModifiers, 0, 0, 0); + ic.sendKeyEvent(event); + } else if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_ENTER]) { + KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_ENTER, 0, eventModifiers, 0, 0, 0); + ic.sendKeyEvent(event); + } + } + }); + return true; + } private void keyDownUp(int keyEventCode) { if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java index 16944ac860..163780e475 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java @@ -2271,44 +2271,5 @@ public final class KMManager { super(context, k); } private static final String HANDLER_TAG = "SWK: JS Handler"; - - @JavascriptInterface - public boolean dispatchKey(final int code, final int eventModifiers) { - Handler mainLoop = new Handler(Looper.getMainLooper()); - mainLoop.post(new Runnable() { - public void run() { - if (SystemKeyboard == null) { - KMLog.LogError(TAG, "dispatchKey failed: SystemKeyboard is null"); - return; - } - - if (SystemKeyboard.subKeysWindow != null) { - return; - } - - InputConnection ic = IMService.getCurrentInputConnection(); - if (ic == null) { - if (isDebugMode()) { - Log.w(HANDLER_TAG, "insertText failed: InputConnection is null"); - } - return; - } - - SystemKeyboard.dismissHelpBubble(); - SystemKeyboard.setShouldShowHelpBubble(false); - - // Handle tab or enter since KMW didn't process it - Log.d(HANDLER_TAG, "dispatchKey called with code: " + code + ", eventModifiers: " + eventModifiers); - if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_TAB]) { - KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_TAB, 0, eventModifiers, 0, 0, 0); - ic.sendKeyEvent(event); - } else if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_ENTER]) { - KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_ENTER, 0, eventModifiers, 0, 0, 0); - ic.sendKeyEvent(event); - } - } - }); - return true; - } } } From 3562a21791044242aafce559061dd0ce1d8731a4 Mon Sep 17 00:00:00 2001 From: Darcy Wong Date: Mon, 20 Mar 2023 11:28:04 +0700 Subject: [PATCH 02/20] refactor(android/engine): Edits for system keyboard --- .../com/keyman/engine/KMKeyboardJSHandler.java | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java index c40a04b39e..a8b6b28e6f 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java @@ -209,28 +209,30 @@ public abstract class KMKeyboardJSHandler { Handler mainLoop = new Handler(Looper.getMainLooper()); mainLoop.post(new Runnable() { public void run() { - if (SystemKeyboard == null) { + if (k == null) { KMLog.LogError(TAG, "dispatchKey failed: SystemKeyboard is null"); return; } - if (SystemKeyboard.subKeysWindow != null) { + if (k.subKeysWindow != null) { return; } - InputConnection ic = IMService.getCurrentInputConnection(); + InputConnection ic = (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) ? + KMTextView.activeView.onCreateInputConnection(new EditorInfo()) : + KMManager.getInputMethodService().getCurrentInputConnection(); if (ic == null) { - if (isDebugMode()) { - Log.w(HANDLER_TAG, "insertText failed: InputConnection is null"); + if (KMManager.isDebugMode()) { + Log.w(TAG, "insertText failed: InputConnection is null"); } return; } - SystemKeyboard.dismissHelpBubble(); - SystemKeyboard.setShouldShowHelpBubble(false); + k.dismissHelpBubble(); + k.setShouldShowHelpBubble(false); // Handle tab or enter since KMW didn't process it - Log.d(HANDLER_TAG, "dispatchKey called with code: " + code + ", eventModifiers: " + eventModifiers); + Log.d(TAG, "dispatchKey called with code: " + code + ", eventModifiers: " + eventModifiers); if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_TAB]) { KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_TAB, 0, eventModifiers, 0, 0, 0); ic.sendKeyEvent(event); From 578fbd81c1790d1c1b91765ae05df0bb7d9702fe Mon Sep 17 00:00:00 2001 From: Darcy Wong Date: Mon, 20 Mar 2023 15:49:11 +0700 Subject: [PATCH 03/20] fix(android/engine): Incorporate InApp dispatchKey --- .../keyman/engine/KMKeyboardJSHandler.java | 24 +++++++++++-- .../java/com/keyman/engine/KMManager.java | 34 ------------------- 2 files changed, 21 insertions(+), 37 deletions(-) diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java index a8b6b28e6f..3afd487c88 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java @@ -210,7 +210,7 @@ public abstract class KMKeyboardJSHandler { mainLoop.post(new Runnable() { public void run() { if (k == null) { - KMLog.LogError(TAG, "dispatchKey failed: SystemKeyboard is null"); + KMLog.LogError(TAG, "dispatchKey failed: Keyboard is null"); return; } @@ -218,6 +218,14 @@ public abstract class KMKeyboardJSHandler { return; } + if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP && + (KMTextView.activeView == null || KMTextView.activeView.getClass() != KMTextView.class)) { + if (KMTextView.activeView == null && KMManager.isDebugMode()) { + Log.w(TAG, "dispatchKey failed: activeView is null"); + } + return; + } + InputConnection ic = (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) ? KMTextView.activeView.onCreateInputConnection(new EditorInfo()) : KMManager.getInputMethodService().getCurrentInputConnection(); @@ -235,10 +243,20 @@ public abstract class KMKeyboardJSHandler { Log.d(TAG, "dispatchKey called with code: " + code + ", eventModifiers: " + eventModifiers); if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_TAB]) { KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_TAB, 0, eventModifiers, 0, 0, 0); - ic.sendKeyEvent(event); + if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { + KMTextView textView = (KMTextView)KMTextView.activeView; + textView.dispatchKeyEvent(event); + } else { + ic.sendKeyEvent(event); + } } else if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_ENTER]) { KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_ENTER, 0, eventModifiers, 0, 0, 0); - ic.sendKeyEvent(event); + if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { + KMTextView textView = (KMTextView)KMTextView.activeView; + textView.dispatchKeyEvent(event); + } else { + ic.sendKeyEvent(event); + } } } }); diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java index 163780e475..60ac19b3fe 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java @@ -2228,48 +2228,14 @@ public final class KMManager { } private static final class KMInAppKeyboardJSHandler extends KMKeyboardJSHandler { - KMInAppKeyboardJSHandler(Context context, KMKeyboard k) { super(context, k); } - private static final String HANDLER_TAG = "IAK: JS Handler"; - - @JavascriptInterface - public boolean dispatchKey(final int code, final int eventModifiers) { - Handler mainLoop = new Handler(Looper.getMainLooper()); - mainLoop.post(new Runnable() { - public void run() { - if (InAppKeyboard == null) { - KMLog.LogError(TAG, "dispatchKey failed: InAppKeyboard is null"); - return; - } - - if (InAppKeyboard.subKeysWindow != null || KMTextView.activeView == null || KMTextView.activeView.getClass() != KMTextView.class) { - if ((KMTextView.activeView == null) && isDebugMode()) { - Log.w(HANDLER_TAG, "dispatchKey failed: activeView is null"); - } - return; - } - - // Handle tab or enter since KMW didn't process it - KMTextView textView = (KMTextView) KMTextView.activeView; - if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_TAB]) { - KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_TAB, 0, eventModifiers, 0, 0, 0); - textView.dispatchKeyEvent(event); - } else if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_ENTER]) { - KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_ENTER, 0, eventModifiers, 0, 0, 0); - textView.dispatchKeyEvent(event); - } - } - }); - return true; - } } private static final class KMSystemKeyboardJSHandler extends KMKeyboardJSHandler { KMSystemKeyboardJSHandler(Context context, KMKeyboard k) { super(context, k); } - private static final String HANDLER_TAG = "SWK: JS Handler"; } } From d8ba76984733e6389c60039009cda82e4c761d6a Mon Sep 17 00:00:00 2001 From: Darcy Wong Date: Tue, 21 Mar 2023 14:16:58 +0700 Subject: [PATCH 04/20] Update android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java Co-authored-by: Marc Durdin --- .../com/keyman/engine/KMKeyboardJSHandler.java | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java index 3afd487c88..130e2b064c 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java @@ -218,12 +218,16 @@ public abstract class KMKeyboardJSHandler { return; } - if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP && - (KMTextView.activeView == null || KMTextView.activeView.getClass() != KMTextView.class)) { - if (KMTextView.activeView == null && KMManager.isDebugMode()) { - Log.w(TAG, "dispatchKey failed: activeView is null"); + if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { + if (KMTextView.activeView == null) { + if (KMManager.isDebugMode()) { + Log.w(TAG, "dispatchKey failed: activeView is null"); + } + return; + } + if (KMTextView.activeView.getClass() != KMTextView.class)) { + return; } - return; } InputConnection ic = (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) ? From ceb4d28ffd9724267358b49fa415a2f9358953ad Mon Sep 17 00:00:00 2001 From: Darcy Wong Date: Tue, 21 Mar 2023 14:53:57 +0700 Subject: [PATCH 05/20] refactor(android/engine): Make helper to get input connection --- .../keyman/engine/KMKeyboardJSHandler.java | 23 ++++++---------- .../java/com/keyman/engine/KMManager.java | 26 ++++++++++++++++++- 2 files changed, 33 insertions(+), 16 deletions(-) diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java index 130e2b064c..6f272feb7c 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java @@ -104,13 +104,9 @@ public abstract class KMKeyboardJSHandler { return; } - InputConnection ic = (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) ? - KMTextView.activeView.onCreateInputConnection(new EditorInfo()) : - KMManager.getInputMethodService().getCurrentInputConnection(); + InputConnection ic = KMManager.getInputConnection(); if (ic == null) { - if (KMManager.isDebugMode()) { - Log.w(TAG, "insertText failed: InputConnection is null"); - } + KMLog.LogError(TAG, "insertText failed: InputConnection is null"); return; } @@ -225,18 +221,14 @@ public abstract class KMKeyboardJSHandler { } return; } - if (KMTextView.activeView.getClass() != KMTextView.class)) { + if (KMTextView.activeView.getClass() != KMTextView.class) { return; } } - InputConnection ic = (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) ? - KMTextView.activeView.onCreateInputConnection(new EditorInfo()) : - KMManager.getInputMethodService().getCurrentInputConnection(); + InputConnection ic = KMManager.getInputConnection(); if (ic == null) { - if (KMManager.isDebugMode()) { - Log.w(TAG, "insertText failed: InputConnection is null"); - } + KMLog.LogError(TAG, "insertText failed: InputConnection is null"); return; } @@ -272,8 +264,9 @@ public abstract class KMKeyboardJSHandler { KMTextView textView = (KMTextView)KMTextView.activeView; textView.keyDownUp(KeyEvent.KEYCODE_ENTER); } else if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_SYSTEM) { - KMManager.getInputMethodService().getCurrentInputConnection().sendKeyEvent(new KeyEvent(KeyEvent.ACTION_DOWN, keyEventCode)); - KMManager.getInputMethodService().getCurrentInputConnection().sendKeyEvent(new KeyEvent(KeyEvent.ACTION_UP, keyEventCode)); + InputConnection ic = KMManager.getInputConnection(); + ic.sendKeyEvent(new KeyEvent(KeyEvent.ACTION_DOWN, keyEventCode)); + ic.sendKeyEvent(new KeyEvent(KeyEvent.ACTION_UP, keyEventCode)); } } diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java index 60ac19b3fe..10d465e615 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java @@ -158,6 +158,7 @@ public final class KMManager { }; protected static InputMethodService IMService; + protected static InputConnection inputConnection; private static boolean debugMode = false; private static boolean shouldAllowSetKeyboard = true; private static boolean didCopyAssets = false; @@ -459,6 +460,29 @@ public final class KMManager { } public static InputMethodService getInputMethodService() { return IMService; } + /** + * Get the input connection in the order: + * 1. Previously saved input connection + * 2. IMService (System keyboard) + * 3. KMTextView.activeView (InApp keyboard) + * @return InputConnection + */ + protected static InputConnection getInputConnection() { + if (inputConnection != null) { + return inputConnection; + } + + // Determine input connection + inputConnection = (IMService != null) ? IMService.getCurrentInputConnection() : + KMTextView.activeView.onCreateInputConnection(new EditorInfo()); + + if (inputConnection == null) { + KMLog.LogError(TAG, "inputConnection is null"); + } + + return inputConnection; + } + public static boolean executeHardwareKeystroke(int code, int shift, int lstates, int eventModifiers) { if (SystemKeyboard != null) { return executeHardwareKeystroke(code, shift, KeyboardType.KEYBOARD_TYPE_SYSTEM, lstates, eventModifiers); @@ -1981,7 +2005,7 @@ public final class KMManager { InAppKeyboardShouldIgnoreSelectionChange = false; } else if (kbType == KeyboardType.KEYBOARD_TYPE_SYSTEM) { if (SystemKeyboard != null && SystemKeyboardWebViewClient.getKeyboardLoaded() && !SystemKeyboardShouldIgnoreSelectionChange) { - InputConnection ic = (IMService != null ? IMService.getCurrentInputConnection() : null); + InputConnection ic = getInputConnection(); if (ic != null) { ExtractedText icText = ic.getExtractedText(new ExtractedTextRequest(), 0); if (icText != null) { From c5e77559b2aa47f521d4cf8b8a35ece3d50af85f Mon Sep 17 00:00:00 2001 From: Darcy Wong Date: Wed, 22 Mar 2023 09:48:50 +0700 Subject: [PATCH 06/20] refactor(android/engine): Additional cleanup and refactoring --- .../keyman/engine/KMKeyboardJSHandler.java | 78 ++++++++++--------- .../java/com/keyman/engine/KMManager.java | 34 ++++---- 2 files changed, 57 insertions(+), 55 deletions(-) diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java index 6f272feb7c..242283ff28 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java @@ -96,15 +96,11 @@ public abstract class KMKeyboardJSHandler { return; } - if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP && - (KMTextView.activeView == null || KMTextView.activeView.getClass() != KMTextView.class)) { - if (KMTextView.activeView == null && KMManager.isDebugMode()) { - Log.w(TAG, "insertText failed: activeView is null"); - } + if (!isInappKMTextViewValid(k.keyboardType)) { return; } - InputConnection ic = KMManager.getInputConnection(); + InputConnection ic = KMManager.getInputConnection(k.keyboardType); if (ic == null) { KMLog.LogError(TAG, "insertText failed: InputConnection is null"); return; @@ -146,7 +142,7 @@ public abstract class KMKeyboardJSHandler { } if (s.length() > 0 && s.charAt(0) == '\n') { - keyDownUp(KeyEvent.KEYCODE_ENTER); + keyDownUp(KeyEvent.KEYCODE_ENTER, 0); ic.endBatchEdit(); return; } @@ -214,21 +210,13 @@ public abstract class KMKeyboardJSHandler { return; } - if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { - if (KMTextView.activeView == null) { - if (KMManager.isDebugMode()) { - Log.w(TAG, "dispatchKey failed: activeView is null"); - } - return; - } - if (KMTextView.activeView.getClass() != KMTextView.class) { - return; - } + if (!isInappKMTextViewValid(k.keyboardType)) { + return; } - InputConnection ic = KMManager.getInputConnection(); + InputConnection ic = KMManager.getInputConnection(k.keyboardType); if (ic == null) { - KMLog.LogError(TAG, "insertText failed: InputConnection is null"); + KMLog.LogError(TAG, "dispatchKey failed: InputConnection is null"); return; } @@ -236,35 +224,30 @@ public abstract class KMKeyboardJSHandler { k.setShouldShowHelpBubble(false); // Handle tab or enter since KMW didn't process it - Log.d(TAG, "dispatchKey called with code: " + code + ", eventModifiers: " + eventModifiers); + if (KMManager.isDebugMode()) { + Log.d(TAG, "dispatchKey called with code: " + code + ", eventModifiers: " + eventModifiers); + } if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_TAB]) { - KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_TAB, 0, eventModifiers, 0, 0, 0); - if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { - KMTextView textView = (KMTextView)KMTextView.activeView; - textView.dispatchKeyEvent(event); - } else { - ic.sendKeyEvent(event); - } + keyDownUp(KeyEvent.KEYCODE_TAB, eventModifiers); } else if (code == KMScanCodeMap.scanCodeMap[KMScanCodeMap.KEY_ENTER]) { - KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_ENTER, 0, eventModifiers, 0, 0, 0); - if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { - KMTextView textView = (KMTextView)KMTextView.activeView; - textView.dispatchKeyEvent(event); - } else { - ic.sendKeyEvent(event); - } + keyDownUp(KeyEvent.KEYCODE_ENTER, eventModifiers); } } }); return true; } - private void keyDownUp(int keyEventCode) { + private void keyDownUp(int keyEventCode, int eventModifiers) { if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { KMTextView textView = (KMTextView)KMTextView.activeView; - textView.keyDownUp(KeyEvent.KEYCODE_ENTER); + if (keyEventCode == KeyEvent.KEYCODE_TAB) { + KeyEvent event = new KeyEvent(0, 0, 0, KeyEvent.KEYCODE_TAB, 0, eventModifiers, 0, 0, 0); + textView.dispatchKeyEvent(event); + } else { + textView.keyDownUp(keyEventCode); + } } else if (k.keyboardType == KeyboardType.KEYBOARD_TYPE_SYSTEM) { - InputConnection ic = KMManager.getInputConnection(); + InputConnection ic = KMManager.getInputConnection(KeyboardType.KEYBOARD_TYPE_SYSTEM); ic.sendKeyEvent(new KeyEvent(KeyEvent.ACTION_DOWN, keyEventCode)); ic.sendKeyEvent(new KeyEvent(KeyEvent.ACTION_UP, keyEventCode)); } @@ -344,4 +327,25 @@ public abstract class KMKeyboardJSHandler { return sequence; } + /** + * If the keyboard type is KEYBOARD_TYPE_INAPP, check if the KMTextView is valid. + * For KEYBOARD_TYPE_SYSTEM, returns true. + * @param keyboardType + * @return boolean - false if keyboard type is INAPP and KMTextView is invalid. Otherwise true + */ + private static boolean isInappKMTextViewValid(KeyboardType keyboardType) { + if (keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { + if (KMTextView.activeView == null) { + if (KMManager.isDebugMode()) { + Log.w(TAG, "activeView is null"); + } + return false; + } + if (KMTextView.activeView.getClass() != KMTextView.class) { + return false; + } + } + + return true; + } } diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java index 10d465e615..e3675cac97 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java @@ -158,7 +158,8 @@ public final class KMManager { }; protected static InputMethodService IMService; - protected static InputConnection inputConnection; + protected static InputConnection inappInputConnection; // Input Connection for InApp Keyboard + private static boolean debugMode = false; private static boolean shouldAllowSetKeyboard = true; private static boolean didCopyAssets = false; @@ -461,26 +462,23 @@ public final class KMManager { public static InputMethodService getInputMethodService() { return IMService; } /** - * Get the input connection in the order: - * 1. Previously saved input connection - * 2. IMService (System keyboard) - * 3. KMTextView.activeView (InApp keyboard) + * Get the input connection based on the keyboard type. + * For InApp keyboard, save the connection to inappInputConnection + * @param {KeyboardType} keyboard * @return InputConnection */ - protected static InputConnection getInputConnection() { - if (inputConnection != null) { - return inputConnection; + protected static InputConnection getInputConnection(KeyboardType keyboard) { + if (keyboard == KeyboardType.KEYBOARD_TYPE_INAPP) { + if (inappInputConnection == null) { + inappInputConnection = KMTextView.activeView.onCreateInputConnection(new EditorInfo()); + } + return inappInputConnection; + } else if (keyboard == KeyboardType.KEYBOARD_TYPE_SYSTEM && IMService != null) { + return IMService.getCurrentInputConnection(); } - // Determine input connection - inputConnection = (IMService != null) ? IMService.getCurrentInputConnection() : - KMTextView.activeView.onCreateInputConnection(new EditorInfo()); - - if (inputConnection == null) { - KMLog.LogError(TAG, "inputConnection is null"); - } - - return inputConnection; + KMLog.LogError(TAG, "Unable to determine input connection"); + return null; } public static boolean executeHardwareKeystroke(int code, int shift, int lstates, int eventModifiers) { @@ -2005,7 +2003,7 @@ public final class KMManager { InAppKeyboardShouldIgnoreSelectionChange = false; } else if (kbType == KeyboardType.KEYBOARD_TYPE_SYSTEM) { if (SystemKeyboard != null && SystemKeyboardWebViewClient.getKeyboardLoaded() && !SystemKeyboardShouldIgnoreSelectionChange) { - InputConnection ic = getInputConnection(); + InputConnection ic = getInputConnection(KeyboardType.KEYBOARD_TYPE_SYSTEM); if (ic != null) { ExtractedText icText = ic.getExtractedText(new ExtractedTextRequest(), 0); if (icText != null) { From f48609eb07d162ec485da9074ebcdb51a0198253 Mon Sep 17 00:00:00 2001 From: Darcy Wong Date: Wed, 22 Mar 2023 14:52:12 +0700 Subject: [PATCH 07/20] refactor(android/engine): Make KMKeyboardJSHandler a normal class --- .../keyman/engine/KMKeyboardJSHandler.java | 2 +- .../java/com/keyman/engine/KMManager.java | 34 +++++-------------- 2 files changed, 9 insertions(+), 27 deletions(-) diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java index 242283ff28..e073008982 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMKeyboardJSHandler.java @@ -23,7 +23,7 @@ import com.keyman.engine.KMManager.KeyboardType; import com.keyman.engine.util.CharSequenceUtil; import com.keyman.engine.util.KMLog; -public abstract class KMKeyboardJSHandler { +public class KMKeyboardJSHandler { private Context context; private KMKeyboard k = null; private static int KM_VIBRATE_DURATION = 100; // milliseconds diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java index e3675cac97..9f84640c5b 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java @@ -423,13 +423,11 @@ public final class KMManager { didCopyAssets = true; } - if (keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP) { - initInAppKeyboard(appContext); - } else if (keyboardType == KeyboardType.KEYBOARD_TYPE_SYSTEM) { - initSystemKeyboard(appContext); - } else { + if (keyboardType == KeyboardType.KEYBOARD_TYPE_UNDEFINED) { String msg = "Cannot initialize: Invalid keyboard type"; KMLog.LogError(TAG, msg); + } else { + initKeyboard(appContext, keyboardType); } JSONUtils.initialize(new File(getPackagesDir())); @@ -631,8 +629,8 @@ public final class KMManager { return params; } - private static void initInAppKeyboard(Context appContext) { - if (InAppKeyboard == null) { + private static void initKeyboard(Context appContext, KeyboardType keyboardType) { + if (keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP && InAppKeyboard == null) { InAppKeyboard = new KMKeyboard(appContext, KeyboardType.KEYBOARD_TYPE_INAPP); RelativeLayout.LayoutParams params = getKeyboardLayoutParams(); InAppKeyboard.setLayoutParams(params); @@ -640,15 +638,11 @@ public final class KMManager { InAppKeyboard.setHorizontalScrollBarEnabled(false); InAppKeyboardWebViewClient = new KMKeyboardWebViewClient(appContext, KeyboardType.KEYBOARD_TYPE_INAPP); InAppKeyboard.setWebViewClient(InAppKeyboardWebViewClient); - InAppKeyboard.addJavascriptInterface(new KMInAppKeyboardJSHandler(appContext, InAppKeyboard), "jsInterface"); + InAppKeyboard.addJavascriptInterface(new KMKeyboardJSHandler(appContext, InAppKeyboard), "jsInterface"); InAppKeyboard.loadKeyboard(); setEngineWebViewVersionStatus(appContext, InAppKeyboard); - } - } - - private static void initSystemKeyboard(Context appContext) { - if (SystemKeyboard == null) { + } else if (keyboardType == KeyboardType.KEYBOARD_TYPE_SYSTEM && SystemKeyboard == null) { SystemKeyboard = new KMKeyboard(appContext, KeyboardType.KEYBOARD_TYPE_SYSTEM); RelativeLayout.LayoutParams params = getKeyboardLayoutParams(); SystemKeyboard.setLayoutParams(params); @@ -656,7 +650,7 @@ public final class KMManager { SystemKeyboard.setHorizontalScrollBarEnabled(false); SystemKeyboardWebViewClient = new KMKeyboardWebViewClient(appContext, KeyboardType.KEYBOARD_TYPE_SYSTEM); SystemKeyboard.setWebViewClient(SystemKeyboardWebViewClient); - SystemKeyboard.addJavascriptInterface(new KMSystemKeyboardJSHandler(appContext, SystemKeyboard), "jsInterface"); + SystemKeyboard.addJavascriptInterface(new KMKeyboardJSHandler(appContext, SystemKeyboard), "jsInterface"); SystemKeyboard.loadKeyboard(); setEngineWebViewVersionStatus(appContext, SystemKeyboard); @@ -2248,16 +2242,4 @@ public final class KMManager { globeKeyState = GlobeKeyState.GLOBE_KEY_STATE_UP; } } - - private static final class KMInAppKeyboardJSHandler extends KMKeyboardJSHandler { - KMInAppKeyboardJSHandler(Context context, KMKeyboard k) { - super(context, k); - } - } - - private static final class KMSystemKeyboardJSHandler extends KMKeyboardJSHandler { - KMSystemKeyboardJSHandler(Context context, KMKeyboard k) { - super(context, k); - } - } } From 468bb37ddfa12f8bf00c0f006fd936c5ba025f9a Mon Sep 17 00:00:00 2001 From: Eberhard Beilharz Date: Wed, 22 Mar 2023 19:28:24 +0100 Subject: [PATCH 08/20] chore(linux): Run and ignore autopkgtests on s390x This change allows the autopkgtests to run on s390x architecture but immediately exits the test with a successful return code. (cherry picked from commit 2f716b3e517ecc4ad4c3a86479533d37fc55a4bc) --- linux/debian/changelog | 8 +++++++- linux/debian/tests/control | 2 +- linux/debian/tests/test-build | 8 ++++++++ 3 files changed, 16 insertions(+), 2 deletions(-) diff --git a/linux/debian/changelog b/linux/debian/changelog index 9e6e7f550c..0366f33d58 100644 --- a/linux/debian/changelog +++ b/linux/debian/changelog @@ -1,7 +1,13 @@ +keyman (16.0.139-3) unstable; urgency=medium + + * debian/tests: Run autopkgtests on s390x but immediately return + + -- Eberhard Beilharz Wed, 22 Mar 2023 19:25:02 +0100 + keyman (16.0.139-2) unstable; urgency=medium * Don't build on s390x because Keyman doesn't work on big-endian architectures - (upstream bug https://github.com/keymanapp/keyman/issues/5111) + (upstream bug https://github.com/keymanapp/keyman/issues/5111) -- Eberhard Beilharz Mon, 20 Mar 2023 19:54:44 +0100 diff --git a/linux/debian/tests/control b/linux/debian/tests/control index c1164c9c8e..904f4536c7 100644 --- a/linux/debian/tests/control +++ b/linux/debian/tests/control @@ -2,4 +2,4 @@ Tests: test-build Depends: @, build-essential, pkg-config, -Architecture: amd64 arm64 armel armhf i386 mips64el mipsel ppc64el riscv64 +Architecture: any diff --git a/linux/debian/tests/test-build b/linux/debian/tests/test-build index db0a343849..cc9b4f6626 100644 --- a/linux/debian/tests/test-build +++ b/linux/debian/tests/test-build @@ -9,6 +9,14 @@ WORKDIR=$(mktemp -d) trap "rm -rf $WORKDIR" 0 INT QUIT ABRT PIPE TERM cd "$WORKDIR" +if [ "$(dpkg --print-architecture)" == "s390x" ]; then + # libkmnkbp doesn't support big endian architectures + # (https://github.com/keymanapp/keyman/issues/5111), so it isn't + # build on s390x and we can't run the tests. Simply ignore. + echo "Not supported on s390x: OK" + exit 0 +fi + # Test all include files are available cat < keymantest.c #include From 4cc90f2722b4f861242b89289ef2c83c1b039244 Mon Sep 17 00:00:00 2001 From: Marc Durdin Date: Thu, 23 Mar 2023 16:53:32 +1100 Subject: [PATCH 09/20] chore(common): use mac /usr/bin/stat rather than homebrew version --- resources/shellHelperFunctions.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/resources/shellHelperFunctions.sh b/resources/shellHelperFunctions.sh index d7612c74f5..3a05faaa8b 100755 --- a/resources/shellHelperFunctions.sh +++ b/resources/shellHelperFunctions.sh @@ -126,7 +126,7 @@ write_download_info() { FILE_EXTENSION="${BASE_FILE##*.}" - FILE_SIZE=$(stat -f"%z" "${BASE_PATH}/${BASE_FILE}") + FILE_SIZE=$(/usr/bin/stat -f"%z" "${BASE_PATH}/${BASE_FILE}") MD5_HASH=$(md5 -q "${BASE_PATH}/${BASE_FILE}") if [[ -f "$DOWNLOAD_INFO_FILEPATH" ]]; then From 631211c1ac0babf986698d439b7c11befc96e19e Mon Sep 17 00:00:00 2001 From: Keyman Build Agent Date: Thu, 23 Mar 2023 14:01:46 -0400 Subject: [PATCH 10/20] auto: increment master version to 17.0.76 --- HISTORY.md | 4 ++++ VERSION.md | 2 +- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/HISTORY.md b/HISTORY.md index 44ebb2af0e..aea894d467 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -1,5 +1,9 @@ # Keyman Version History +## 17.0.75 alpha 2023-03-23 + +* chore(common): define BUILDER_CONFIGURATION env var (#8496) + ## 17.0.74 alpha 2023-03-22 * chore(windows): update sentry-native to 0.6.0 (#8464) diff --git a/VERSION.md b/VERSION.md index 4dc77ece12..fd883fd259 100644 --- a/VERSION.md +++ b/VERSION.md @@ -1 +1 @@ -17.0.75 \ No newline at end of file +17.0.76 \ No newline at end of file From 6e611adc655855f0de49db1325ccd79fa0732c8d Mon Sep 17 00:00:00 2001 From: Marc Durdin Date: Fri, 24 Mar 2023 15:43:07 +0700 Subject: [PATCH 11/20] chore(mac): update stat path --- mac/Keyman4MacIM/write-download_info.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mac/Keyman4MacIM/write-download_info.sh b/mac/Keyman4MacIM/write-download_info.sh index 716caea1a9..d185185ffb 100755 --- a/mac/Keyman4MacIM/write-download_info.sh +++ b/mac/Keyman4MacIM/write-download_info.sh @@ -81,7 +81,7 @@ DOWNLOAD_INFO_FILEPATH="${DMG_FILEPATH}.download_info" if [[ ! -f "$DMG_FILEPATH" ]]; then builder_die "Cannot compute file size or MD5 for non-existent DMG file: $DMG_FILEPATH" fi -DMG_FILE_SIZE=$(stat -f"%z" "$DMG_FILEPATH") +DMG_FILE_SIZE=$(/usr/bin/stat -f"%z" "$DMG_FILEPATH") DMG_MD5=$(md5 -q "$DMG_FILEPATH") if [[ -f "$DOWNLOAD_INFO_FILEPATH" ]]; then From 25cf7d2ed75ba8d2837b2ddb49faa4181be28906 Mon Sep 17 00:00:00 2001 From: Eberhard Beilharz Date: Fri, 24 Mar 2023 16:04:10 +0100 Subject: [PATCH 12/20] chore(linux): Revert "Run and ignore autopkgtests on s390x" This reverts commit 2f716b3e517ecc4ad4c3a86479533d37fc55a4bc. (cherry picked from commit 7a9f366c6a2b278c68e5e8421563908821125a94) --- linux/debian/changelog | 6 ++++++ linux/debian/tests/control | 2 +- linux/debian/tests/test-build | 8 -------- 3 files changed, 7 insertions(+), 9 deletions(-) diff --git a/linux/debian/changelog b/linux/debian/changelog index 0366f33d58..9f69cc9a12 100644 --- a/linux/debian/changelog +++ b/linux/debian/changelog @@ -1,3 +1,9 @@ +keyman (16.0.139-4) unstable; urgency=medium + + * debian/tests: Revert previous change and ignore s390x from autopkgtests + + -- Eberhard Beilharz Fri, 24 Mar 2023 16:05:07 +0100 + keyman (16.0.139-3) unstable; urgency=medium * debian/tests: Run autopkgtests on s390x but immediately return diff --git a/linux/debian/tests/control b/linux/debian/tests/control index 904f4536c7..c1164c9c8e 100644 --- a/linux/debian/tests/control +++ b/linux/debian/tests/control @@ -2,4 +2,4 @@ Tests: test-build Depends: @, build-essential, pkg-config, -Architecture: any +Architecture: amd64 arm64 armel armhf i386 mips64el mipsel ppc64el riscv64 diff --git a/linux/debian/tests/test-build b/linux/debian/tests/test-build index cc9b4f6626..db0a343849 100644 --- a/linux/debian/tests/test-build +++ b/linux/debian/tests/test-build @@ -9,14 +9,6 @@ WORKDIR=$(mktemp -d) trap "rm -rf $WORKDIR" 0 INT QUIT ABRT PIPE TERM cd "$WORKDIR" -if [ "$(dpkg --print-architecture)" == "s390x" ]; then - # libkmnkbp doesn't support big endian architectures - # (https://github.com/keymanapp/keyman/issues/5111), so it isn't - # build on s390x and we can't run the tests. Simply ignore. - echo "Not supported on s390x: OK" - exit 0 -fi - # Test all include files are available cat < keymantest.c #include From 255fabe6fe9ef4af4dbe580d49142d7fdd974f7b Mon Sep 17 00:00:00 2001 From: Eberhard Beilharz Date: Fri, 24 Mar 2023 16:46:15 +0100 Subject: [PATCH 13/20] chore(linux): Remove python3-raven dependency Now that we no longer support Ubuntu 18.04 Bionic we can remove the python3-raven dependency. --- linux/debian/control | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/linux/debian/control b/linux/debian/control index 58bb436217..6fdd2bc817 100644 --- a/linux/debian/control +++ b/linux/debian/control @@ -22,7 +22,7 @@ Build-Depends: python3-pil, python3-pip, python3-qrcode, - python3-sentry-sdk (>= 1.1) | python3-raven, + python3-sentry-sdk (>= 1.1), python3-requests, python3-requests-cache, python3-setuptools, @@ -85,7 +85,7 @@ Depends: keyman-engine, python3-bs4, python3-gi, - python3-sentry-sdk (>= 1.1) | python3-raven, + python3-sentry-sdk (>= 1.1), dbus-x11, ${misc:Depends}, ${python3:Depends}, From 1b9dd00b08e0571842f05bfe38c40d5bbc53fc29 Mon Sep 17 00:00:00 2001 From: Keyman Build Agent Date: Fri, 24 Mar 2023 14:01:50 -0400 Subject: [PATCH 14/20] auto: increment master version to 17.0.77 --- HISTORY.md | 5 +++++ VERSION.md | 2 +- 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/HISTORY.md b/HISTORY.md index aea894d467..571a1dec39 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -1,5 +1,10 @@ # Keyman Version History +## 17.0.76 alpha 2023-03-24 + +* chore(linux): Run and ignore autopkgtests on s390x (#8492) +* refactor(android/engine): Consolidate dispatchKey (#8483) + ## 17.0.75 alpha 2023-03-23 * chore(common): define BUILDER_CONFIGURATION env var (#8496) diff --git a/VERSION.md b/VERSION.md index fd883fd259..0b4c1f08cf 100644 --- a/VERSION.md +++ b/VERSION.md @@ -1 +1 @@ -17.0.76 \ No newline at end of file +17.0.77 \ No newline at end of file From ffa121d74c60b6303622ceec911df227551a62b6 Mon Sep 17 00:00:00 2001 From: Keyman Build Agent Date: Sat, 25 Mar 2023 14:01:40 -0400 Subject: [PATCH 15/20] auto: increment master version to 17.0.78 --- HISTORY.md | 4 ++++ VERSION.md | 2 +- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/HISTORY.md b/HISTORY.md index 571a1dec39..b7b18839b0 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -1,5 +1,9 @@ # Keyman Version History +## 17.0.77 alpha 2023-03-25 + +* chore(common): use mac /usr/bin/stat rather than homebrew version (#8498) + ## 17.0.76 alpha 2023-03-24 * chore(linux): Run and ignore autopkgtests on s390x (#8492) diff --git a/VERSION.md b/VERSION.md index 0b4c1f08cf..e7b0d3c9e8 100644 --- a/VERSION.md +++ b/VERSION.md @@ -1 +1 @@ -17.0.77 \ No newline at end of file +17.0.78 \ No newline at end of file From 72c6ad17d4d5a93a36a5ba8d00935f8cd993dcfe Mon Sep 17 00:00:00 2001 From: Darcy Wong Date: Mon, 27 Mar 2023 10:56:13 +0700 Subject: [PATCH 16/20] refactor(android/engine): Apply suggestions --- .../java/com/keyman/engine/KMManager.java | 43 ++++++++++--------- 1 file changed, 23 insertions(+), 20 deletions(-) diff --git a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java index 9f84640c5b..8ad90bf6cc 100644 --- a/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java +++ b/android/KMEA/app/src/main/java/com/keyman/engine/KMManager.java @@ -630,31 +630,34 @@ public final class KMManager { } private static void initKeyboard(Context appContext, KeyboardType keyboardType) { + KMKeyboard keyboard = null; + KMKeyboardWebViewClient webViewClient = null; + if (keyboardType == KeyboardType.KEYBOARD_TYPE_INAPP && InAppKeyboard == null) { InAppKeyboard = new KMKeyboard(appContext, KeyboardType.KEYBOARD_TYPE_INAPP); - RelativeLayout.LayoutParams params = getKeyboardLayoutParams(); - InAppKeyboard.setLayoutParams(params); - InAppKeyboard.setVerticalScrollBarEnabled(false); - InAppKeyboard.setHorizontalScrollBarEnabled(false); - InAppKeyboardWebViewClient = new KMKeyboardWebViewClient(appContext, KeyboardType.KEYBOARD_TYPE_INAPP); - InAppKeyboard.setWebViewClient(InAppKeyboardWebViewClient); - InAppKeyboard.addJavascriptInterface(new KMKeyboardJSHandler(appContext, InAppKeyboard), "jsInterface"); - InAppKeyboard.loadKeyboard(); - - setEngineWebViewVersionStatus(appContext, InAppKeyboard); + InAppKeyboardWebViewClient = new KMKeyboardWebViewClient(appContext, keyboardType); + keyboard = InAppKeyboard; + webViewClient = InAppKeyboardWebViewClient; } else if (keyboardType == KeyboardType.KEYBOARD_TYPE_SYSTEM && SystemKeyboard == null) { SystemKeyboard = new KMKeyboard(appContext, KeyboardType.KEYBOARD_TYPE_SYSTEM); - RelativeLayout.LayoutParams params = getKeyboardLayoutParams(); - SystemKeyboard.setLayoutParams(params); - SystemKeyboard.setVerticalScrollBarEnabled(false); - SystemKeyboard.setHorizontalScrollBarEnabled(false); - SystemKeyboardWebViewClient = new KMKeyboardWebViewClient(appContext, KeyboardType.KEYBOARD_TYPE_SYSTEM); - SystemKeyboard.setWebViewClient(SystemKeyboardWebViewClient); - SystemKeyboard.addJavascriptInterface(new KMKeyboardJSHandler(appContext, SystemKeyboard), "jsInterface"); - SystemKeyboard.loadKeyboard(); - - setEngineWebViewVersionStatus(appContext, SystemKeyboard); + SystemKeyboardWebViewClient = new KMKeyboardWebViewClient(appContext, keyboardType); + keyboard = SystemKeyboard; + webViewClient = SystemKeyboardWebViewClient; } + + if (keyboard == null) { + return; + } + + RelativeLayout.LayoutParams params = getKeyboardLayoutParams(); + keyboard.setLayoutParams(params); + keyboard.setVerticalScrollBarEnabled(false); + keyboard.setHorizontalScrollBarEnabled(false); + keyboard.setWebViewClient(webViewClient); + keyboard.addJavascriptInterface(new KMKeyboardJSHandler(appContext, keyboard), "jsInterface"); + keyboard.loadKeyboard(); + + setEngineWebViewVersionStatus(appContext, keyboard); } public static String getLanguagePredictionPreferenceKey(String langID) { From 6afae82b2ebd8dd51fa2e43f9be762aae64bbe9b Mon Sep 17 00:00:00 2001 From: Eberhard Beilharz Date: Mon, 27 Mar 2023 18:41:05 +0200 Subject: [PATCH 17/20] docs(linux): Update minimum required Ubuntu version --- docs/build/linux-ubuntu.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/build/linux-ubuntu.md b/docs/build/linux-ubuntu.md index d5cb971f8c..153fc5ccbd 100644 --- a/docs/build/linux-ubuntu.md +++ b/docs/build/linux-ubuntu.md @@ -21,7 +21,7 @@ The following projects **cannot** be built on Linux: ## System Requirements -* Minimum Ubuntu version: Ubuntu 18.04 +* Minimum Ubuntu version: Ubuntu 20.04 Other Linux distributions will also work if appropriate dependencies are installed. From de28cabb20dc34f328c63890a6b8f291d3c3b3bc Mon Sep 17 00:00:00 2001 From: Keyman Build Agent Date: Mon, 27 Mar 2023 14:01:50 -0400 Subject: [PATCH 18/20] auto: increment master version to 17.0.79 --- HISTORY.md | 5 +++++ VERSION.md | 2 +- 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/HISTORY.md b/HISTORY.md index b7b18839b0..4a29cbb000 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -1,5 +1,10 @@ # Keyman Version History +## 17.0.78 alpha 2023-03-27 + +* chore(linux): Remove python3-raven dependency (#8507) +* refactor(android/engine): Make KMKeyboardJSHandler a normal class (#8494) + ## 17.0.77 alpha 2023-03-25 * chore(common): use mac /usr/bin/stat rather than homebrew version (#8498) diff --git a/VERSION.md b/VERSION.md index e7b0d3c9e8..78f04483ed 100644 --- a/VERSION.md +++ b/VERSION.md @@ -1 +1 @@ -17.0.78 \ No newline at end of file +17.0.79 \ No newline at end of file From 8f4a4b3e6ce028f98c6d466cd7c8e7105dea45cd Mon Sep 17 00:00:00 2001 From: Eberhard Beilharz Date: Tue, 28 Mar 2023 09:21:09 +0200 Subject: [PATCH 19/20] docs(linux): Update common questions - add Ubuntu 18.04 as being last supported in Keyman 16 - clarify that km-config needs to be started from command line in order to disable error reporting --- linux/help/common/index.md | 20 +++++++++++++------- 1 file changed, 13 insertions(+), 7 deletions(-) diff --git a/linux/help/common/index.md b/linux/help/common/index.md index 7bbc820dd0..a25eb07da0 100644 --- a/linux/help/common/index.md +++ b/linux/help/common/index.md @@ -57,22 +57,28 @@ sudo dpkg --purge ibus-kmfl libkmfl ## Q. What Linux distros will Keyman work with? -**A.** Keyman runs on Debian, Ubuntu, Wasta Linux and can be compiled to run from source in most distributions. +**A.** Keyman runs on Debian, Ubuntu, Wasta Linux and can be compiled to run +from source in most distributions. **Note:** Keyman for Linux no longer supports Ubuntu 16.04 LTS (Xenial Xerus). +Keyman 16 was the last version that supports Ubuntu 18.04 LTS (Bionic Beaver). ## Q. Will my existing Windows Keyman keyboard work with Keyman for Linux? -**A.** Most keyboards will work without change. A small subset of keyboards require features which -are not yet available in Keyman for Linux. These features will be progressively implemented. +**A.** Most keyboards will work without change. A small subset of keyboards +require features which are not yet available in Keyman for Linux. These +features will be progressively implemented. ## Q. How can I disable automatically reporting errors? -**A.** If Keyman crashes, it will automatically send a report to the development team. This report -is anonymous and contains only technical details relating to the crash. It does not include keystroke -data or personally identifying data. If you don't want these automatic error reports to be sent you -can set the environment variable `KEYMAN_NOSENTRY`: +**A.** If Keyman crashes, it will automatically send a report to the development +team. This report is anonymous and contains only technical details relating to +the crash. It does not include keystroke data or personally identifying data. If +you don't want these automatic error reports to be sent you can set the +environment variable `KEYMAN_NOSENTRY` and start `km-config` from +the command line: ```bash export KEYMAN_NOSENTRY=1 +km-config ``` From cbe98f397551bed20f1c82030451e7c0e33ef141 Mon Sep 17 00:00:00 2001 From: Keyman Build Agent Date: Tue, 28 Mar 2023 14:02:08 -0400 Subject: [PATCH 20/20] auto: increment master version to 17.0.80 --- HISTORY.md | 6 ++++++ VERSION.md | 2 +- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/HISTORY.md b/HISTORY.md index 4a29cbb000..fed4a177fb 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -1,5 +1,11 @@ # Keyman Version History +## 17.0.79 alpha 2023-03-28 + +* chore(linux): Revert "Run and ignore autopkgtests on s390x" (#8506) +* docs(linux): Update minimum required Ubuntu version (#8526) +* docs(linux): Update common questions (#8532) + ## 17.0.78 alpha 2023-03-27 * chore(linux): Remove python3-raven dependency (#8507) diff --git a/VERSION.md b/VERSION.md index 78f04483ed..31498260bd 100644 --- a/VERSION.md +++ b/VERSION.md @@ -1 +1 @@ -17.0.79 \ No newline at end of file +17.0.80 \ No newline at end of file