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.systemui.screenshot.message 18 19 import android.content.ComponentName 20 import androidx.test.ext.junit.runners.AndroidJUnit4 21 import android.content.pm.PackageManager 22 import android.graphics.Canvas 23 import android.graphics.ColorFilter 24 import android.graphics.drawable.Drawable 25 import android.os.UserHandle 26 import com.android.systemui.screenshot.data.model.ProfileType 27 import com.android.systemui.screenshot.data.repository.ProfileTypeRepository 28 import com.google.common.truth.Truth.assertThat 29 import kotlinx.coroutines.test.runTest 30 import org.junit.Test 31 import org.junit.runner.RunWith 32 33 @RunWith(AndroidJUnit4::class) 34 class ProfileMessageControllerTest { 35 @Test <lambda>null36 fun personalScreenshot() = runTest { 37 assertThat( 38 getMessageController() 39 .onScreenshotTaken(UserHandle.of(profileTypeRepository.personalUser)) 40 ) 41 .isNull() 42 } 43 44 @Test <lambda>null45 fun communalScreenshot() = runTest { 46 assertThat( 47 getMessageController() 48 .onScreenshotTaken(UserHandle.of(profileTypeRepository.communalUser)) 49 ) 50 .isNull() 51 } 52 53 @Test <lambda>null54 fun noUserScreenshot() = runTest { 55 assertThat(getMessageController().onScreenshotTaken(null)).isNull() 56 } 57 58 @Test <lambda>null59 fun alreadyDismissed() = runTest { 60 val messageController = getMessageController() 61 profileFirstRunSettings.onMessageDismissed(ProfileMessageController.FirstRunProfile.WORK) 62 assertThat( 63 messageController.onScreenshotTaken(UserHandle.of(profileTypeRepository.workUser)) 64 ) 65 .isNull() 66 } 67 68 @Test <lambda>null69 fun noFileManager() = runTest { 70 val messageController = getMessageController(fileManagerComponent = null) 71 val data = 72 messageController.onScreenshotTaken(UserHandle.of(profileTypeRepository.workUser)) 73 assertThat(data?.profileType).isEqualTo(ProfileMessageController.FirstRunProfile.WORK) 74 assertThat(data?.labeledIcon?.label).isEqualTo(DEFAULT_APP_NAME) 75 assertThat(data?.labeledIcon?.badgedIcon).isNull() 76 } 77 78 @Test <lambda>null79 fun fileManagerNotFound() = runTest { 80 val messageController = 81 getMessageController(fileManagerComponent = ComponentName("Something", "Random")) 82 val data = 83 messageController.onScreenshotTaken(UserHandle.of(profileTypeRepository.privateUser)) 84 assertThat(data?.profileType).isEqualTo(ProfileMessageController.FirstRunProfile.PRIVATE) 85 assertThat(data?.labeledIcon?.label).isEqualTo(DEFAULT_APP_NAME) 86 assertThat(data?.labeledIcon?.badgedIcon).isNull() 87 } 88 89 @Test <lambda>null90 fun fileManagerFound() = runTest { 91 val messageController = getMessageController() 92 val data = 93 messageController.onScreenshotTaken(UserHandle.of(profileTypeRepository.privateUser)) 94 assertThat(data?.profileType).isEqualTo(ProfileMessageController.FirstRunProfile.PRIVATE) 95 assertThat(data?.labeledIcon?.label).isEqualTo(FILE_MANAGER_LABEL) 96 assertThat(data?.labeledIcon?.badgedIcon).isEqualTo(drawable) 97 } 98 99 private val drawable = 100 object : Drawable() { drawnull101 override fun draw(canvas: Canvas) {} 102 setAlphanull103 override fun setAlpha(alpha: Int) {} 104 setColorFilternull105 override fun setColorFilter(colorFilter: ColorFilter?) {} 106 getOpacitynull107 override fun getOpacity(): Int = 0 108 } 109 110 private val packageLabelIconProvider = 111 object : PackageLabelIconProvider { 112 override suspend fun getPackageLabelIcon( 113 componentName: ComponentName, 114 userHandle: UserHandle 115 ): LabeledIcon { 116 if (componentName.equals(FILE_MANAGER_COMPONENT)) { 117 return LabeledIcon(FILE_MANAGER_LABEL, drawable) 118 } else { 119 throw PackageManager.NameNotFoundException() 120 } 121 } 122 } 123 124 private class FakeProfileFirstRunResources(private val fileManager: ComponentName?) : 125 ProfileFirstRunFileResources { fileManagerComponentNamenull126 override fun fileManagerComponentName(): ComponentName? { 127 return fileManager 128 } 129 defaultFileAppnull130 override fun defaultFileApp() = LabeledIcon(DEFAULT_APP_NAME, badgedIcon = null) 131 } 132 133 private val profileFirstRunSettings = 134 object : ProfileFirstRunSettings { 135 private val dismissed = 136 mutableMapOf( 137 ProfileMessageController.FirstRunProfile.WORK to false, 138 ProfileMessageController.FirstRunProfile.PRIVATE to false, 139 ) 140 141 override fun messageAlreadyDismissed( 142 profileType: ProfileMessageController.FirstRunProfile 143 ): Boolean { 144 return dismissed.getOrDefault(profileType, false) 145 } 146 147 override fun onMessageDismissed(profileType: ProfileMessageController.FirstRunProfile) { 148 dismissed[profileType] = true 149 } 150 } 151 152 private val profileTypeRepository = 153 object : ProfileTypeRepository { getProfileTypenull154 override suspend fun getProfileType(userId: Int): ProfileType { 155 return when (userId) { 156 workUser -> ProfileType.WORK 157 privateUser -> ProfileType.PRIVATE 158 communalUser -> ProfileType.COMMUNAL 159 else -> ProfileType.NONE 160 } 161 } 162 163 val personalUser = 0 164 val workUser = 1 165 val privateUser = 2 166 val communalUser = 3 167 } 168 getMessageControllernull169 private fun getMessageController( 170 fileManagerComponent: ComponentName? = FILE_MANAGER_COMPONENT 171 ) = 172 ProfileMessageController( 173 packageLabelIconProvider, 174 FakeProfileFirstRunResources(fileManagerComponent), 175 profileFirstRunSettings, 176 profileTypeRepository 177 ) 178 179 companion object { 180 val FILE_MANAGER_COMPONENT = ComponentName("package", "component") 181 const val DEFAULT_APP_NAME = "default app" 182 const val FILE_MANAGER_LABEL = "file manager" 183 } 184 } 185