1 /*
2  * Copyright (C) 2024 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.settings.biometrics.fingerprint2
18 
19 import android.hardware.fingerprint.FingerprintManager
20 import android.view.MotionEvent
21 import android.view.accessibility.AccessibilityManager
22 import androidx.fragment.app.FragmentActivity
23 import androidx.lifecycle.ViewModelStore
24 import androidx.lifecycle.ViewModelStoreOwner
25 import com.android.internal.widget.LockPatternUtils
26 import com.android.settings.SettingsApplication
27 import com.android.settings.biometrics.GatekeeperPasswordProvider
28 import com.android.settings.biometrics.fingerprint2.data.repository.DebuggingRepository
29 import com.android.settings.biometrics.fingerprint2.data.repository.DebuggingRepositoryImpl
30 import com.android.settings.biometrics.fingerprint2.data.repository.FingerprintSensorRepository
31 import com.android.settings.biometrics.fingerprint2.data.repository.FingerprintSensorRepositoryImpl
32 import com.android.settings.biometrics.fingerprint2.debug.data.repository.UdfpsEnrollDebugRepositoryImpl
33 import com.android.settings.biometrics.fingerprint2.debug.domain.interactor.DebugTouchEventInteractorImpl
34 import com.android.settings.biometrics.fingerprint2.domain.interactor.AccessibilityInteractor
35 import com.android.settings.biometrics.fingerprint2.domain.interactor.AccessibilityInteractorImpl
36 import com.android.settings.biometrics.fingerprint2.domain.interactor.DebuggingInteractor
37 import com.android.settings.biometrics.fingerprint2.domain.interactor.DebuggingInteractorImpl
38 import com.android.settings.biometrics.fingerprint2.domain.interactor.DisplayDensityInteractor
39 import com.android.settings.biometrics.fingerprint2.domain.interactor.DisplayDensityInteractorImpl
40 import com.android.settings.biometrics.fingerprint2.domain.interactor.EnrollStageInteractor
41 import com.android.settings.biometrics.fingerprint2.domain.interactor.EnrollStageInteractorImpl
42 import com.android.settings.biometrics.fingerprint2.domain.interactor.FingerprintEnrollInteractor
43 import com.android.settings.biometrics.fingerprint2.domain.interactor.FingerprintEnrollInteractorImpl
44 import com.android.settings.biometrics.fingerprint2.domain.interactor.FingerprintManagerInteractorImpl
45 import com.android.settings.biometrics.fingerprint2.domain.interactor.FingerprintSensorInteractor
46 import com.android.settings.biometrics.fingerprint2.domain.interactor.FingerprintSensorInteractorImpl
47 import com.android.settings.biometrics.fingerprint2.domain.interactor.FoldStateInteractor
48 import com.android.settings.biometrics.fingerprint2.domain.interactor.FoldStateInteractorImpl
49 import com.android.settings.biometrics.fingerprint2.domain.interactor.OrientationInteractor
50 import com.android.settings.biometrics.fingerprint2.domain.interactor.OrientationInteractorImpl
51 import com.android.settings.biometrics.fingerprint2.domain.interactor.TouchEventInteractor
52 import com.android.settings.biometrics.fingerprint2.domain.interactor.UdfpsEnrollInteractor
53 import com.android.settings.biometrics.fingerprint2.domain.interactor.UdfpsEnrollInteractorImpl
54 import com.android.settings.biometrics.fingerprint2.domain.interactor.VibrationInteractor
55 import com.android.settings.biometrics.fingerprint2.domain.interactor.VibrationInteractorImpl
56 import com.android.settings.biometrics.fingerprint2.lib.domain.interactor.FingerprintManagerInteractor
57 import com.android.settings.biometrics.fingerprint2.lib.model.Settings
58 import java.util.concurrent.Executors
59 import kotlinx.coroutines.MainScope
60 import kotlinx.coroutines.asCoroutineDispatcher
61 import kotlinx.coroutines.flow.Flow
62 import kotlinx.coroutines.flow.flowOf
63 
64 /**
65  * This class should handle all repo & interactor creation needed by the ViewModels for the
66  * biometrics code.
67  *
68  * This code is instantiated within the [SettingsApplication], all repos should be private &
69  * immutable and all interactors should public and immutable
70  */
71 class BiometricsEnvironment(context: SettingsApplication) : ViewModelStoreOwner {
72 
73   private val executorService = Executors.newSingleThreadExecutor()
74   private val backgroundDispatcher = executorService.asCoroutineDispatcher()
75   private val applicationScope = MainScope()
76   private val gateKeeperPasswordProvider = GatekeeperPasswordProvider(LockPatternUtils(context))
77   private val fingerprintManager =
78     context.getSystemService(FragmentActivity.FINGERPRINT_SERVICE) as FingerprintManager?
79 
80   private val fingerprintSensorRepository: FingerprintSensorRepository =
81     FingerprintSensorRepositoryImpl(fingerprintManager, backgroundDispatcher, applicationScope)
82   private val debuggingRepository: DebuggingRepository = DebuggingRepositoryImpl()
83   private val udfpsDebugRepo = UdfpsEnrollDebugRepositoryImpl()
84 
85   /** For now, interactors are public to those with access to the [BiometricsEnvironment] class */
<lambda>null86   val fingerprintEnrollInteractor: FingerprintEnrollInteractor by lazy {
87     FingerprintEnrollInteractorImpl(context, fingerprintManager, Settings)
88   }
89 
90   /** [FingerprintManagerInteractor] to be used to construct view models */
<lambda>null91   val fingerprintManagerInteractor: FingerprintManagerInteractor by lazy {
92     FingerprintManagerInteractorImpl(
93       context,
94       backgroundDispatcher,
95       fingerprintManager,
96       fingerprintSensorRepository,
97       gateKeeperPasswordProvider,
98       fingerprintEnrollInteractor,
99     )
100   }
101 
<lambda>null102   val accessibilityInteractor: AccessibilityInteractor by lazy {
103     AccessibilityInteractorImpl(
104       context.getSystemService(AccessibilityManager::class.java)!!,
105       applicationScope,
106     )
107   }
108 
<lambda>null109   val foldStateInteractor: FoldStateInteractor by lazy { FoldStateInteractorImpl(context) }
110 
<lambda>null111   val orientationInteractor: OrientationInteractor by lazy { OrientationInteractorImpl(context) }
112 
<lambda>null113   val vibrationInteractor: VibrationInteractor by lazy { VibrationInteractorImpl(context) }
114 
<lambda>null115   val displayDensityInteractor: DisplayDensityInteractor by lazy {
116     DisplayDensityInteractorImpl(context, applicationScope)
117   }
118 
<lambda>null119   val debuggingInteractor: DebuggingInteractor by lazy {
120     DebuggingInteractorImpl(debuggingRepository)
121   }
122 
<lambda>null123   val enrollStageInteractor: EnrollStageInteractor by lazy { EnrollStageInteractorImpl() }
124 
<lambda>null125   val udfpsEnrollInteractor: UdfpsEnrollInteractor by lazy {
126     UdfpsEnrollInteractorImpl(context, accessibilityInteractor)
127   }
128 
<lambda>null129   val sensorInteractor: FingerprintSensorInteractor by lazy {
130     FingerprintSensorInteractorImpl(fingerprintSensorRepository)
131   }
132 
<lambda>null133   val touchEventInteractor: TouchEventInteractor by lazy {
134     if (debuggingRepository.isDebuggingEnabled()) {
135       DebugTouchEventInteractorImpl(udfpsDebugRepo)
136     } else {
137       object : TouchEventInteractor {
138         override val touchEvent: Flow<MotionEvent> = flowOf()
139       }
140     }
141   }
142 
143   override val viewModelStore: ViewModelStore = ViewModelStore()
144 }
145