1 /*
2  * Copyright (C) 2011 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.cts.verifier.bluetooth;
18 
19 import com.android.cts.verifier.R;
20 
21 import android.app.Activity;
22 import android.app.AlertDialog;
23 import android.bluetooth.BluetoothAdapter;
24 import android.bluetooth.BluetoothDevice;
25 import android.content.BroadcastReceiver;
26 import android.content.Context;
27 import android.content.DialogInterface;
28 import android.content.Intent;
29 import android.content.IntentFilter;
30 import android.os.Bundle;
31 import android.view.View;
32 import android.view.View.OnClickListener;
33 import android.widget.AdapterView;
34 import android.widget.ArrayAdapter;
35 import android.widget.Button;
36 import android.widget.ListView;
37 import android.widget.ProgressBar;
38 import android.widget.TextView;
39 import android.widget.AdapterView.OnItemClickListener;
40 
41 import java.util.Set;
42 
43 /**
44  * {@link Activity} that shows a list of paired and new devices and returns the device selected
45  * by the user. When the user selects a paired device, it forwards them to the Bluetooth settings
46  * page, so that they can unpair it for the test.
47  */
48 public class DevicePickerActivity extends Activity {
49 
50     public static final String EXTRA_DEVICE_ADDRESS = "deviceAddress";
51 
52     private static final int ENABLE_BLUETOOTH_REQUEST = 1;
53 
54     private BluetoothAdapter mBluetoothAdapter;
55 
56     private DiscoveryReceiver mReceiver;
57 
58     private ArrayAdapter<Device> mNewDevicesAdapter;
59 
60     private ArrayAdapter<Device> mPairedDevicesAdapter;
61 
62     private TextView mEmptyNewView;
63 
64     private ProgressBar mProgressBar;
65 
66     @Override
onCreate(Bundle savedInstanceState)67     protected void onCreate(Bundle savedInstanceState) {
68         super.onCreate(savedInstanceState);
69         setContentView(R.layout.bt_device_picker);
70 
71         mProgressBar = (ProgressBar) findViewById(R.id.bt_progress_bar);
72 
73         mPairedDevicesAdapter = new ArrayAdapter<Device>(this, R.layout.bt_device_name);
74         ListView pairedDevicesListView = (ListView) findViewById(R.id.bt_paired_devices);
75         pairedDevicesListView.setAdapter(mPairedDevicesAdapter);
76         pairedDevicesListView.setOnItemClickListener(new PairedDeviceClickListener());
77 
78         View emptyPairedView = findViewById(R.id.bt_empty_paired_devices);
79         pairedDevicesListView.setEmptyView(emptyPairedView);
80 
81         mNewDevicesAdapter = new ArrayAdapter<Device>(this, R.layout.bt_device_name);
82         ListView newDevicesListView = (ListView) findViewById(R.id.bt_new_devices);
83         newDevicesListView.setAdapter(mNewDevicesAdapter);
84         newDevicesListView.setOnItemClickListener(new NewDeviceClickListener());
85 
86         mEmptyNewView = (TextView) findViewById(R.id.bt_empty_new_devices);
87         newDevicesListView.setEmptyView(mEmptyNewView);
88 
89         mReceiver = new DiscoveryReceiver();
90         IntentFilter filter = new IntentFilter(BluetoothAdapter.ACTION_DISCOVERY_STARTED);
91         filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_FINISHED);
92         filter.addAction(BluetoothDevice.ACTION_FOUND);
93         registerReceiver(mReceiver, filter);
94 
95         Button scanButton = (Button) findViewById(R.id.bt_scan_button);
96         scanButton.setOnClickListener(new OnClickListener() {
97             @Override
98             public void onClick(View v) {
99                 scan();
100             }
101         });
102 
103         mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
104         if (mBluetoothAdapter.isEnabled()) {
105             scan();
106         } else {
107             Intent intent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
108             startActivityForResult(intent, ENABLE_BLUETOOTH_REQUEST);
109         }
110     }
111 
112     @Override
onActivityResult(int requestCode, int resultCode, Intent data)113     protected void onActivityResult(int requestCode, int resultCode, Intent data) {
114         super.onActivityResult(requestCode, resultCode, data);
115         if (requestCode == ENABLE_BLUETOOTH_REQUEST) {
116             if (resultCode == RESULT_OK) {
117                 scan();
118             } else {
119                 setResult(RESULT_CANCELED);
120                 finish();
121             }
122         }
123     }
124 
scan()125     private void scan() {
126         populatePairedDevices();
127         mNewDevicesAdapter.clear();
128         if (mBluetoothAdapter.isDiscovering()) {
129             mBluetoothAdapter.cancelDiscovery();
130         }
131         mBluetoothAdapter.startDiscovery();
132     }
133 
populatePairedDevices()134     private void populatePairedDevices() {
135         mPairedDevicesAdapter.clear();
136         Set<BluetoothDevice> pairedDevices = mBluetoothAdapter.getBondedDevices();
137         for (BluetoothDevice device : pairedDevices) {
138             mPairedDevicesAdapter.add(Device.fromBluetoothDevice(device));
139         }
140     }
141 
142     @Override
onDestroy()143     protected void onDestroy() {
144         super.onDestroy();
145         if (mBluetoothAdapter != null) {
146             mBluetoothAdapter.cancelDiscovery();
147         }
148         unregisterReceiver(mReceiver);
149     }
150 
151     class NewDeviceClickListener implements OnItemClickListener {
152         @Override
onItemClick(AdapterView<?> parent, View view, int position, long id)153         public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
154             Intent data = new Intent();
155             Device device = (Device) parent.getItemAtPosition(position);
156             data.putExtra(EXTRA_DEVICE_ADDRESS, device.mAddress);
157             setResult(RESULT_OK, data);
158             finish();
159         }
160     }
161 
162     class PairedDeviceClickListener implements OnItemClickListener {
163         @Override
onItemClick(AdapterView<?> parent, View view, int position, long id)164         public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
165             new AlertDialog.Builder(DevicePickerActivity.this)
166                 .setIcon(android.R.drawable.ic_dialog_alert)
167                 .setMessage(R.string.bt_unpair)
168                 .setPositiveButton(R.string.bt_settings, new DialogInterface.OnClickListener() {
169                     @Override
170                     public void onClick(DialogInterface dialog, int which) {
171                         if (mBluetoothAdapter != null) {
172                             mBluetoothAdapter.cancelDiscovery();
173                         }
174                         Intent intent = new Intent();
175                         intent.setAction(android.provider.Settings.ACTION_BLUETOOTH_SETTINGS);
176                         startActivity(intent);
177                     }
178                 })
179                 .show();
180         }
181     }
182 
183     class DiscoveryReceiver extends BroadcastReceiver {
184         @Override
onReceive(Context context, Intent intent)185         public void onReceive(Context context, Intent intent) {
186             if (BluetoothAdapter.ACTION_DISCOVERY_STARTED.equals(intent.getAction())) {
187                 mEmptyNewView.setText(R.string.bt_scanning);
188                 mProgressBar.setVisibility(View.VISIBLE);
189             } else if (BluetoothAdapter.ACTION_DISCOVERY_FINISHED.equals(intent.getAction())) {
190                 mEmptyNewView.setText(R.string.bt_no_devices);
191                 mProgressBar.setVisibility(View.INVISIBLE);
192             } else if (BluetoothDevice.ACTION_FOUND.equals(intent.getAction())) {
193                 BluetoothDevice device = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);
194                 if (device.getBondState() != BluetoothDevice.BOND_BONDED) {
195                     mNewDevicesAdapter.add(Device.fromBluetoothDevice(device));
196                 }
197             }
198         }
199     }
200 
201     static class Device {
202 
203         String mName;
204 
205         String mAddress;
206 
Device(String name, String address)207         Device(String name, String address) {
208             mName = name;
209             mAddress = address;
210         }
211 
212         @Override
toString()213         public String toString() {
214             return mName + "\n" + mAddress;
215         }
216 
fromBluetoothDevice(BluetoothDevice device)217         static Device fromBluetoothDevice(BluetoothDevice device) {
218             return new Device(device.getName() != null ? device.getName() : "",
219                     device.getAddress());
220         }
221     }
222 }
223