WIP sendBroadcast

This commit is contained in:
Romain Vimont 2020-11-09 21:33:25 +01:00
commit 160ae02b93
3 changed files with 42 additions and 6 deletions

View file

@ -1,5 +1,8 @@
package com.genymobile.scrcpy; package com.genymobile.scrcpy;
import com.genymobile.scrcpy.wrappers.ServiceManager;
import android.content.Intent;
import android.os.Build; import android.os.Build;
import android.os.SystemClock; import android.os.SystemClock;
import android.view.InputDevice; import android.view.InputDevice;
@ -149,12 +152,12 @@ public class Controller {
private boolean injectChar(char c) { private boolean injectChar(char c) {
if (options.useADBKeyboard()) { if (options.useADBKeyboard()) {
// Process latin keys the same way in order to provide same reaction speed. // Process latin keys the same way in order to provide same reaction speed.
try { Intent intent = new Intent();
Process process = Runtime.getRuntime().exec("am broadcast -a ADB_INPUT_CHARS --eia chars " + String.valueOf((int) c)); intent.setAction("ADB_INPUT_CHARS");
return process.waitFor() == 0; int[] chars = {c};
} catch (Throwable throwable) { intent.putExtra("chars", chars);
return false; device.sendBroadcast(intent);
} return true;
} else { } else {
String decomposed = KeyComposition.decompose(c); String decomposed = KeyComposition.decompose(c);
char[] chars = decomposed != null ? decomposed.toCharArray() : new char[]{c}; char[] chars = decomposed != null ? decomposed.toCharArray() : new char[]{c};

View file

@ -8,6 +8,7 @@ import com.genymobile.scrcpy.wrappers.SurfaceControl;
import com.genymobile.scrcpy.wrappers.WindowManager; import com.genymobile.scrcpy.wrappers.WindowManager;
import android.content.IOnPrimaryClipChangedListener; import android.content.IOnPrimaryClipChangedListener;
import android.content.Intent;
import android.graphics.Rect; import android.graphics.Rect;
import android.os.Build; import android.os.Build;
import android.os.IBinder; import android.os.IBinder;
@ -273,4 +274,8 @@ public final class Device {
public static ContentProvider createSettingsProvider() { public static ContentProvider createSettingsProvider() {
return SERVICE_MANAGER.getActivityManager().createSettingsProvider(); return SERVICE_MANAGER.getActivityManager().createSettingsProvider();
} }
public void sendBroadcast(Intent intent) {
SERVICE_MANAGER.getActivityManager().sendBroadcast(intent);
}
} }

View file

@ -2,7 +2,9 @@ package com.genymobile.scrcpy.wrappers;
import com.genymobile.scrcpy.Ln; import com.genymobile.scrcpy.Ln;
import android.content.Intent;
import android.os.Binder; import android.os.Binder;
import android.os.Bundle;
import android.os.IBinder; import android.os.IBinder;
import android.os.IInterface; import android.os.IInterface;
@ -16,6 +18,7 @@ public class ActivityManager {
private Method getContentProviderExternalMethod; private Method getContentProviderExternalMethod;
private boolean getContentProviderExternalMethodLegacy; private boolean getContentProviderExternalMethodLegacy;
private Method removeContentProviderExternalMethod; private Method removeContentProviderExternalMethod;
private Method broadcastIntentMethod;
public ActivityManager(IInterface manager) { public ActivityManager(IInterface manager) {
this.manager = manager; this.manager = manager;
@ -42,6 +45,22 @@ public class ActivityManager {
return removeContentProviderExternalMethod; return removeContentProviderExternalMethod;
} }
private Method getBroadcastIntentMethod() throws NoSuchMethodException {
if (broadcastIntentMethod == null) {
try {
Class<?> iApplicationThreadClass = Class.forName("android.app.IApplicationThread");
Class<?> iIntentReceiverClass = Class.forName("android.content.IIntentReceiver");
broadcastIntentMethod = manager.getClass()
.getMethod("broadcastIntent", iApplicationThreadClass, Intent.class, String.class, iIntentReceiverClass, int.class,
String.class, Bundle.class, String[].class, int.class, Bundle.class, boolean.class, boolean.class, int.class);
return broadcastIntentMethod;
} catch (ClassNotFoundException e) {
throw new AssertionError(e);
}
}
return broadcastIntentMethod;
}
private ContentProvider getContentProviderExternal(String name, IBinder token) { private ContentProvider getContentProviderExternal(String name, IBinder token) {
try { try {
Method method = getGetContentProviderExternalMethod(); Method method = getGetContentProviderExternalMethod();
@ -84,4 +103,13 @@ public class ActivityManager {
public ContentProvider createSettingsProvider() { public ContentProvider createSettingsProvider() {
return getContentProviderExternal("settings", new Binder()); return getContentProviderExternal("settings", new Binder());
} }
public void sendBroadcast(Intent intent) {
try {
Method method = getBroadcastIntentMethod();
method.invoke(manager, null, intent, null, null, 0, null, null, null, -1, null, true, false, ServiceManager.USER_ID);
} catch (InvocationTargetException | IllegalAccessException | NoSuchMethodException e) {
Ln.e("Could not invoke method", e);
}
}
} }