Make BiometricUnlockController injectable.

Bug: 142952576
Test: atest SystemUITests
Change-Id: Ib2e274325aa3bfb4627879ab36ef4efe187530eb
diff --git a/packages/CarSystemUI/src/com/android/systemui/CarSystemUIModule.java b/packages/CarSystemUI/src/com/android/systemui/CarSystemUIModule.java
index 0f44e08..93e553f 100644
--- a/packages/CarSystemUI/src/com/android/systemui/CarSystemUIModule.java
+++ b/packages/CarSystemUI/src/com/android/systemui/CarSystemUIModule.java
@@ -102,6 +102,9 @@
             CarSystemUIRootComponent systemUIRootComponent);
 
     @Binds
+    public abstract StatusBar bindStatusBar(CarStatusBar statusBar);
+
+    @Binds
     @IntoMap
     @ClassKey(StatusBar.class)
     public abstract SystemUI providesStatusBar(CarStatusBar statusBar);
diff --git a/packages/CarSystemUI/src/com/android/systemui/statusbar/car/CarStatusBar.java b/packages/CarSystemUI/src/com/android/systemui/statusbar/car/CarStatusBar.java
index cd81a5c..16073ae 100644
--- a/packages/CarSystemUI/src/com/android/systemui/statusbar/car/CarStatusBar.java
+++ b/packages/CarSystemUI/src/com/android/systemui/statusbar/car/CarStatusBar.java
@@ -106,6 +106,7 @@
 import com.android.systemui.statusbar.notification.logging.NotificationLogger;
 import com.android.systemui.statusbar.notification.row.NotificationGutsManager;
 import com.android.systemui.statusbar.phone.AutoHideController;
+import com.android.systemui.statusbar.phone.BiometricUnlockController;
 import com.android.systemui.statusbar.phone.CollapsedStatusBarFragment;
 import com.android.systemui.statusbar.phone.DozeParameters;
 import com.android.systemui.statusbar.phone.HeadsUpManagerPhone;
@@ -299,6 +300,7 @@
             DozeParameters dozeParameters,
             ScrimController scrimController,
             Lazy<LockscreenWallpaper> lockscreenWallpaperLazy,
+            Lazy<BiometricUnlockController> biometricUnlockControllerLazy,
 
             /* Car Settings injected components. */
             NavigationBarViewFactory navigationBarViewFactory) {
@@ -361,7 +363,8 @@
                 notifLog,
                 dozeParameters,
                 scrimController,
-                lockscreenWallpaperLazy);
+                lockscreenWallpaperLazy,
+                biometricUnlockControllerLazy);
         mScrimController = scrimController;
         mNavigationBarViewFactory = navigationBarViewFactory;
     }
diff --git a/packages/SystemUI/src/com/android/systemui/dagger/SystemServicesModule.java b/packages/SystemUI/src/com/android/systemui/dagger/SystemServicesModule.java
index 891bf615..fffba8c 100644
--- a/packages/SystemUI/src/com/android/systemui/dagger/SystemServicesModule.java
+++ b/packages/SystemUI/src/com/android/systemui/dagger/SystemServicesModule.java
@@ -34,6 +34,7 @@
 import android.view.WindowManager;
 import android.view.WindowManagerGlobal;
 
+import com.android.internal.util.LatencyTracker;
 import com.android.settingslib.bluetooth.LocalBluetoothManager;
 import com.android.systemui.dagger.qualifiers.BgHandler;
 import com.android.systemui.dagger.qualifiers.MainResources;
@@ -75,6 +76,12 @@
         return WindowManagerGlobal.getWindowManagerService();
     }
 
+    @Singleton
+    @Provides
+    static LatencyTracker provideLatencyTracker(Context context) {
+        return LatencyTracker.getInstance(context);
+    }
+
     @SuppressLint("MissingPermission")
     @Singleton
     @Provides
diff --git a/packages/SystemUI/src/com/android/systemui/dagger/SystemUIModule.java b/packages/SystemUI/src/com/android/systemui/dagger/SystemUIModule.java
index 30f1397..41ac69c 100644
--- a/packages/SystemUI/src/com/android/systemui/dagger/SystemUIModule.java
+++ b/packages/SystemUI/src/com/android/systemui/dagger/SystemUIModule.java
@@ -36,7 +36,9 @@
  * A dagger module for injecting components of System UI that are not overridden by the System UI
  * implementation.
  */
