Skip to content

Commit 400d99e

Browse files
author
Seth Schroeder
committed
the input method can act as another source of key events for Key Mapper
1 parent e680494 commit 400d99e

3 files changed

Lines changed: 80 additions & 16 deletions

File tree

app/src/main/AndroidManifest.xml

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,13 +15,14 @@
1515
-->
1616

1717
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
18-
coreApp="true"
19-
package="io.github.sds100.keymapper.inputmethod.latin">
18+
coreApp="true"
19+
package="io.github.sds100.keymapper.inputmethod.latin">
2020

2121
<uses-permission android:name="android.permission.READ_USER_DICTIONARY" />
2222
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
2323
<uses-permission android:name="android.permission.VIBRATE" />
2424
<uses-permission android:name="android.permission.WRITE_USER_DICTIONARY" />
25+
<uses-permission android:name="io.github.sds100.keymapper.KEY_EVENT_RECEIVER" />
2526

2627
<!-- A signature-protected permission to ask AOSP Keyboard to close the software keyboard.
2728
To use this, add the following line into calling application's AndroidManifest.xml
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
package io.github.sds100.keymapper.api;
2+
3+
import android.view.KeyEvent;
4+
5+
interface IKeyEventReceiver {
6+
boolean onKeyEvent(in KeyEvent event);
7+
}

app/src/main/java/io/github/sds100/keymapper/inputmethod/latin/LatinIME.java

Lines changed: 70 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -16,13 +16,19 @@
1616

1717
package io.github.sds100.keymapper.inputmethod.latin;
1818

19+
import static io.github.sds100.keymapper.inputmethod.latin.common.Constants.ImeOption.FORCE_ASCII;
20+
import static io.github.sds100.keymapper.inputmethod.latin.common.Constants.ImeOption.NO_MICROPHONE;
21+
import static io.github.sds100.keymapper.inputmethod.latin.common.Constants.ImeOption.NO_MICROPHONE_COMPAT;
22+
1923
import android.app.AlertDialog;
2024
import android.content.BroadcastReceiver;
25+
import android.content.ComponentName;
2126
import android.content.Context;
2227
import android.content.DialogInterface;
2328
import android.content.DialogInterface.OnClickListener;
2429
import android.content.Intent;
2530
import android.content.IntentFilter;
31+
import android.content.ServiceConnection;
2632
import android.content.res.Configuration;
2733
import android.content.res.Resources;
2834
import android.graphics.Color;
@@ -33,7 +39,7 @@
3339
import android.os.IBinder;
3440
import android.os.Message;
3541
import android.os.Process;
36-
import android.os.SystemClock;
42+
import android.os.RemoteException;
3743
import android.text.InputType;
3844
import android.util.Log;
3945
import android.util.PrintWriterPrinter;
@@ -50,6 +56,16 @@
5056
import android.view.inputmethod.InputConnection;
5157
import android.view.inputmethod.InputMethodSubtype;
5258

59+
import java.io.FileDescriptor;
60+
import java.io.PrintWriter;
61+
import java.util.ArrayList;
62+
import java.util.List;
63+
import java.util.Locale;
64+
import java.util.concurrent.TimeUnit;
65+
66+
import javax.annotation.Nonnull;
67+
68+
import io.github.sds100.keymapper.api.IKeyEventReceiver;
5369
import io.github.sds100.keymapper.inputmethod.accessibility.AccessibilityUtils;
5470
import io.github.sds100.keymapper.inputmethod.annotations.UsedForTesting;
5571
import io.github.sds100.keymapper.inputmethod.compat.EditorInfoCompatUtils;
@@ -92,19 +108,6 @@
92108
import io.github.sds100.keymapper.inputmethod.latin.utils.SubtypeLocaleUtils;
93109
import io.github.sds100.keymapper.inputmethod.latin.utils.ViewLayoutUtils;
94110

95-
import java.io.FileDescriptor;
96-
import java.io.PrintWriter;
97-
import java.util.ArrayList;
98-
import java.util.List;
99-
import java.util.Locale;
100-
import java.util.concurrent.TimeUnit;
101-
102-
import javax.annotation.Nonnull;
103-
104-
import static io.github.sds100.keymapper.inputmethod.latin.common.Constants.ImeOption.FORCE_ASCII;
105-
import static io.github.sds100.keymapper.inputmethod.latin.common.Constants.ImeOption.NO_MICROPHONE;
106-
import static io.github.sds100.keymapper.inputmethod.latin.common.Constants.ImeOption.NO_MICROPHONE_COMPAT;
107-
108111
/**
109112
* Input method implementation for Qwerty'ish keyboard.
110113
*/
@@ -214,8 +217,28 @@ public void onReceive(Context context, Intent intent) {
214217
}
215218
}
216219
}
220+
217221
final RestartAfterDeviceUnlockReceiver mRestartAfterDeviceUnlockReceiver = new RestartAfterDeviceUnlockReceiver();
218222

