diff --git a/core/java/android/app/Instrumentation.java b/core/java/android/app/Instrumentation.java index 995a9f31b341..638b30e3b46f 100644 --- a/core/java/android/app/Instrumentation.java +++ b/core/java/android/app/Instrumentation.java @@ -1154,11 +1154,30 @@ public class Instrumentation { if ((event.getSource() & InputDevice.SOURCE_CLASS_POINTER) == 0) { event.setSource(InputDevice.SOURCE_TOUCHSCREEN); } + + syncInputTransactionsAndInjectEvent(event); + } + + private void syncInputTransactionsAndInjectEvent(MotionEvent event) { + final boolean syncBefore = event.getAction() == MotionEvent.ACTION_DOWN + || event.isFromSource(InputDevice.SOURCE_MOUSE); + final boolean syncAfter = event.getAction() == MotionEvent.ACTION_UP; + try { - WindowManagerGlobal.getWindowManagerService().injectInputAfterTransactionsApplied(event, - InputManager.INJECT_INPUT_EVENT_MODE_WAIT_FOR_FINISH, - true /* waitForAnimations */); + if (syncBefore) { + WindowManagerGlobal.getWindowManagerService() + .syncInputTransactions(true /*waitForAnimations*/); + } + + InputManager.getInstance().injectInputEvent( + event, InputManager.INJECT_INPUT_EVENT_MODE_WAIT_FOR_RESULT); + + if (syncAfter) { + WindowManagerGlobal.getWindowManagerService() + .syncInputTransactions(true /*waitForAnimations*/); + } } catch (RemoteException e) { + e.rethrowFromSystemServer(); } } diff --git a/core/java/android/app/UiAutomationConnection.java b/core/java/android/app/UiAutomationConnection.java index e016027329ac..5d6e2bda0b83 100644 --- a/core/java/android/app/UiAutomationConnection.java +++ b/core/java/android/app/UiAutomationConnection.java @@ -36,7 +36,10 @@ import android.os.UserHandle; import android.permission.IPermissionManager; import android.util.Log; import android.view.IWindowManager; +import android.view.InputDevice; import android.view.InputEvent; +import android.view.KeyEvent; +import android.view.MotionEvent; import android.view.SurfaceControl; import android.view.WindowAnimationFrameStats; import android.view.WindowContentFrameStats; @@ -132,13 +135,36 @@ public final class UiAutomationConnection extends IUiAutomationConnection.Stub { throwIfShutdownLocked(); throwIfNotConnectedLocked(); } - final int mode = (sync) ? InputManager.INJECT_INPUT_EVENT_MODE_WAIT_FOR_FINISH - : InputManager.INJECT_INPUT_EVENT_MODE_ASYNC; + + final boolean syncTransactionsBefore; + final boolean syncTransactionsAfter; + if (event instanceof KeyEvent) { + KeyEvent keyEvent = (KeyEvent) event; + syncTransactionsBefore = keyEvent.getAction() == KeyEvent.ACTION_DOWN; + syncTransactionsAfter = keyEvent.getAction() == KeyEvent.ACTION_UP; + } else { + MotionEvent motionEvent = (MotionEvent) event; + syncTransactionsBefore = motionEvent.getAction() == MotionEvent.ACTION_DOWN + || motionEvent.isFromSource(InputDevice.SOURCE_MOUSE); + syncTransactionsAfter = motionEvent.getAction() == MotionEvent.ACTION_UP; + } + final long identity = Binder.clearCallingIdentity(); try { - return mWindowManager.injectInputAfterTransactionsApplied(event, mode, - waitForAnimations); + if (syncTransactionsBefore) { + mWindowManager.syncInputTransactions(waitForAnimations); + } + + final boolean result = InputManager.getInstance().injectInputEvent(event, + sync ? InputManager.INJECT_INPUT_EVENT_MODE_WAIT_FOR_FINISH + : InputManager.INJECT_INPUT_EVENT_MODE_ASYNC); + + if (syncTransactionsAfter) { + mWindowManager.syncInputTransactions(waitForAnimations); + } + return result; } catch (RemoteException e) { + e.rethrowFromSystemServer(); } finally { Binder.restoreCallingIdentity(identity); } diff --git a/core/java/android/hardware/input/InputManagerInternal.java b/core/java/android/hardware/input/InputManagerInternal.java index 3f20002c8028..b37c27c2a9e7 100644 --- a/core/java/android/hardware/input/InputManagerInternal.java +++ b/core/java/android/hardware/input/InputManagerInternal.java @@ -21,7 +21,6 @@ import android.graphics.PointF; import android.hardware.display.DisplayViewport; import android.os.IBinder; import android.view.InputChannel; -import android.view.InputEvent; import java.util.List; @@ -31,14 +30,6 @@ import java.util.List; * @hide Only for use within the system server. */ public abstract class InputManagerInternal { - /** - * Inject an input event. - * - * @param event The InputEvent to inject - * @param mode Synchronous or asynchronous mode - * @return True if injection has succeeded - */ - public abstract boolean injectInputEvent(InputEvent event, int mode); /** * Called by the display manager to set information about the displays as needed diff --git a/core/java/android/view/IWindowManager.aidl b/core/java/android/view/IWindowManager.aidl index a35a195c50b1..5ce5477daa0f 100644 --- a/core/java/android/view/IWindowManager.aidl +++ b/core/java/android/view/IWindowManager.aidl @@ -676,17 +676,6 @@ interface IWindowManager */ void setDisplayImePolicy(int displayId, int imePolicy); - /** - * Waits for transactions to get applied before injecting input, optionally waiting for - * animations to complete. This includes waiting for the input windows to get sent to - * InputManager. - * - * This is needed for testing since the system add windows and injects input - * quick enough that the windows don't have time to get sent to InputManager. - */ - boolean injectInputAfterTransactionsApplied(in InputEvent ev, int mode, - boolean waitForAnimations); - /** * Waits until input information has been sent from WindowManager to native InputManager, * optionally waiting for animations to complete. diff --git a/services/core/java/com/android/server/input/InputManagerService.java b/services/core/java/com/android/server/input/InputManagerService.java index 140a28f111e6..7360bbc5e54d 100644 --- a/services/core/java/com/android/server/input/InputManagerService.java +++ b/services/core/java/com/android/server/input/InputManagerService.java @@ -898,10 +898,6 @@ public class InputManagerService extends IInputManager.Stub @Override // Binder call public boolean injectInputEvent(InputEvent event, int mode) { - return injectInputEventInternal(event, mode); - } - - private boolean injectInputEventInternal(InputEvent event, int mode) { Objects.requireNonNull(event, "event must not be null"); if (mode != InputEventInjectionSync.NONE && mode != InputEventInjectionSync.WAIT_FOR_FINISHED @@ -3663,11 +3659,6 @@ public class InputManagerService extends IInputManager.Stub setDisplayViewportsInternal(viewports); } - @Override - public boolean injectInputEvent(InputEvent event, int mode) { - return injectInputEventInternal(event, mode); - } - @Override public void setInteractive(boolean interactive) { nativeSetInteractive(mPtr, interactive); diff --git a/services/core/java/com/android/server/wm/WindowManagerService.java b/services/core/java/com/android/server/wm/WindowManagerService.java index 500af8ec0e01..77d31df0bee7 100644 --- a/services/core/java/com/android/server/wm/WindowManagerService.java +++ b/services/core/java/com/android/server/wm/WindowManagerService.java @@ -181,7 +181,6 @@ import android.hardware.configstore.V1_1.ISurfaceFlingerConfigs; import android.hardware.display.DisplayManager; import android.hardware.display.DisplayManagerInternal; import android.hardware.input.InputManager; -import android.hardware.input.InputManagerInternal; import android.net.Uri; import android.os.Binder; import android.os.Build; @@ -256,7 +255,6 @@ import android.view.IWindowSessionCallback; import android.view.InputApplicationHandle; import android.view.InputChannel; import android.view.InputDevice; -import android.view.InputEvent; import android.view.InputWindowHandle; import android.view.InsetsSourceControl; import android.view.InsetsState; @@ -8319,37 +8317,6 @@ public class WindowManagerService extends IWindowManager.Stub } } - @Override - public boolean injectInputAfterTransactionsApplied(InputEvent ev, int mode, - boolean waitForAnimations) { - boolean isDown; - boolean isUp; - - if (ev instanceof KeyEvent) { - KeyEvent keyEvent = (KeyEvent) ev; - isDown = keyEvent.getAction() == KeyEvent.ACTION_DOWN; - isUp = keyEvent.getAction() == KeyEvent.ACTION_UP; - } else { - MotionEvent motionEvent = (MotionEvent) ev; - isDown = motionEvent.getAction() == MotionEvent.ACTION_DOWN; - isUp = motionEvent.getAction() == MotionEvent.ACTION_UP; - } - final boolean isMouseEvent = ev.getSource() == InputDevice.SOURCE_MOUSE; - - // For ACTION_DOWN, syncInputTransactions before injecting input. - // For all mouse events, also sync before injecting. - // For ACTION_UP, sync after injecting. - if (isDown || isMouseEvent) { - syncInputTransactions(waitForAnimations); - } - final boolean result = - LocalServices.getService(InputManagerInternal.class).injectInputEvent(ev, mode); - if (isUp) { - syncInputTransactions(waitForAnimations); - } - return result; - } - @Override public void syncInputTransactions(boolean waitForAnimations) { final long token = Binder.clearCallingIdentity();