diff --git a/packages/SystemUI/plugin/src/com/android/systemui/plugins/ActivityStarter.java b/packages/SystemUI/plugin/src/com/android/systemui/plugins/ActivityStarter.java index 1fec3314a13e0..6d4dbf632d762 100644 --- a/packages/SystemUI/plugin/src/com/android/systemui/plugins/ActivityStarter.java +++ b/packages/SystemUI/plugin/src/com/android/systemui/plugins/ActivityStarter.java @@ -79,6 +79,11 @@ public interface ActivityStarter { void postStartActivityDismissingKeyguard(Intent intent, int delay); void postStartActivityDismissingKeyguard(Intent intent, int delay, @Nullable ActivityLaunchAnimator.Controller animationController); + + /** Posts a start activity intent that dismisses keyguard. */ + void postStartActivityDismissingKeyguard(Intent intent, int delay, + @Nullable ActivityLaunchAnimator.Controller animationController, + @Nullable String customMessage); void postStartActivityDismissingKeyguard(PendingIntent intent); /** @@ -93,6 +98,10 @@ public interface ActivityStarter { void dismissKeyguardThenExecute(OnDismissAction action, @Nullable Runnable cancel, boolean afterKeyguardGone); + /** Authenticates if needed and dismisses keyguard to execute an action. */ + void dismissKeyguardThenExecute(OnDismissAction action, @Nullable Runnable cancel, + boolean afterKeyguardGone, @Nullable String customMessage); + interface Callback { void onActivityStarted(int resultCode); } diff --git a/packages/SystemUI/res/values/strings.xml b/packages/SystemUI/res/values/strings.xml index 19deefbc41984..26502f1c17523 100644 --- a/packages/SystemUI/res/values/strings.xml +++ b/packages/SystemUI/res/values/strings.xml @@ -3069,6 +3069,9 @@ --> Customize lock screen + + Unlock to customize lock screen + Wi-Fi not available diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardAbsKeyInputViewController.java b/packages/SystemUI/src/com/android/keyguard/KeyguardAbsKeyInputViewController.java index 1980f70d63a41..510fcbfd8bee2 100644 --- a/packages/SystemUI/src/com/android/keyguard/KeyguardAbsKeyInputViewController.java +++ b/packages/SystemUI/src/com/android/keyguard/KeyguardAbsKeyInputViewController.java @@ -116,7 +116,7 @@ public abstract class KeyguardAbsKeyInputViewController } @Override - public void showMessage(CharSequence message, ColorStateList colorState) { + public void showMessage(CharSequence message, ColorStateList colorState, boolean animated) { } public void startAppearAnimation() { diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardPatternViewController.java b/packages/SystemUI/src/com/android/keyguard/KeyguardPatternViewController.java index 5c56aab9a6112..39225fb03939f 100644 --- a/packages/SystemUI/src/com/android/keyguard/KeyguardPatternViewController.java +++ b/packages/SystemUI/src/com/android/keyguard/KeyguardPatternViewController.java @@ -333,14 +333,14 @@ public class KeyguardPatternViewController } @Override - public void showMessage(CharSequence message, ColorStateList colorState) { + public void showMessage(CharSequence message, ColorStateList colorState, boolean animated) { if (mMessageAreaController == null) { return; } if (colorState != null) { mMessageAreaController.setNextMessageColor(colorState); } - mMessageAreaController.setMessage(message); + mMessageAreaController.setMessage(message, animated); } @Override diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityContainerController.java b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityContainerController.java index db38d34149157..76e051ea25f33 100644 --- a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityContainerController.java +++ b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityContainerController.java @@ -65,7 +65,6 @@ import com.android.keyguard.KeyguardSecurityContainer.BouncerUiEvent; import com.android.keyguard.KeyguardSecurityContainer.SwipeListener; import com.android.keyguard.KeyguardSecurityModel.SecurityMode; import com.android.keyguard.dagger.KeyguardBouncerScope; -import com.android.settingslib.Utils; import com.android.settingslib.utils.ThreadUtils; import com.android.systemui.Gefingerpoken; import com.android.systemui.R; @@ -307,7 +306,7 @@ public class KeyguardSecurityContainerController extends ViewController controller.onPause()); } mView.onPause(); mView.clearFocus(); @@ -513,13 +512,15 @@ public class KeyguardSecurityContainerController extends ViewController controller.showPromptReason(reason)); } } - public void showMessage(CharSequence message, ColorStateList colorState) { + /** Set message of bouncer title. */ + public void showMessage(CharSequence message, ColorStateList colorState, boolean animated) { if (mCurrentSecurityMode != SecurityMode.None) { - getCurrentSecurityController().showMessage(message, colorState); + getCurrentSecurityController( + controller -> controller.showMessage(message, colorState, animated)); } } @@ -634,7 +635,8 @@ public class KeyguardSecurityContainerController extends ViewController controller.onResume(reason)); } mView.onResume( mSecurityModel.getSecurityMode(KeyguardUpdateMonitor.getCurrentUser()), @@ -645,7 +647,7 @@ public class KeyguardSecurityContainerController extends ViewController controller.startAppearAnimation()); } } @@ -684,24 +686,23 @@ public class KeyguardSecurityContainerController extends ViewController { + boolean didRunAnimation = controller.startDisappearAnimation( + onFinishRunnable); + if (!didRunAnimation && onFinishRunnable != null) { + onFinishRunnable.run(); + } + }); } - - if (!didRunAnimation && onFinishRunnable != null) { - onFinishRunnable.run(); - } - - return didRunAnimation; + return true; } public void onStartingToHide() { if (mCurrentSecurityMode != SecurityMode.None) { - getCurrentSecurityController().onStartingToHide(); + getCurrentSecurityController(controller -> controller.onStartingToHide()); } } @@ -809,8 +810,9 @@ public class KeyguardSecurityContainerController extends ViewController oldView = getCurrentSecurityController(); + getCurrentSecurityController(oldView -> oldView.onPause()); - // Emulate Activity life cycle - if (oldView != null) { - oldView.onPause(); - } + mCurrentSecurityMode = securityMode; - KeyguardInputViewController newView = changeSecurityMode(securityMode); - if (newView != null) { - newView.onResume(KeyguardSecurityView.VIEW_REVEALED); - mSecurityViewFlipperController.show(newView); - configureMode(); - } + getCurrentSecurityController( + newView -> { + newView.onResume(KeyguardSecurityView.VIEW_REVEALED); + mSecurityViewFlipperController.show(newView); + configureMode(); + mKeyguardSecurityCallback.onSecurityModeChanged( + securityMode, newView != null && newView.needsInput()); - mKeyguardSecurityCallback.onSecurityModeChanged( - securityMode, newView != null && newView.needsInput()); + }); } /** @@ -986,7 +985,7 @@ public class KeyguardSecurityContainerController extends ViewController showMessage(getContext().getString(R.string.keyguard_unlock_to_continue), - null), mFalsingA11yDelegate); + /* colorState= */ null, /* animated= */ true), mFalsingA11yDelegate); } public void reportFailedUnlockAttempt(int userId, int timeoutMs) { @@ -1033,15 +1032,11 @@ public class KeyguardSecurityContainerController extends ViewController getCurrentSecurityController() { - return mSecurityViewFlipperController - .getSecurityView(mCurrentSecurityMode, mKeyguardSecurityCallback); - } - - private KeyguardInputViewController changeSecurityMode( - SecurityMode securityMode) { - mCurrentSecurityMode = securityMode; - return getCurrentSecurityController(); + private void getCurrentSecurityController( + KeyguardSecurityViewFlipperController.OnViewInflatedCallback onViewInflatedCallback) { + mSecurityViewFlipperController + .getSecurityView(mCurrentSecurityMode, mKeyguardSecurityCallback, + onViewInflatedCallback); } /** @@ -1091,28 +1086,22 @@ public class KeyguardSecurityContainerController extends ViewController mView.reloadColors()); + reinflateViewFlipper(controller -> mView.reloadColors()); } /** Handles density or font scale changes. */ private void onDensityOrFontScaleChanged() { - reinflateViewFlipper(() -> mView.onDensityOrFontScaleChanged()); + reinflateViewFlipper(controller -> mView.onDensityOrFontScaleChanged()); } /** * Reinflate the view flipper child view. */ public void reinflateViewFlipper( - KeyguardSecurityViewFlipperController.OnViewInflatedListener onViewInflatedListener) { + KeyguardSecurityViewFlipperController.OnViewInflatedCallback onViewInflatedListener) { mSecurityViewFlipperController.clearViews(); - if (mFeatureFlags.isEnabled(Flags.ASYNC_INFLATE_BOUNCER)) { - mSecurityViewFlipperController.asynchronouslyInflateView(mCurrentSecurityMode, - mKeyguardSecurityCallback, onViewInflatedListener); - } else { - mSecurityViewFlipperController.getSecurityView(mCurrentSecurityMode, - mKeyguardSecurityCallback); - onViewInflatedListener.onViewInflated(); - } + mSecurityViewFlipperController.asynchronouslyInflateView(mCurrentSecurityMode, + mKeyguardSecurityCallback, onViewInflatedListener); } /** diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityView.java b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityView.java index 67d77e53738a1..22ad725faaa2d 100644 --- a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityView.java +++ b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityView.java @@ -106,7 +106,7 @@ public interface KeyguardSecurityView { * @param message the message to show * @param colorState the color to use */ - void showMessage(CharSequence message, ColorStateList colorState); + void showMessage(CharSequence message, ColorStateList colorState, boolean animated); /** * Starts the animation which should run when the security view appears. diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityViewFlipperController.java b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityViewFlipperController.java index ddf11997d3a72..fbacd6818648b 100644 --- a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityViewFlipperController.java +++ b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityViewFlipperController.java @@ -28,7 +28,6 @@ import com.android.keyguard.KeyguardSecurityModel.SecurityMode; import com.android.keyguard.dagger.KeyguardBouncerScope; import com.android.systemui.R; import com.android.systemui.flags.FeatureFlags; -import com.android.systemui.flags.Flags; import com.android.systemui.util.ViewController; import java.util.ArrayList; @@ -54,23 +53,19 @@ public class KeyguardSecurityViewFlipperController private final Factory mKeyguardSecurityViewControllerFactory; private final FeatureFlags mFeatureFlags; - private final ViewMediatorCallback mViewMediatorCallback; - @Inject protected KeyguardSecurityViewFlipperController(KeyguardSecurityViewFlipper view, LayoutInflater layoutInflater, AsyncLayoutInflater asyncLayoutInflater, KeyguardInputViewController.Factory keyguardSecurityViewControllerFactory, EmergencyButtonController.Factory emergencyButtonControllerFactory, - FeatureFlags featureFlags, - ViewMediatorCallback viewMediatorCallback) { + FeatureFlags featureFlags) { super(view); mKeyguardSecurityViewControllerFactory = keyguardSecurityViewControllerFactory; mLayoutInflater = layoutInflater; mEmergencyButtonControllerFactory = emergencyButtonControllerFactory; mAsyncLayoutInflater = asyncLayoutInflater; mFeatureFlags = featureFlags; - mViewMediatorCallback = viewMediatorCallback; } @Override @@ -97,40 +92,17 @@ public class KeyguardSecurityViewFlipperController @VisibleForTesting - KeyguardInputViewController getSecurityView(SecurityMode securityMode, - KeyguardSecurityCallback keyguardSecurityCallback) { - KeyguardInputViewController childController = null; + void getSecurityView(SecurityMode securityMode, + KeyguardSecurityCallback keyguardSecurityCallback, + OnViewInflatedCallback onViewInflatedCallback) { for (KeyguardInputViewController child : mChildren) { if (child.getSecurityMode() == securityMode) { - childController = child; - break; + onViewInflatedCallback.onViewInflated(child); + return; } } - if (!mFeatureFlags.isEnabled(Flags.ASYNC_INFLATE_BOUNCER) && childController == null - && securityMode != SecurityMode.None && securityMode != SecurityMode.Invalid) { - int layoutId = getLayoutIdFor(securityMode); - KeyguardInputView view = null; - if (layoutId != 0) { - if (DEBUG) Log.v(TAG, "inflating on main thread id = " + layoutId); - view = (KeyguardInputView) mLayoutInflater.inflate( - layoutId, mView, false); - mView.addView(view); - childController = mKeyguardSecurityViewControllerFactory.create( - view, securityMode, keyguardSecurityCallback); - childController.init(); - - mChildren.add(childController); - } - } - - if (childController == null) { - childController = new NullKeyguardInputViewController( - securityMode, keyguardSecurityCallback, - mEmergencyButtonControllerFactory.create(null)); - } - - return childController; + asynchronouslyInflateView(securityMode, keyguardSecurityCallback, onViewInflatedCallback); } /** @@ -143,7 +115,7 @@ public class KeyguardSecurityViewFlipperController */ public void asynchronouslyInflateView(SecurityMode securityMode, KeyguardSecurityCallback keyguardSecurityCallback, - @Nullable OnViewInflatedListener onViewInflatedListener) { + @Nullable OnViewInflatedCallback onViewInflatedListener) { int layoutId = getLayoutIdFor(securityMode); if (layoutId != 0) { if (DEBUG) Log.v(TAG, "inflating on bg thread id = " + layoutId); @@ -156,9 +128,8 @@ public class KeyguardSecurityViewFlipperController keyguardSecurityCallback); childController.init(); mChildren.add(childController); - mViewMediatorCallback.setNeedsInput(childController.needsInput()); if (onViewInflatedListener != null) { - onViewInflatedListener.onViewInflated(); + onViewInflatedListener.onViewInflated(childController); } }); } @@ -184,33 +155,9 @@ public class KeyguardSecurityViewFlipperController } } - private static class NullKeyguardInputViewController - extends KeyguardInputViewController { - protected NullKeyguardInputViewController(SecurityMode securityMode, - KeyguardSecurityCallback keyguardSecurityCallback, - EmergencyButtonController emergencyButtonController) { - super(null, securityMode, keyguardSecurityCallback, emergencyButtonController, - null); - } - - @Override - public boolean needsInput() { - return false; - } - - @Override - public void onStartingToHide() { - } - - @Override - protected int getInitialMessageResId() { - return 0; - } - } - /** Listener to when view has finished inflation. */ - public interface OnViewInflatedListener { + public interface OnViewInflatedCallback { /** Notifies that view has been inflated */ - void onViewInflated(); + void onViewInflated(KeyguardInputViewController controller); } } diff --git a/packages/SystemUI/src/com/android/keyguard/ViewMediatorCallback.java b/packages/SystemUI/src/com/android/keyguard/ViewMediatorCallback.java index 334bb1ec12cb9..9308773858e37 100644 --- a/packages/SystemUI/src/com/android/keyguard/ViewMediatorCallback.java +++ b/packages/SystemUI/src/com/android/keyguard/ViewMediatorCallback.java @@ -95,6 +95,11 @@ public interface ViewMediatorCallback { */ CharSequence consumeCustomMessage(); + /** + * Sets a message to be consumed the next time the bouncer shows up. + */ + void setCustomMessage(CharSequence customMessage); + /** * Call when cancel button is pressed in bouncer. */ diff --git a/packages/SystemUI/src/com/android/systemui/ActivityStarterDelegate.java b/packages/SystemUI/src/com/android/systemui/ActivityStarterDelegate.java index 7af6f6677f3f5..401f6c9c747dd 100644 --- a/packages/SystemUI/src/com/android/systemui/ActivityStarterDelegate.java +++ b/packages/SystemUI/src/com/android/systemui/ActivityStarterDelegate.java @@ -26,12 +26,12 @@ import com.android.systemui.dagger.SysUISingleton; import com.android.systemui.plugins.ActivityStarter; import com.android.systemui.statusbar.phone.CentralSurfaces; +import dagger.Lazy; + import java.util.Optional; import javax.inject.Inject; -import dagger.Lazy; - /** * Single common instance of ActivityStarter that can be gotten and referenced from anywhere, but * delegates to an actual implementation (CentralSurfaces). @@ -141,6 +141,14 @@ public class ActivityStarterDelegate implements ActivityStarter { starter -> starter.postStartActivityDismissingKeyguard(intent)); } + @Override + public void postStartActivityDismissingKeyguard(Intent intent, int delay, + @Nullable ActivityLaunchAnimator.Controller animationController, String customMessage) { + mActualStarterOptionalLazy.get().ifPresent( + starter -> starter.postStartActivityDismissingKeyguard(intent, delay, + animationController, customMessage)); + } + @Override public void postStartActivityDismissingKeyguard(PendingIntent intent, ActivityLaunchAnimator.Controller animationController) { @@ -161,4 +169,12 @@ public class ActivityStarterDelegate implements ActivityStarter { mActualStarterOptionalLazy.get().ifPresent( starter -> starter.dismissKeyguardThenExecute(action, cancel, afterKeyguardGone)); } + + @Override + public void dismissKeyguardThenExecute(OnDismissAction action, @Nullable Runnable cancel, + boolean afterKeyguardGone, String customMessage) { + mActualStarterOptionalLazy.get().ifPresent( + starter -> starter.dismissKeyguardThenExecute(action, cancel, afterKeyguardGone, + customMessage)); + } } diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java index 416b2379eef81..0fd479afcf481 100644 --- a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java +++ b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java @@ -857,6 +857,11 @@ public class KeyguardViewMediator implements CoreStartable, Dumpable, mCustomMessage = null; return message; } + + @Override + public void setCustomMessage(CharSequence customMessage) { + mCustomMessage = customMessage; + } }; /** diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardBottomAreaViewBinder.kt b/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardBottomAreaViewBinder.kt index 68ac7e1c71e5e..d96609c24dbd2 100644 --- a/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardBottomAreaViewBinder.kt +++ b/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardBottomAreaViewBinder.kt @@ -498,7 +498,7 @@ object KeyguardBottomAreaViewBinder { activityStarter: ActivityStarter, view: View, ) { - activityStarter.startActivity( + activityStarter.postStartActivityDismissingKeyguard( Intent(Intent.ACTION_SET_WALLPAPER).apply { flags = Intent.FLAG_ACTIVITY_NEW_TASK view.context @@ -506,8 +506,9 @@ object KeyguardBottomAreaViewBinder { .takeIf { it.isNotEmpty() } ?.let { packageName -> setPackage(packageName) } }, - /* dismissShade= */ true, - ActivityLaunchAnimator.Controller.fromView(view), + /* delay= */ 0, + /* animationController= */ ActivityLaunchAnimator.Controller.fromView(view), + /* customMessage= */ view.context.getString(R.string.keyguard_unlock_to_customize_ls) ) } diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardBouncerViewBinder.kt b/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardBouncerViewBinder.kt index 72dc7a4f7753d..6bbc6f61cc6fd 100644 --- a/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardBouncerViewBinder.kt +++ b/packages/SystemUI/src/com/android/systemui/keyguard/ui/binder/KeyguardBouncerViewBinder.kt @@ -193,7 +193,11 @@ object KeyguardBouncerViewBinder { launch { viewModel.bouncerShowMessage.collect { - securityContainerController.showMessage(it.message, it.colorStateList) + securityContainerController.showMessage( + it.message, + it.colorStateList, + /* animated= */ true + ) viewModel.onMessageShown() } } diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/CentralSurfaces.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/CentralSurfaces.java index 0195d4532ae0a..3a1272fa32e8d 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/CentralSurfaces.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/CentralSurfaces.java @@ -326,6 +326,13 @@ public interface CentralSurfaces extends Dumpable, ActivityStarter, LifecycleOwn @Nullable ActivityLaunchAnimator.Controller animationController, UserHandle userHandle); + /** Starts an activity intent that dismisses keyguard. */ + void startActivityDismissingKeyguard(Intent intent, boolean onlyProvisioned, + boolean dismissShade, boolean disallowEnterPictureInPictureWhileLaunching, + Callback callback, int flags, + @Nullable ActivityLaunchAnimator.Controller animationController, + UserHandle userHandle, @Nullable String customMessage); + void readyForKeyguardDone(); void executeRunnableDismissingKeyguard(Runnable runnable, @@ -339,7 +346,8 @@ public interface CentralSurfaces extends Dumpable, ActivityStarter, LifecycleOwn boolean dismissShade, boolean afterKeyguardGone, boolean deferred, - boolean willAnimateOnKeyguard); + boolean willAnimateOnKeyguard, + @Nullable String customMessage); void resetUserExpandedStates(); diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/CentralSurfacesImpl.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/CentralSurfacesImpl.java index 0ec20ca9a7e9a..0960efb7388f2 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/CentralSurfacesImpl.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/CentralSurfacesImpl.java @@ -2413,12 +2413,23 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { startActivityDismissingKeyguard(intent, onlyProvisioned, dismissShade, 0); } + @Override + public void startActivityDismissingKeyguard(Intent intent, boolean onlyProvisioned, + boolean dismissShade, boolean disallowEnterPictureInPictureWhileLaunching, + Callback callback, int flags, + @androidx.annotation.Nullable ActivityLaunchAnimator.Controller animationController, + UserHandle userHandle) { + startActivityDismissingKeyguard(intent, onlyProvisioned, dismissShade, + disallowEnterPictureInPictureWhileLaunching, callback, flags, animationController, + userHandle, null /* customMessage */); + } + @Override public void startActivityDismissingKeyguard(final Intent intent, boolean onlyProvisioned, final boolean dismissShade, final boolean disallowEnterPictureInPictureWhileLaunching, final Callback callback, int flags, @Nullable ActivityLaunchAnimator.Controller animationController, - final UserHandle userHandle) { + final UserHandle userHandle, @Nullable String customMessage) { if (onlyProvisioned && !mDeviceProvisionedController.isDeviceProvisioned()) return; final boolean willLaunchResolverActivity = @@ -2505,7 +2516,8 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { && mKeyguardStateController.isOccluded(); boolean deferred = !occluded; executeRunnableDismissingKeyguard(runnable, cancelRunnable, dismissShadeDirectly, - willLaunchResolverActivity, deferred /* deferred */, animate); + willLaunchResolverActivity, deferred /* deferred */, animate, + customMessage /* customMessage */); } /** @@ -2558,7 +2570,7 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { final boolean afterKeyguardGone, final boolean deferred) { executeRunnableDismissingKeyguard(runnable, cancelAction, dismissShade, afterKeyguardGone, - deferred, false /* willAnimateOnKeyguard */); + deferred, false /* willAnimateOnKeyguard */, null /* customMessage */); } @Override @@ -2567,7 +2579,8 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { final boolean dismissShade, final boolean afterKeyguardGone, final boolean deferred, - final boolean willAnimateOnKeyguard) { + final boolean willAnimateOnKeyguard, + @Nullable String customMessage) { OnDismissAction onDismissAction = new OnDismissAction() { @Override public boolean onDismiss() { @@ -2596,7 +2609,7 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { return willAnimateOnKeyguard; } }; - dismissKeyguardThenExecute(onDismissAction, cancelAction, afterKeyguardGone); + dismissKeyguardThenExecute(onDismissAction, cancelAction, afterKeyguardGone, customMessage); } private final BroadcastReceiver mBroadcastReceiver = new BroadcastReceiver() { @@ -2677,6 +2690,12 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { @Override public void dismissKeyguardThenExecute(OnDismissAction action, Runnable cancelAction, boolean afterKeyguardGone) { + dismissKeyguardThenExecute(action, cancelAction, afterKeyguardGone, null); + } + + @Override + public void dismissKeyguardThenExecute(OnDismissAction action, Runnable cancelAction, + boolean afterKeyguardGone, String customMessage) { if (!action.willRunAnimationOnKeyguard() && mWakefulnessLifecycle.getWakefulness() == WAKEFULNESS_ASLEEP && mKeyguardStateController.canDismissLockScreen() @@ -2689,7 +2708,7 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { } if (mKeyguardStateController.isShowing()) { mStatusBarKeyguardViewManager.dismissWithAction(action, cancelAction, - afterKeyguardGone); + afterKeyguardGone, customMessage); } else { // If the keyguard isn't showing but the device is dreaming, we should exit the dream. if (mKeyguardUpdateMonitor.isDreaming()) { @@ -2697,7 +2716,9 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { } action.onDismiss(); } + } + /** * Notify the shade controller that the current user changed * @@ -2902,6 +2923,14 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { @Override public void postStartActivityDismissingKeyguard(Intent intent, int delay, @Nullable ActivityLaunchAnimator.Controller animationController) { + postStartActivityDismissingKeyguard(intent, delay, animationController, + null /* customMessage */); + } + + @Override + public void postStartActivityDismissingKeyguard(Intent intent, int delay, + @Nullable ActivityLaunchAnimator.Controller animationController, + @Nullable String customMessage) { mMainExecutor.executeDelayed( () -> startActivityDismissingKeyguard(intent, true /* onlyProvisioned */, @@ -2910,7 +2939,7 @@ public class CentralSurfacesImpl implements CoreStartable, CentralSurfaces { null /* callback */, 0 /* flags */, animationController, - getActivityUserHandle(intent)), + getActivityUserHandle(intent), customMessage), delay); } diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarKeyguardViewManager.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarKeyguardViewManager.java index 49b58df23fdbf..70aab61ffed07 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarKeyguardViewManager.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBarKeyguardViewManager.java @@ -656,9 +656,11 @@ public class StatusBarKeyguardViewManager implements RemoteInputController.Callb } updateAlternateBouncerShowing(mAlternateBouncerInteractor.show()); + setKeyguardMessage(message, null); return; } + mViewMediatorCallback.setCustomMessage(message); if (afterKeyguardGone) { // we'll handle the dismiss action after keyguard is gone, so just show the // bouncer diff --git a/packages/SystemUI/tests/src/com/android/keyguard/KeyguardSecurityContainerControllerTest.java b/packages/SystemUI/tests/src/com/android/keyguard/KeyguardSecurityContainerControllerTest.java index 3e4fd891a668f..f4df26dec89e2 100644 --- a/packages/SystemUI/tests/src/com/android/keyguard/KeyguardSecurityContainerControllerTest.java +++ b/packages/SystemUI/tests/src/com/android/keyguard/KeyguardSecurityContainerControllerTest.java @@ -16,8 +16,6 @@ package com.android.keyguard; -import static android.view.WindowInsets.Type.ime; - import static com.android.keyguard.KeyguardSecurityContainer.MODE_DEFAULT; import static com.android.keyguard.KeyguardSecurityContainer.MODE_ONE_HANDED; @@ -29,9 +27,9 @@ import static junit.framework.Assert.assertTrue; import static org.mockito.ArgumentMatchers.any; import static org.mockito.ArgumentMatchers.anyBoolean; import static org.mockito.ArgumentMatchers.anyInt; -import static org.mockito.ArgumentMatchers.anyLong; import static org.mockito.ArgumentMatchers.argThat; import static org.mockito.ArgumentMatchers.eq; +import static org.mockito.Mockito.atLeastOnce; import static org.mockito.Mockito.clearInvocations; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.never; @@ -164,6 +162,10 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { @Captor private ArgumentCaptor mSwipeListenerArgumentCaptor; + @Captor + private ArgumentCaptor + mOnViewInflatedCallbackArgumentCaptor; + private KeyguardSecurityContainerController mKeyguardSecurityContainerController; private KeyguardPasswordViewController mKeyguardPasswordViewController; private KeyguardPasswordView mKeyguardPasswordView; @@ -184,8 +186,6 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { when(mAdminSecondaryLockScreenControllerFactory.create(any(KeyguardSecurityCallback.class))) .thenReturn(mAdminSecondaryLockScreenController); when(mSecurityViewFlipper.getWindowInsetsController()).thenReturn(mWindowInsetsController); - when(mKeyguardSecurityViewFlipperController.getSecurityView(any(SecurityMode.class), - any(KeyguardSecurityCallback.class))).thenReturn(mInputViewController); mKeyguardPasswordView = spy((KeyguardPasswordView) LayoutInflater.from(mContext).inflate( R.layout.keyguard_password_view, null)); when(mKeyguardPasswordView.getRootView()).thenReturn(mSecurityViewFlipper); @@ -230,28 +230,18 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { mKeyguardSecurityContainerController.showSecurityScreen(mode); if (mode == SecurityMode.Invalid) { verify(mKeyguardSecurityViewFlipperController, never()).getSecurityView( - any(SecurityMode.class), any(KeyguardSecurityCallback.class)); + any(SecurityMode.class), any(KeyguardSecurityCallback.class), any( + KeyguardSecurityViewFlipperController.OnViewInflatedCallback.class) + ); } else { verify(mKeyguardSecurityViewFlipperController).getSecurityView( - eq(mode), any(KeyguardSecurityCallback.class)); + eq(mode), any(KeyguardSecurityCallback.class), any( + KeyguardSecurityViewFlipperController.OnViewInflatedCallback.class) + ); } } } - @Test - public void startDisappearAnimation_animatesKeyboard() { - when(mKeyguardSecurityModel.getSecurityMode(anyInt())).thenReturn( - SecurityMode.Password); - when(mKeyguardSecurityViewFlipperController.getSecurityView( - eq(SecurityMode.Password), any(KeyguardSecurityCallback.class))) - .thenReturn((KeyguardInputViewController) mKeyguardPasswordViewController); - mKeyguardSecurityContainerController.showSecurityScreen(SecurityMode.Password); - - mKeyguardSecurityContainerController.startDisappearAnimation(null); - verify(mWindowInsetsController).controlWindowInsetsAnimation( - eq(ime()), anyLong(), any(), any(), any()); - } - @Test public void onResourcesUpdate_callsThroughOnRotationChange() { clearInvocations(mView); @@ -300,9 +290,7 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { @Test public void showSecurityScreen_oneHandedMode_flagDisabled_noOneHandedMode() { mTestableResources.addOverride(R.bool.can_use_one_handed_bouncer, false); - when(mKeyguardSecurityViewFlipperController.getSecurityView( - eq(SecurityMode.Pattern), any(KeyguardSecurityCallback.class))) - .thenReturn((KeyguardInputViewController) mKeyguardPasswordViewController); + setupGetSecurityView(SecurityMode.Pattern); mKeyguardSecurityContainerController.showSecurityScreen(SecurityMode.Pattern); verify(mView).initMode(eq(MODE_DEFAULT), eq(mGlobalSettings), eq(mFalsingManager), @@ -314,11 +302,7 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { @Test public void showSecurityScreen_oneHandedMode_flagEnabled_oneHandedMode() { mTestableResources.addOverride(R.bool.can_use_one_handed_bouncer, true); - when(mKeyguardSecurityViewFlipperController.getSecurityView( - eq(SecurityMode.Pattern), any(KeyguardSecurityCallback.class))) - .thenReturn((KeyguardInputViewController) mKeyguardPasswordViewController); - - mKeyguardSecurityContainerController.showSecurityScreen(SecurityMode.Pattern); + setupGetSecurityView(SecurityMode.Pattern); verify(mView).initMode(eq(MODE_ONE_HANDED), eq(mGlobalSettings), eq(mFalsingManager), eq(mUserSwitcherController), any(KeyguardSecurityContainer.UserSwitcherViewMode.UserSwitcherCallback.class), @@ -328,9 +312,8 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { @Test public void showSecurityScreen_twoHandedMode_flagEnabled_noOneHandedMode() { mTestableResources.addOverride(R.bool.can_use_one_handed_bouncer, true); - setupGetSecurityView(); + setupGetSecurityView(SecurityMode.Password); - mKeyguardSecurityContainerController.showSecurityScreen(SecurityMode.Password); verify(mView).initMode(eq(MODE_DEFAULT), eq(mGlobalSettings), eq(mFalsingManager), eq(mUserSwitcherController), any(KeyguardSecurityContainer.UserSwitcherViewMode.UserSwitcherCallback.class), @@ -342,17 +325,18 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { ArgumentCaptor captor = ArgumentCaptor.forClass( KeyguardSecurityContainer.UserSwitcherViewMode.UserSwitcherCallback.class); + setupGetSecurityView(SecurityMode.Password); - setupGetSecurityView(); - - mKeyguardSecurityContainerController.showSecurityScreen(SecurityMode.Password); verify(mView).initMode(anyInt(), any(GlobalSettings.class), any(FalsingManager.class), any(UserSwitcherController.class), captor.capture(), eq(mFalsingA11yDelegate)); captor.getValue().showUnlockToContinueMessage(); + getViewControllerImmediately(); verify(mKeyguardPasswordViewControllerMock).showMessage( - getContext().getString(R.string.keyguard_unlock_to_continue), null); + /* message= */ getContext().getString(R.string.keyguard_unlock_to_continue), + /* colorState= */ null, + /* animated= */ true); } @Test @@ -455,7 +439,7 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { KeyguardSecurityContainer.SwipeListener registeredSwipeListener = getRegisteredSwipeListener(); when(mKeyguardUpdateMonitor.isFaceDetectionRunning()).thenReturn(false); - setupGetSecurityView(); + setupGetSecurityView(SecurityMode.Password); registeredSwipeListener.onSwipeUp(); @@ -481,11 +465,14 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { getRegisteredSwipeListener(); when(mKeyguardUpdateMonitor.requestFaceAuth(FaceAuthApiRequestReason.SWIPE_UP_ON_BOUNCER)) .thenReturn(true); - setupGetSecurityView(); + setupGetSecurityView(SecurityMode.Password); + clearInvocations(mKeyguardSecurityViewFlipperController); registeredSwipeListener.onSwipeUp(); + getViewControllerImmediately(); - verify(mKeyguardPasswordViewControllerMock).showMessage(null, null); + verify(mKeyguardPasswordViewControllerMock).showMessage(/* message= */ + null, /* colorState= */ null, /* animated= */ true); } @Test @@ -494,11 +481,12 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { getRegisteredSwipeListener(); when(mKeyguardUpdateMonitor.requestFaceAuth(FaceAuthApiRequestReason.SWIPE_UP_ON_BOUNCER)) .thenReturn(false); - setupGetSecurityView(); + setupGetSecurityView(SecurityMode.Password); registeredSwipeListener.onSwipeUp(); - verify(mKeyguardPasswordViewControllerMock, never()).showMessage(null, null); + verify(mKeyguardPasswordViewControllerMock, never()).showMessage(/* message= */ + null, /* colorState= */ null, /* animated= */ true); } @Test @@ -512,10 +500,15 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { configurationListenerArgumentCaptor.getValue().onDensityOrFontScaleChanged(); - verify(mView).onDensityOrFontScaleChanged(); verify(mKeyguardSecurityViewFlipperController).clearViews(); - verify(mKeyguardSecurityViewFlipperController).getSecurityView(eq(SecurityMode.PIN), - any(KeyguardSecurityCallback.class)); + verify(mKeyguardSecurityViewFlipperController).asynchronouslyInflateView( + eq(SecurityMode.PIN), + any(KeyguardSecurityCallback.class), + mOnViewInflatedCallbackArgumentCaptor.capture()); + + mOnViewInflatedCallbackArgumentCaptor.getValue().onViewInflated(mInputViewController); + + verify(mView).onDensityOrFontScaleChanged(); } @Test @@ -529,12 +522,17 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { configurationListenerArgumentCaptor.getValue().onThemeChanged(); - verify(mView).reloadColors(); verify(mKeyguardSecurityViewFlipperController).clearViews(); - verify(mKeyguardSecurityViewFlipperController).getSecurityView(eq(SecurityMode.PIN), - any(KeyguardSecurityCallback.class)); + verify(mKeyguardSecurityViewFlipperController).asynchronouslyInflateView( + eq(SecurityMode.PIN), + any(KeyguardSecurityCallback.class), + mOnViewInflatedCallbackArgumentCaptor.capture()); + + mOnViewInflatedCallbackArgumentCaptor.getValue().onViewInflated(mInputViewController); + verify(mView).reset(); verify(mKeyguardSecurityViewFlipperController).reset(); + verify(mView).reloadColors(); } @Test @@ -548,10 +546,15 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { configurationListenerArgumentCaptor.getValue().onUiModeChanged(); - verify(mView).reloadColors(); verify(mKeyguardSecurityViewFlipperController).clearViews(); - verify(mKeyguardSecurityViewFlipperController).getSecurityView(eq(SecurityMode.PIN), - any(KeyguardSecurityCallback.class)); + verify(mKeyguardSecurityViewFlipperController).asynchronouslyInflateView( + eq(SecurityMode.PIN), + any(KeyguardSecurityCallback.class), + mOnViewInflatedCallbackArgumentCaptor.capture()); + + mOnViewInflatedCallbackArgumentCaptor.getValue().onViewInflated(mInputViewController); + + verify(mView).reloadColors(); } @Test @@ -614,6 +617,11 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { @Test public void testOnStartingToHide() { mKeyguardSecurityContainerController.onStartingToHide(); + verify(mKeyguardSecurityViewFlipperController).getSecurityView(any(SecurityMode.class), + any(KeyguardSecurityCallback.class), + mOnViewInflatedCallbackArgumentCaptor.capture()); + + mOnViewInflatedCallbackArgumentCaptor.getValue().onViewInflated(mInputViewController); verify(mInputViewController).onStartingToHide(); } @@ -673,26 +681,17 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { verify(mView).updatePositionByTouchX(1.0f); } - - @Test - public void testReinflateViewFlipper() { - mKeyguardSecurityContainerController.reinflateViewFlipper(() -> {}); - verify(mKeyguardSecurityViewFlipperController).clearViews(); - verify(mKeyguardSecurityViewFlipperController).getSecurityView(any(SecurityMode.class), - any(KeyguardSecurityCallback.class)); - } - @Test public void testReinflateViewFlipper_asyncBouncerFlagOn() { when(mFeatureFlags.isEnabled(Flags.ASYNC_INFLATE_BOUNCER)).thenReturn(true); - KeyguardSecurityViewFlipperController.OnViewInflatedListener onViewInflatedListener = - () -> { + KeyguardSecurityViewFlipperController.OnViewInflatedCallback onViewInflatedCallback = + controller -> { }; - mKeyguardSecurityContainerController.reinflateViewFlipper(onViewInflatedListener); + mKeyguardSecurityContainerController.reinflateViewFlipper(onViewInflatedCallback); verify(mKeyguardSecurityViewFlipperController).clearViews(); verify(mKeyguardSecurityViewFlipperController).asynchronouslyInflateView( any(SecurityMode.class), - any(KeyguardSecurityCallback.class), eq(onViewInflatedListener)); + any(KeyguardSecurityCallback.class), eq(onViewInflatedCallback)); } @Test @@ -715,14 +714,17 @@ public class KeyguardSecurityContainerControllerTest extends SysuiTestCase { return mSwipeListenerArgumentCaptor.getValue(); } - private void attachView() { - mKeyguardSecurityContainerController.onViewAttached(); - verify(mKeyguardUpdateMonitor).registerCallback(mKeyguardUpdateMonitorCallback.capture()); + private void setupGetSecurityView(SecurityMode securityMode) { + mKeyguardSecurityContainerController.showSecurityScreen(securityMode); + getViewControllerImmediately(); } - private void setupGetSecurityView() { - when(mKeyguardSecurityViewFlipperController.getSecurityView( - any(), any(KeyguardSecurityCallback.class))) - .thenReturn((KeyguardInputViewController) mKeyguardPasswordViewControllerMock); + private void getViewControllerImmediately() { + verify(mKeyguardSecurityViewFlipperController, atLeastOnce()).getSecurityView( + any(SecurityMode.class), any(), + mOnViewInflatedCallbackArgumentCaptor.capture()); + mOnViewInflatedCallbackArgumentCaptor.getValue().onViewInflated( + (KeyguardInputViewController) mKeyguardPasswordViewControllerMock); + } } diff --git a/packages/SystemUI/tests/src/com/android/keyguard/KeyguardSecurityViewFlipperControllerTest.java b/packages/SystemUI/tests/src/com/android/keyguard/KeyguardSecurityViewFlipperControllerTest.java index eaf7b1ec21005..cd187540ba742 100644 --- a/packages/SystemUI/tests/src/com/android/keyguard/KeyguardSecurityViewFlipperControllerTest.java +++ b/packages/SystemUI/tests/src/com/android/keyguard/KeyguardSecurityViewFlipperControllerTest.java @@ -78,8 +78,6 @@ public class KeyguardSecurityViewFlipperControllerTest extends SysuiTestCase { private KeyguardSecurityCallback mKeyguardSecurityCallback; @Mock private FeatureFlags mFeatureFlags; - @Mock - private ViewMediatorCallback mViewMediatorCallback; private KeyguardSecurityViewFlipperController mKeyguardSecurityViewFlipperController; @@ -96,7 +94,7 @@ public class KeyguardSecurityViewFlipperControllerTest extends SysuiTestCase { mKeyguardSecurityViewFlipperController = new KeyguardSecurityViewFlipperController(mView, mLayoutInflater, mAsyncLayoutInflater, mKeyguardSecurityViewControllerFactory, - mEmergencyButtonControllerFactory, mFeatureFlags, mViewMediatorCallback); + mEmergencyButtonControllerFactory, mFeatureFlags); } @Test @@ -108,16 +106,28 @@ public class KeyguardSecurityViewFlipperControllerTest extends SysuiTestCase { reset(mLayoutInflater); when(mLayoutInflater.inflate(anyInt(), eq(mView), eq(false))) .thenReturn(mInputView); - mKeyguardSecurityViewFlipperController.getSecurityView(mode, mKeyguardSecurityCallback); - if (mode == SecurityMode.Invalid || mode == SecurityMode.None) { - verify(mLayoutInflater, never()).inflate( - anyInt(), any(ViewGroup.class), anyBoolean()); - } else { - verify(mLayoutInflater).inflate(anyInt(), eq(mView), eq(false)); - } + mKeyguardSecurityViewFlipperController.getSecurityView(mode, mKeyguardSecurityCallback, + controller -> { + if (mode == SecurityMode.Invalid || mode == SecurityMode.None) { + verify(mLayoutInflater, never()).inflate( + anyInt(), any(ViewGroup.class), anyBoolean()); + } else { + verify(mLayoutInflater).inflate(anyInt(), eq(mView), eq(false)); + } + }); } } + @Test + public void getSecurityView_NotInflated() { + mKeyguardSecurityViewFlipperController.clearViews(); + mKeyguardSecurityViewFlipperController.getSecurityView(SecurityMode.PIN, + mKeyguardSecurityCallback, + controller -> {}); + verify(mAsyncLayoutInflater).inflate(anyInt(), eq(mView), any( + AsyncLayoutInflater.OnInflateFinishedListener.class)); + } + @Test public void asynchronouslyInflateView() { mKeyguardSecurityViewFlipperController.asynchronouslyInflateView(SecurityMode.PIN, @@ -136,7 +146,6 @@ public class KeyguardSecurityViewFlipperControllerTest extends SysuiTestCase { argumentCaptor.getValue().onInflateFinished( LayoutInflater.from(getContext()).inflate(R.layout.keyguard_password_view, null), R.layout.keyguard_password_view, mView); - verify(mViewMediatorCallback).setNeedsInput(anyBoolean()); } @Test diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/CentralSurfacesImplTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/CentralSurfacesImplTest.java index 48710a42f6160..63320693831c1 100644 --- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/CentralSurfacesImplTest.java +++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/CentralSurfacesImplTest.java @@ -1278,12 +1278,13 @@ public class CentralSurfacesImplTest extends SysuiTestCase { new Intent(), /* onlyProvisioned = */false, /* dismissShade = */false); - verify(mStatusBarKeyguardViewManager).addAfterKeyguardGoneRunnable(any(Runnable.class)); ArgumentCaptor onDismissActionCaptor = ArgumentCaptor.forClass(OnDismissAction.class); verify(mStatusBarKeyguardViewManager) - .dismissWithAction(onDismissActionCaptor.capture(), any(Runnable.class), eq(true)); + .dismissWithAction(onDismissActionCaptor.capture(), any(Runnable.class), eq(true), + eq(null)); assertThat(onDismissActionCaptor.getValue().onDismiss()).isFalse(); + verify(mStatusBarKeyguardViewManager).addAfterKeyguardGoneRunnable(any(Runnable.class)); } @Test