223+
private final Object keyEventReceiverLock = new Object();
224+
private IKeyEventReceiver keyEventReceiverBinder = null;
225+
226+
private final ServiceConnection keyEventReceiverConnection = new ServiceConnection() {
227+
@Override
228+
public void onServiceConnected(ComponentName name, IBinder service) {
229+
synchronized (keyEventReceiverLock) {
230+
keyEventReceiverBinder = IKeyEventReceiver.Stub.asInterface(service);
231+
}
232+
}
233+
234+
@Override
235+
public void onServiceDisconnected(ComponentName name) {
236+
synchronized (keyEventReceiverLock) {
237+
keyEventReceiverBinder = null;
238+
}
239+
}
240+
};
241+
219242
final static class KeyMapperBroadcastReceiver extends BroadcastReceiver {
220243
private final InputMethodService mIms;
221244

@@ -759,6 +782,15 @@ public void onCreate() {
759782

760783
registerReceiver(mKeyMapperBroadcastReceiver, keyMapperIntentFilter);
761784

785+
try {
786+
ComponentName keyEventReceiverComponent = new ComponentName("io.github.sds100.keymapper", "io.github.sds100.keymapper.api.KeyEventReceiver");
787+
Intent keyEventReceiverServiceIntent = new Intent();
788+
keyEventReceiverServiceIntent.setComponent(keyEventReceiverComponent);
789+
bindService(keyEventReceiverServiceIntent, keyEventReceiverConnection, 0);
790+
} catch (SecurityException e) {
791+
Log.e(TAG, e.toString());
792+
}
793+
762794
StatsUtils.onCreate(mSettings.getCurrent(), mRichImm);
763795
}
764796

@@ -871,6 +903,7 @@ public void onDestroy() {
871903
unregisterReceiver(mRestartAfterDeviceUnlockReceiver);
872904
unregisterReceiver(mKeyMapperBroadcastReceiver);
873905
mStatsUtilsManager.onDestroy(this /* context */);
906+
unbindService(keyEventReceiverConnection);
874907
super.onDestroy();
875908
}
876909

@@ -1889,6 +1922,17 @@ private HardwareEventDecoder getHardwareKeyEventDecoder(final int deviceId) {
18891922
// Hooks for hardware keyboard
18901923
@Override
18911924
public boolean onKeyDown(final int keyCode, final KeyEvent keyEvent) {
1925+
1926+
if (keyEventReceiverBinder != null) {
1927+
try {
1928+
if (keyEventReceiverBinder.onKeyEvent(keyEvent)) {
1929+
return true;
1930+
}
1931+
} catch (RemoteException e) {
1932+
1933+
}
1934+
}
1935+
18921936
if (mEmojiAltPhysicalKeyDetector == null) {
18931937
mEmojiAltPhysicalKeyDetector = new EmojiAltPhysicalKeyDetector(
18941938
getApplicationContext().getResources());
@@ -1909,11 +1953,22 @@ public boolean onKeyDown(final int keyCode, final KeyEvent keyEvent) {
19091953
mHandler);
19101954
return true;
19111955
}
1956+
19121957
return super.onKeyDown(keyCode, keyEvent);
19131958
}
19141959

19151960
@Override
19161961
public boolean onKeyUp(final int keyCode, final KeyEvent keyEvent) {
1962+
if (keyEventReceiverBinder != null) {
1963+
try {
1964+
if (keyEventReceiverBinder.onKeyEvent(keyEvent)) {
1965+
return true;
1966+
}
1967+
} catch (RemoteException e) {
1968+
1969+
}
1970+
}
1971+
19171972
if (mEmojiAltPhysicalKeyDetector == null) {
19181973
mEmojiAltPhysicalKeyDetector = new EmojiAltPhysicalKeyDetector(
19191974
getApplicationContext().getResources());
@@ -1926,6 +1981,7 @@ public boolean onKeyUp(final int keyCode, final KeyEvent keyEvent) {
19261981
if (mInputLogic.mCurrentlyPressedHardwareKeys.remove(keyIdentifier)) {
19271982
return true;
19281983
}
1984+
19291985
return super.onKeyUp(keyCode, keyEvent);
19301986
}
19311987

0 commit comments

Comments
 (0)