-@Module(includes = {AssistModule.class, ComponentBinder.class, PeopleHubModule.class})
+@Module(includes = {AssistModule.class,
+                    ComponentBinder.class,
+                    PeopleHubModule.class})
 public abstract class SystemUIModule {
 
     @Singleton
diff --git a/packages/SystemUI/src/com/android/systemui/doze/DozeFactory.java b/packages/SystemUI/src/com/android/systemui/doze/DozeFactory.java
index a36ff0d..33f68cf 100644
--- a/packages/SystemUI/src/com/android/systemui/doze/DozeFactory.java
+++ b/packages/SystemUI/src/com/android/systemui/doze/DozeFactory.java
@@ -57,6 +57,7 @@
     private final ProximitySensor mProximitySensor;
     private final DelayedWakeLock.Builder mDelayedWakeLockBuilder;
     private final Handler mHandler;
+    private final BiometricUnlockController mBiometricUnlockController;
 
     @Inject
     public DozeFactory(FalsingManager falsingManager, DozeLog dozeLog,
@@ -65,7 +66,8 @@
             WakefulnessLifecycle wakefulnessLifecycle, KeyguardUpdateMonitor keyguardUpdateMonitor,
             DockManager dockManager, @Nullable IWallpaperManager wallpaperManager,
             ProximitySensor proximitySensor,
-            DelayedWakeLock.Builder delayedWakeLockBuilder, Handler handler) {
+            DelayedWakeLock.Builder delayedWakeLockBuilder, Handler handler,
+            BiometricUnlockController biometricUnlockController) {
         mFalsingManager = falsingManager;
         mDozeLog = dozeLog;
         mDozeParameters = dozeParameters;
@@ -79,6 +81,7 @@
         mProximitySensor = proximitySensor;
         mDelayedWakeLockBuilder = delayedWakeLockBuilder;
         mHandler = handler;
+        mBiometricUnlockController = biometricUnlockController;
     }
 
     /** Creates a DozeMachine with its parts for {@code dozeService}. */
@@ -107,9 +110,7 @@
                 createDozeScreenBrightness(dozeService, wrappedService, mAsyncSensorManager, host,
                         mDozeParameters, mHandler),
                 new DozeWallpaperState(
-                        mWallpaperManager,
-                        getBiometricUnlockController(dozeService),
-                        mDozeParameters),
+                        mWallpaperManager, mBiometricUnlockController, mDozeParameters),
                 new DozeDockHandler(dozeService, machine, host, config, mHandler, mDockManager),
                 new DozeAuthRemover(dozeService)
         });
@@ -149,10 +150,4 @@
         final SystemUIApplication app = (SystemUIApplication) appCandidate;
         return app.getComponent(DozeHost.class);
     }
-
-    public static BiometricUnlockController getBiometricUnlockController(DozeService service) {
-        Application appCandidate = service.getApplication();
-        final SystemUIApplication app = (SystemUIApplication) appCandidate;
-        return app.getComponent(BiometricUnlockController.class);
-    }
 }
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java
index 548afd5..b9516cf 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java
@@ -18,6 +18,7 @@
 
 import android.annotation.IntDef;
 import android.content.Context;
+import android.content.res.Resources;
 import android.hardware.biometrics.BiometricSourceType;
 import android.metrics.LogMaker;
 import android.os.Handler;
@@ -34,6 +35,7 @@
 import com.android.keyguard.KeyguardUpdateMonitor;
 import com.android.keyguard.KeyguardUpdateMonitorCallback;
 import com.android.systemui.Dependency;
+import com.android.systemui.dagger.qualifiers.MainResources;
 import com.android.systemui.keyguard.KeyguardViewMediator;
 import com.android.systemui.keyguard.ScreenLifecycle;
 import com.android.systemui.keyguard.WakefulnessLifecycle;
@@ -44,6 +46,8 @@
 import java.lang.annotation.Retention;
 import java.lang.annotation.RetentionPolicy;
 
