PhoneStatusBarPolicy.java revision 2b69735e014872ca2183b4a39a8381daa337e146
1/* 2 * Copyright (C) 2008 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 17package com.android.systemui.statusbar.phone; 18 19import android.app.StatusBarManager; 20import android.bluetooth.BluetoothAdapter; 21import android.content.BroadcastReceiver; 22import android.content.Context; 23import android.content.Intent; 24import android.content.IntentFilter; 25import android.location.LocationManager; 26import android.media.AudioManager; 27import android.net.ConnectivityManager; 28import android.net.NetworkInfo; 29import android.net.wifi.WifiManager; 30import android.os.Binder; 31import android.os.Handler; 32import android.os.RemoteException; 33import android.os.storage.StorageManager; 34import android.provider.Settings; 35import android.telephony.PhoneStateListener; 36import android.telephony.ServiceState; 37import android.telephony.SignalStrength; 38import android.telephony.TelephonyManager; 39import android.util.Slog; 40 41import com.android.internal.telephony.IccCard; 42import com.android.internal.telephony.TelephonyIntents; 43import com.android.internal.telephony.cdma.EriInfo; 44import com.android.internal.telephony.cdma.TtyIntent; 45import com.android.server.am.BatteryStatsService; 46import com.android.systemui.R; 47 48/** 49 * This class contains all of the policy about which icons are installed in the status 50 * bar at boot time. It goes through the normal API for icons, even though it probably 51 * strictly doesn't need to. 52 */ 53public class PhoneStatusBarPolicy { 54 private static final String TAG = "PhoneStatusBarPolicy"; 55 56 // message codes for the handler 57 private static final int EVENT_BATTERY_CLOSE = 4; 58 59 private static final int AM_PM_STYLE_NORMAL = 0; 60 private static final int AM_PM_STYLE_SMALL = 1; 61 private static final int AM_PM_STYLE_GONE = 2; 62 63 private static final int AM_PM_STYLE = AM_PM_STYLE_GONE; 64 65 private static final int INET_CONDITION_THRESHOLD = 50; 66 67 private final Context mContext; 68 private final StatusBarManager mService; 69 private final Handler mHandler = new Handler(); 70 71 // storage 72 private StorageManager mStorageManager; 73 74 75 // Assume it's all good unless we hear otherwise. We don't always seem 76 // to get broadcasts that it *is* there. 77 IccCard.State mSimState = IccCard.State.READY; 78 79 // ringer volume 80 private boolean mVolumeVisible; 81 82 // bluetooth device status 83 private boolean mBluetoothEnabled; 84 85 // wifi 86 private static final int[][] sWifiSignalImages = { 87 { R.drawable.stat_sys_wifi_signal_1, 88 R.drawable.stat_sys_wifi_signal_2, 89 R.drawable.stat_sys_wifi_signal_3, 90 R.drawable.stat_sys_wifi_signal_4 }, 91 { R.drawable.stat_sys_wifi_signal_1_fully, 92 R.drawable.stat_sys_wifi_signal_2_fully, 93 R.drawable.stat_sys_wifi_signal_3_fully, 94 R.drawable.stat_sys_wifi_signal_4_fully } 95 }; 96 private static final int sWifiTemporarilyNotConnectedImage = 97 R.drawable.stat_sys_wifi_signal_0; 98 99 private int mLastWifiSignalLevel = -1; 100 private boolean mIsWifiConnected = false; 101 102 // state of inet connection - 0 not connected, 100 connected 103 private int mInetCondition = 0; 104 105 // sync state 106 // If sync is active the SyncActive icon is displayed. If sync is not active but 107 // sync is failing the SyncFailing icon is displayed. Otherwise neither are displayed. 108 109 private BroadcastReceiver mIntentReceiver = new BroadcastReceiver() { 110 @Override 111 public void onReceive(Context context, Intent intent) { 112 String action = intent.getAction(); 113 if (action.equals(Intent.ACTION_ALARM_CHANGED)) { 114 updateAlarm(intent); 115 } 116 else if (action.equals(Intent.ACTION_SYNC_STATE_CHANGED)) { 117 updateSyncState(intent); 118 } 119 else if (action.equals(BluetoothAdapter.ACTION_STATE_CHANGED) || 120 action.equals(BluetoothAdapter.ACTION_CONNECTION_STATE_CHANGED)) { 121 updateBluetooth(intent); 122 } 123 else if (action.equals(AudioManager.RINGER_MODE_CHANGED_ACTION) || 124 action.equals(AudioManager.VIBRATE_SETTING_CHANGED_ACTION)) { 125 updateVolume(); 126 } 127 else if (action.equals(TelephonyIntents.ACTION_SIM_STATE_CHANGED)) { 128 updateSimState(intent); 129 } 130 else if (action.equals(TtyIntent.TTY_ENABLED_CHANGE_ACTION)) { 131 updateTTY(intent); 132 } 133 } 134 }; 135 136 public PhoneStatusBarPolicy(Context context) { 137 mContext = context; 138 mService = (StatusBarManager)context.getSystemService(Context.STATUS_BAR_SERVICE); 139 140 // storage 141 mStorageManager = (StorageManager) context.getSystemService(Context.STORAGE_SERVICE); 142 mStorageManager.registerListener( 143 new com.android.systemui.usb.StorageNotification(context)); 144 145 // TTY status 146 mService.setIcon("tty", R.drawable.stat_sys_tty_mode, 0, null); 147 mService.setIconVisibility("tty", false); 148 149 // Cdma Roaming Indicator, ERI 150 mService.setIcon("cdma_eri", R.drawable.stat_sys_roaming_cdma_0, 0, null); 151 mService.setIconVisibility("cdma_eri", false); 152 153 // bluetooth status 154 mService.setIcon("bluetooth", R.drawable.stat_sys_data_bluetooth, 0, null); 155 BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); 156 if (adapter != null) { 157 mBluetoothEnabled = adapter.isEnabled(); 158 } else { 159 mBluetoothEnabled = false; 160 } 161 mService.setIconVisibility("bluetooth", mBluetoothEnabled); 162 163 // Alarm clock 164 mService.setIcon("alarm_clock", R.drawable.stat_notify_alarm, 0, null); 165 mService.setIconVisibility("alarm_clock", false); 166 167 // Sync state 168 mService.setIcon("sync_active", com.android.internal.R.drawable.stat_notify_sync_anim0, 169 0, null); 170 mService.setIcon("sync_failing", com.android.internal.R.drawable.stat_notify_sync_error, 171 0, null); 172 mService.setIconVisibility("sync_active", false); 173 mService.setIconVisibility("sync_failing", false); 174 175 // volume 176 mService.setIcon("volume", R.drawable.stat_sys_ringer_silent, 0, null); 177 mService.setIconVisibility("volume", false); 178 updateVolume(); 179 180 IntentFilter filter = new IntentFilter(); 181 182 // Register for Intent broadcasts for... 183 filter.addAction(Intent.ACTION_ALARM_CHANGED); 184 filter.addAction(Intent.ACTION_SYNC_STATE_CHANGED); 185 filter.addAction(AudioManager.RINGER_MODE_CHANGED_ACTION); 186 filter.addAction(AudioManager.VIBRATE_SETTING_CHANGED_ACTION); 187 filter.addAction(BluetoothAdapter.ACTION_STATE_CHANGED); 188 filter.addAction(BluetoothAdapter.ACTION_CONNECTION_STATE_CHANGED); 189 filter.addAction(TelephonyIntents.ACTION_SIM_STATE_CHANGED); 190 filter.addAction(TtyIntent.TTY_ENABLED_CHANGE_ACTION); 191 mContext.registerReceiver(mIntentReceiver, filter, null, mHandler); 192 } 193 194 private final void updateAlarm(Intent intent) { 195 boolean alarmSet = intent.getBooleanExtra("alarmSet", false); 196 mService.setIconVisibility("alarm_clock", alarmSet); 197 } 198 199 private final void updateSyncState(Intent intent) { 200 boolean isActive = intent.getBooleanExtra("active", false); 201 boolean isFailing = intent.getBooleanExtra("failing", false); 202 mService.setIconVisibility("sync_active", isActive); 203 // Don't display sync failing icon: BUG 1297963 Set sync error timeout to "never" 204 //mService.setIconVisibility("sync_failing", isFailing && !isActive); 205 } 206 207 private final void updateSimState(Intent intent) { 208 String stateExtra = intent.getStringExtra(IccCard.INTENT_KEY_ICC_STATE); 209 if (IccCard.INTENT_VALUE_ICC_ABSENT.equals(stateExtra)) { 210 mSimState = IccCard.State.ABSENT; 211 } 212 else if (IccCard.INTENT_VALUE_ICC_READY.equals(stateExtra)) { 213 mSimState = IccCard.State.READY; 214 } 215 else if (IccCard.INTENT_VALUE_ICC_LOCKED.equals(stateExtra)) { 216 final String lockedReason = intent.getStringExtra(IccCard.INTENT_KEY_LOCKED_REASON); 217 if (IccCard.INTENT_VALUE_LOCKED_ON_PIN.equals(lockedReason)) { 218 mSimState = IccCard.State.PIN_REQUIRED; 219 } 220 else if (IccCard.INTENT_VALUE_LOCKED_ON_PUK.equals(lockedReason)) { 221 mSimState = IccCard.State.PUK_REQUIRED; 222 } 223 else { 224 mSimState = IccCard.State.NETWORK_LOCKED; 225 } 226 } else { 227 mSimState = IccCard.State.UNKNOWN; 228 } 229 } 230 231 private final void updateVolume() { 232 AudioManager audioManager = (AudioManager) mContext.getSystemService(Context.AUDIO_SERVICE); 233 final int ringerMode = audioManager.getRingerMode(); 234 final boolean visible = ringerMode == AudioManager.RINGER_MODE_SILENT || 235 ringerMode == AudioManager.RINGER_MODE_VIBRATE; 236 237 final int iconId; 238 String contentDescription = null; 239 if (audioManager.shouldVibrate(AudioManager.VIBRATE_TYPE_RINGER)) { 240 iconId = R.drawable.stat_sys_ringer_vibrate; 241 contentDescription = mContext.getString(R.string.accessibility_ringer_vibrate); 242 } else { 243 iconId = R.drawable.stat_sys_ringer_silent; 244 contentDescription = mContext.getString(R.string.accessibility_ringer_silent); 245 } 246 247 if (visible) { 248 mService.setIcon("volume", iconId, 0, contentDescription); 249 } 250 if (visible != mVolumeVisible) { 251 mService.setIconVisibility("volume", visible); 252 mVolumeVisible = visible; 253 } 254 } 255 256 private final void updateBluetooth(Intent intent) { 257 int iconId = R.drawable.stat_sys_data_bluetooth; 258 String contentDescription = null; 259 String action = intent.getAction(); 260 if (action.equals(BluetoothAdapter.ACTION_STATE_CHANGED)) { 261 int state = intent.getIntExtra(BluetoothAdapter.EXTRA_STATE, BluetoothAdapter.ERROR); 262 mBluetoothEnabled = state == BluetoothAdapter.STATE_ON; 263 } else if (action.equals(BluetoothAdapter.ACTION_CONNECTION_STATE_CHANGED)) { 264 int state = intent.getIntExtra(BluetoothAdapter.EXTRA_CONNECTION_STATE, 265 BluetoothAdapter.STATE_DISCONNECTED); 266 if (state == BluetoothAdapter.STATE_CONNECTED) { 267 iconId = R.drawable.stat_sys_data_bluetooth_connected; 268 contentDescription = mContext.getString(R.string.accessibility_bluetooth_connected); 269 } else { 270 contentDescription = mContext.getString( 271 R.string.accessibility_bluetooth_disconnected); 272 } 273 } else { 274 return; 275 } 276 277 mService.setIcon("bluetooth", iconId, 0, contentDescription); 278 mService.setIconVisibility("bluetooth", mBluetoothEnabled); 279 } 280 281 private final void updateTTY(Intent intent) { 282 final String action = intent.getAction(); 283 final boolean enabled = intent.getBooleanExtra(TtyIntent.TTY_ENABLED, false); 284 285 if (false) Slog.v(TAG, "updateTTY: enabled: " + enabled); 286 287 if (enabled) { 288 // TTY is on 289 if (false) Slog.v(TAG, "updateTTY: set TTY on"); 290 mService.setIcon("tty", R.drawable.stat_sys_tty_mode, 0, 291 mContext.getString(R.string.accessibility_tty_enabled)); 292 mService.setIconVisibility("tty", true); 293 } else { 294 // TTY is off 295 if (false) Slog.v(TAG, "updateTTY: set TTY off"); 296 mService.setIconVisibility("tty", false); 297 } 298 } 299} 300