Home | History | Annotate | Download | only in tiles
      1 /*
      2  * Copyright (C) 2014 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.qs.tiles;
     18 
     19 import android.content.ComponentName;
     20 import android.content.Context;
     21 import android.content.Intent;
     22 import android.content.res.Resources;
     23 import android.view.LayoutInflater;
     24 import android.view.View;
     25 import android.view.ViewGroup;
     26 
     27 import com.android.internal.logging.MetricsLogger;
     28 import com.android.systemui.R;
     29 import com.android.systemui.qs.QSTile;
     30 import com.android.systemui.qs.QSTileView;
     31 import com.android.systemui.qs.SignalTileView;
     32 import com.android.systemui.statusbar.policy.NetworkController;
     33 import com.android.systemui.statusbar.policy.NetworkController.IconState;
     34 import com.android.systemui.statusbar.policy.NetworkController.MobileDataController;
     35 import com.android.systemui.statusbar.policy.NetworkController.MobileDataController.DataUsageInfo;
     36 import com.android.systemui.statusbar.policy.NetworkController.SignalCallback;
     37 import com.android.systemui.statusbar.policy.SignalCallbackAdapter;
     38 
     39 /** Quick settings tile: Cellular **/
     40 public class CellularTile extends QSTile<QSTile.SignalState> {
     41     private static final Intent CELLULAR_SETTINGS = new Intent().setComponent(new ComponentName(
     42             "com.android.settings", "com.android.settings.Settings$DataUsageSummaryActivity"));
     43 
     44     private final NetworkController mController;
     45     private final MobileDataController mDataController;
     46     private final CellularDetailAdapter mDetailAdapter;
     47 
     48     private final CellSignalCallback mSignalCallback = new CellSignalCallback();
     49 
     50     public CellularTile(Host host) {
     51         super(host);
     52         mController = host.getNetworkController();
     53         mDataController = mController.getMobileDataController();
     54         mDetailAdapter = new CellularDetailAdapter();
     55     }
     56 
     57     @Override
     58     protected SignalState newTileState() {
     59         return new SignalState();
     60     }
     61 
     62     @Override
     63     public DetailAdapter getDetailAdapter() {
     64         return mDetailAdapter;
     65     }
     66 
     67     @Override
     68     public void setListening(boolean listening) {
     69         if (listening) {
     70             mController.addSignalCallback(mSignalCallback);
     71         } else {
     72             mController.removeSignalCallback(mSignalCallback);
     73         }
     74     }
     75 
     76     @Override
     77     public QSTileView createTileView(Context context) {
     78         return new SignalTileView(context);
     79     }
     80 
     81     @Override
     82     protected void handleClick() {
     83         MetricsLogger.action(mContext, getMetricsCategory());
     84         if (mDataController.isMobileDataSupported()) {
     85             showDetail(true);
     86         } else {
     87             mHost.startActivityDismissingKeyguard(CELLULAR_SETTINGS);
     88         }
     89     }
     90 
     91     @Override
     92     protected void handleUpdateState(SignalState state, Object arg) {
     93         state.visible = mController.hasMobileDataFeature();
     94         if (!state.visible) return;
     95         CallbackInfo cb = (CallbackInfo) arg;
     96         if (cb == null) {
     97             cb = mSignalCallback.mInfo;
     98         }
     99 
    100         final Resources r = mContext.getResources();
    101         final int iconId = cb.noSim ? R.drawable.ic_qs_no_sim
    102                 : !cb.enabled || cb.airplaneModeEnabled ? R.drawable.ic_qs_signal_disabled
    103                 : cb.mobileSignalIconId > 0 ? cb.mobileSignalIconId
    104                 : R.drawable.ic_qs_signal_no_signal;
    105         state.icon = ResourceIcon.get(iconId);
    106         state.isOverlayIconWide = cb.isDataTypeIconWide;
    107         state.autoMirrorDrawable = !cb.noSim;
    108         state.overlayIconId = cb.enabled && (cb.dataTypeIconId > 0) ? cb.dataTypeIconId : 0;
    109         state.filter = iconId != R.drawable.ic_qs_no_sim;
    110         state.activityIn = cb.enabled && cb.activityIn;
    111         state.activityOut = cb.enabled && cb.activityOut;
    112 
    113         state.label = cb.enabled
    114                 ? removeTrailingPeriod(cb.enabledDesc)
    115                 : r.getString(R.string.quick_settings_rssi_emergency_only);
    116 
    117         final String signalContentDesc = cb.enabled && (cb.mobileSignalIconId > 0)
    118                 ? cb.signalContentDescription
    119                 : r.getString(R.string.accessibility_no_signal);
    120         final String dataContentDesc = cb.enabled && (cb.dataTypeIconId > 0) && !cb.wifiEnabled
    121                 ? cb.dataContentDescription
    122                 : r.getString(R.string.accessibility_no_data);
    123         state.contentDescription = r.getString(
    124                 R.string.accessibility_quick_settings_mobile,
    125                 signalContentDesc, dataContentDesc,
    126                 state.label);
    127     }
    128 
    129     @Override
    130     public int getMetricsCategory() {
    131         return MetricsLogger.QS_CELLULAR;
    132     }
    133 
    134     // Remove the period from the network name
    135     public static String removeTrailingPeriod(String string) {
    136         if (string == null) return null;
    137         final int length = string.length();
    138         if (string.endsWith(".")) {
    139             return string.substring(0, length - 1);
    140         }
    141         return string;
    142     }
    143 
    144     private static final class CallbackInfo {
    145         boolean enabled;
    146         boolean wifiEnabled;
    147         boolean airplaneModeEnabled;
    148         int mobileSignalIconId;
    149         String signalContentDescription;
    150         int dataTypeIconId;
    151         String dataContentDescription;
    152         boolean activityIn;
    153         boolean activityOut;
    154         String enabledDesc;
    155         boolean noSim;
    156         boolean isDataTypeIconWide;
    157     }
    158 
    159     private final class CellSignalCallback extends SignalCallbackAdapter {
    160         private final CallbackInfo mInfo = new CallbackInfo();
    161         @Override
    162         public void setWifiIndicators(boolean enabled, IconState statusIcon, IconState qsIcon,
    163                 boolean activityIn, boolean activityOut, String description) {
    164             mInfo.wifiEnabled = enabled;
    165             refreshState(mInfo);
    166         }
    167 
    168         @Override
    169         public void setMobileDataIndicators(IconState statusIcon, IconState qsIcon, int statusType,
    170                 int qsType, boolean activityIn, boolean activityOut, String typeContentDescription,
    171                 String description, boolean isWide, int subId) {
    172             if (qsIcon == null) {
    173                 // Not data sim, don't display.
    174                 return;
    175             }
    176             mInfo.enabled = qsIcon.visible;
    177             mInfo.mobileSignalIconId = qsIcon.icon;
    178             mInfo.signalContentDescription = qsIcon.contentDescription;
    179             mInfo.dataTypeIconId = qsType;
    180             mInfo.dataContentDescription = typeContentDescription;
    181             mInfo.activityIn = activityIn;
    182             mInfo.activityOut = activityOut;
    183             mInfo.enabledDesc = description;
    184             mInfo.isDataTypeIconWide = qsType != 0 && isWide;
    185             refreshState(mInfo);
    186         }
    187 
    188         @Override
    189         public void setNoSims(boolean show) {
    190             mInfo.noSim = show;
    191             if (mInfo.noSim) {
    192                 // Make sure signal gets cleared out when no sims.
    193                 mInfo.mobileSignalIconId = 0;
    194                 mInfo.dataTypeIconId = 0;
    195                 // Show a No SIMs description to avoid emergency calls message.
    196                 mInfo.enabled = true;
    197                 mInfo.enabledDesc = mContext.getString(
    198                         R.string.keyguard_missing_sim_message_short);
    199                 mInfo.signalContentDescription = mInfo.enabledDesc;
    200             }
    201             refreshState(mInfo);
    202         }
    203 
    204         @Override
    205         public void setIsAirplaneMode(IconState icon) {
    206             mInfo.airplaneModeEnabled = icon.visible;
    207             refreshState(mInfo);
    208         }
    209 
    210         @Override
    211         public void setMobileDataEnabled(boolean enabled) {
    212             mDetailAdapter.setMobileDataEnabled(enabled);
    213         }
    214     };
    215 
    216     private final class CellularDetailAdapter implements DetailAdapter {
    217 
    218         @Override
    219         public int getTitle() {
    220             return R.string.quick_settings_cellular_detail_title;
    221         }
    222 
    223         @Override
    224         public Boolean getToggleState() {
    225             return mDataController.isMobileDataSupported()
    226                     ? mDataController.isMobileDataEnabled()
    227                     : null;
    228         }
    229 
    230         @Override
    231         public Intent getSettingsIntent() {
    232             return CELLULAR_SETTINGS;
    233         }
    234 
    235         @Override
    236         public void setToggleState(boolean state) {
    237             MetricsLogger.action(mContext, MetricsLogger.QS_CELLULAR_TOGGLE, state);
    238             mDataController.setMobileDataEnabled(state);
    239         }
    240 
    241         @Override
    242         public int getMetricsCategory() {
    243             return MetricsLogger.QS_DATAUSAGEDETAIL;
    244         }
    245 
    246         @Override
    247         public View createDetailView(Context context, View convertView, ViewGroup parent) {
    248             final DataUsageDetailView v = (DataUsageDetailView) (convertView != null
    249                     ? convertView
    250                     : LayoutInflater.from(mContext).inflate(R.layout.data_usage, parent, false));
    251             final DataUsageInfo info = mDataController.getDataUsageInfo();
    252             if (info == null) return v;
    253             v.bind(info);
    254             return v;
    255         }
    256 
    257         public void setMobileDataEnabled(boolean enabled) {
    258             fireToggleStateChanged(enabled);
    259         }
    260     }
    261 }
    262