+import javax.inject.Inject;
+
 /**
  * Controller which coordinates all the biometric unlocking actions with the UI.
  */
@@ -145,31 +149,16 @@
     private boolean mHasScreenTurnedOnSinceAuthenticating;
     private boolean mFadedAwayAfterWakeAndUnlock;
 
-    private final MetricsLogger mMetricsLogger = Dependency.get(MetricsLogger.class);
+    private final MetricsLogger mMetricsLogger;
 
-    public BiometricUnlockController(
-            Context context,
-            DozeScrimController dozeScrimController,
-            KeyguardViewMediator keyguardViewMediator,
-            ScrimController scrimController,
-            StatusBar statusBar,
-            KeyguardStateController keyguardStateController, Handler handler,
-            KeyguardUpdateMonitor keyguardUpdateMonitor,
-            KeyguardBypassController keyguardBypassController,
-            DozeParameters dozeParameters) {
-        this(context, dozeScrimController, keyguardViewMediator, scrimController, statusBar,
-                keyguardStateController, handler, keyguardUpdateMonitor,
-                context.getResources()
-                        .getInteger(com.android.internal.R.integer.config_wakeUpDelayDoze),
-                keyguardBypassController, dozeParameters);
-    }
-
-    @VisibleForTesting
-    protected BiometricUnlockController(Context context, DozeScrimController dozeScrimController,
+    @Inject
+    public BiometricUnlockController(Context context, DozeScrimController dozeScrimController,
             KeyguardViewMediator keyguardViewMediator, ScrimController scrimController,
             StatusBar statusBar, KeyguardStateController keyguardStateController, Handler handler,
-            KeyguardUpdateMonitor keyguardUpdateMonitor, int wakeUpDelay,
-            KeyguardBypassController keyguardBypassController, DozeParameters dozeParameters) {
+            KeyguardUpdateMonitor keyguardUpdateMonitor,
+            @MainResources Resources resources,
+            KeyguardBypassController keyguardBypassController, DozeParameters dozeParameters,
+            MetricsLogger metricsLogger) {
         mContext = context;
         mPowerManager = context.getSystemService(PowerManager.class);
         mUpdateMonitor = keyguardUpdateMonitor;
@@ -185,9 +174,10 @@
         mStatusBar = statusBar;
         mKeyguardStateController = keyguardStateController;
         mHandler = handler;
-        mWakeUpDelay = wakeUpDelay;
+        mWakeUpDelay = resources.getInteger(com.android.internal.R.integer.config_wakeUpDelayDoze);
         mKeyguardBypassController = keyguardBypassController;
         mKeyguardBypassController.setUnlockController(this);
+        mMetricsLogger = metricsLogger;
     }
 
     public void setStatusBarKeyguardViewManager(
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
index 97e09dc..4e0af64 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
@@ -356,7 +356,7 @@
     private VolumeComponent mVolumeComponent;
     private BrightnessMirrorController mBrightnessMirrorController;
     private boolean mBrightnessMirrorVisible;
-    protected BiometricUnlockController mBiometricUnlockController;
+    private BiometricUnlockController mBiometricUnlockController;
     private final LightBarController mLightBarController;
     private final Lazy<LockscreenWallpaper> mLockscreenWallpaperLazy;
     protected LockscreenWallpaper mLockscreenWallpaper;
@@ -398,6 +398,7 @@
     private final StatusBarWindowViewController.Builder mStatusBarWindowViewControllerBuilder;
     private final NotifLog mNotifLog;
     private final DozeParameters mDozeParameters;
+    private final Lazy<BiometricUnlockController> mBiometricUnlockControllerLazy;
 
     // expanded notifications
     protected NotificationPanelView mNotificationPanel; // the sliding/resizing panel within the notification window
@@ -691,7 +692,8 @@
             NotifLog notifLog,
             DozeParameters dozeParameters,
             ScrimController scrimController,
-            Lazy<LockscreenWallpaper> lockscreenWallpaperLazy) {
+            Lazy<LockscreenWallpaper> lockscreenWallpaperLazy,
+            Lazy<BiometricUnlockController> biometricUnlockControllerLazy) {
         super(context);
         mFeatureFlags = featureFlags;
         mLightBarController = lightBarController;
@@ -751,6 +753,7 @@
         mDozeParameters = dozeParameters;
         mScrimController = scrimController;
         mLockscreenWallpaperLazy = lockscreenWallpaperLazy;
+        mBiometricUnlockControllerLazy = biometricUnlockControllerLazy;
 
         mBubbleExpandListener =
                 (isExpanding, key) -> {
@@ -1370,11 +1373,7 @@
 
     protected void startKeyguard() {
         Trace.beginSection("StatusBar#startKeyguard");
-        mBiometricUnlockController = new BiometricUnlockController(mContext,
-                mDozeScrimController, mKeyguardViewMediator,
-                mScrimController, this, mKeyguardStateController, new Handler(),
-                mKeyguardUpdateMonitor, mKeyguardBypassController, mDozeParameters);
-        putComponent(BiometricUnlockController.class, mBiometricUnlockController);
+        mBiometricUnlockController = mBiometricUnlockControllerLazy.get();
         mStatusBarKeyguardViewManager = mKeyguardViewMediator.registerStatusBar(this,
                 getBouncerContainer(), mNotificationPanel, mBiometricUnlockController,
                 mStatusBarWindow.findViewById(R.id.lock_icon_container), mStackScroller,
diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/BiometricsUnlockControllerTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/BiometricsUnlockControllerTest.java
index 72bea56..4a0b371 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/BiometricsUnlockControllerTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/BiometricsUnlockControllerTest.java
@@ -34,7 +34,9 @@
 import android.test.suitebuilder.annotation.SmallTest;
 import android.testing.AndroidTestingRunner;
 import android.testing.TestableLooper.RunWithLooper;
+import android.testing.TestableResources;
 
+import com.android.internal.logging.MetricsLogger;
 import com.android.keyguard.KeyguardUpdateMonitor;
 import com.android.systemui.SysuiTestCase;
 import com.android.systemui.keyguard.KeyguardViewMediator;
@@ -78,11 +80,14 @@
     private KeyguardBypassController mKeyguardBypassController;
     @Mock
     private DozeParameters mDozeParameters;
+    @Mock
+    private MetricsLogger mMetricsLogger;
     private BiometricUnlockController mBiometricUnlockController;
 
     @Before
     public void setUp() {
         MockitoAnnotations.initMocks(this);
+        TestableResources res = getContext().getOrCreateTestableResources();
         when(mStatusBarKeyguardViewManager.isShowing()).thenReturn(true);
         when(mUpdateMonitor.isDeviceInteractive()).thenReturn(true);
         when(mKeyguardStateController.isFaceAuthEnabled()).thenReturn(true);
@@ -92,10 +97,11 @@
         mDependency.injectTestDependency(NotificationMediaManager.class, mMediaManager);
         mDependency.injectTestDependency(StatusBarWindowController.class,
                 mStatusBarWindowController);
+        res.addOverride(com.android.internal.R.integer.config_wakeUpDelayDoze, 0);
         mBiometricUnlockController = new BiometricUnlockController(mContext, mDozeScrimController,
                 mKeyguardViewMediator, mScrimController, mStatusBar, mKeyguardStateController,
-                mHandler, mUpdateMonitor, 0 /* wakeUpDelay */, mKeyguardBypassController,
-                mDozeParameters);
+                mHandler, mUpdateMonitor, res.getResources(), mKeyguardBypassController,
+                mDozeParameters, mMetricsLogger);
         mBiometricUnlockController.setStatusBarKeyguardViewManager(mStatusBarKeyguardViewManager);
     }
 
diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/StatusBarTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/StatusBarTest.java
index 03d0cea..f5e92e4 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/StatusBarTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/StatusBarTest.java
@@ -61,7 +61,9 @@
 import android.testing.TestableLooper.RunWithLooper;
 import android.util.DisplayMetrics;
 import android.util.SparseArray;
+import android.view.ViewGroup;
 import android.view.ViewGroup.LayoutParams;
+import android.widget.LinearLayout;
 
 import androidx.test.filters.SmallTest;
 
@@ -70,6 +72,7 @@
 import com.android.internal.logging.testing.FakeMetricsLogger;
 import com.android.internal.statusbar.IStatusBarService;
 import com.android.keyguard.KeyguardUpdateMonitor;
+import com.android.keyguard.ViewMediatorCallback;
 import com.android.systemui.Dependency;
 import com.android.systemui.ForegroundServiceController;
 import com.android.systemui.InitController;
@@ -173,6 +176,7 @@
     @Mock private ScrimController mScrimController;
     @Mock private DozeScrimController mDozeScrimController;
     @Mock private ArrayList<NotificationEntry> mNotificationList;
+    @Mock private Lazy<BiometricUnlockController> mBiometricUnlockControllerLazy;
     @Mock private BiometricUnlockController mBiometricUnlockController;
     @Mock private NotificationData mNotificationData;
     @Mock private NotificationInterruptionStateProvider.HeadsUpSuppressor mHeadsUpSuppressor;
@@ -227,11 +231,14 @@
     @Mock private DozeParameters mDozeParameters;
     @Mock private Lazy<LockscreenWallpaper> mLockscreenWallpaperLazy;
     @Mock private LockscreenWallpaper mLockscreenWallpaper;
+    @Mock private LinearLayout mLockIconContainer;
+    @Mock private ViewMediatorCallback mKeyguardVieMediatorCallback;
 
     @Before
     public void setup() throws Exception {
         MockitoAnnotations.initMocks(this);
         mDependency.injectTestDependency(NotificationFilter.class, mNotificationFilter);
+        mDependency.injectMockDependency(KeyguardDismissUtil.class);
 
         IPowerManager powerManagerService = mock(IPowerManager.class);
         mPowerManager = new PowerManager(mContext, powerManagerService,
@@ -293,6 +300,7 @@
                 .thenReturn(mStatusBarWindowViewController);
 
         when(mLockscreenWallpaperLazy.get()).thenReturn(mLockscreenWallpaper);
+        when(mBiometricUnlockControllerLazy.get()).thenReturn(mBiometricUnlockController);
 
         mStatusBar = new StatusBar(
                 mContext,
@@ -356,13 +364,24 @@
                 mNotifLog,
                 mDozeParameters,
                 mScrimController,
-                mLockscreenWallpaperLazy);
+                mLockscreenWallpaperLazy,
+                mBiometricUnlockControllerLazy);
+
+        when(mStatusBarWindowView.findViewById(R.id.lock_icon_container)).thenReturn(
+                mLockIconContainer);
+
+        when(mKeyguardViewMediator.registerStatusBar(any(StatusBar.class), any(ViewGroup.class),
+                any(NotificationPanelView.class), any(BiometricUnlockController.class),
+                any(ViewGroup.class), any(ViewGroup.class), any(KeyguardBypassController.class)))
+                .thenReturn(mStatusBarKeyguardViewManager);
+
+        when(mKeyguardViewMediator.getViewMediatorCallback()).thenReturn(
+                mKeyguardVieMediatorCallback);
+
         // TODO: we should be able to call mStatusBar.start() and have all the below values
         // initialized automatically.
         mStatusBar.mComponents = mContext.getComponents();
-        mStatusBar.mStatusBarKeyguardViewManager = mStatusBarKeyguardViewManager;
         mStatusBar.mStatusBarWindow = mStatusBarWindowView;
-        mStatusBar.mBiometricUnlockController = mBiometricUnlockController;
         mStatusBar.mNotificationPanel = mNotificationPanelView;
         mStatusBar.mCommandQueue = mCommandQueue;
         mStatusBar.mDozeScrimController = mDozeScrimController;
@@ -373,6 +392,7 @@
         mStatusBar.mBarService = mBarService;
         mStatusBar.mStackScroller = mStackScroller;
         mStatusBar.mStatusBarWindowViewController = mStatusBarWindowViewController;
+        mStatusBar.startKeyguard();
         mStatusBar.putComponent(StatusBar.class, mStatusBar);
         Dependency.get(InitController.class).executePostInitTasks();
         entryManager.setUpForTest(mock(NotificationPresenter.class), mStackScroller,