diff options
| -rw-r--r-- | api/test-current.txt | 1 | ||||
| -rw-r--r-- | core/java/android/app/IUiAutomationConnection.aidl | 1 | ||||
| -rw-r--r-- | core/java/android/app/UiAutomation.java | 19 | ||||
| -rw-r--r-- | core/java/android/app/UiAutomationConnection.java | 25 | ||||
| -rw-r--r-- | core/java/android/view/IWindowManager.aidl | 11 | ||||
| -rw-r--r-- | services/core/java/com/android/server/wm/WindowManagerService.java | 22 |
6 files changed, 62 insertions, 17 deletions
diff --git a/api/test-current.txt b/api/test-current.txt index 63c8df047f90..a665c0af8fb3 100644 --- a/api/test-current.txt +++ b/api/test-current.txt @@ -369,6 +369,7 @@ package android.app { method public android.os.ParcelFileDescriptor[] executeShellCommandRw(String); method @Deprecated public boolean grantRuntimePermission(String, String, android.os.UserHandle); method @Deprecated public boolean revokeRuntimePermission(String, String, android.os.UserHandle); + method public void syncInputTransactions(); } public class UiModeManager { diff --git a/core/java/android/app/IUiAutomationConnection.aidl b/core/java/android/app/IUiAutomationConnection.aidl index 96da72a1b517..8c3180b400ef 100644 --- a/core/java/android/app/IUiAutomationConnection.aidl +++ b/core/java/android/app/IUiAutomationConnection.aidl @@ -37,6 +37,7 @@ interface IUiAutomationConnection { void connect(IAccessibilityServiceClient client, int flags); void disconnect(); boolean injectInputEvent(in InputEvent event, boolean sync); + void syncInputTransactions(); boolean setRotation(int rotation); Bitmap takeScreenshot(in Rect crop, int rotation); boolean clearWindowContentFrameStats(int windowId); diff --git a/core/java/android/app/UiAutomation.java b/core/java/android/app/UiAutomation.java index 494467324581..3935628b707f 100644 --- a/core/java/android/app/UiAutomation.java +++ b/core/java/android/app/UiAutomation.java @@ -602,6 +602,25 @@ public final class UiAutomation { } /** + * A request for WindowManagerService to wait until all animations have completed and input + * information has been sent from WindowManager to native InputManager. + * + * @hide + */ + @TestApi + public void syncInputTransactions() { + synchronized (mLock) { + throwIfNotConnectedLocked(); + } + try { + // Calling out without a lock held. + mUiAutomationConnection.syncInputTransactions(); + } catch (RemoteException re) { + Log.e(LOG_TAG, "Error while syncing input transactions!", re); + } + } + + /** * Sets the device rotation. A client can freeze the rotation in * desired state or freeze the rotation to its current state or * unfreeze the rotation (rotating the device changes its rotation diff --git a/core/java/android/app/UiAutomationConnection.java b/core/java/android/app/UiAutomationConnection.java index 7e074460bff8..dc07df8d7a87 100644 --- a/core/java/android/app/UiAutomationConnection.java +++ b/core/java/android/app/UiAutomationConnection.java @@ -128,19 +128,30 @@ public final class UiAutomationConnection extends IUiAutomationConnection.Stub { : InputManager.INJECT_INPUT_EVENT_MODE_ASYNC; final long identity = Binder.clearCallingIdentity(); try { - IWindowManager manager = IWindowManager.Stub.asInterface( - ServiceManager.getService(Context.WINDOW_SERVICE)); - try { - return manager.injectInputAfterTransactionsApplied(event, mode); - } catch (RemoteException e) { - } - return false; + return mWindowManager.injectInputAfterTransactionsApplied(event, mode); + } catch (RemoteException e) { } finally { Binder.restoreCallingIdentity(identity); } + return false; } @Override + public void syncInputTransactions() { + synchronized (mLock) { + throwIfCalledByNotTrustedUidLocked(); + throwIfShutdownLocked(); + throwIfNotConnectedLocked(); + } + + try { + mWindowManager.syncInputTransactions(); + } catch (RemoteException e) { + } + } + + + @Override public boolean setRotation(int rotation) { synchronized (mLock) { throwIfCalledByNotTrustedUidLocked(); diff --git a/core/java/android/view/IWindowManager.aidl b/core/java/android/view/IWindowManager.aidl index 6c37319c6303..c730fe2dc114 100644 --- a/core/java/android/view/IWindowManager.aidl +++ b/core/java/android/view/IWindowManager.aidl @@ -640,5 +640,14 @@ interface IWindowManager * 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 injectInputAfterTransactionsApplied(in InputEvent ev, int mode); + + /** + * Waits until all animations have completed and input information has been sent from + * WindowManager to native InputManager. + * + * This is needed for testing since we need to ensure input information has been propagated to + * native InputManager before proceeding with tests. + */ + void syncInputTransactions(); } diff --git a/services/core/java/com/android/server/wm/WindowManagerService.java b/services/core/java/com/android/server/wm/WindowManagerService.java index d46aa7bdcaeb..dae29b2cf180 100644 --- a/services/core/java/com/android/server/wm/WindowManagerService.java +++ b/services/core/java/com/android/server/wm/WindowManagerService.java @@ -7550,20 +7550,24 @@ public class WindowManagerService extends IWindowManager.Stub } if (shouldWaitForAnimToComplete) { - waitForAnimationsToComplete(); - - synchronized (mGlobalLock) { - mWindowPlacerLocked.performSurfacePlacementIfScheduled(); - mRoot.forAllDisplays(displayContent -> - displayContent.getInputMonitor().updateInputWindowsImmediately()); - } - - new SurfaceControl.Transaction().syncInputWindows().apply(true); + syncInputTransactions(); } return LocalServices.getService(InputManagerInternal.class).injectInputEvent(ev, mode); } + @Override + public void syncInputTransactions() { + waitForAnimationsToComplete(); + + synchronized (mGlobalLock) { + mWindowPlacerLocked.performSurfacePlacementIfScheduled(); + mRoot.forAllDisplays(displayContent -> + displayContent.getInputMonitor().updateInputWindowsImmediately()); + } + new SurfaceControl.Transaction().syncInputWindows().apply(true); + } + private void waitForAnimationsToComplete() { synchronized (mGlobalLock) { long timeoutRemaining = ANIMATION_COMPLETED_TIMEOUT_MS; |