BluetoothTile.java revision 64fe15846c541950b574bfb681efb8a794183ff6
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 17package com.android.systemui.qs.tiles; 18 19import android.content.Context; 20import android.content.Intent; 21import android.provider.Settings; 22import android.text.TextUtils; 23import android.view.View; 24import android.view.ViewGroup; 25 26import com.android.systemui.R; 27import com.android.systemui.qs.QSDetailItems; 28import com.android.systemui.qs.QSDetailItems.Item; 29import com.android.systemui.qs.QSTile; 30import com.android.systemui.statusbar.policy.BluetoothController; 31import com.android.systemui.statusbar.policy.BluetoothController.PairedDevice; 32 33import java.util.Set; 34 35/** Quick settings tile: Bluetooth **/ 36public class BluetoothTile extends QSTile<QSTile.BooleanState> { 37 private static final Intent BLUETOOTH_SETTINGS = new Intent(Settings.ACTION_BLUETOOTH_SETTINGS); 38 39 private final BluetoothController mController; 40 private final BluetoothDetailAdapter mDetailAdapter; 41 42 public BluetoothTile(Host host) { 43 super(host); 44 mController = host.getBluetoothController(); 45 mDetailAdapter = new BluetoothDetailAdapter(); 46 } 47 48 @Override 49 public boolean supportsDualTargets() { 50 return true; 51 } 52 53 @Override 54 public DetailAdapter getDetailAdapter() { 55 return mDetailAdapter; 56 } 57 58 @Override 59 protected BooleanState newTileState() { 60 return new BooleanState(); 61 } 62 63 @Override 64 public void setListening(boolean listening) { 65 if (listening) { 66 mController.addStateChangedCallback(mCallback); 67 } else { 68 mController.removeStateChangedCallback(mCallback); 69 } 70 } 71 72 @Override 73 protected void handleClick() { 74 final boolean isEnabled = (Boolean)mState.value; 75 mController.setBluetoothEnabled(!isEnabled); 76 } 77 78 @Override 79 protected void handleSecondaryClick() { 80 showDetail(true); 81 } 82 83 @Override 84 protected void handleUpdateState(BooleanState state, Object arg) { 85 final boolean supported = mController.isBluetoothSupported(); 86 final boolean enabled = mController.isBluetoothEnabled(); 87 final boolean connected = mController.isBluetoothConnected(); 88 final boolean connecting = mController.isBluetoothConnecting(); 89 state.visible = supported; 90 state.value = enabled; 91 final String stateContentDescription; 92 if (enabled) { 93 state.label = null; 94 if (connected) { 95 state.iconId = R.drawable.ic_qs_bluetooth_connected; 96 stateContentDescription = mContext.getString(R.string.accessibility_desc_connected); 97 state.label = mController.getLastDeviceName(); 98 } else if (connecting) { 99 state.iconId = R.drawable.ic_qs_bluetooth_connecting; 100 stateContentDescription = 101 mContext.getString(R.string.accessibility_desc_connecting); 102 state.label = mContext.getString(R.string.quick_settings_bluetooth_label); 103 } else { 104 state.iconId = R.drawable.ic_qs_bluetooth_on; 105 stateContentDescription = mContext.getString(R.string.accessibility_desc_on); 106 } 107 if (TextUtils.isEmpty(state.label)) { 108 state.label = mContext.getString(R.string.quick_settings_bluetooth_label); 109 } 110 } else { 111 state.iconId = R.drawable.ic_qs_bluetooth_off; 112 state.label = mContext.getString(R.string.quick_settings_bluetooth_label); 113 stateContentDescription = mContext.getString(R.string.accessibility_desc_off); 114 } 115 state.contentDescription = mContext.getString( 116 R.string.accessibility_quick_settings_bluetooth, stateContentDescription); 117 } 118 119 private final BluetoothController.Callback mCallback = new BluetoothController.Callback() { 120 @Override 121 public void onBluetoothStateChange(boolean enabled, boolean connecting) { 122 refreshState(); 123 } 124 @Override 125 public void onBluetoothPairedDevicesChanged() { 126 mUiHandler.post(new Runnable() { 127 @Override 128 public void run() { 129 mDetailAdapter.updateItems(); 130 } 131 }); 132 } 133 }; 134 135 private final class BluetoothDetailAdapter implements DetailAdapter, QSDetailItems.Callback { 136 private QSDetailItems mItems; 137 138 @Override 139 public int getTitle() { 140 return R.string.quick_settings_bluetooth_label; 141 } 142 143 @Override 144 public Boolean getToggleState() { 145 return mState.value; 146 } 147 148 @Override 149 public Intent getSettingsIntent() { 150 return BLUETOOTH_SETTINGS; 151 } 152 153 @Override 154 public void setToggleState(boolean state) { 155 mController.setBluetoothEnabled(state); 156 showDetail(false); 157 } 158 159 @Override 160 public View createDetailView(Context context, View convertView, ViewGroup parent) { 161 mItems = QSDetailItems.convertOrInflate(context, convertView, parent); 162 mItems.setTagSuffix("Bluetooth"); 163 mItems.setEmptyState(R.drawable.ic_qs_bluetooth_detail_empty, 164 R.string.quick_settings_bluetooth_detail_empty_text); 165 mItems.setCallback(this); 166 updateItems(); 167 setItemsVisible(mState.value); 168 return mItems; 169 } 170 171 public void setItemsVisible(boolean visible) { 172 if (mItems == null) return; 173 mItems.setItemsVisible(visible); 174 } 175 176 private void updateItems() { 177 if (mItems == null) return; 178 Item[] items = null; 179 final Set<PairedDevice> devices = mController.getPairedDevices(); 180 if (devices != null) { 181 items = new Item[devices.size()]; 182 int i = 0; 183 for (PairedDevice device : devices) { 184 final Item item = new Item(); 185 item.icon = R.drawable.ic_qs_bluetooth_on; 186 item.line1 = device.name; 187 if (device.state == PairedDevice.STATE_CONNECTED) { 188 item.icon = R.drawable.ic_qs_bluetooth_connected; 189 item.line2 = mContext.getString(R.string.quick_settings_connected); 190 item.canDisconnect = true; 191 } else if (device.state == PairedDevice.STATE_CONNECTING) { 192 item.icon = R.drawable.ic_qs_bluetooth_connecting; 193 item.line2 = mContext.getString(R.string.quick_settings_connecting); 194 } 195 item.tag = device; 196 items[i++] = item; 197 } 198 } 199 mItems.setItems(items); 200 } 201 202 @Override 203 public void onDetailItemClick(Item item) { 204 if (item == null || item.tag == null) return; 205 final PairedDevice device = (PairedDevice) item.tag; 206 if (device != null && device.state == PairedDevice.STATE_DISCONNECTED) { 207 mController.connect(device); 208 } 209 } 210 211 @Override 212 public void onDetailItemDisconnect(Item item) { 213 if (item == null || item.tag == null) return; 214 final PairedDevice device = (PairedDevice) item.tag; 215 if (device != null) { 216 mController.disconnect(device); 217 } 218 } 219 } 220} 221