KeyguardBottomAreaView: cleanup.
1. Removes the feature flag 2. Removes dead code Fix: 241137298 Test: Manually verified that the home controls button shows up in the lock-screen, animates properly, and responds to clicks properly. The device can be unlocked and re-loced. Change-Id: I7a76bdf84ede1c67e5901487d5572a9c1704fc68 Merged-In: I7a76bdf84ede1c67e5901487d5572a9c1704fc68
This commit is contained in:
committed by
Ale Nijamkin
parent
d2a99344b0
commit
2470dfa8f0
@@ -83,48 +83,6 @@
|
|||||||
android:layout_marginBottom="@dimen/keyguard_affordance_vertical_offset"
|
android:layout_marginBottom="@dimen/keyguard_affordance_vertical_offset"
|
||||||
android:visibility="gone" />
|
android:visibility="gone" />
|
||||||
|
|
||||||
<ImageView
|
|
||||||
android:id="@+id/wallet_button"
|
|
||||||
android:layout_height="@dimen/keyguard_affordance_fixed_height"
|
|
||||||
android:layout_width="@dimen/keyguard_affordance_fixed_width"
|
|
||||||
android:layout_gravity="bottom|end"
|
|
||||||
android:scaleType="center"
|
|
||||||
android:tint="?android:attr/textColorPrimary"
|
|
||||||
android:src="@drawable/ic_wallet_lockscreen"
|
|
||||||
android:background="@drawable/keyguard_bottom_affordance_bg"
|
|
||||||
android:layout_marginEnd="@dimen/keyguard_affordance_horizontal_offset"
|
|
||||||
android:layout_marginBottom="@dimen/keyguard_affordance_vertical_offset"
|
|
||||||
android:contentDescription="@string/accessibility_wallet_button"
|
|
||||||
android:visibility="gone" />
|
|
||||||
|
|
||||||
<ImageView
|
|
||||||
android:id="@+id/qr_code_scanner_button"
|
|
||||||
android:layout_height="@dimen/keyguard_affordance_fixed_height"
|
|
||||||
android:layout_width="@dimen/keyguard_affordance_fixed_width"
|
|
||||||
android:layout_gravity="bottom|end"
|
|
||||||
android:scaleType="center"
|
|
||||||
android:tint="?android:attr/textColorPrimary"
|
|
||||||
android:src="@drawable/ic_qr_code_scanner"
|
|
||||||
android:background="@drawable/keyguard_bottom_affordance_bg"
|
|
||||||
android:layout_marginEnd="@dimen/keyguard_affordance_horizontal_offset"
|
|
||||||
android:layout_marginBottom="@dimen/keyguard_affordance_vertical_offset"
|
|
||||||
android:contentDescription="@string/accessibility_qr_code_scanner_button"
|
|
||||||
android:visibility="gone" />
|
|
||||||
|
|
||||||
<ImageView
|
|
||||||
android:id="@+id/controls_button"
|
|
||||||
android:layout_height="@dimen/keyguard_affordance_fixed_height"
|
|
||||||
android:layout_width="@dimen/keyguard_affordance_fixed_width"
|
|
||||||
android:layout_gravity="bottom|start"
|
|
||||||
android:scaleType="center"
|
|
||||||
android:tint="?android:attr/textColorPrimary"
|
|
||||||
android:src="@drawable/controls_icon"
|
|
||||||
android:background="@drawable/keyguard_bottom_affordance_bg"
|
|
||||||
android:layout_marginStart="@dimen/keyguard_affordance_horizontal_offset"
|
|
||||||
android:layout_marginBottom="@dimen/keyguard_affordance_vertical_offset"
|
|
||||||
android:contentDescription="@string/quick_controls_title"
|
|
||||||
android:visibility="gone" />
|
|
||||||
|
|
||||||
<FrameLayout
|
<FrameLayout
|
||||||
android:id="@+id/overlay_container"
|
android:id="@+id/overlay_container"
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
|
|||||||
@@ -50,12 +50,10 @@ constructor(
|
|||||||
viewsIdToTranslate =
|
viewsIdToTranslate =
|
||||||
setOf(
|
setOf(
|
||||||
ViewIdToTranslate(R.id.keyguard_status_area, LEFT, filterNever),
|
ViewIdToTranslate(R.id.keyguard_status_area, LEFT, filterNever),
|
||||||
ViewIdToTranslate(R.id.controls_button, LEFT, filterNever),
|
|
||||||
ViewIdToTranslate(R.id.lockscreen_clock_view_large, LEFT, filterSplitShadeOnly),
|
ViewIdToTranslate(R.id.lockscreen_clock_view_large, LEFT, filterSplitShadeOnly),
|
||||||
ViewIdToTranslate(R.id.lockscreen_clock_view, LEFT, filterNever),
|
ViewIdToTranslate(R.id.lockscreen_clock_view, LEFT, filterNever),
|
||||||
ViewIdToTranslate(
|
ViewIdToTranslate(
|
||||||
R.id.notification_stack_scroller, RIGHT, filterSplitShadeOnly),
|
R.id.notification_stack_scroller, RIGHT, filterSplitShadeOnly),
|
||||||
ViewIdToTranslate(R.id.wallet_button, RIGHT, filterNever),
|
|
||||||
ViewIdToTranslate(R.id.start_button, LEFT, filterNever),
|
ViewIdToTranslate(R.id.start_button, LEFT, filterNever),
|
||||||
ViewIdToTranslate(R.id.end_button, RIGHT, filterNever)),
|
ViewIdToTranslate(R.id.end_button, RIGHT, filterNever)),
|
||||||
progressProvider = unfoldProgressProvider)
|
progressProvider = unfoldProgressProvider)
|
||||||
|
|||||||
@@ -88,13 +88,6 @@ public class Flags {
|
|||||||
public static final ResourceBooleanFlag FACE_SCANNING_ANIM =
|
public static final ResourceBooleanFlag FACE_SCANNING_ANIM =
|
||||||
new ResourceBooleanFlag(205, R.bool.config_enableFaceScanningAnimation);
|
new ResourceBooleanFlag(205, R.bool.config_enableFaceScanningAnimation);
|
||||||
|
|
||||||
/**
|
|
||||||
* Whether the KeyguardBottomArea(View|Controller) should use the modern architecture or the old
|
|
||||||
* one.
|
|
||||||
*/
|
|
||||||
public static final ReleasedFlag MODERN_BOTTOM_AREA = new ReleasedFlag(206, true);
|
|
||||||
|
|
||||||
|
|
||||||
public static final UnreleasedFlag LOCKSCREEN_CUSTOM_CLOCKS = new UnreleasedFlag(207);
|
public static final UnreleasedFlag LOCKSCREEN_CUSTOM_CLOCKS = new UnreleasedFlag(207);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -116,7 +116,6 @@ import com.android.systemui.biometrics.AuthController;
|
|||||||
import com.android.systemui.camera.CameraGestureHelper;
|
import com.android.systemui.camera.CameraGestureHelper;
|
||||||
import com.android.systemui.classifier.Classifier;
|
import com.android.systemui.classifier.Classifier;
|
||||||
import com.android.systemui.classifier.FalsingCollector;
|
import com.android.systemui.classifier.FalsingCollector;
|
||||||
import com.android.systemui.controls.dagger.ControlsComponent;
|
|
||||||
import com.android.systemui.dagger.SysUISingleton;
|
import com.android.systemui.dagger.SysUISingleton;
|
||||||
import com.android.systemui.dagger.qualifiers.DisplayId;
|
import com.android.systemui.dagger.qualifiers.DisplayId;
|
||||||
import com.android.systemui.dagger.qualifiers.Main;
|
import com.android.systemui.dagger.qualifiers.Main;
|
||||||
@@ -139,7 +138,6 @@ import com.android.systemui.plugins.FalsingManager.FalsingTapListener;
|
|||||||
import com.android.systemui.plugins.qs.QS;
|
import com.android.systemui.plugins.qs.QS;
|
||||||
import com.android.systemui.plugins.statusbar.StatusBarStateController;
|
import com.android.systemui.plugins.statusbar.StatusBarStateController;
|
||||||
import com.android.systemui.plugins.statusbar.StatusBarStateController.StateListener;
|
import com.android.systemui.plugins.statusbar.StatusBarStateController.StateListener;
|
||||||
import com.android.systemui.qrcodescanner.controller.QRCodeScannerController;
|
|
||||||
import com.android.systemui.screenrecord.RecordingController;
|
import com.android.systemui.screenrecord.RecordingController;
|
||||||
import com.android.systemui.shade.transition.ShadeTransitionController;
|
import com.android.systemui.shade.transition.ShadeTransitionController;
|
||||||
import com.android.systemui.shared.system.QuickStepContract;
|
import com.android.systemui.shared.system.QuickStepContract;
|
||||||
@@ -216,7 +214,6 @@ import com.android.systemui.util.LargeScreenUtils;
|
|||||||
import com.android.systemui.util.ListenerSet;
|
import com.android.systemui.util.ListenerSet;
|
||||||
import com.android.systemui.util.Utils;
|
import com.android.systemui.util.Utils;
|
||||||
import com.android.systemui.util.time.SystemClock;
|
import com.android.systemui.util.time.SystemClock;
|
||||||
import com.android.systemui.wallet.controller.QuickAccessWalletController;
|
|
||||||
import com.android.wm.shell.animation.FlingAnimationUtils;
|
import com.android.wm.shell.animation.FlingAnimationUtils;
|
||||||
|
|
||||||
import java.io.PrintWriter;
|
import java.io.PrintWriter;
|
||||||
@@ -324,9 +321,6 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
private final FragmentService mFragmentService;
|
private final FragmentService mFragmentService;
|
||||||
private final ScrimController mScrimController;
|
private final ScrimController mScrimController;
|
||||||
private final PrivacyDotViewController mPrivacyDotViewController;
|
private final PrivacyDotViewController mPrivacyDotViewController;
|
||||||
private final QuickAccessWalletController mQuickAccessWalletController;
|
|
||||||
private final QRCodeScannerController mQRCodeScannerController;
|
|
||||||
private final ControlsComponent mControlsComponent;
|
|
||||||
private final NotificationRemoteInputManager mRemoteInputManager;
|
private final NotificationRemoteInputManager mRemoteInputManager;
|
||||||
|
|
||||||
private final LockscreenShadeTransitionController mLockscreenShadeTransitionController;
|
private final LockscreenShadeTransitionController mLockscreenShadeTransitionController;
|
||||||
@@ -695,8 +689,8 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
};
|
};
|
||||||
|
|
||||||
private final CameraGestureHelper mCameraGestureHelper;
|
private final CameraGestureHelper mCameraGestureHelper;
|
||||||
private final Provider<KeyguardBottomAreaViewModel> mKeyguardBottomAreaViewModelProvider;
|
private final KeyguardBottomAreaViewModel mKeyguardBottomAreaViewModel;
|
||||||
private final Provider<KeyguardBottomAreaInteractor> mKeyguardBottomAreaInteractorProvider;
|
private final KeyguardBottomAreaInteractor mKeyguardBottomAreaInteractor;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
public NotificationPanelViewController(NotificationPanelView view,
|
public NotificationPanelViewController(NotificationPanelView view,
|
||||||
@@ -745,8 +739,6 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
NavigationModeController navigationModeController,
|
NavigationModeController navigationModeController,
|
||||||
FragmentService fragmentService,
|
FragmentService fragmentService,
|
||||||
ContentResolver contentResolver,
|
ContentResolver contentResolver,
|
||||||
QuickAccessWalletController quickAccessWalletController,
|
|
||||||
QRCodeScannerController qrCodeScannerController,
|
|
||||||
RecordingController recordingController,
|
RecordingController recordingController,
|
||||||
LargeScreenShadeHeaderController largeScreenShadeHeaderController,
|
LargeScreenShadeHeaderController largeScreenShadeHeaderController,
|
||||||
ScreenOffAnimationController screenOffAnimationController,
|
ScreenOffAnimationController screenOffAnimationController,
|
||||||
@@ -754,7 +746,6 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
PanelExpansionStateManager panelExpansionStateManager,
|
PanelExpansionStateManager panelExpansionStateManager,
|
||||||
NotificationRemoteInputManager remoteInputManager,
|
NotificationRemoteInputManager remoteInputManager,
|
||||||
Optional<SysUIUnfoldComponent> unfoldComponent,
|
Optional<SysUIUnfoldComponent> unfoldComponent,
|
||||||
ControlsComponent controlsComponent,
|
|
||||||
InteractionJankMonitor interactionJankMonitor,
|
InteractionJankMonitor interactionJankMonitor,
|
||||||
QsFrameTranslateController qsFrameTranslateController,
|
QsFrameTranslateController qsFrameTranslateController,
|
||||||
SysUiState sysUiState,
|
SysUiState sysUiState,
|
||||||
@@ -767,8 +758,8 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
ShadeTransitionController shadeTransitionController,
|
ShadeTransitionController shadeTransitionController,
|
||||||
SystemClock systemClock,
|
SystemClock systemClock,
|
||||||
CameraGestureHelper cameraGestureHelper,
|
CameraGestureHelper cameraGestureHelper,
|
||||||
Provider<KeyguardBottomAreaViewModel> keyguardBottomAreaViewModelProvider,
|
KeyguardBottomAreaViewModel keyguardBottomAreaViewModel,
|
||||||
Provider<KeyguardBottomAreaInteractor> keyguardBottomAreaInteractorProvider) {
|
KeyguardBottomAreaInteractor keyguardBottomAreaInteractor) {
|
||||||
super(view,
|
super(view,
|
||||||
falsingManager,
|
falsingManager,
|
||||||
dozeLog,
|
dozeLog,
|
||||||
@@ -790,9 +781,6 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
mVibratorHelper = vibratorHelper;
|
mVibratorHelper = vibratorHelper;
|
||||||
mKeyguardMediaController = keyguardMediaController;
|
mKeyguardMediaController = keyguardMediaController;
|
||||||
mPrivacyDotViewController = privacyDotViewController;
|
mPrivacyDotViewController = privacyDotViewController;
|
||||||
mQuickAccessWalletController = quickAccessWalletController;
|
|
||||||
mQRCodeScannerController = qrCodeScannerController;
|
|
||||||
mControlsComponent = controlsComponent;
|
|
||||||
mMetricsLogger = metricsLogger;
|
mMetricsLogger = metricsLogger;
|
||||||
mConfigurationController = configurationController;
|
mConfigurationController = configurationController;
|
||||||
mFlingAnimationUtilsBuilder = flingAnimationUtilsBuilder;
|
mFlingAnimationUtilsBuilder = flingAnimationUtilsBuilder;
|
||||||
@@ -896,7 +884,7 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
|
|
||||||
mQsFrameTranslateController = qsFrameTranslateController;
|
mQsFrameTranslateController = qsFrameTranslateController;
|
||||||
updateUserSwitcherFlags();
|
updateUserSwitcherFlags();
|
||||||
mKeyguardBottomAreaViewModelProvider = keyguardBottomAreaViewModelProvider;
|
mKeyguardBottomAreaViewModel = keyguardBottomAreaViewModel;
|
||||||
onFinishInflate();
|
onFinishInflate();
|
||||||
keyguardUnlockAnimationController.addKeyguardUnlockAnimationListener(
|
keyguardUnlockAnimationController.addKeyguardUnlockAnimationListener(
|
||||||
new KeyguardUnlockAnimationController.KeyguardUnlockAnimationListener() {
|
new KeyguardUnlockAnimationController.KeyguardUnlockAnimationListener() {
|
||||||
@@ -950,7 +938,7 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
mCameraGestureHelper = cameraGestureHelper;
|
mCameraGestureHelper = cameraGestureHelper;
|
||||||
mKeyguardBottomAreaInteractorProvider = keyguardBottomAreaInteractorProvider;
|
mKeyguardBottomAreaInteractor = keyguardBottomAreaInteractor;
|
||||||
}
|
}
|
||||||
|
|
||||||
@VisibleForTesting
|
@VisibleForTesting
|
||||||
@@ -1275,17 +1263,7 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void initBottomArea() {
|
private void initBottomArea() {
|
||||||
if (mFeatureFlags.isEnabled(Flags.MODERN_BOTTOM_AREA)) {
|
mKeyguardBottomArea.init(mKeyguardBottomAreaViewModel, mFalsingManager);
|
||||||
mKeyguardBottomArea.init(mKeyguardBottomAreaViewModelProvider.get(), mFalsingManager);
|
|
||||||
} else {
|
|
||||||
// TODO(b/235403546): remove this method call when the new implementation is complete
|
|
||||||
// and these are not needed.
|
|
||||||
mKeyguardBottomArea.init(
|
|
||||||
mFalsingManager,
|
|
||||||
mQuickAccessWalletController,
|
|
||||||
mControlsComponent,
|
|
||||||
mQRCodeScannerController);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@VisibleForTesting
|
@VisibleForTesting
|
||||||
@@ -1402,7 +1380,6 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
}
|
}
|
||||||
|
|
||||||
mNotificationStackScrollLayoutController.setIntrinsicPadding(stackScrollerPadding);
|
mNotificationStackScrollLayoutController.setIntrinsicPadding(stackScrollerPadding);
|
||||||
mKeyguardBottomArea.setAntiBurnInOffsetX(mClockPositionResult.clockX);
|
|
||||||
|
|
||||||
mStackScrollerMeasuringPass++;
|
mStackScrollerMeasuringPass++;
|
||||||
requestScrollerTopPaddingUpdate(animate);
|
requestScrollerTopPaddingUpdate(animate);
|
||||||
@@ -1452,7 +1429,7 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
mKeyguardStatusViewController.getClockBottom(mStatusBarHeaderHeightKeyguard),
|
mKeyguardStatusViewController.getClockBottom(mStatusBarHeaderHeightKeyguard),
|
||||||
mKeyguardStatusViewController.isClockTopAligned());
|
mKeyguardStatusViewController.isClockTopAligned());
|
||||||
mClockPositionAlgorithm.run(mClockPositionResult);
|
mClockPositionAlgorithm.run(mClockPositionResult);
|
||||||
mKeyguardBottomAreaInteractorProvider.get().setClockPosition(
|
mKeyguardBottomAreaInteractor.setClockPosition(
|
||||||
mClockPositionResult.clockX, mClockPositionResult.clockY);
|
mClockPositionResult.clockX, mClockPositionResult.clockY);
|
||||||
boolean animate = mNotificationStackScrollLayoutController.isAddOrRemoveAnimationPending();
|
boolean animate = mNotificationStackScrollLayoutController.isAddOrRemoveAnimationPending();
|
||||||
boolean animateClock = (animate || mAnimateNextPositionUpdate) && shouldAnimateClockChange;
|
boolean animateClock = (animate || mAnimateNextPositionUpdate) && shouldAnimateClockChange;
|
||||||
@@ -3295,8 +3272,7 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
getExpandedFraction());
|
getExpandedFraction());
|
||||||
float alpha = Math.min(expansionAlpha, 1 - computeQsExpansionFraction());
|
float alpha = Math.min(expansionAlpha, 1 - computeQsExpansionFraction());
|
||||||
alpha *= mBottomAreaShadeAlpha;
|
alpha *= mBottomAreaShadeAlpha;
|
||||||
mKeyguardBottomArea.setComponentAlphas(alpha);
|
mKeyguardBottomAreaInteractor.setAlpha(alpha);
|
||||||
mKeyguardBottomAreaInteractorProvider.get().setAlpha(alpha);
|
|
||||||
mLockIconViewController.setAlpha(alpha);
|
mLockIconViewController.setAlpha(alpha);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -3495,8 +3471,7 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void updateDozingVisibilities(boolean animate) {
|
private void updateDozingVisibilities(boolean animate) {
|
||||||
mKeyguardBottomArea.setDozing(mDozing, animate);
|
mKeyguardBottomAreaInteractor.setAnimateDozingTransitions(animate);
|
||||||
mKeyguardBottomAreaInteractorProvider.get().setAnimateDozingTransitions(animate);
|
|
||||||
if (!mDozing && animate) {
|
if (!mDozing && animate) {
|
||||||
mKeyguardStatusBarViewController.animateKeyguardStatusBarIn();
|
mKeyguardStatusBarViewController.animateKeyguardStatusBarIn();
|
||||||
}
|
}
|
||||||
@@ -3797,8 +3772,7 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
mView.setDozing(dozing);
|
mView.setDozing(dozing);
|
||||||
mDozing = dozing;
|
mDozing = dozing;
|
||||||
mNotificationStackScrollLayoutController.setDozing(mDozing, animate);
|
mNotificationStackScrollLayoutController.setDozing(mDozing, animate);
|
||||||
mKeyguardBottomArea.setDozing(mDozing, animate);
|
mKeyguardBottomAreaInteractor.setAnimateDozingTransitions(animate);
|
||||||
mKeyguardBottomAreaInteractorProvider.get().setAnimateDozingTransitions(animate);
|
|
||||||
mKeyguardStatusBarViewController.setDozing(mDozing);
|
mKeyguardStatusBarViewController.setDozing(mDozing);
|
||||||
|
|
||||||
if (dozing) {
|
if (dozing) {
|
||||||
@@ -3847,7 +3821,6 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
|
|
||||||
public void dozeTimeTick() {
|
public void dozeTimeTick() {
|
||||||
mLockIconViewController.dozeTimeTick();
|
mLockIconViewController.dozeTimeTick();
|
||||||
mKeyguardBottomArea.dozeTimeTick();
|
|
||||||
mKeyguardStatusViewController.dozeTimeTick();
|
mKeyguardStatusViewController.dozeTimeTick();
|
||||||
if (mInterpolatedDarkAmount > 0) {
|
if (mInterpolatedDarkAmount > 0) {
|
||||||
positionClockAndNotifications();
|
positionClockAndNotifications();
|
||||||
@@ -4670,7 +4643,6 @@ public final class NotificationPanelViewController extends PanelViewController {
|
|||||||
public void onDozeAmountChanged(float linearAmount, float amount) {
|
public void onDozeAmountChanged(float linearAmount, float amount) {
|
||||||
mInterpolatedDarkAmount = amount;
|
mInterpolatedDarkAmount = amount;
|
||||||
mLinearDarkAmount = linearAmount;
|
mLinearDarkAmount = linearAmount;
|
||||||
mKeyguardBottomArea.setDarkAmount(mInterpolatedDarkAmount);
|
|
||||||
positionClockAndNotifications();
|
positionClockAndNotifications();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,682 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2014 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License
|
|
||||||
*/
|
|
||||||
|
|
||||||
package com.android.systemui.statusbar.phone;
|
|
||||||
|
|
||||||
import static com.android.internal.util.Preconditions.checkNotNull;
|
|
||||||
import static com.android.systemui.controls.dagger.ControlsComponent.Visibility.AVAILABLE;
|
|
||||||
import static com.android.systemui.doze.util.BurnInHelperKt.getBurnInOffset;
|
|
||||||
import static com.android.systemui.wallet.controller.QuickAccessWalletController.WalletChangeEvent.DEFAULT_PAYMENT_APP_CHANGE;
|
|
||||||
import static com.android.systemui.wallet.controller.QuickAccessWalletController.WalletChangeEvent.WALLET_PREFERENCE_CHANGE;
|
|
||||||
|
|
||||||
import android.app.ActivityTaskManager;
|
|
||||||
import android.app.admin.DevicePolicyManager;
|
|
||||||
import android.content.Context;
|
|
||||||
import android.content.Intent;
|
|
||||||
import android.content.IntentFilter;
|
|
||||||
import android.content.res.ColorStateList;
|
|
||||||
import android.content.res.Configuration;
|
|
||||||
import android.graphics.drawable.Drawable;
|
|
||||||
import android.os.RemoteException;
|
|
||||||
import android.os.UserHandle;
|
|
||||||
import android.service.quickaccesswallet.GetWalletCardsError;
|
|
||||||
import android.service.quickaccesswallet.GetWalletCardsResponse;
|
|
||||||
import android.service.quickaccesswallet.QuickAccessWalletClient;
|
|
||||||
import android.util.AttributeSet;
|
|
||||||
import android.util.Log;
|
|
||||||
import android.util.TypedValue;
|
|
||||||
import android.view.View;
|
|
||||||
import android.view.ViewGroup;
|
|
||||||
import android.view.ViewPropertyAnimator;
|
|
||||||
import android.view.WindowInsets;
|
|
||||||
import android.widget.FrameLayout;
|
|
||||||
import android.widget.ImageView;
|
|
||||||
import android.widget.TextView;
|
|
||||||
|
|
||||||
import androidx.annotation.NonNull;
|
|
||||||
import androidx.annotation.Nullable;
|
|
||||||
|
|
||||||
import com.android.settingslib.Utils;
|
|
||||||
import com.android.systemui.Dependency;
|
|
||||||
import com.android.systemui.R;
|
|
||||||
import com.android.systemui.animation.ActivityLaunchAnimator;
|
|
||||||
import com.android.systemui.animation.Interpolators;
|
|
||||||
import com.android.systemui.controls.dagger.ControlsComponent;
|
|
||||||
import com.android.systemui.controls.management.ControlsListingController;
|
|
||||||
import com.android.systemui.controls.ui.ControlsActivity;
|
|
||||||
import com.android.systemui.controls.ui.ControlsUiController;
|
|
||||||
import com.android.systemui.keyguard.ui.binder.KeyguardBottomAreaViewBinder;
|
|
||||||
import com.android.systemui.keyguard.ui.viewmodel.KeyguardBottomAreaViewModel;
|
|
||||||
import com.android.systemui.plugins.ActivityStarter;
|
|
||||||
import com.android.systemui.plugins.FalsingManager;
|
|
||||||
import com.android.systemui.qrcodescanner.controller.QRCodeScannerController;
|
|
||||||
import com.android.systemui.statusbar.policy.KeyguardStateController;
|
|
||||||
import com.android.systemui.wallet.controller.QuickAccessWalletController;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Implementation for the bottom area of the Keyguard, including camera/phone affordance and status
|
|
||||||
* text.
|
|
||||||
*/
|
|
||||||
public class KeyguardBottomAreaView extends FrameLayout {
|
|
||||||
|
|
||||||
private static final String TAG = "CentralSurfaces/KeyguardBottomAreaView";
|
|
||||||
private static final int DOZE_ANIMATION_ELEMENT_DURATION = 250;
|
|
||||||
|
|
||||||
private ImageView mWalletButton;
|
|
||||||
private ImageView mQRCodeScannerButton;
|
|
||||||
private ImageView mControlsButton;
|
|
||||||
private boolean mHasCard = false;
|
|
||||||
private final WalletCardRetriever mCardRetriever = new WalletCardRetriever();
|
|
||||||
private QuickAccessWalletController mQuickAccessWalletController;
|
|
||||||
private QRCodeScannerController mQRCodeScannerController;
|
|
||||||
private ControlsComponent mControlsComponent;
|
|
||||||
private boolean mControlServicesAvailable = false;
|
|
||||||
|
|
||||||
@Nullable private View mAmbientIndicationArea;
|
|
||||||
private ViewGroup mIndicationArea;
|
|
||||||
private TextView mIndicationText;
|
|
||||||
private TextView mIndicationTextBottom;
|
|
||||||
private ViewGroup mOverlayContainer;
|
|
||||||
|
|
||||||
private ActivityStarter mActivityStarter;
|
|
||||||
private KeyguardStateController mKeyguardStateController;
|
|
||||||
private FalsingManager mFalsingManager;
|
|
||||||
|
|
||||||
private boolean mDozing;
|
|
||||||
private int mIndicationBottomMargin;
|
|
||||||
private int mIndicationPadding;
|
|
||||||
private float mDarkAmount;
|
|
||||||
private int mBurnInXOffset;
|
|
||||||
private int mBurnInYOffset;
|
|
||||||
|
|
||||||
private final ControlsListingController.ControlsListingCallback mListingCallback =
|
|
||||||
serviceInfos -> post(() -> {
|
|
||||||
boolean available = !serviceInfos.isEmpty();
|
|
||||||
|
|
||||||
if (available != mControlServicesAvailable) {
|
|
||||||
mControlServicesAvailable = available;
|
|
||||||
updateControlsVisibility();
|
|
||||||
updateAffordanceColors();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
private final KeyguardStateController.Callback mKeyguardStateCallback =
|
|
||||||
new KeyguardStateController.Callback() {
|
|
||||||
@Override
|
|
||||||
public void onKeyguardShowingChanged() {
|
|
||||||
if (mKeyguardStateController.isShowing()) {
|
|
||||||
if (mQuickAccessWalletController != null) {
|
|
||||||
mQuickAccessWalletController.queryWalletCards(mCardRetriever);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
@Nullable private KeyguardBottomAreaViewBinder.Binding mBinding;
|
|
||||||
private boolean mUsesBinder;
|
|
||||||
|
|
||||||
public KeyguardBottomAreaView(Context context) {
|
|
||||||
this(context, null);
|
|
||||||
}
|
|
||||||
|
|
||||||
public KeyguardBottomAreaView(Context context, AttributeSet attrs) {
|
|
||||||
this(context, attrs, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
public KeyguardBottomAreaView(Context context, AttributeSet attrs, int defStyleAttr) {
|
|
||||||
this(context, attrs, defStyleAttr, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
public KeyguardBottomAreaView(Context context, AttributeSet attrs, int defStyleAttr,
|
|
||||||
int defStyleRes) {
|
|
||||||
super(context, attrs, defStyleAttr, defStyleRes);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Initializes the view.
|
|
||||||
*/
|
|
||||||
public void init(
|
|
||||||
final KeyguardBottomAreaViewModel viewModel,
|
|
||||||
final FalsingManager falsingManager) {
|
|
||||||
Log.i(TAG, System.identityHashCode(this) + " initialized with a binder");
|
|
||||||
mUsesBinder = true;
|
|
||||||
mBinding = KeyguardBottomAreaViewBinder.bind(this, viewModel, falsingManager);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Initializes the {@link KeyguardBottomAreaView} with the given dependencies
|
|
||||||
*
|
|
||||||
* @deprecated Use
|
|
||||||
* {@link #init(KeyguardBottomAreaViewModel, FalsingManager)} instead
|
|
||||||
*/
|
|
||||||
@Deprecated
|
|
||||||
public void init(
|
|
||||||
FalsingManager falsingManager,
|
|
||||||
QuickAccessWalletController controller,
|
|
||||||
ControlsComponent controlsComponent,
|
|
||||||
QRCodeScannerController qrCodeScannerController) {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
Log.i(TAG, "initialized without a binder");
|
|
||||||
mFalsingManager = falsingManager;
|
|
||||||
|
|
||||||
mQuickAccessWalletController = controller;
|
|
||||||
mQuickAccessWalletController.setupWalletChangeObservers(
|
|
||||||
mCardRetriever, WALLET_PREFERENCE_CHANGE, DEFAULT_PAYMENT_APP_CHANGE);
|
|
||||||
mQuickAccessWalletController.updateWalletPreference();
|
|
||||||
mQuickAccessWalletController.queryWalletCards(mCardRetriever);
|
|
||||||
updateWalletVisibility();
|
|
||||||
|
|
||||||
mControlsComponent = controlsComponent;
|
|
||||||
mControlsComponent.getControlsListingController().ifPresent(
|
|
||||||
c -> c.addCallback(mListingCallback));
|
|
||||||
|
|
||||||
mQRCodeScannerController = qrCodeScannerController;
|
|
||||||
mQRCodeScannerController.registerQRCodeScannerChangeObservers(
|
|
||||||
QRCodeScannerController.DEFAULT_QR_CODE_SCANNER_CHANGE,
|
|
||||||
QRCodeScannerController.QR_CODE_SCANNER_PREFERENCE_CHANGE);
|
|
||||||
updateQRCodeButtonVisibility();
|
|
||||||
|
|
||||||
updateAffordanceColors();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Initializes this instance of {@link KeyguardBottomAreaView} based on the given instance of
|
|
||||||
* another {@link KeyguardBottomAreaView}
|
|
||||||
*/
|
|
||||||
public void initFrom(KeyguardBottomAreaView oldBottomArea) {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// if it exists, continue to use the original ambient indication container
|
|
||||||
// instead of the newly inflated one
|
|
||||||
if (mAmbientIndicationArea != null) {
|
|
||||||
// remove old ambient indication from its parent
|
|
||||||
View originalAmbientIndicationView =
|
|
||||||
oldBottomArea.findViewById(R.id.ambient_indication_container);
|
|
||||||
((ViewGroup) originalAmbientIndicationView.getParent())
|
|
||||||
.removeView(originalAmbientIndicationView);
|
|
||||||
|
|
||||||
// remove current ambient indication from its parent (discard)
|
|
||||||
ViewGroup ambientIndicationParent = (ViewGroup) mAmbientIndicationArea.getParent();
|
|
||||||
int ambientIndicationIndex =
|
|
||||||
ambientIndicationParent.indexOfChild(mAmbientIndicationArea);
|
|
||||||
ambientIndicationParent.removeView(mAmbientIndicationArea);
|
|
||||||
|
|
||||||
// add the old ambient indication to this view
|
|
||||||
ambientIndicationParent.addView(originalAmbientIndicationView, ambientIndicationIndex);
|
|
||||||
mAmbientIndicationArea = originalAmbientIndicationView;
|
|
||||||
|
|
||||||
// update burn-in offsets
|
|
||||||
dozeTimeTick();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onFinishInflate() {
|
|
||||||
super.onFinishInflate();
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
mOverlayContainer = findViewById(R.id.overlay_container);
|
|
||||||
mWalletButton = findViewById(R.id.wallet_button);
|
|
||||||
mQRCodeScannerButton = findViewById(R.id.qr_code_scanner_button);
|
|
||||||
mControlsButton = findViewById(R.id.controls_button);
|
|
||||||
mIndicationArea = findViewById(R.id.keyguard_indication_area);
|
|
||||||
mAmbientIndicationArea = findViewById(R.id.ambient_indication_container);
|
|
||||||
mIndicationText = findViewById(R.id.keyguard_indication_text);
|
|
||||||
mIndicationTextBottom = findViewById(R.id.keyguard_indication_text_bottom);
|
|
||||||
mIndicationBottomMargin = getResources().getDimensionPixelSize(
|
|
||||||
R.dimen.keyguard_indication_margin_bottom);
|
|
||||||
mBurnInYOffset = getResources().getDimensionPixelSize(
|
|
||||||
R.dimen.default_burn_in_prevention_offset);
|
|
||||||
mKeyguardStateController = Dependency.get(KeyguardStateController.class);
|
|
||||||
mKeyguardStateController.addCallback(mKeyguardStateCallback);
|
|
||||||
setClipChildren(false);
|
|
||||||
setClipToPadding(false);
|
|
||||||
mActivityStarter = Dependency.get(ActivityStarter.class);
|
|
||||||
|
|
||||||
mIndicationPadding = getResources().getDimensionPixelSize(
|
|
||||||
R.dimen.keyguard_indication_area_padding);
|
|
||||||
updateWalletVisibility();
|
|
||||||
updateQRCodeButtonVisibility();
|
|
||||||
updateControlsVisibility();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onAttachedToWindow() {
|
|
||||||
super.onAttachedToWindow();
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
final IntentFilter filter = new IntentFilter();
|
|
||||||
filter.addAction(DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED);
|
|
||||||
mKeyguardStateController.addCallback(mKeyguardStateCallback);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onDetachedFromWindow() {
|
|
||||||
super.onDetachedFromWindow();
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
mKeyguardStateController.removeCallback(mKeyguardStateCallback);
|
|
||||||
|
|
||||||
if (mQuickAccessWalletController != null) {
|
|
||||||
mQuickAccessWalletController.unregisterWalletChangeObservers(
|
|
||||||
WALLET_PREFERENCE_CHANGE, DEFAULT_PAYMENT_APP_CHANGE);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mQRCodeScannerController != null) {
|
|
||||||
mQRCodeScannerController.unregisterQRCodeScannerChangeObservers(
|
|
||||||
QRCodeScannerController.DEFAULT_QR_CODE_SCANNER_CHANGE,
|
|
||||||
QRCodeScannerController.QR_CODE_SCANNER_PREFERENCE_CHANGE);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mControlsComponent != null) {
|
|
||||||
mControlsComponent.getControlsListingController().ifPresent(
|
|
||||||
c -> c.removeCallback(mListingCallback));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void onConfigurationChanged(Configuration newConfig) {
|
|
||||||
super.onConfigurationChanged(newConfig);
|
|
||||||
if (mUsesBinder) {
|
|
||||||
if (mBinding != null) {
|
|
||||||
mBinding.onConfigurationChanged();
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
mIndicationBottomMargin = getResources().getDimensionPixelSize(
|
|
||||||
R.dimen.keyguard_indication_margin_bottom);
|
|
||||||
mBurnInYOffset = getResources().getDimensionPixelSize(
|
|
||||||
R.dimen.default_burn_in_prevention_offset);
|
|
||||||
MarginLayoutParams mlp = (MarginLayoutParams) mIndicationArea.getLayoutParams();
|
|
||||||
if (mlp.bottomMargin != mIndicationBottomMargin) {
|
|
||||||
mlp.bottomMargin = mIndicationBottomMargin;
|
|
||||||
mIndicationArea.setLayoutParams(mlp);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Respect font size setting.
|
|
||||||
mIndicationTextBottom.setTextSize(TypedValue.COMPLEX_UNIT_PX,
|
|
||||||
getResources().getDimensionPixelSize(
|
|
||||||
com.android.internal.R.dimen.text_size_small_material));
|
|
||||||
mIndicationText.setTextSize(TypedValue.COMPLEX_UNIT_PX,
|
|
||||||
getResources().getDimensionPixelSize(
|
|
||||||
com.android.internal.R.dimen.text_size_small_material));
|
|
||||||
|
|
||||||
ViewGroup.LayoutParams lp = mWalletButton.getLayoutParams();
|
|
||||||
lp.width = getResources().getDimensionPixelSize(R.dimen.keyguard_affordance_fixed_width);
|
|
||||||
lp.height = getResources().getDimensionPixelSize(R.dimen.keyguard_affordance_fixed_height);
|
|
||||||
mWalletButton.setLayoutParams(lp);
|
|
||||||
|
|
||||||
lp = mQRCodeScannerButton.getLayoutParams();
|
|
||||||
lp.width = getResources().getDimensionPixelSize(R.dimen.keyguard_affordance_fixed_width);
|
|
||||||
lp.height = getResources().getDimensionPixelSize(R.dimen.keyguard_affordance_fixed_height);
|
|
||||||
mQRCodeScannerButton.setLayoutParams(lp);
|
|
||||||
|
|
||||||
lp = mControlsButton.getLayoutParams();
|
|
||||||
lp.width = getResources().getDimensionPixelSize(R.dimen.keyguard_affordance_fixed_width);
|
|
||||||
lp.height = getResources().getDimensionPixelSize(R.dimen.keyguard_affordance_fixed_height);
|
|
||||||
mControlsButton.setLayoutParams(lp);
|
|
||||||
|
|
||||||
mIndicationPadding = getResources().getDimensionPixelSize(
|
|
||||||
R.dimen.keyguard_indication_area_padding);
|
|
||||||
|
|
||||||
updateWalletVisibility();
|
|
||||||
updateQRCodeButtonVisibility();
|
|
||||||
updateAffordanceColors();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void updateWalletVisibility() {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mDozing
|
|
||||||
|| mQuickAccessWalletController == null
|
|
||||||
|| !mQuickAccessWalletController.isWalletEnabled()
|
|
||||||
|| !mHasCard) {
|
|
||||||
mWalletButton.setVisibility(GONE);
|
|
||||||
|
|
||||||
if (mControlsButton.getVisibility() == GONE) {
|
|
||||||
mIndicationArea.setPadding(0, 0, 0, 0);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
mWalletButton.setVisibility(VISIBLE);
|
|
||||||
mWalletButton.setOnClickListener(this::onWalletClick);
|
|
||||||
mIndicationArea.setPadding(mIndicationPadding, 0, mIndicationPadding, 0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void updateControlsVisibility() {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mControlsComponent == null) return;
|
|
||||||
|
|
||||||
mControlsButton.setImageResource(mControlsComponent.getTileImageId());
|
|
||||||
mControlsButton.setContentDescription(getContext()
|
|
||||||
.getString(mControlsComponent.getTileTitleId()));
|
|
||||||
updateAffordanceColors();
|
|
||||||
|
|
||||||
boolean hasFavorites = mControlsComponent.getControlsController()
|
|
||||||
.map(c -> c.getFavorites().size() > 0)
|
|
||||||
.orElse(false);
|
|
||||||
if (mDozing
|
|
||||||
|| !hasFavorites
|
|
||||||
|| !mControlServicesAvailable
|
|
||||||
|| mControlsComponent.getVisibility() != AVAILABLE) {
|
|
||||||
mControlsButton.setVisibility(GONE);
|
|
||||||
if (mWalletButton.getVisibility() == GONE) {
|
|
||||||
mIndicationArea.setPadding(0, 0, 0, 0);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
mControlsButton.setVisibility(VISIBLE);
|
|
||||||
mControlsButton.setOnClickListener(this::onControlsClick);
|
|
||||||
mIndicationArea.setPadding(mIndicationPadding, 0, mIndicationPadding, 0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setDarkAmount(float darkAmount) {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (darkAmount == mDarkAmount) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
mDarkAmount = darkAmount;
|
|
||||||
dozeTimeTick();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns a list of animators to use to animate the indication areas.
|
|
||||||
*/
|
|
||||||
public List<ViewPropertyAnimator> getIndicationAreaAnimators() {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return checkNotNull(mBinding).getIndicationAreaAnimators();
|
|
||||||
}
|
|
||||||
|
|
||||||
List<ViewPropertyAnimator> animators =
|
|
||||||
new ArrayList<>(mAmbientIndicationArea != null ? 2 : 1);
|
|
||||||
animators.add(mIndicationArea.animate());
|
|
||||||
if (mAmbientIndicationArea != null) {
|
|
||||||
animators.add(mAmbientIndicationArea.animate());
|
|
||||||
}
|
|
||||||
return animators;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public boolean hasOverlappingRendering() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void startFinishDozeAnimation() {
|
|
||||||
long delay = 0;
|
|
||||||
if (mWalletButton.getVisibility() == View.VISIBLE) {
|
|
||||||
startFinishDozeAnimationElement(mWalletButton, delay);
|
|
||||||
}
|
|
||||||
if (mQRCodeScannerButton.getVisibility() == View.VISIBLE) {
|
|
||||||
startFinishDozeAnimationElement(mQRCodeScannerButton, delay);
|
|
||||||
}
|
|
||||||
if (mControlsButton.getVisibility() == View.VISIBLE) {
|
|
||||||
startFinishDozeAnimationElement(mControlsButton, delay);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void startFinishDozeAnimationElement(View element, long delay) {
|
|
||||||
element.setAlpha(0f);
|
|
||||||
element.setTranslationY(element.getHeight() / 2);
|
|
||||||
element.animate()
|
|
||||||
.alpha(1f)
|
|
||||||
.translationY(0f)
|
|
||||||
.setInterpolator(Interpolators.LINEAR_OUT_SLOW_IN)
|
|
||||||
.setStartDelay(delay)
|
|
||||||
.setDuration(DOZE_ANIMATION_ELEMENT_DURATION);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setDozing(boolean dozing, boolean animate) {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
mDozing = dozing;
|
|
||||||
|
|
||||||
updateWalletVisibility();
|
|
||||||
updateControlsVisibility();
|
|
||||||
updateQRCodeButtonVisibility();
|
|
||||||
|
|
||||||
if (dozing) {
|
|
||||||
mOverlayContainer.setVisibility(INVISIBLE);
|
|
||||||
} else {
|
|
||||||
mOverlayContainer.setVisibility(VISIBLE);
|
|
||||||
if (animate) {
|
|
||||||
startFinishDozeAnimation();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void dozeTimeTick() {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
int burnInYOffset = getBurnInOffset(mBurnInYOffset * 2, false /* xAxis */)
|
|
||||||
- mBurnInYOffset;
|
|
||||||
mIndicationArea.setTranslationY(burnInYOffset * mDarkAmount);
|
|
||||||
if (mAmbientIndicationArea != null) {
|
|
||||||
mAmbientIndicationArea.setTranslationY(burnInYOffset * mDarkAmount);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setAntiBurnInOffsetX(int burnInXOffset) {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mBurnInXOffset == burnInXOffset) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
mBurnInXOffset = burnInXOffset;
|
|
||||||
mIndicationArea.setTranslationX(burnInXOffset);
|
|
||||||
if (mAmbientIndicationArea != null) {
|
|
||||||
mAmbientIndicationArea.setTranslationX(burnInXOffset);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Sets the alpha of various sub-components, for example the indication areas and bottom quick
|
|
||||||
* action buttons. Does not set the alpha of the lock icon.
|
|
||||||
*/
|
|
||||||
public void setComponentAlphas(float alpha) {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
setImportantForAccessibility(
|
|
||||||
alpha == 0f
|
|
||||||
? View.IMPORTANT_FOR_ACCESSIBILITY_NO_HIDE_DESCENDANTS
|
|
||||||
: View.IMPORTANT_FOR_ACCESSIBILITY_AUTO);
|
|
||||||
if (mAmbientIndicationArea != null) {
|
|
||||||
mAmbientIndicationArea.setAlpha(alpha);
|
|
||||||
}
|
|
||||||
mIndicationArea.setAlpha(alpha);
|
|
||||||
mWalletButton.setAlpha(alpha);
|
|
||||||
mQRCodeScannerButton.setAlpha(alpha);
|
|
||||||
mControlsButton.setAlpha(alpha);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public WindowInsets onApplyWindowInsets(WindowInsets insets) {
|
|
||||||
int bottom = insets.getDisplayCutout() != null
|
|
||||||
? insets.getDisplayCutout().getSafeInsetBottom() : 0;
|
|
||||||
if (isPaddingRelative()) {
|
|
||||||
setPaddingRelative(getPaddingStart(), getPaddingTop(), getPaddingEnd(), bottom);
|
|
||||||
} else {
|
|
||||||
setPadding(getPaddingLeft(), getPaddingTop(), getPaddingRight(), bottom);
|
|
||||||
}
|
|
||||||
return insets;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void updateQRCodeButtonVisibility() {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mQuickAccessWalletController != null
|
|
||||||
&& mQuickAccessWalletController.isWalletEnabled()) {
|
|
||||||
// Don't enable if quick access wallet is enabled
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mQRCodeScannerController != null
|
|
||||||
&& mQRCodeScannerController.isEnabledForLockScreenButton()) {
|
|
||||||
mQRCodeScannerButton.setVisibility(VISIBLE);
|
|
||||||
mQRCodeScannerButton.setOnClickListener(this::onQRCodeScannerClicked);
|
|
||||||
mIndicationArea.setPadding(mIndicationPadding, 0, mIndicationPadding, 0);
|
|
||||||
} else {
|
|
||||||
mQRCodeScannerButton.setVisibility(GONE);
|
|
||||||
if (mControlsButton.getVisibility() == GONE) {
|
|
||||||
mIndicationArea.setPadding(0, 0, 0, 0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void onQRCodeScannerClicked(View view) {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
Intent intent = mQRCodeScannerController.getIntent();
|
|
||||||
if (intent != null) {
|
|
||||||
try {
|
|
||||||
ActivityTaskManager.getService().startActivityAsUser(
|
|
||||||
null, getContext().getBasePackageName(),
|
|
||||||
getContext().getAttributionTag(), intent,
|
|
||||||
intent.resolveTypeIfNeeded(getContext().getContentResolver()),
|
|
||||||
null, null, 0, Intent.FLAG_ACTIVITY_NEW_TASK, null, null,
|
|
||||||
UserHandle.CURRENT.getIdentifier());
|
|
||||||
} catch (RemoteException e) {
|
|
||||||
// This is unexpected. Nonetheless, just log the error and prevent the UI from
|
|
||||||
// crashing
|
|
||||||
Log.e(TAG, "Unexpected intent: " + intent
|
|
||||||
+ " when the QR code scanner button was clicked");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void updateAffordanceColors() {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
int iconColor = Utils.getColorAttrDefaultColor(
|
|
||||||
mContext,
|
|
||||||
com.android.internal.R.attr.textColorPrimary);
|
|
||||||
mWalletButton.getDrawable().setTint(iconColor);
|
|
||||||
mControlsButton.getDrawable().setTint(iconColor);
|
|
||||||
mQRCodeScannerButton.getDrawable().setTint(iconColor);
|
|
||||||
|
|
||||||
ColorStateList bgColor = Utils.getColorAttr(
|
|
||||||
mContext,
|
|
||||||
com.android.internal.R.attr.colorSurface);
|
|
||||||
mWalletButton.setBackgroundTintList(bgColor);
|
|
||||||
mControlsButton.setBackgroundTintList(bgColor);
|
|
||||||
mQRCodeScannerButton.setBackgroundTintList(bgColor);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void onWalletClick(View v) {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// More coming here; need to inform the user about how to proceed
|
|
||||||
if (mFalsingManager.isFalseTap(FalsingManager.LOW_PENALTY)) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
ActivityLaunchAnimator.Controller animationController = createLaunchAnimationController(v);
|
|
||||||
mQuickAccessWalletController.startQuickAccessUiIntent(
|
|
||||||
mActivityStarter, animationController, mHasCard);
|
|
||||||
}
|
|
||||||
|
|
||||||
protected ActivityLaunchAnimator.Controller createLaunchAnimationController(View view) {
|
|
||||||
return ActivityLaunchAnimator.Controller.fromView(view, null);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void onControlsClick(View v) {
|
|
||||||
if (mUsesBinder) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mFalsingManager.isFalseTap(FalsingManager.LOW_PENALTY)) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
Intent intent = new Intent(mContext, ControlsActivity.class)
|
|
||||||
.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK)
|
|
||||||
.putExtra(ControlsUiController.EXTRA_ANIMATE, true);
|
|
||||||
|
|
||||||
ActivityLaunchAnimator.Controller controller =
|
|
||||||
v != null ? ActivityLaunchAnimator.Controller.fromView(v, null /* cujType */)
|
|
||||||
: null;
|
|
||||||
if (mControlsComponent.getVisibility() == AVAILABLE) {
|
|
||||||
mActivityStarter.startActivity(intent, true /* dismissShade */, controller,
|
|
||||||
true /* showOverLockscreenWhenLocked */);
|
|
||||||
} else {
|
|
||||||
mActivityStarter.postStartActivityDismissingKeyguard(intent, 0 /* delay */, controller);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private class WalletCardRetriever implements
|
|
||||||
QuickAccessWalletClient.OnWalletCardsRetrievedCallback {
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onWalletCardsRetrieved(@NonNull GetWalletCardsResponse response) {
|
|
||||||
mHasCard = !response.getWalletCards().isEmpty();
|
|
||||||
Drawable tileIcon = mQuickAccessWalletController.getWalletClient().getTileIcon();
|
|
||||||
if (tileIcon != null) {
|
|
||||||
mWalletButton.setImageDrawable(tileIcon);
|
|
||||||
}
|
|
||||||
post(() -> {
|
|
||||||
updateWalletVisibility();
|
|
||||||
updateAffordanceColors();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void onWalletCardRetrievalError(@NonNull GetWalletCardsError error) {
|
|
||||||
mHasCard = false;
|
|
||||||
post(() -> {
|
|
||||||
updateWalletVisibility();
|
|
||||||
updateAffordanceColors();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -0,0 +1,117 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2014 The Android Open Source Project
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License
|
||||||
|
*/
|
||||||
|
package com.android.systemui.statusbar.phone
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import android.content.res.Configuration
|
||||||
|
import android.util.AttributeSet
|
||||||
|
import android.view.View
|
||||||
|
import android.view.ViewGroup
|
||||||
|
import android.view.ViewPropertyAnimator
|
||||||
|
import android.view.WindowInsets
|
||||||
|
import android.widget.FrameLayout
|
||||||
|
import com.android.systemui.R
|
||||||
|
import com.android.systemui.keyguard.ui.binder.KeyguardBottomAreaViewBinder
|
||||||
|
import com.android.systemui.keyguard.ui.binder.KeyguardBottomAreaViewBinder.bind
|
||||||
|
import com.android.systemui.keyguard.ui.viewmodel.KeyguardBottomAreaViewModel
|
||||||
|
import com.android.systemui.plugins.FalsingManager
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Renders the bottom area of the lock-screen. Concerned primarily with the quick affordance UI
|
||||||
|
* elements. A secondary concern is the interaction of the quick affordance elements with the
|
||||||
|
* indication area between them, though the indication area is primarily controlled elsewhere.
|
||||||
|
*/
|
||||||
|
class KeyguardBottomAreaView
|
||||||
|
@JvmOverloads
|
||||||
|
constructor(
|
||||||
|
context: Context,
|
||||||
|
attrs: AttributeSet? = null,
|
||||||
|
defStyleAttr: Int = 0,
|
||||||
|
defStyleRes: Int = 0,
|
||||||
|
) :
|
||||||
|
FrameLayout(
|
||||||
|
context,
|
||||||
|
attrs,
|
||||||
|
defStyleAttr,
|
||||||
|
defStyleRes,
|
||||||
|
) {
|
||||||
|
|
||||||
|
private var ambientIndicationArea: View? = null
|
||||||
|
private lateinit var binding: KeyguardBottomAreaViewBinder.Binding
|
||||||
|
|
||||||
|
/** Initializes the view. */
|
||||||
|
fun init(
|
||||||
|
viewModel: KeyguardBottomAreaViewModel,
|
||||||
|
falsingManager: FalsingManager,
|
||||||
|
) {
|
||||||
|
binding = bind(this, viewModel, falsingManager)
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Initializes this instance of [KeyguardBottomAreaView] based on the given instance of another
|
||||||
|
* [KeyguardBottomAreaView]
|
||||||
|
*/
|
||||||
|
fun initFrom(oldBottomArea: KeyguardBottomAreaView) {
|
||||||
|
// if it exists, continue to use the original ambient indication container
|
||||||
|
// instead of the newly inflated one
|
||||||
|
ambientIndicationArea?.let { nonNullAmbientIndicationArea ->
|
||||||
|
// remove old ambient indication from its parent
|
||||||
|
val originalAmbientIndicationView =
|
||||||
|
oldBottomArea.findViewById<View>(R.id.ambient_indication_container)
|
||||||
|
(originalAmbientIndicationView.parent as ViewGroup).removeView(
|
||||||
|
originalAmbientIndicationView
|
||||||
|
)
|
||||||
|
|
||||||
|
// remove current ambient indication from its parent (discard)
|
||||||
|
val ambientIndicationParent = nonNullAmbientIndicationArea.parent as ViewGroup
|
||||||
|
val ambientIndicationIndex =
|
||||||
|
ambientIndicationParent.indexOfChild(nonNullAmbientIndicationArea)
|
||||||
|
ambientIndicationParent.removeView(nonNullAmbientIndicationArea)
|
||||||
|
|
||||||
|
// add the old ambient indication to this view
|
||||||
|
ambientIndicationParent.addView(originalAmbientIndicationView, ambientIndicationIndex)
|
||||||
|
ambientIndicationArea = originalAmbientIndicationView
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onFinishInflate() {
|
||||||
|
super.onFinishInflate()
|
||||||
|
ambientIndicationArea = findViewById(R.id.ambient_indication_container)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onConfigurationChanged(newConfig: Configuration) {
|
||||||
|
super.onConfigurationChanged(newConfig)
|
||||||
|
binding.onConfigurationChanged()
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Returns a list of animators to use to animate the indication areas. */
|
||||||
|
val indicationAreaAnimators: List<ViewPropertyAnimator>
|
||||||
|
get() = binding.getIndicationAreaAnimators()
|
||||||
|
|
||||||
|
override fun hasOverlappingRendering(): Boolean {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onApplyWindowInsets(insets: WindowInsets): WindowInsets {
|
||||||
|
val bottom = insets.displayCutout?.safeInsetBottom ?: 0
|
||||||
|
if (isPaddingRelative) {
|
||||||
|
setPaddingRelative(paddingStart, paddingTop, paddingEnd, bottom)
|
||||||
|
} else {
|
||||||
|
setPadding(paddingLeft, paddingTop, paddingRight, bottom)
|
||||||
|
}
|
||||||
|
return insets
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -547,8 +547,6 @@ public class NotificationPanelViewControllerTest extends SysuiTestCase {
|
|||||||
mNavigationModeController,
|
mNavigationModeController,
|
||||||
mFragmentService,
|
mFragmentService,
|
||||||
mContentResolver,
|
mContentResolver,
|
||||||
mQuickAccessWalletController,
|
|
||||||
mQrCodeScannerController,
|
|
||||||
mRecordingController,
|
mRecordingController,
|
||||||
mLargeScreenShadeHeaderController,
|
mLargeScreenShadeHeaderController,
|
||||||
mScreenOffAnimationController,
|
mScreenOffAnimationController,
|
||||||
@@ -556,7 +554,6 @@ public class NotificationPanelViewControllerTest extends SysuiTestCase {
|
|||||||
mPanelExpansionStateManager,
|
mPanelExpansionStateManager,
|
||||||
mNotificationRemoteInputManager,
|
mNotificationRemoteInputManager,
|
||||||
mSysUIUnfoldComponent,
|
mSysUIUnfoldComponent,
|
||||||
mControlsComponent,
|
|
||||||
mInteractionJankMonitor,
|
mInteractionJankMonitor,
|
||||||
mQsFrameTranslateController,
|
mQsFrameTranslateController,
|
||||||
mSysUiState,
|
mSysUiState,
|
||||||
@@ -569,8 +566,8 @@ public class NotificationPanelViewControllerTest extends SysuiTestCase {
|
|||||||
mShadeTransitionController,
|
mShadeTransitionController,
|
||||||
mSystemClock,
|
mSystemClock,
|
||||||
mock(CameraGestureHelper.class),
|
mock(CameraGestureHelper.class),
|
||||||
() -> mKeyguardBottomAreaViewModel,
|
mKeyguardBottomAreaViewModel,
|
||||||
() -> mKeyguardBottomAreaInteractor);
|
mKeyguardBottomAreaInteractor);
|
||||||
mNotificationPanelViewController.initDependencies(
|
mNotificationPanelViewController.initDependencies(
|
||||||
mCentralSurfaces,
|
mCentralSurfaces,
|
||||||
() -> {},
|
() -> {},
|
||||||
|
|||||||
@@ -1,54 +0,0 @@
|
|||||||
package com.android.systemui.statusbar.phone
|
|
||||||
|
|
||||||
import android.testing.AndroidTestingRunner
|
|
||||||
import android.testing.TestableLooper
|
|
||||||
import android.view.LayoutInflater
|
|
||||||
import androidx.test.filters.SmallTest
|
|
||||||
import com.android.systemui.R
|
|
||||||
import com.android.systemui.SysuiTestCase
|
|
||||||
import com.android.systemui.assist.AssistManager
|
|
||||||
import com.android.systemui.plugins.ActivityStarter
|
|
||||||
import com.android.systemui.statusbar.policy.AccessibilityController
|
|
||||||
import com.android.systemui.statusbar.policy.FlashlightController
|
|
||||||
import com.android.systemui.statusbar.policy.KeyguardStateController
|
|
||||||
import com.android.systemui.tuner.TunerService
|
|
||||||
import java.util.concurrent.Executor
|
|
||||||
import org.junit.Before
|
|
||||||
import org.junit.Test
|
|
||||||
import org.junit.runner.RunWith
|
|
||||||
import org.mockito.Mock
|
|
||||||
import org.mockito.MockitoAnnotations
|
|
||||||
|
|
||||||
@SmallTest
|
|
||||||
@RunWith(AndroidTestingRunner::class)
|
|
||||||
@TestableLooper.RunWithLooper(setAsMainLooper = true)
|
|
||||||
class KeyguardBottomAreaTest : SysuiTestCase() {
|
|
||||||
|
|
||||||
@Mock
|
|
||||||
private lateinit var mCentralSurfaces: CentralSurfaces
|
|
||||||
private lateinit var mKeyguardBottomArea: KeyguardBottomAreaView
|
|
||||||
|
|
||||||
@Before
|
|
||||||
fun setup() {
|
|
||||||
MockitoAnnotations.initMocks(this)
|
|
||||||
// Mocked dependencies
|
|
||||||
mDependency.injectMockDependency(AccessibilityController::class.java)
|
|
||||||
mDependency.injectMockDependency(ActivityStarter::class.java)
|
|
||||||
mDependency.injectMockDependency(AssistManager::class.java)
|
|
||||||
mDependency.injectTestDependency(Executor::class.java, Executor { it.run() })
|
|
||||||
mDependency.injectMockDependency(FlashlightController::class.java)
|
|
||||||
mDependency.injectMockDependency(KeyguardStateController::class.java)
|
|
||||||
mDependency.injectMockDependency(TunerService::class.java)
|
|
||||||
|
|
||||||
mKeyguardBottomArea = LayoutInflater.from(mContext).inflate(
|
|
||||||
R.layout.keyguard_bottom_area, null, false) as KeyguardBottomAreaView
|
|
||||||
}
|
|
||||||
|
|
||||||
@Test
|
|
||||||
fun initFrom_doesntCrash() {
|
|
||||||
val other = LayoutInflater.from(mContext).inflate(R.layout.keyguard_bottom_area,
|
|
||||||
null, false) as KeyguardBottomAreaView
|
|
||||||
|
|
||||||
other.initFrom(mKeyguardBottomArea)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Reference in New Issue
Block a user