1 /*
2  * Copyright (C) 2018 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.applications.appinfo;
18 
19 import android.content.Context;
20 import android.net.NetworkTemplate;
21 import android.os.Bundle;
22 import android.text.format.DateUtils;
23 import android.text.format.Formatter;
24 
25 import androidx.annotation.VisibleForTesting;
26 import androidx.loader.app.LoaderManager;
27 import androidx.loader.content.Loader;
28 import androidx.preference.Preference;
29 import androidx.preference.PreferenceScreen;
30 
31 import com.android.settings.R;
32 import com.android.settings.SettingsPreferenceFragment;
33 import com.android.settings.Utils;
34 import com.android.settings.datausage.AppDataUsage;
35 import com.android.settings.datausage.DataUsageUtils;
36 import com.android.settingslib.AppItem;
37 import com.android.settingslib.core.lifecycle.LifecycleObserver;
38 import com.android.settingslib.core.lifecycle.events.OnPause;
39 import com.android.settingslib.core.lifecycle.events.OnResume;
40 import com.android.settingslib.net.NetworkCycleDataForUid;
41 import com.android.settingslib.net.NetworkCycleDataForUidLoader;
42 
43 import java.util.List;
44 
45 public class AppDataUsagePreferenceController extends AppInfoPreferenceControllerBase
46         implements LoaderManager.LoaderCallbacks<List<NetworkCycleDataForUid>>, LifecycleObserver,
47         OnResume, OnPause {
48 
49     private List<NetworkCycleDataForUid> mAppUsageData;
50 
AppDataUsagePreferenceController(Context context, String key)51     public AppDataUsagePreferenceController(Context context, String key) {
52         super(context, key);
53     }
54 
55     @Override
getAvailabilityStatus()56     public int getAvailabilityStatus() {
57         return isBandwidthControlEnabled() ? AVAILABLE : CONDITIONALLY_UNAVAILABLE;
58     }
59 
60     @Override
displayPreference(PreferenceScreen screen)61     public void displayPreference(PreferenceScreen screen) {
62         super.displayPreference(screen);
63     }
64 
65     @Override
updateState(Preference preference)66     public void updateState(Preference preference) {
67         preference.setSummary(getDataSummary());
68     }
69 
70     @Override
onResume()71     public void onResume() {
72         if (isAvailable()) {
73             final int uid = mParent.getAppEntry().info.uid;
74             final AppItem app = new AppItem(uid);
75             app.addUid(uid);
76             mParent.getLoaderManager().restartLoader(mParent.LOADER_CHART_DATA, null /* args */,
77                     this);
78         }
79     }
80 
81     @Override
onPause()82     public void onPause() {
83         if (isAvailable()) {
84             mParent.getLoaderManager().destroyLoader(mParent.LOADER_CHART_DATA);
85         }
86     }
87 
88     @Override
onCreateLoader(int id, Bundle args)89     public Loader<List<NetworkCycleDataForUid>> onCreateLoader(int id, Bundle args) {
90         final NetworkTemplate template = getTemplate(mContext);
91         return NetworkCycleDataForUidLoader.builder(mContext)
92             .addUid(mParent.getAppEntry().info.uid)
93             .setRetrieveDetail(false)
94             .setNetworkTemplate(template)
95             .build();
96     }
97 
98     @Override
onLoadFinished(Loader<List<NetworkCycleDataForUid>> loader, List<NetworkCycleDataForUid> data)99     public void onLoadFinished(Loader<List<NetworkCycleDataForUid>> loader,
100             List<NetworkCycleDataForUid> data) {
101         mAppUsageData = data;
102         updateState(mPreference);
103     }
104 
105     @Override
onLoaderReset(Loader<List<NetworkCycleDataForUid>> loader)106     public void onLoaderReset(Loader<List<NetworkCycleDataForUid>> loader) {
107         // Leave last result.
108     }
109 
110     @Override
getDetailFragmentClass()111     protected Class<? extends SettingsPreferenceFragment> getDetailFragmentClass() {
112         return AppDataUsage.class;
113     }
114 
getDataSummary()115     private CharSequence getDataSummary() {
116         if (mAppUsageData != null) {
117             long totalBytes = 0;
118             long startTime = System.currentTimeMillis();
119             for (NetworkCycleDataForUid data : mAppUsageData) {
120                 totalBytes += data.getTotalUsage();
121                 final long cycleStart = data.getStartTime();
122                 if (cycleStart < startTime) {
123                     startTime = cycleStart;
124                 }
125             }
126             if (totalBytes == 0) {
127                 return mContext.getString(R.string.no_data_usage);
128             }
129             return mContext.getString(R.string.data_summary_format,
130                     Formatter.formatFileSize(mContext, totalBytes, Formatter.FLAG_IEC_UNITS),
131                     DateUtils.formatDateTime(mContext, startTime,
132                             DateUtils.FORMAT_SHOW_DATE | DateUtils.FORMAT_ABBREV_MONTH));
133         }
134         return mContext.getString(R.string.computing_size);
135     }
136 
getTemplate(Context context)137     private static NetworkTemplate getTemplate(Context context) {
138         if (DataUsageUtils.hasReadyMobileRadio(context)) {
139             return NetworkTemplate.buildTemplateMobileWildcard();
140         }
141         if (DataUsageUtils.hasWifiRadio(context)) {
142             return NetworkTemplate.buildTemplateWifiWildcard();
143         }
144         return NetworkTemplate.buildTemplateEthernet();
145     }
146 
147     @VisibleForTesting
isBandwidthControlEnabled()148     boolean isBandwidthControlEnabled() {
149         return Utils.isBandwidthControlEnabled();
150     }
151 
152 }
153