1 /* 2 * Copyright (C) 2017 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.deviceinfo.storage; 18 19 import android.content.Context; 20 import android.content.pm.UserInfo; 21 import android.graphics.drawable.Drawable; 22 import android.os.UserManager; 23 import android.support.annotation.NonNull; 24 import android.support.annotation.Nullable; 25 import android.support.annotation.VisibleForTesting; 26 import android.support.v7.preference.PreferenceGroup; 27 import android.support.v7.preference.PreferenceScreen; 28 import android.util.SparseArray; 29 30 import com.android.settings.Utils; 31 import com.android.settings.core.PreferenceControllerMixin; 32 import com.android.settings.deviceinfo.StorageItemPreference; 33 import com.android.settingslib.core.AbstractPreferenceController; 34 35 import java.util.ArrayList; 36 import java.util.List; 37 38 /** 39 * SecondaryUserController controls the preferences on the Storage screen which had to do with 40 * secondary users. 41 */ 42 public class SecondaryUserController extends AbstractPreferenceController implements 43 PreferenceControllerMixin, StorageAsyncLoader.ResultHandler, 44 UserIconLoader.UserIconHandler { 45 // PreferenceGroupKey to try to add our preference onto. 46 private static final String TARGET_PREFERENCE_GROUP_KEY = "pref_secondary_users"; 47 private static final String PREFERENCE_KEY_BASE = "pref_user_"; 48 private static final int USER_PROFILE_INSERTION_LOCATION = 6; 49 private static final int SIZE_NOT_SET = -1; 50 51 private @NonNull UserInfo mUser; 52 private @Nullable StorageItemPreference mStoragePreference; 53 private Drawable mUserIcon; 54 private long mSize; 55 private long mTotalSizeBytes; 56 57 /** 58 * Adds the appropriate controllers to a controller list for handling all secondary users on 59 * a device. 60 * @param context Context for initializing the preference controllers. 61 * @param userManager UserManagerWrapper for figuring out which controllers to add. 62 */ 63 public static List<AbstractPreferenceController> getSecondaryUserControllers( 64 Context context, UserManager userManager) { 65 List<AbstractPreferenceController> controllers = new ArrayList<>(); 66 UserInfo primaryUser = userManager.getPrimaryUser(); 67 boolean addedUser = false; 68 List<UserInfo> infos = userManager.getUsers(); 69 for (int i = 0, size = infos.size(); i < size; i++) { 70 UserInfo info = infos.get(i); 71 if (info.isPrimary()) { 72 continue; 73 } 74 75 if (info == null || Utils.isProfileOf(primaryUser, info)) { 76 controllers.add( 77 new UserProfileController(context, info, USER_PROFILE_INSERTION_LOCATION)); 78 continue; 79 } 80 81 controllers.add(new SecondaryUserController(context, info)); 82 addedUser = true; 83 } 84 85 if (!addedUser) { 86 controllers.add(new NoSecondaryUserController(context)); 87 } 88 return controllers; 89 } 90 91 /** 92 * Constructor for a given secondary user. 93 * @param context Context to initialize the underlying {@link AbstractPreferenceController}. 94 * @param info {@link UserInfo} for the secondary user which this controllers covers. 95 */ 96 @VisibleForTesting 97 SecondaryUserController(Context context, @NonNull UserInfo info) { 98 super(context); 99 mUser = info; 100 mSize = SIZE_NOT_SET; 101 } 102 103 @Override 104 public void displayPreference(PreferenceScreen screen) { 105 if (mStoragePreference == null) { 106 mStoragePreference = new StorageItemPreference(screen.getContext()); 107 108 PreferenceGroup group = 109 (PreferenceGroup) screen.findPreference(TARGET_PREFERENCE_GROUP_KEY); 110 mStoragePreference.setTitle(mUser.name); 111 mStoragePreference.setKey(PREFERENCE_KEY_BASE + mUser.id); 112 if (mSize != SIZE_NOT_SET) { 113 mStoragePreference.setStorageSize(mSize, mTotalSizeBytes); 114 } 115 116 group.setVisible(true); 117 group.addPreference(mStoragePreference); 118 maybeSetIcon(); 119 } 120 } 121 122 @Override 123 public boolean isAvailable() { 124 return true; 125 } 126 127 @Override 128 public String getPreferenceKey() { 129 return mStoragePreference != null ? mStoragePreference.getKey() : null; 130 } 131 132 /** 133 * Returns the user for which this is the secondary user controller. 134 */ 135 @NonNull 136 public UserInfo getUser() { 137 return mUser; 138 } 139 140 /** 141 * Sets the size for the preference. 142 * @param size Size in bytes. 143 */ 144 public void setSize(long size) { 145 mSize = size; 146 if (mStoragePreference != null) { 147 mStoragePreference.setStorageSize(mSize, mTotalSizeBytes); 148 } 149 } 150 151 /** 152 * Sets the total size for the preference for the progress bar. 153 * @param totalSizeBytes Total size in bytes. 154 */ 155 public void setTotalSize(long totalSizeBytes) { 156 mTotalSizeBytes = totalSizeBytes; 157 } 158 159 public void handleResult(SparseArray<StorageAsyncLoader.AppsStorageResult> stats) { 160 int userId = getUser().id; 161 StorageAsyncLoader.AppsStorageResult result = stats.get(userId); 162 if (result != null) { 163 setSize(result.externalStats.totalBytes); 164 } 165 } 166 167 @Override 168 public void handleUserIcons(SparseArray<Drawable> fetchedIcons) { 169 mUserIcon = fetchedIcons.get(mUser.id); 170 maybeSetIcon(); 171 } 172 173 private void maybeSetIcon() { 174 if (mUserIcon != null && mStoragePreference != null) { 175 mStoragePreference.setIcon(mUserIcon); 176 } 177 } 178 179 private static class NoSecondaryUserController extends AbstractPreferenceController implements 180 PreferenceControllerMixin { 181 public NoSecondaryUserController(Context context) { 182 super(context); 183 } 184 185 @Override 186 public void displayPreference(PreferenceScreen screen) { 187 PreferenceGroup group = 188 (PreferenceGroup) screen.findPreference(TARGET_PREFERENCE_GROUP_KEY); 189 if (group == null) { 190 return; 191 } 192 screen.removePreference(group); 193 } 194 195 @Override 196 public boolean isAvailable() { 197 return true; 198 } 199 200 @Override 201 public String getPreferenceKey() { 202 return null; 203 } 204 205 } 206 } 207