1 /*
2  *  Copyright (C) 2023 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 
18 package com.android.systemui.keyguard.data.quickaffordance
19 
20 import android.app.StatusBarManager
21 import android.app.admin.DevicePolicyManager
22 import android.content.Context
23 import android.content.Intent
24 import com.android.systemui.ActivityIntentHelper
25 import com.android.systemui.res.R
26 import com.android.systemui.animation.Expandable
27 import com.android.systemui.camera.CameraIntents
28 import com.android.systemui.camera.CameraIntentsWrapper
29 import com.android.systemui.common.shared.model.ContentDescription
30 import com.android.systemui.common.shared.model.Icon
31 import com.android.systemui.dagger.SysUISingleton
32 import com.android.systemui.dagger.qualifiers.Application
33 import com.android.systemui.dagger.qualifiers.Background
34 import com.android.systemui.settings.UserTracker
35 import javax.inject.Inject
36 import kotlinx.coroutines.CoroutineDispatcher
37 import kotlinx.coroutines.flow.Flow
38 import kotlinx.coroutines.flow.flow
39 import kotlinx.coroutines.withContext
40 
41 @SysUISingleton
42 class VideoCameraQuickAffordanceConfig
43 @Inject
44 constructor(
45     @Application private val context: Context,
46     private val cameraIntents: CameraIntentsWrapper,
47     private val activityIntentHelper: ActivityIntentHelper,
48     private val userTracker: UserTracker,
49     private val devicePolicyManager: DevicePolicyManager,
50     @Background private val backgroundDispatcher: CoroutineDispatcher,
51 ) : KeyguardQuickAffordanceConfig {
52 
53     private val intent: Intent
<lambda>null54         get() = cameraIntents.getVideoCameraIntent(userTracker.userId).apply {
55             putExtra(
56                 CameraIntents.EXTRA_LAUNCH_SOURCE,
57                 StatusBarManager.CAMERA_LAUNCH_SOURCE_QUICK_AFFORDANCE,
58             )
59         }
60 
61     override val key: String
62         get() = BuiltInKeyguardQuickAffordanceKeys.VIDEO_CAMERA
63 
pickerNamenull64     override fun pickerName(): String = context.getString(R.string.video_camera)
65 
66     override val pickerIconResourceId: Int
67         get() = R.drawable.ic_videocam
68 
69     override val lockScreenState: Flow<KeyguardQuickAffordanceConfig.LockScreenState>
70         get() = flow {
71             emit(
72                 if (isLaunchable()) {
73                     KeyguardQuickAffordanceConfig.LockScreenState.Visible(
74                         icon =
75                             Icon.Resource(
76                                 R.drawable.ic_videocam,
77                                 ContentDescription.Resource(R.string.video_camera)
78                             )
79                     )
80                 } else {
81                     KeyguardQuickAffordanceConfig.LockScreenState.Hidden
82                 }
83             )
84         }
85 
getPickerScreenStatenull86     override suspend fun getPickerScreenState(): KeyguardQuickAffordanceConfig.PickerScreenState {
87         return if (isLaunchable()) {
88             super.getPickerScreenState()
89         } else {
90             KeyguardQuickAffordanceConfig.PickerScreenState.UnavailableOnDevice
91         }
92     }
93 
onTriggerednull94     override fun onTriggered(
95         expandable: Expandable?
96     ): KeyguardQuickAffordanceConfig.OnTriggeredResult {
97         return KeyguardQuickAffordanceConfig.OnTriggeredResult.StartActivity(
98             intent = intent,
99             canShowWhileLocked = false,
100         )
101     }
102 
isLaunchablenull103     private suspend fun isLaunchable(): Boolean {
104         return activityIntentHelper.getTargetActivityInfo(
105             intent,
106             userTracker.userId,
107             true,
108         ) != null &&
109             withContext(backgroundDispatcher) {
110                 !devicePolicyManager.getCameraDisabled(null, userTracker.userId)
111             }
112     }
113 }
114