diff options
| author | 2017-09-20 00:18:26 +0000 | |
|---|---|---|
| committer | 2017-09-20 00:18:26 +0000 | |
| commit | 85cac19a66ecb75d5ba5c8cc7c381fb9c71cb071 (patch) | |
| tree | d62b4df5799d2c170be1019f31e6c31b83adb715 | |
| parent | dbb33c058b13cca8b4ba916bac9a4bd08d0ddcc4 (diff) | |
| parent | 9282193c8408f392e7a3b9660390afa2194f023b (diff) | |
Merge "Handle showWhenLocked on secondary displays" into oc-mr1-dev
am: 9282193c84
Change-Id: Idbd4d3f24dffaad11518dd3d4d16ca7c7137ee94
8 files changed, 108 insertions, 45 deletions
diff --git a/core/java/android/app/IActivityManager.aidl b/core/java/android/app/IActivityManager.aidl index 897e42bc2b22..18117481b0ea 100644 --- a/core/java/android/app/IActivityManager.aidl +++ b/core/java/android/app/IActivityManager.aidl @@ -308,7 +308,15 @@ interface IActivityManager { boolean shouldUpRecreateTask(in IBinder token, in String destAffinity); boolean navigateUpTo(in IBinder token, in Intent target, int resultCode, in Intent resultData); - void setLockScreenShown(boolean showing); + /** + * Informs ActivityManagerService that the keyguard is showing. + * + * @param showing True if the keyguard is showing, false otherwise. + * @param secondaryDisplayShowing The displayId of the secondary display on which the keyguard + * is showing, or INVALID_DISPLAY if there is no such display. Only meaningful if + * showing is true. + */ + void setLockScreenShown(boolean showing, int secondaryDisplayShowing); boolean finishActivityAffinity(in IBinder token); // This is not public because you need to be very careful in how you // manage your activity to make sure it is always the uid you expect. diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardDisplayManager.java b/packages/SystemUI/src/com/android/keyguard/KeyguardDisplayManager.java index 8de1d317c5ed..2bc0e45c725d 100644 --- a/packages/SystemUI/src/com/android/keyguard/KeyguardDisplayManager.java +++ b/packages/SystemUI/src/com/android/keyguard/KeyguardDisplayManager.java @@ -15,6 +15,8 @@ */ package com.android.keyguard; +import static android.view.Display.INVALID_DISPLAY; + import android.app.Presentation; import android.content.Context; import android.content.DialogInterface; @@ -28,16 +30,21 @@ import android.view.Display; import android.view.View; import android.view.WindowManager; +// TODO(multi-display): Support multiple external displays public class KeyguardDisplayManager { protected static final String TAG = "KeyguardDisplayManager"; private static boolean DEBUG = KeyguardConstants.DEBUG; + + private final ViewMediatorCallback mCallback; + private final MediaRouter mMediaRouter; + private final Context mContext; + Presentation mPresentation; - private MediaRouter mMediaRouter; - private Context mContext; private boolean mShowing; - public KeyguardDisplayManager(Context context) { + public KeyguardDisplayManager(Context context, ViewMediatorCallback callback) { mContext = context; + mCallback = callback; mMediaRouter = (MediaRouter) mContext.getSystemService(Context.MEDIA_ROUTER_SERVICE); } @@ -90,6 +97,7 @@ public class KeyguardDisplayManager { }; protected void updateDisplays(boolean showing) { + Presentation originalPresentation = mPresentation; if (showing) { MediaRouter.RouteInfo route = mMediaRouter.getSelectedRoute( MediaRouter.ROUTE_TYPE_REMOTE_DISPLAY); @@ -121,6 +129,13 @@ public class KeyguardDisplayManager { mPresentation = null; } } + + // mPresentation is only updated when the display changes + if (mPresentation != originalPresentation) { + final int displayId = mPresentation != null + ? mPresentation.getDisplay().getDisplayId() : INVALID_DISPLAY; + mCallback.onSecondaryDisplayShowingChanged(displayId); + } } private final static class KeyguardPresentation extends Presentation { diff --git a/packages/SystemUI/src/com/android/keyguard/ViewMediatorCallback.java b/packages/SystemUI/src/com/android/keyguard/ViewMediatorCallback.java index 327d218913d2..b194de43a718 100644 --- a/packages/SystemUI/src/com/android/keyguard/ViewMediatorCallback.java +++ b/packages/SystemUI/src/com/android/keyguard/ViewMediatorCallback.java @@ -88,4 +88,9 @@ public interface ViewMediatorCallback { * {@link KeyguardSecurityView#PROMPT_REASON_TIMEOUT}. */ int getBouncerPromptReason(); + + /** + * Invoked when the secondary display showing a keyguard window changes. + */ + void onSecondaryDisplayShowingChanged(int displayId); } diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java index 3eb68f5214c0..28adca97b8bf 100644 --- a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java +++ b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java @@ -17,6 +17,7 @@ package com.android.systemui.keyguard; import static android.provider.Settings.System.SCREEN_OFF_TIMEOUT; +import static android.view.Display.INVALID_DISPLAY; import static com.android.internal.telephony.IccCardConstants.State.ABSENT; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.SOME_AUTH_REQUIRED_AFTER_USER_REQUEST; @@ -239,6 +240,9 @@ public class KeyguardViewMediator extends SystemUI { // answer whether the input should be restricted) private boolean mShowing; + // display id of the secondary display on which we have put a keyguard window + private int mSecondaryDisplayShowing = INVALID_DISPLAY; + /** Cached value of #isInputRestricted */ private boolean mInputRestricted; @@ -646,6 +650,13 @@ public class KeyguardViewMediator extends SystemUI { } return KeyguardSecurityView.PROMPT_REASON_NONE; } + + @Override + public void onSecondaryDisplayShowingChanged(int displayId) { + synchronized (KeyguardViewMediator.this) { + setShowingLocked(mShowing, displayId, false); + } + } }; public void userActivity() { @@ -670,7 +681,7 @@ public class KeyguardViewMediator extends SystemUI { filter.addAction(Intent.ACTION_SHUTDOWN); mContext.registerReceiver(mBroadcastReceiver, filter); - mKeyguardDisplayManager = new KeyguardDisplayManager(mContext); + mKeyguardDisplayManager = new KeyguardDisplayManager(mContext, mViewMediatorCallback); mAlarmManager = (AlarmManager) mContext.getSystemService(Context.ALARM_SERVICE); @@ -685,7 +696,8 @@ public class KeyguardViewMediator extends SystemUI { com.android.keyguard.R.bool.config_enableKeyguardService)) { setShowingLocked(!shouldWaitForProvisioning() && !mLockPatternUtils.isLockScreenDisabled( - KeyguardUpdateMonitor.getCurrentUser()), true /* forceCallbacks */); + KeyguardUpdateMonitor.getCurrentUser()), + mSecondaryDisplayShowing, true /* forceCallbacks */); } mStatusBarKeyguardViewManager = @@ -1694,10 +1706,10 @@ public class KeyguardViewMediator extends SystemUI { playSound(mTrustedSoundId); } - private void updateActivityLockScreenState(boolean showing) { + private void updateActivityLockScreenState(boolean showing, int secondaryDisplayShowing) { mUiOffloadThread.submit(() -> { try { - ActivityManager.getService().setLockScreenShown(showing); + ActivityManager.getService().setLockScreenShown(showing, secondaryDisplayShowing); } catch (RemoteException e) { } }); @@ -2060,30 +2072,39 @@ public class KeyguardViewMediator extends SystemUI { } private void setShowingLocked(boolean showing) { - setShowingLocked(showing, false /* forceCallbacks */); + setShowingLocked(showing, mSecondaryDisplayShowing, false /* forceCallbacks */); } - private void setShowingLocked(boolean showing, boolean forceCallbacks) { - if (showing != mShowing || forceCallbacks) { + private void setShowingLocked( + boolean showing, int secondaryDisplayShowing, boolean forceCallbacks) { + final boolean notifyDefaultDisplayCallbacks = showing != mShowing || forceCallbacks; + if (notifyDefaultDisplayCallbacks || secondaryDisplayShowing != mSecondaryDisplayShowing) { mShowing = showing; - int size = mKeyguardStateCallbacks.size(); - for (int i = size - 1; i >= 0; i--) { - IKeyguardStateCallback callback = mKeyguardStateCallbacks.get(i); - try { - callback.onShowingStateChanged(showing); - } catch (RemoteException e) { - Slog.w(TAG, "Failed to call onShowingStateChanged", e); - if (e instanceof DeadObjectException) { - mKeyguardStateCallbacks.remove(callback); - } + mSecondaryDisplayShowing = secondaryDisplayShowing; + if (notifyDefaultDisplayCallbacks) { + notifyDefaultDisplayCallbacks(showing); + } + updateActivityLockScreenState(showing, secondaryDisplayShowing); + } + } + + private void notifyDefaultDisplayCallbacks(boolean showing) { + int size = mKeyguardStateCallbacks.size(); + for (int i = size - 1; i >= 0; i--) { + IKeyguardStateCallback callback = mKeyguardStateCallbacks.get(i); + try { + callback.onShowingStateChanged(showing); + } catch (RemoteException e) { + Slog.w(TAG, "Failed to call onShowingStateChanged", e); + if (e instanceof DeadObjectException) { + mKeyguardStateCallbacks.remove(callback); } } - updateInputRestrictedLocked(); - mUiOffloadThread.submit(() -> { - mTrustManager.reportKeyguardShowingChanged(); - }); - updateActivityLockScreenState(showing); } + updateInputRestrictedLocked(); + mUiOffloadThread.submit(() -> { + mTrustManager.reportKeyguardShowingChanged(); + }); } private void notifyTrustedChangedLocked(boolean trusted) { diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java index 69285a48dde9..1f8b83eb3374 100644 --- a/services/core/java/com/android/server/am/ActivityManagerService.java +++ b/services/core/java/com/android/server/am/ActivityManagerService.java @@ -713,7 +713,7 @@ public class ActivityManagerService extends IActivityManager.Stub public boolean canShowErrorDialogs() { return mShowDialogs && !mSleeping && !mShuttingDown - && !mKeyguardController.isKeyguardShowing() + && !mKeyguardController.isKeyguardShowing(DEFAULT_DISPLAY) && !(UserManager.isDeviceInDemoMode(mContext) && mUserController.getCurrentUser().isDemo()); } @@ -12614,7 +12614,7 @@ public class ActivityManagerService extends IActivityManager.Stub } @Override - public void setLockScreenShown(boolean showing) { + public void setLockScreenShown(boolean showing, int secondaryDisplayShowing) { if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) != PackageManager.PERMISSION_GRANTED) { throw new SecurityException("Requires permission " @@ -12624,7 +12624,7 @@ public class ActivityManagerService extends IActivityManager.Stub synchronized(this) { long ident = Binder.clearCallingIdentity(); try { - mKeyguardController.setKeyguardShown(showing); + mKeyguardController.setKeyguardShown(showing, secondaryDisplayShowing); } finally { Binder.restoreCallingIdentity(ident); } @@ -24087,7 +24087,7 @@ public class ActivityManagerService extends IActivityManager.Stub @Override public void notifyKeyguardTrustedChanged() { synchronized (ActivityManagerService.this) { - if (mKeyguardController.isKeyguardShowing()) { + if (mKeyguardController.isKeyguardShowing(DEFAULT_DISPLAY)) { mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); } } diff --git a/services/core/java/com/android/server/am/ActivityStack.java b/services/core/java/com/android/server/am/ActivityStack.java index 791b2c066821..a0817c475918 100644 --- a/services/core/java/com/android/server/am/ActivityStack.java +++ b/services/core/java/com/android/server/am/ActivityStack.java @@ -1980,7 +1980,8 @@ class ActivityStack<T extends StackWindowController> extends ConfigurationContai boolean checkKeyguardVisibility(ActivityRecord r, boolean shouldBeVisible, boolean isTop) { final boolean isInPinnedStack = r.getStack().getStackId() == PINNED_STACK_ID; - final boolean keyguardShowing = mStackSupervisor.mKeyguardController.isKeyguardShowing(); + final boolean keyguardShowing = mStackSupervisor.mKeyguardController.isKeyguardShowing( + mDisplayId != INVALID_DISPLAY ? mDisplayId : DEFAULT_DISPLAY); final boolean keyguardLocked = mStackSupervisor.mKeyguardController.isKeyguardLocked(); final boolean showWhenLocked = r.canShowWhenLocked() && !isInPinnedStack; final boolean dismissKeyguard = r.hasDismissKeyguardWindows(); @@ -5205,8 +5206,8 @@ class ActivityStack<T extends StackWindowController> extends ConfigurationContai voiceInteractor, type); // add the task to stack first, mTaskPositioner might need the stack association addTask(task, toTop, "createTaskRecord"); - final boolean isLockscreenShown = - mService.mStackSupervisor.mKeyguardController.isKeyguardShowing(); + final boolean isLockscreenShown = mService.mStackSupervisor.mKeyguardController + .isKeyguardShowing(mDisplayId != INVALID_DISPLAY ? mDisplayId : DEFAULT_DISPLAY); if (!layoutTaskInStack(task, info.windowLayout) && mBounds != null && task.isResizeable() && !isLockscreenShown) { task.updateOverrideConfiguration(mBounds); diff --git a/services/core/java/com/android/server/am/KeyguardController.java b/services/core/java/com/android/server/am/KeyguardController.java index cea80c8d0e9d..85961135d84f 100644 --- a/services/core/java/com/android/server/am/KeyguardController.java +++ b/services/core/java/com/android/server/am/KeyguardController.java @@ -19,6 +19,7 @@ package com.android.server.am; import static android.app.ActivityManager.StackId.DOCKED_STACK_ID; import static android.os.Trace.TRACE_TAG_ACTIVITY_MANAGER; import static android.view.Display.DEFAULT_DISPLAY; +import static android.view.Display.INVALID_DISPLAY; import static android.view.WindowManagerPolicy.KEYGUARD_GOING_AWAY_FLAG_NO_WINDOW_ANIMATIONS; import static android.view.WindowManagerPolicy.KEYGUARD_GOING_AWAY_FLAG_TO_SHADE; import static android.view.WindowManagerPolicy.KEYGUARD_GOING_AWAY_FLAG_WITH_WALLPAPER; @@ -66,6 +67,7 @@ class KeyguardController { private int mBeforeUnoccludeTransit; private int mVisibilityTransactionDepth; private SleepToken mSleepToken; + private int mSecondaryDisplayShowing = INVALID_DISPLAY; KeyguardController(ActivityManagerService service, ActivityStackSupervisor stackSupervisor) { @@ -78,10 +80,12 @@ class KeyguardController { } /** - * @return true if Keyguard is showing, not going away, and not being occluded, false otherwise + * @return true if Keyguard is showing, not going away, and not being occluded on the given + * display, false otherwise */ - boolean isKeyguardShowing() { - return mKeyguardShowing && !mKeyguardGoingAway && !mOccluded; + boolean isKeyguardShowing(int displayId) { + return mKeyguardShowing && !mKeyguardGoingAway && + (displayId == DEFAULT_DISPLAY ? !mOccluded : displayId == mSecondaryDisplayShowing); } /** @@ -94,15 +98,19 @@ class KeyguardController { /** * Update the Keyguard showing state. */ - void setKeyguardShown(boolean showing) { - if (showing == mKeyguardShowing) { + void setKeyguardShown(boolean showing, int secondaryDisplayShowing) { + boolean showingChanged = showing != mKeyguardShowing; + if (!showingChanged && secondaryDisplayShowing == mSecondaryDisplayShowing) { return; } mKeyguardShowing = showing; - dismissDockedStackIfNeeded(); - if (showing) { - setKeyguardGoingAway(false); - mDismissalRequested = false; + mSecondaryDisplayShowing = secondaryDisplayShowing; + if (showingChanged) { + dismissDockedStackIfNeeded(); + if (showing) { + setKeyguardGoingAway(false); + mDismissalRequested = false; + } } mStackSupervisor.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS); updateKeyguardSleepToken(); @@ -337,9 +345,9 @@ class KeyguardController { } private void updateKeyguardSleepToken() { - if (mSleepToken == null && isKeyguardShowing()) { + if (mSleepToken == null && isKeyguardShowing(DEFAULT_DISPLAY)) { mSleepToken = mService.acquireSleepToken("Keyguard", DEFAULT_DISPLAY); - } else if (mSleepToken != null && !isKeyguardShowing()) { + } else if (mSleepToken != null && !isKeyguardShowing(DEFAULT_DISPLAY)) { mSleepToken.release(); mSleepToken = null; } diff --git a/services/core/java/com/android/server/policy/keyguard/KeyguardServiceDelegate.java b/services/core/java/com/android/server/policy/keyguard/KeyguardServiceDelegate.java index 50e5e7bd2312..5a5471b1b4f5 100644 --- a/services/core/java/com/android/server/policy/keyguard/KeyguardServiceDelegate.java +++ b/services/core/java/com/android/server/policy/keyguard/KeyguardServiceDelegate.java @@ -1,5 +1,7 @@ package com.android.server.policy.keyguard; +import static android.view.Display.INVALID_DISPLAY; + import android.app.ActivityManager; import android.content.ComponentName; import android.content.Context; @@ -201,7 +203,10 @@ public class KeyguardServiceDelegate { mKeyguardState.reset(); mHandler.post(() -> { try { - ActivityManager.getService().setLockScreenShown(true); + // There are no longer any keyguard windows on secondary displays, so pass + // INVALID_DISPLAY. All that means is that showWhenLocked activities on + // secondary displays now get to show. + ActivityManager.getService().setLockScreenShown(true, INVALID_DISPLAY); } catch (RemoteException e) { // Local call. } |