bluetooth.jd revision 50e990c64fa23ce94efa76b9e72df7f8ec3cee6a
19066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectpage.title=Bluetooth
29066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project@jd:body
39066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<div id="qv-wrapper"> 
5d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<div id="qv"> 
6d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
7d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <h2>Quickview</h2> 
8d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <ul> 
9ec80d7f311b1a0899bb4caf5b380b07027e902d1Scott Main    <li>Android's bluetooth APIs allow your application to perform wireless data transactions with
10d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickother devices</li> 
11d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  </ul> 
12d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
13d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <h2>In this document</h2> 
14d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <ol> 
15d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li><a href="#TheBasics">The Basics</a></li> 
16d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li><a href="#Permissions">Bluetooth Permissions</a></li> 
17d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li><a href="#SettingUp">Setting Up Bluetooth</a></li> 
18d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li><a href="#FindingDevices">Finding Devices</a> 
19d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick      <ol> 
20d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick        <li><a href="#QueryingPairedDevices">Querying paired devices</a></li> 
21d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick        <li><a href="#DiscoveringDevices">Discovering devices</a></li> 
22d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick      </ol></li> 
23d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li><a href="#ConnectingDevices">Connecting Devices</a> 
24d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick      <ol> 
25d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick        <li><a href="#ConnectingAsAServer">Connecting as a server</a></li> 
26d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick        <li><a href="#ConnectingAsAClient">Connecting as a client</a></li> 
27d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick      </ol></li> 
28d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li><a href="#ManagingAConnection">Managing a Connection</a></li>
29d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li><a href="#Profiles">Working with Profiles</a> 
30ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main      <ol>
31d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick        <li><a href="#AT-Commands">Vendor-specific AT commands</a>
322e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick        <li><a href="#HDP">Health Device Profile</a>
33a90eb8fec1c67177b614b945bcc4a4b14aaabaffScott Main      </ol></li>
34d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  </ol> 
35d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
36d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <h2>Key classes</h2> 
37d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <ol> 
38d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li>{@link android.bluetooth.BluetoothAdapter}</li> 
39d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li>{@link android.bluetooth.BluetoothDevice}</li> 
40d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li>{@link android.bluetooth.BluetoothSocket}</li> 
41d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li>{@link android.bluetooth.BluetoothServerSocket}</li> 
42d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  </ol> 
43d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
44d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <h2>Related samples</h2> 
45d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <ol> 
46d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    <li><a href="{@docRoot}resources/samples/BluetoothChat/index.html">Bluetooth Chat</a></li> 
472e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <li><a href="{@docRoot}resources/samples/BluetoothHDP/index.html">Bluetooth HDP (Health Device Profile)</a></li>
48d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  </ol> 
49d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
50d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</div> 
51d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</div> 
52d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
53d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
54ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>The Android platform includes support for the Bluetooth network stack,
55ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwhich allows a device to wirelessly exchange data with other Bluetooth devices.
56ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainThe application framework provides access to the Bluetooth functionality through
57ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe Android Bluetooth APIs. These APIs let applications wirelessly
58ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnect to other Bluetooth devices, enabling point-to-point and multipoint
59d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickwireless features.</p> 
60d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
61ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Using the Bluetooth APIs, an Android application can perform the
62ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainfollowing:</p>
63ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<ul>
64ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main  <li>Scan for other Bluetooth devices</li>
65ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main  <li>Query the local Bluetooth adapter for paired Bluetooth devices</li>
66ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main  <li>Establish RFCOMM channels</li>
67ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main  <li>Connect to other devices through service discovery</li>
68ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main  <li>Transfer data to and from other devices</li>
69ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main  <li>Manage multiple connections</li>
70ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main</ul>
71ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main
72ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main
73ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<h2 id="TheBasics">The Basics</h2>
74ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main
75bb64fa1e3dde8910397d159eaa300c4444b0073cScott Main<p>This document describes how to use the Android Bluetooth APIs to accomplish
76ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe four major tasks necessary to communicate using Bluetooth: setting up
77ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainBluetooth, finding devices that are either paired or available in the local
78d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickarea, connecting devices, and transferring data between devices.</p> 
79d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
80ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>All of the Bluetooth APIs are available in the {@link android.bluetooth}
81d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickpackage. Here's a summary of the classes and interfaces you will need to create Bluetooth
82d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnections:</p> 
83d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
84d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dl> 
85d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dt>{@link android.bluetooth.BluetoothAdapter}</dt> 
86ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<dd>Represents the local Bluetooth adapter (Bluetooth radio). The
87ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothAdapter} is the entry-point for all Bluetooth
88ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maininteraction. Using this,
89ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainyou can discover other Bluetooth devices, query a list of bonded (paired)
90ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindevices, instantiate a {@link android.bluetooth.BluetoothDevice} using a known
91ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainMAC address, and create a {@link android.bluetooth.BluetoothServerSocket} to
92ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainlisten for communications
93d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickfrom other devices.</dd> 
94d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
95d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dt>{@link android.bluetooth.BluetoothDevice}</dt> 
96ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<dd>Represents a remote Bluetooth device. Use this to request a connection
97ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwith a remote device through a {@link android.bluetooth.BluetoothSocket} or
98ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainquery information about the
99d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickdevice such as its name, address, class, and bonding state.</dd> 
100d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
101d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dt>{@link android.bluetooth.BluetoothSocket}</dt> 
102ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<dd>Represents the interface for a Bluetooth socket (similar to a TCP
103ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link java.net.Socket}). This is the connection point that allows
104ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainan application to exchange data with another Bluetooth device via InputStream
105d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickand OutputStream.</dd> 
106d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
107d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dt>{@link android.bluetooth.BluetoothServerSocket}</dt> 
108ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<dd>Represents an open server socket that listens for incoming requests
109ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main(similar to a TCP {@link java.net.ServerSocket}). In order to connect two
110ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainAndroid devices, one device must open a server socket with this class. When a
111ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainremote Bluetooth device makes a connection request to the this device, the
112ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothServerSocket} will return a connected {@link
113ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket} when the
114d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnection is accepted.</dd> 
115d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
116d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dt>{@link android.bluetooth.BluetoothClass}</dt> 
117ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<dd>Describes the general characteristics and capabilities of a Bluetooth
118ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindevice. This is a read-only set of properties that define the device's major and
119ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainminor device classes and its services. However, this does not reliably describe
120ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainall Bluetooth profiles and services supported by the device, but is useful as a
121d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickhint to the device type.</dd> 
122d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
123d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dt>{@link android.bluetooth.BluetoothProfile}</dt> <dd>An interface that
124d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickrepresents a Bluetooth profile. A <em>Bluetooth profile</em> is a wireless
125d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickinterface specification for Bluetooth-based communication between devices. An
126d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickexample is the Hands-Free profile.  For more discussion of profiles, see <a
127d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickhref="#Profiles">Working with Profiles</a></dd> 
128d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
129d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dt>{@link android.bluetooth.BluetoothHeadset}</dt> <dd>Provides support for
130d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickBluetooth headsets to be used with mobile phones. This includes both  Bluetooth
131d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickHeadset and Hands-Free (v1.5) profiles.</dd> 
132d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
133d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dt>{@link android.bluetooth.BluetoothA2dp}</dt> <dd> Defines how high quality
134d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickaudio can be streamed from one device to another over a Bluetooth connection.
135d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick"A2DP" stands for Advanced Audio Distribution Profile.</dd> 
136d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
1372e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<dt>{@link android.bluetooth.BluetoothHealth}</dt>
1382e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<dd> Represents a Health Device Profile proxy that controls the Bluetooth service.</dd>
1392e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
1402e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<dt>{@link android.bluetooth.BluetoothHealthCallback}</dt>
1412e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
1422e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<dd>An abstract class that you use to implement {@link
1432e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickandroid.bluetooth.BluetoothHealth} callbacks. You must extend this class and
1442e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickimplement the callback methods to receive updates about changes in the
1452e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickapplication’s registration state and Bluetooth channel state.</dd>
1462e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
1472e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<dt>{@link android.bluetooth.BluetoothHealthAppConfiguration}</dt>
1482e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
1492e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<dd>Represents an application configuration that the Bluetooth Health third-party 
1502e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickapplication registers to communicate with a remote Bluetooth health
1512e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickdevice.</dd> 
1522e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
1532e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<dt>{@link android.bluetooth.BluetoothProfile.ServiceListener}</dt>
154d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
155d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<dd>An interface that notifies {@link android.bluetooth.BluetoothProfile} IPC
156d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickclients when they have  been connected to or disconnected from the service (that
1572e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickis, the internal service that runs a particular profile). </dd>
158d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
159d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</dl> 
160d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
161d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
162d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
163d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
164d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h2 id="Permissions">Bluetooth Permissions</h2> 
165d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
166ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>In order to use Bluetooth features in your application, you need to declare
167ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainat least one of two Bluetooth permissions: {@link
168ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.Manifest.permission#BLUETOOTH} and {@link
169d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.Manifest.permission#BLUETOOTH_ADMIN}.</p> 
170d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
171ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>You must request the {@link android.Manifest.permission#BLUETOOTH} permission
172ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainin order to perform any Bluetooth communication, such as requesting a
173d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnection, accepting a connection, and transferring data.</p> 
174d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
175ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>You must request the {@link android.Manifest.permission#BLUETOOTH_ADMIN}
176ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainpermission in order to initiate device discovery or manipulate Bluetooth
177ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainsettings. Most applications need this permission solely for the
178ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainability to discover local Bluetooth devices. The other abilities granted by this
179ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainpermission should not be used, unless the application is a "power manager" that
180ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwill modify Bluetooth settings upon user request. <strong>Note:</strong> If you
181ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainuse {@link android.Manifest.permission#BLUETOOTH_ADMIN} permission, then must
182d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickalso have the {@link android.Manifest.permission#BLUETOOTH} permission.</p> 
183d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
184ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Declare the Bluetooth permission(s) in your application manifest file. For
185d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickexample:</p> 
186d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
187d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre> 
188ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main&lt;manifest ... >
189ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main  &lt;uses-permission android:name="android.permission.BLUETOOTH" />
190ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main  ...
191ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main&lt;/manifest>
192d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
193d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
194ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>See the <a
195d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickhref="{@docRoot}guide/topics/manifest/uses-permission-element.html">&lt;uses-permission></a> 
196d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickreference for more information about declaring application permissions.</p> 
197d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
198d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
199d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h2 id="SettingUp">Setting Up Bluetooth</h2> 
200d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
201d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<div class="figure" style="width:200px"> 
202d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<img src="{@docRoot}images/bt_enable_request.png" /> 
203ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<strong>Figure 1:</strong> The enabling Bluetooth dialog.
204d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</div> 
205d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
206ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Before your application can communicate over Bluetooth, you need to verify
207d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickthat Bluetooth is supported on the device, and if so, ensure that it is enabled.</p> 
208d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
209ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>If Bluetooth is not supported, then you should gracefully disable any
210ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainBluetooth features. If Bluetooth is supported, but disabled, then you can request that the
211ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainuser enable Bluetooth without leaving your application. This setup is
212d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickaccomplished in two steps, using the {@link android.bluetooth.BluetoothAdapter}.</p> 
213d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
214d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
215d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<ol> 
216ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<li>Get the {@link android.bluetooth.BluetoothAdapter}
217ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>The {@link android.bluetooth.BluetoothAdapter} is required for any and all Bluetooth
218ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainactivity. To get the {@link android.bluetooth.BluetoothAdapter}, call the static {@link
219ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#getDefaultAdapter()} method. This returns a
220ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothAdapter} that represents the device's own
221ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainBluetooth adapter (the Bluetooth radio). There's one Bluetooth adapter for the
222ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainentire system, and your application can interact with it using this object. If
223ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothAdapter#getDefaultAdapter()} returns null,
224d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickthen the device does not support Bluetooth and your story ends here. For example:</p> 
225d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre> 
226ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainBluetoothAdapter mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
227ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainif (mBluetoothAdapter == null) {
228ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    // Device does not support Bluetooth
229ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main}
230d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
231d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</li> 
232d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
233ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<li>Enable Bluetooth
234ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Next, you need to ensure that Bluetooth is enabled. Call {@link
235ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#isEnabled()} to check whether Bluetooth is
236ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maincurrently enable. If this method returns false, then Bluetooth is disabled. To
237ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainrequest that Bluetooth be enabled, call {@link
238ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.app.Activity#startActivityForResult(Intent,int) startActivityForResult()}
239ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwith the {@link android.bluetooth.BluetoothAdapter#ACTION_REQUEST_ENABLE} action Intent.
240ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainThis will issue a request to enable Bluetooth through the system settings (without
241d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickstopping your application). For example:</p> 
242d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre> 
243ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainif (!mBluetoothAdapter.isEnabled()) {
244ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    Intent enableBtIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
245ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    startActivityForResult(enableBtIntent, REQUEST_ENABLE_BT);
246ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main}
247d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
248d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
249ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>A dialog will appear requesting user permission to enable Bluetooth, as shown
250ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainin Figure 1. If the user responds "Yes," the system will begin to enable Bluetooth
251d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickand focus will return to your application once the process completes (or fails).</p> 
25293dc642eaf48e3db58c4929df26283fbc5fd663fScott Main
25393dc642eaf48e3db58c4929df26283fbc5fd663fScott Main<p>The {@code REQUEST_ENABLE_BT} constant passed to {@link
25493dc642eaf48e3db58c4929df26283fbc5fd663fScott Mainandroid.app.Activity#startActivityForResult(Intent,int) startActivityForResult()} is a locally
25593dc642eaf48e3db58c4929df26283fbc5fd663fScott Maindefined integer (which must be greater than 0), that the system passes back to you in your
25693dc642eaf48e3db58c4929df26283fbc5fd663fScott Main{@link
25793dc642eaf48e3db58c4929df26283fbc5fd663fScott Mainandroid.app.Activity#onActivityResult(int,int,Intent) onActivityResult()} implementation as the
25893dc642eaf48e3db58c4929df26283fbc5fd663fScott Main<code>requestCode</code> parameter.</p>
25993dc642eaf48e3db58c4929df26283fbc5fd663fScott Main
26093dc642eaf48e3db58c4929df26283fbc5fd663fScott Main<p>If enabling Bluetooth succeeds, your activity receives the {@link
261ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.app.Activity#RESULT_OK} result code in the {@link
262ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.app.Activity#onActivityResult(int,int,Intent) onActivityResult()}
263ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maincallback. If Bluetooth was not enabled
26493dc642eaf48e3db58c4929df26283fbc5fd663fScott Maindue to an error (or the user responded "No") then the result code is {@link
26593dc642eaf48e3db58c4929df26283fbc5fd663fScott Mainandroid.app.Activity#RESULT_CANCELED}.</p>
266d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</li> 
267d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</ol> 
268d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
269ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Optionally, your application can also listen for the
270ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothAdapter#ACTION_STATE_CHANGED} broadcast Intent, which
271ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe system will broadcast whenever the Bluetooth state has changed. This broadcast contains
272ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe extra fields {@link android.bluetooth.BluetoothAdapter#EXTRA_STATE} and {@link
273ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#EXTRA_PREVIOUS_STATE}, containing the new and old
274ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainBluetooth states, respectively. Possible values for these extra fields are
275ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothAdapter#STATE_TURNING_ON}, {@link
276ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#STATE_ON}, {@link
277ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#STATE_TURNING_OFF}, and {@link
278ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#STATE_OFF}. Listening for this
279ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainbroadcast can be useful to detect changes made to the Bluetooth state while your
280d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickapp is running.</p> 
281d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
282ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p class="note"><strong>Tip:</strong> Enabling discoverability will automatically
283ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainenable Bluetooth. If you plan to consistently enable device discoverability before
284ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainperforming Bluetooth activity, you can skip
285ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainstep 2 above. Read about <a href="#EnablingDiscoverability">enabling discoverability</a>,
286d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickbelow.</p> 
287d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
288d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
289d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h2 id="FindingDevices">Finding Devices</h2> 
290d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
291ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Using the {@link android.bluetooth.BluetoothAdapter}, you can find remote Bluetooth
292ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindevices either through device discovery or by querying the list of paired (bonded)
293d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickdevices.</p> 
294d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
295ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Device discovery is a scanning procedure that searches the local area for
296ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainBluetooth enabled devices and then requesting some information about each one
297ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main(this is sometimes referred to as "discovering," "inquiring" or "scanning").
298ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainHowever, a Bluetooth device within the local area will respond to a discovery
299ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainrequest only if it is currently enabled to be discoverable. If a device is
300ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindiscoverable, it will respond to the discovery request by sharing some
301ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maininformation, such as the device name, class, and its unique MAC address. Using
302ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthis information, the device performing discovery can then choose to initiate a
303d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnection to the discovered device.</p> 
304d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
305ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Once a connection is made with a remote device for the first time, a pairing
306ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainrequest is automatically presented to the user. When a device is
307ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainpaired, the basic information about that device (such as the device name, class,
308ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainand MAC address) is saved and can be read using the Bluetooth APIs. Using the
309ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainknown MAC address for a remote device, a connection can be initiated with it at
310d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickany time without performing discovery (assuming the device is within range).</p> 
311d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
312ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Remember there is a difference between being paired and being connected. To
313ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainbe paired means that two devices are aware of each other's existence, have a
314ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainshared link-key that can be used for authentication, and are capable of
315ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainestablishing an encrypted connection with each other. To be connected means that
316ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe devices currently share an RFCOMM channel and are able to transmit data with
317ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maineach other. The current Android Bluetooth API's require devices to be paired
318ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainbefore an RFCOMM connection can be established. (Pairing is automatically performed
319d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickwhen you initiate an encrypted connection with the Bluetooth APIs.)</p> 
320d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
321ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>The following sections describe how to find devices that have been paired, or
322d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickdiscover new devices using device discovery.</p> 
323d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
324ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p class="note"><strong>Note:</strong> Android-powered devices are not
325ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindiscoverable by default. A user can make
326ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe device discoverable for a limited time through the system settings, or an
327ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainapplication can request that the user enable discoverability without leaving the
328d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickapplication. How to <a href="#EnablingDiscoverability">enable discoverability</a> 
329d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickis discussed below.</p> 
330d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
331d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
332d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h3 id="QueryingPairedDevices">Querying paired devices</h3> 
333d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
334ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Before performing device discovery, its worth querying the set
335ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainof paired devices to see if the desired device is already known. To do so,
336ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maincall {@link android.bluetooth.BluetoothAdapter#getBondedDevices()}. This
337ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwill return a Set of {@link android.bluetooth.BluetoothDevice}s representing
33836cdecd89dbc3eb503197414f525e30ee241ba66Scott Mainpaired devices. For example, you can query all paired devices and then
339d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickshow the name of each device to the user, using an ArrayAdapter:</p> 
340d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre> 
341ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainSet&lt;BluetoothDevice> pairedDevices = mBluetoothAdapter.getBondedDevices();
342ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main// If there are paired devices
343ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainif (pairedDevices.size() > 0) {
344ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    // Loop through paired devices
345ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    for (BluetoothDevice device : pairedDevices) {
346ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // Add the name and address to an array adapter to show in a ListView
347ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        mArrayAdapter.add(device.getName() + "\n" + device.getAddress());
348ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
349ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main}
350d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
351d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
352ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>All that's needed from the {@link android.bluetooth.BluetoothDevice} object
353ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainin order to initiate a connection is the MAC address. In this example, it's saved
354ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainas a part of an ArrayAdapter that's shown to the user. The MAC address can later
355ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainbe extracted in order to initiate the connection. You can learn more about creating
356d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormicka connection in the section about <a href="#ConnectingDevices">Connecting Devices</a>.</p> 
357d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
358d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
359d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h3 id="DiscoveringDevices">Discovering devices</h3> 
360d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
361ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>To start discovering devices, simply call {@link
362ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#startDiscovery()}. The
363ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainprocess is asynchronous and the method will immediately return with a boolean
364ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainindicating whether discovery has successfully started. The discovery process
365ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainusually involves an inquiry scan of about 12 seconds, followed by a page scan of
366d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickeach found device to retrieve its Bluetooth name.</p> 
367d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
368ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Your application must register a BroadcastReceiver for the
369ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothDevice#ACTION_FOUND} Intent in
370ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainorder to receive information about each
371ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindevice discovered. For each device, the system will broadcast the
372ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothDevice#ACTION_FOUND} Intent. This
373ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainIntent carries the extra fields
374ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothDevice#EXTRA_DEVICE} and
375ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothDevice#EXTRA_CLASS}, containing a
376ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothDevice} and a {@link
377ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothClass}, respectively. For example, here's how you can
378d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickregister to handle the broadcast when devices are discovered:</p> 
379d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre> 
380ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main// Create a BroadcastReceiver for ACTION_FOUND
381ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainprivate final BroadcastReceiver mReceiver = new BroadcastReceiver() {
382ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public void onReceive(Context context, Intent intent) {
383ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        String action = intent.getAction();
384ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // When discovery finds a device
385ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        if (BluetoothDevice.ACTION_FOUND.equals(action)) {
386ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            // Get the BluetoothDevice object from the Intent
387ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            BluetoothDevice device = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);
388ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            // Add the name and address to an array adapter to show in a ListView
389ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            mArrayAdapter.add(device.getName() + "\n" + device.getAddress());
390ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        }
391ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
392ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main};
393ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main// Register the BroadcastReceiver
394ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainIntentFilter filter = new IntentFilter(BluetoothDevice.ACTION_FOUND);
395ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainregisterReceiver(mReceiver, filter); // Don't forget to unregister during onDestroy
396d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
397d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
398ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>All that's needed from the {@link android.bluetooth.BluetoothDevice} object
399ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainin order to initiate a
400ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnection is the MAC address. In this example, it's saved as a part of an
401ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainArrayAdapter that's shown to the user. The MAC address can later be extracted in
402ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainorder to initiate the connection. You can learn more about creating a connection
403d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickin the section about <a href="#ConnectingDevices">Connecting Devices</a>.</p> 
404d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
405ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p class="caution"><strong>Caution:</strong> Performing device discovery is
406ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maina heavy procedure for the Bluetooth
407ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainadapter and will consume a lot of its resources. Once you have found a device to
408ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnect, be certain that you always stop discovery with
409ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothAdapter#cancelDiscovery()} before
410ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainattempting a connection. Also, if you
411ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainalready hold a connection with a device, then performing discovery can
412ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainsignificantly reduce the bandwidth available for the connection, so you should
413d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormicknot perform discovery while connected.</p> 
414d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
415d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h4 id="EnablingDiscoverability">Enabling discoverability</h4> 
416d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
417ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>If you would like to make the local device discoverable to other devices,
418ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maincall {@link android.app.Activity#startActivityForResult(Intent,int)} with the
419d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick{@link android.bluetooth.BluetoothAdapter#ACTION_REQUEST_DISCOVERABLE} action
420d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickIntent. This will issue a request to enable discoverable mode through the system
421d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormicksettings (without stopping your application). By default, the device will become
422d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickdiscoverable for 120 seconds. You can define a different duration by adding the
423d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick{@link android.bluetooth.BluetoothAdapter#EXTRA_DISCOVERABLE_DURATION} Intent
424d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickextra. The maximum duration an app can set is 3600 seconds, and a value of 0
425d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickmeans the device is always discoverable. Any value below 0 or above 3600 is
426d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickautomatically set to 120 secs). For example, this snippet sets the duration to
427d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick300:</p> 
428d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
429d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre>Intent discoverableIntent = new
430ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainIntent(BluetoothAdapter.ACTION_REQUEST_DISCOVERABLE);
431ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MaindiscoverableIntent.putExtra(BluetoothAdapter.EXTRA_DISCOVERABLE_DURATION, 300);
432ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainstartActivity(discoverableIntent);
433d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
434d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
435d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<div class="figure" style="width:200px"> 
436d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<img src="{@docRoot}images/bt_enable_discoverable.png" /> 
437ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<strong>Figure 2:</strong> The enabling discoverability dialog.
438d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</div> 
439d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
440ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>A dialog will be displayed, requesting user permission to make the device
441ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindiscoverable, as shown in Figure 2. If the user responds "Yes," then the device
44293dc642eaf48e3db58c4929df26283fbc5fd663fScott Mainwill become discoverable for the specified amount of time. Your activity will
443ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthen receive a call to the {@link android.app.Activity#onActivityResult(int,int,Intent)
444ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainonActivityResult())} callback, with the result code equal to the duration that the device
445ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainis discoverable. If the user responded "No" or if an error occurred, the result code will
44693dc642eaf48e3db58c4929df26283fbc5fd663fScott Mainbe {@link android.app.Activity#RESULT_CANCELED}.</p> 
447d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
448ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p class="note"><strong>Note:</strong> If Bluetooth has not been enabled on the device,
449d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickthen enabling device discoverability will automatically enable Bluetooth.</p> 
450d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
451ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>The device will silently remain in discoverable mode for the allotted time.
452ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainIf you would like to be notified when the discoverable mode has changed, you can
453ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainregister a BroadcastReceiver for the {@link
454ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#ACTION_SCAN_MODE_CHANGED}
455ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainIntent. This will contain the extra fields {@link
456ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#EXTRA_SCAN_MODE} and
457ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothAdapter#EXTRA_PREVIOUS_SCAN_MODE}, which tell you the
458ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainnew and old scan mode, respectively. Possible values for each are
459ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothAdapter#SCAN_MODE_CONNECTABLE_DISCOVERABLE},
460ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothAdapter#SCAN_MODE_CONNECTABLE}, or {@link
461ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#SCAN_MODE_NONE},
462ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwhich indicate that the device is either in discoverable mode, not in
463ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindiscoverable mode but still able to receive connections, or not in discoverable
464d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickmode and unable to receive connections, respectively.</p> 
465d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
466ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>You do not need to enable device discoverability if you will be initiating
467ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe connection to a remote device. Enabling discoverability is only necessary when
468ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainyou want your application to host a server socket that will accept incoming
469ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnections, because the remote devices must be able to discover the device
470d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickbefore it can initiate the connection.</p> 
471d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
472d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
473d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
474d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h2 id="ConnectingDevices">Connecting Devices</h2> 
475d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
476ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>In order to create a connection between your application on two devices, you
477ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainmust implement both the server-side and client-side mechanisms, because one
478ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindevice must open a server socket and the other one must initiate the connection
479ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main(using the server device's MAC address to initiate a connection). The server and
480ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainclient are considered connected to each other when they each have a connected
481ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothSocket} on the same RFCOMM channel. At this
482ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainpoint, each device can obtain input and output streams and data transfer can
483ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainbegin, which is discussed in the section about <a
484369c1c1fa22802b6504c5cde533d797841700a66Scott Mainhref="#ManagingAConnection">Managing a Connection</a>. This section describes how
485d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickto initiate the connection between two devices.</p> 
486d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
487ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>The server device and the client device each obtain the required {@link
488ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket} in different ways. The server will receive it
489ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwhen an incoming connection is accepted. The client will receive it when it
490d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickopens an RFCOMM channel to the server.</p> 
491d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
492d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<div class="figure" style="width:200px"> 
493d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<img src="{@docRoot}images/bt_pairing_request.png" /> 
494fe7f27aabfb339b86eeb3a40ce894b91eafd26f0Scott Main<strong>Figure 3:</strong> The Bluetooth pairing dialog.
495d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</div> 
496d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
497ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>One implementation technique is to automatically prepare each device as a
498ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainserver, so that each one has a server socket open and listening for connections.
499ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainThen either device can initiate a connection with the other and become the
500ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainclient. Alternatively, one device can explicitly "host" the connection and open
501ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maina server socket on demand and the other device can simply initiate the
502d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnection.</p> 
503d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
504ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p class="note"><strong>Note:</strong> If the two devices have not been previously paired,
505ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthen the Android framework will automatically show a pairing request notification or
506fe7f27aabfb339b86eeb3a40ce894b91eafd26f0Scott Maindialog to the user during the connection procedure, as shown in Figure 3. So
507fe7f27aabfb339b86eeb3a40ce894b91eafd26f0Scott Mainwhen attempting to connect devices,
508ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainyour application does not need to be concerned about whether or not the devices are
509ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainpaired. Your RFCOMM connection attempt will block until the user has successfully paired,
510d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickor will fail if the user rejects pairing, or if pairing fails or times out. </p> 
511d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
512d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
513d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h3 id="ConnectingAsAServer">Connecting as a server</h3> 
514d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
515ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>When you want to connect two devices, one must act as a server by holding an
516ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainopen {@link android.bluetooth.BluetoothServerSocket}. The purpose of the server
517ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainsocket is to listen for incoming connection requests and when one is accepted,
518ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainprovide a connected {@link android.bluetooth.BluetoothSocket}. When the {@link
519ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket} is acquired from the {@link
520ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket},
521ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe {@link android.bluetooth.BluetoothServerSocket} can (and should) be
522d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickdiscarded, unless you want to accept more connections.</p> 
523d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
524d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<div class="sidebox-wrapper"> 
525d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<div class="sidebox"> 
526d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h2>About UUID</h2> 
527d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
528ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>A Universally Unique Identifier (UUID) is a standardized 128-bit format for a string
529ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainID used to uniquely identify information. The point of a UUID is that it's big
530ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainenough that you can select any random and it won't clash. In this case, it's
531ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainused to uniquely identify your application's Bluetooth service. To get a UUID to
532ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainuse with your application, you can use one of the many random UUID generators on
533ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe web, then initialize a {@link java.util.UUID} with {@link
534d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickjava.util.UUID#fromString(String)}.</p> 
535d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</div> 
536d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</div> 
537d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
538ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Here's the basic procedure to set up a server socket and accept a
539d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnection:</p> 
540d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
541d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<ol> 
542ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<li>Get a {@link android.bluetooth.BluetoothServerSocket} by calling the
543ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link
544ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#listenUsingRfcommWithServiceRecord(String,
545ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainUUID)}.
546ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>The string is an identifiable name of your service, which the system will
547ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainautomatically write to a new Service Discovery Protocol (SDP) database entry on
548ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe device (the name is arbitrary and can simply be your application name). The
549ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainUUID is also included in the SDP entry and will be the basis for the connection
550ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainagreement with the client device. That is, when the client attempts to connect
551ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwith this device, it will carry a UUID that uniquely identifies the service with
552ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwhich it wants to connect. These UUIDs must match in order for the connection to
553d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickbe accepted (in the next step).</p> 
554d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</li> 
555d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
556ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<li>Start listening for connection requests by calling
557ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothServerSocket#accept()}.
558ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>This is a blocking call. It will return when either a connection has been
559ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainaccepted or an exception has occurred. A connection is accepted only when a
560ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainremote device has sent a connection request with a UUID matching the one
561ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainregistered with this listening server socket. When successful, {@link
562ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket#accept()} will
563d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickreturn a connected {@link android.bluetooth.BluetoothSocket}.</p> 
564d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</li> 
565d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
566ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<li>Unless you want to accept additional connections, call
567ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothServerSocket#close()}.
568ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>This releases the server socket and all its resources, but does <em>not</em> close the
569ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnected {@link android.bluetooth.BluetoothSocket} that's been returned by {@link
570ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket#accept()}. Unlike TCP/IP, RFCOMM only allows one
571ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnected client per channel at a time, so in most cases it makes sense to call {@link
572ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket#close()} on the {@link
573ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket} immediately after accepting a connected
574d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormicksocket.</p> 
575d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</li> 
576d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</ol> 
577d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
578ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>The {@link android.bluetooth.BluetoothServerSocket#accept()} call should not
57993dc642eaf48e3db58c4929df26283fbc5fd663fScott Mainbe executed in the main activity UI thread because it is a blocking call and
580ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwill prevent any other interaction with the application. It usually makes
581ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainsense to do all work with a {@link android.bluetooth.BluetoothServerSocket} or {@link
582ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket} in a new
583ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthread managed by your application. To abort a blocked call such as {@link
584ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket#accept()}, call {@link
585ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket#close()} on the {@link
586ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket} (or {@link
587ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket}) from another thread and the blocked call will
588ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainimmediately return. Note that all methods on a {@link
589ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket} or {@link android.bluetooth.BluetoothSocket}
590d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickare thread-safe.</p> 
591d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
592d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h4>Example</h4> 
593d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
594ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Here's a simplified thread for the server component that accepts incoming
595d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnections:</p> 
596d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre> 
597ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainprivate class AcceptThread extends Thread {
598ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    private final BluetoothServerSocket mmServerSocket;
599d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
600ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public AcceptThread() {
601ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // Use a temporary object that is later assigned to mmServerSocket,
602ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // because mmServerSocket is final
603ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        BluetoothServerSocket tmp = null;
604ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        try {
605ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            // MY_UUID is the app's UUID string, also used by the client code
6062785443c6e93c05a4885f4eeb76b12dd8c0e59b5Scott Main            tmp = mBluetoothAdapter.listenUsingRfcommWithServiceRecord(NAME, MY_UUID);
607ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        } catch (IOException e) { }
608ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        mmServerSocket = tmp;
609ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
610d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
611ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public void run() {
612ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        BluetoothSocket socket = null;
613ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // Keep listening until exception occurs or a socket is returned
614ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        while (true) {
615ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            try {
616ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                socket = mmServerSocket.accept();
617ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            } catch (IOException e) {
618ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                break;
619ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            }
620ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            // If a connection was accepted
621ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            if (socket != null) {
622ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                // Do work to manage the connection (in a separate thread)
623ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                manageConnectedSocket(socket);
624ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                mmServerSocket.close();
625ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                break;
626ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            }
627ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        }
628ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
629d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
630ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    /** Will cancel the listening socket, and cause the thread to finish */
631ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public void cancel() {
632ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        try {
633ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            mmServerSocket.close();
634ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        } catch (IOException e) { }
635ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
636ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main}
637d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
638d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
639ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>In this example, only one incoming connection is desired, so as soon as a
640ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnection is accepted and the {@link android.bluetooth.BluetoothSocket} is
641ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainacquired, the application
642ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainsends the acquired {@link android.bluetooth.BluetoothSocket} to a separate
643ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthread, closes the
644d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick{@link android.bluetooth.BluetoothServerSocket} and breaks the loop.</p> 
645d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
646ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Note that when {@link android.bluetooth.BluetoothServerSocket#accept()}
647ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainreturns the {@link android.bluetooth.BluetoothSocket}, the socket is already
648ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnected, so you should <em>not</em> call {@link
649ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket#connect()} (as you do from the
650d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickclient-side).</p> 
651d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
652ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p><code>manageConnectedSocket()</code> is a fictional method in the application
653ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthat will
654ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maininitiate the thread for transferring data, which is discussed in the section
655d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickabout <a href="#ManagingAConnection">Managing a Connection</a>.</p> 
656d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
657ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>You should usually close your {@link android.bluetooth.BluetoothServerSocket}
658ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainas soon as you are done listening for incoming connections. In this example, {@link
659ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothServerSocket#close()} is called as soon
660ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainas the {@link android.bluetooth.BluetoothSocket} is acquired. You may also want
661ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainto provide a public method in your thread that can close the private {@link
662ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket} in the event that you need to stop listening on the
663d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickserver socket.</p> 
664d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
665d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
666d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h3 id="ConnectingAsAClient">Connecting as a client</h3> 
667d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
668ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>In order to initiate a connection with a remote device (a device holding an
669ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainopen
670ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainserver socket), you must first obtain a {@link
671ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothDevice} object that represents the remote device.
672ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main(Getting a {@link android.bluetooth.BluetoothDevice} is covered in the above
673ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainsection about <a
674ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainhref="#FindingDevices">Finding Devices</a>.) You must then use the
675ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothDevice} to acquire a {@link
676d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.bluetooth.BluetoothSocket} and initiate the connection.</p> 
677d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
678d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<p>Here's the basic procedure:</p> 
679d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
680d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<ol> 
681ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<li>Using the {@link android.bluetooth.BluetoothDevice}, get a {@link
682ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket} by calling {@link
683ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothDevice#createRfcommSocketToServiceRecord(UUID)}.
684ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>This initializes a {@link android.bluetooth.BluetoothSocket} that will
685ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnect to the {@link android.bluetooth.BluetoothDevice}. The UUID passed here
686ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainmust match the UUID used by the server device when it opened its
687ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main{@link android.bluetooth.BluetoothServerSocket} (with {@link
688ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothAdapter#listenUsingRfcommWithServiceRecord(String,
689ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainUUID)}). Using the same UUID is simply a matter of hard-coding the UUID string
690ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maininto your application and then referencing it from both the server and client
691d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickcode.</p> 
692d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</li> 
693d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
694ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<li>Initiate the connection by calling {@link
695ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket#connect()}.
696ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Upon this call, the system will perform an SDP lookup on the remote device in
697ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainorder to match the UUID. If the lookup is successful and the remote device
698ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainaccepts the connection, it will share the RFCOMM channel to use during the
699ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainconnection and {@link
700ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket#connect()} will return. This method is a
701ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainblocking call. If, for
702ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainany reason, the connection fails or the {@link
703ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket#connect()} method times out (after about
704d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick12 seconds), then it will throw an exception.</p> 
705ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Because {@link
706ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket#connect()} is a blocking call, this connection
70793dc642eaf48e3db58c4929df26283fbc5fd663fScott Mainprocedure should always be performed in a thread separate from the main activity
708d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickthread.</p> 
709ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p class="note">Note: You should always ensure that the device is not performing
710ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maindevice discovery when you call {@link
711ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket#connect()}. If discovery is in progress, then
712ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthe
713d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnection attempt will be significantly slowed and is more likely to fail.</p> 
714d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</li> 
715d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</ol> 
716d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
717d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h4>Example</h4> 
718d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
719ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Here is a basic example of a thread that initiates a Bluetooth
720d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnection:</p> 
721d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre> 
722ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainprivate class ConnectThread extends Thread {
723ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    private final BluetoothSocket mmSocket;
724ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    private final BluetoothDevice mmDevice;
725d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
726ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public ConnectThread(BluetoothDevice device) {
727ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // Use a temporary object that is later assigned to mmSocket,
728ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // because mmSocket is final
729ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        BluetoothSocket tmp = null;
730ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        mmDevice = device;
731d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
732ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // Get a BluetoothSocket to connect with the given BluetoothDevice
733ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        try {
734ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            // MY_UUID is the app's UUID string, also used by the server code
735ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            tmp = device.createRfcommSocketToServiceRecord(MY_UUID);
736ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        } catch (IOException e) { }
737ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        mmSocket = tmp;
738ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
739d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
740ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public void run() {
741ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // Cancel discovery because it will slow down the connection
7422785443c6e93c05a4885f4eeb76b12dd8c0e59b5Scott Main        mBluetoothAdapter.cancelDiscovery();
743d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
744ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        try {
745ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            // Connect the device through the socket. This will block
746ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            // until it succeeds or throws an exception
747ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            mmSocket.connect();
748ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        } catch (IOException connectException) {
749ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            // Unable to connect; close the socket and get out
750ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            try {
751ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                mmSocket.close();
752ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            } catch (IOException closeException) { }
753ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            return;
754ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        }
755d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
756ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // Do work to manage the connection (in a separate thread)
757ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        manageConnectedSocket(mmSocket);
758ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
759d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
760ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    /** Will cancel an in-progress connection, and close the socket */
761ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public void cancel() {
762ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        try {
763ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            mmSocket.close();
764ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        } catch (IOException e) { }
765ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
766ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main}
767d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
768d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
769ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Notice that {@link android.bluetooth.BluetoothAdapter#cancelDiscovery()} is called
770ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainbefore the connection is made. You should always do this before connecting and it is safe
771ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainto call without actually checking whether it is running or not (but if you do want to
772d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickcheck, call {@link android.bluetooth.BluetoothAdapter#isDiscovering()}).</p> 
773d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
774ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p><code>manageConnectedSocket()</code> is a fictional method in the application
775ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainthat will initiate the thread for transferring data, which is discussed in the section
776d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickabout <a href="#ManagingAConnection">Managing a Connection</a>.</p> 
777d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
778ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>When you're done with your {@link android.bluetooth.BluetoothSocket}, always
779ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maincall {@link android.bluetooth.BluetoothSocket#close()} to clean up.
780ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainDoing so will immediately close the connected socket and clean up all internal
781d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickresources.</p> 
782d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
783d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
784d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h2 id="ManagingAConnection">Managing a Connection</h2> 
785d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
786ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>When you have successfully connected two (or more) devices, each one will
787ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainhave a connected {@link android.bluetooth.BluetoothSocket}. This is where the fun
788ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainbegins because you can share data between devices. Using the {@link
789ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket}, the general procedure to transfer arbitrary data is
790d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormicksimple:</p> 
791d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<ol> 
792ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<li>Get the {@link java.io.InputStream} and {@link java.io.OutputStream} that
793ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainhandle transmissions through the socket, via {@link
794ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainandroid.bluetooth.BluetoothSocket#getInputStream()} and
795d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick{@link android.bluetooth.BluetoothSocket#getOutputStream}, respectively.</li> 
796d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
797ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<li>Read and write data to the streams with {@link
798d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickjava.io.InputStream#read(byte[])} and {@link java.io.OutputStream#write(byte[])}.</li> 
799d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</ol> 
800d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
801d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<p>That's it.</p> 
802d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
803ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>There are, of course, implementation details to consider. First and foremost,
804ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainyou should use a dedicated thread for all stream reading and writing. This is
805ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainimportant because both {@link java.io.InputStream#read(byte[])} and {@link
806ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainjava.io.OutputStream#write(byte[])} methods are blocking calls. {@link
807ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainjava.io.InputStream#read(byte[])} will block until there is something to read
808ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainfrom the stream. {@link java.io.OutputStream#write(byte[])} does not usually
809ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainblock, but can block for flow control if the remote device is not calling {@link
810ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainjava.io.InputStream#read(byte[])} quickly enough and the intermediate buffers are full.
811ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainSo, your main loop in the thread should be dedicated to reading from the {@link
812ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainjava.io.InputStream}. A separate public method in the thread can be used to initiate
813d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickwrites to the {@link java.io.OutputStream}.</p> 
814d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
815d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h4>Example</h4> 
816d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
817d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<p>Here's an example of how this might look:</p> 
818d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre> 
819ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainprivate class ConnectedThread extends Thread {
820ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    private final BluetoothSocket mmSocket;
821ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    private final InputStream mmInStream;
822ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    private final OutputStream mmOutStream;
823d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
824ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public ConnectedThread(BluetoothSocket socket) {
825ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        mmSocket = socket;
826ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        InputStream tmpIn = null;
827ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        OutputStream tmpOut = null;
828d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
829ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // Get the input and output streams, using temp objects because
830ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // member streams are final
831ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        try {
832ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            tmpIn = socket.getInputStream();
833ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            tmpOut = socket.getOutputStream();
834ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        } catch (IOException e) { }
835d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
836ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        mmInStream = tmpIn;
837ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        mmOutStream = tmpOut;
838ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
839d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
840ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public void run() {
841ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        byte[] buffer = new byte[1024];  // buffer store for the stream
842ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        int bytes; // bytes returned from read()
843d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
844ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        // Keep listening to the InputStream until an exception occurs
845ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        while (true) {
846ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            try {
847ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                // Read from the InputStream
848ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                bytes = mmInStream.read(buffer);
84993dc642eaf48e3db58c4929df26283fbc5fd663fScott Main                // Send the obtained bytes to the UI activity
850ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                mHandler.obtainMessage(MESSAGE_READ, bytes, -1, buffer)
851ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                        .sendToTarget();
852ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            } catch (IOException e) {
853ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main                break;
854ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            }
855ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        }
856ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
857d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
85893dc642eaf48e3db58c4929df26283fbc5fd663fScott Main    /* Call this from the main activity to send data to the remote device */
859ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public void write(byte[] bytes) {
860ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        try {
861ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            mmOutStream.write(bytes);
862ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        } catch (IOException e) { }
863ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
864d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
86593dc642eaf48e3db58c4929df26283fbc5fd663fScott Main    /* Call this from the main activity to shutdown the connection */
866ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    public void cancel() {
867ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        try {
868ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main            mmSocket.close();
869ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main        } catch (IOException e) { }
870ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main    }
871ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main}
872d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
873d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
874ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>The constructor acquires the necessary streams and once executed, the thread
875ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainwill wait for data to come through the InputStream. When {@link
876ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainjava.io.InputStream#read(byte[])} returns with
87793dc642eaf48e3db58c4929df26283fbc5fd663fScott Mainbytes from the stream, the data is sent to the main activity using a member
878ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainHandler from the parent class. Then it goes back and waits for more bytes from
879d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickthe stream.</p> 
880d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
881ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>Sending outgoing data is as simple as calling the thread's
88293dc642eaf48e3db58c4929df26283fbc5fd663fScott Main<code>write()</code> method from the main activity and passing in the bytes to
883ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainbe sent. This method then simply calls {@link
884d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickjava.io.OutputStream#write(byte[])} to send the data to the remote device.</p> 
885d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
886ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Main<p>The thread's <code>cancel()</code> method is important so that the connection
887ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Maincan be
888ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott Mainterminated at any time by closing the {@link android.bluetooth.BluetoothSocket}.
889ed2a70d6495b3f1928e36ad2b00ee4d33b2c0379Scott MainThis should always be called when you're done using the Bluetooth
890d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickconnection.</p> 
891d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
892d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<div class="special"> 
893d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<p>For a  demonstration of using the Bluetooth APIs, see the <a
894d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickhref="{@docRoot}resources/samples/BluetoothChat/index.html">Bluetooth Chat sample app</a>.</p> 
895d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</div> 
896d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
897d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h2 id="Profiles">Working with Profiles</h2> 
898d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
899d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<p>Starting in Android 3.0, the Bluetooth API includes support for working with
900d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickBluetooth profiles. A <em>Bluetooth profile</em> is a wireless interface
901d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickspecification for Bluetooth-based communication between devices. An example
902d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickis the Hands-Free profile. For a mobile phone to connect to a wireless headset,
903d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickboth devices must support the Hands-Free profile. </p> 
904d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
905d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<p>You can implement the interface {@link android.bluetooth.BluetoothProfile} to write
906d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickyour own classes to support a particular Bluetooth profile. The Android
907d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickBluetooth API provides implementations for the following Bluetooth
908d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickprofiles:</p> 
909d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<ul> 
910d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
911d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <li><strong>Headset</strong>. The Headset profile provides support for
912d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickBluetooth headsets to be used with mobile phones. Android provides the {@link
913d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.bluetooth.BluetoothHeadset} class, which is a proxy for controlling the
914d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickBluetooth Headset Service via interprocess communication (<a
91550e990c64fa23ce94efa76b9e72df7f8ec3cee6aScott Mainhref="{@docRoot}guide/components/processes-and-threads.html#IPC">IPC</a
916d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick>). This includes both  Bluetooth Headset and Hands-Free (v1.5) profiles. The
917d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick{@link android.bluetooth.BluetoothHeadset} class includes support for AT commands.
9182e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickFor more discussion of this topic, see <a href="#AT-Commands">Vendor-specific AT commands</a></li>
919d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
920d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <li><strong>A2DP</strong>. The Advanced Audio Distribution Profile (A2DP)
921d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickprofile defines how high quality audio can be streamed from one device to
922d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickanother over a Bluetooth connection. Android provides the {@link
923d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.bluetooth.BluetoothA2dp} class, which is a proxy for controlling
924d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickthe Bluetooth A2DP  Service via IPC.</li> 
925d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
9262e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick <li><strong>Health Device</strong>. Android 4.0 (API level 14) introduces
9272e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormicksupport for the Bluetooth Health Device Profile (HDP). This lets you create
9282e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickapplications that use Bluetooth to communicate with health devices that support
9292e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickBluetooth, such as heart-rate monitors, blood meters, thermometers, scales, and
9302e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickso on. For a list of supported devices and their corresponding device data
9312e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickspecialization codes, refer to <strong>Bluetooth Assigned Numbers</strong> at <a
9322e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickhref="http://www.bluetooth.org">www.bluetooth.org</a>. Note that these values
9332e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickare also referenced in the ISO/IEEE 11073-20601 [7] specification as
9342e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickMDC_DEV_SPEC_PROFILE_* in the Nomenclature Codes Annex. For more discussion of
9352e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickHDP, see <a href="#HDP">Health Device Profile</a>.</li> 
9362e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
937d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</ul> 
938d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
939d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<p>Here are the basic steps for working with a profile:</p> 
940d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<ol> 
941d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
942cd1b08e1e239269f7d0d48119505313f52d3dd5aScott Main  <li>Get the default adapter, as described in
94350e990c64fa23ce94efa76b9e72df7f8ec3cee6aScott Main    <a href="{@docRoot}guide/topics/connectivity/bluetooth.html#SettingUp">Setting Up
944cd1b08e1e239269f7d0d48119505313f52d3dd5aScott Main      Bluetooth</a>.</li> 
945d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
946d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <li>Use {@link
947d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.bluetooth.BluetoothAdapter#getProfileProxy(android.content.Context,
948d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.bluetooth.BluetoothProfile.ServiceListener, int) getProfileProxy()} to
949d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickestablish a connection to the profile proxy object associated with the profile.
950d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickIn the example below, the profile proxy object is an instance of {@link
951d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.bluetooth.BluetoothHeadset}. </li> 
952d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
953d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <li>Set up a  {@link android.bluetooth.BluetoothProfile.ServiceListener}. This
954d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormicklistener notifies {@link android.bluetooth.BluetoothProfile} IPC clients when
955d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickthey have been connected to or disconnected from the service.</li> 
956d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
957d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <li>In {@link
958d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.bluetooth.BluetoothProfile.ServiceListener#onServiceConnected(int,
959d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.bluetooth.BluetoothProfile) onServiceConnected()}, get a handle
960d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickto the profile proxy object.</li> 
961d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
962d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick  <li>Once you have the profile proxy object, you can use it to monitor the
963d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickstate of the connection and perform other operations that are relevant to that
964d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickprofile.</li> 
965d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</ol> 
9662e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
9672e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<p> For example, this code snippet shows how to connect to a {@link
9682e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickandroid.bluetooth.BluetoothHeadset} proxy object so that you can control the
969d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickHeadset profile:</p> 
970d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
971d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<pre>BluetoothHeadset mBluetoothHeadset;
972d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
973d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick// Get the default adapter
974d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickBluetoothAdapter mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
975d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
976d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick// Establish connection to the proxy.
977d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickmBluetoothAdapter.getProfileProxy(context, mProfileListener, BluetoothProfile.HEADSET);
978d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
979d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickprivate BluetoothProfile.ServiceListener mProfileListener = new BluetoothProfile.ServiceListener() {
980d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    public void onServiceConnected(int profile, BluetoothProfile proxy) {
981d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick        if (profile == BluetoothProfile.HEADSET) {
982d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick            mBluetoothHeadset = (BluetoothHeadset) proxy;
983d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick        }
984d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    }
985d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    public void onServiceDisconnected(int profile) {
986d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick        if (profile == BluetoothProfile.HEADSET) {
987d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick            mBluetoothHeadset = null;
988d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick        }
989d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick    }
990d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick};
991d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
992d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick// ... call functions on mBluetoothHeadset
993d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick 
994d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick// Close proxy connection after use.
995d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickmBluetoothAdapter.closeProfileProxy(mBluetoothHeadset);
996d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick</pre> 
997d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
9982e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
9992e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
1000d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<h3 id="AT-Commands">Vendor-specific AT commands</h3> 
1001d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick
1002d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormick<p>Starting in Android 3.0, applications can register to receive system
1003d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickbroadcasts of pre-defined vendor-specific AT commands sent by headsets (such as
1004d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormicka Plantronics +XEVENT command). For example, an application could receive
1005d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickbroadcasts that indicate a connected device's battery level and could notify the
1006d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickuser or take other action as needed. Create a broadcast receiver for the {@link
1007d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickandroid.bluetooth.BluetoothHeadset#ACTION_VENDOR_SPECIFIC_HEADSET_EVENT} intent
1008d4fac2c0263fda4b20f253edd594cf909e61eb4eKatie McCormickto handle vendor-specific AT commands for the headset.</p>
10092e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10102e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<h3 id="HDP">Health Device Profile</h3>
10112e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10122e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<p>Android 4.0 (API level 14) introduces support for the Bluetooth Health Device
10132e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickProfile (HDP). This lets you create applications that use Bluetooth to
10142e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickcommunicate with health devices that support Bluetooth, such as heart-rate
10152e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickmonitors, blood meters, thermometers, and scales. The Bluetooth Health API
10162e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickincludes the classes {@link android.bluetooth.BluetoothHealth}, {@link
10172e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickandroid.bluetooth.BluetoothHealthCallback}, and {@link
10182e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickandroid.bluetooth.BluetoothHealthAppConfiguration}, which are described in <a
10192e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickhref="#TheBasics">The Basics</a>. </p>
10202e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10212e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<p>In using the Bluetooth Health API, it's helpful to understand these key HDP concepts:</p>
10222e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<table>
10232e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <tr>
10242e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <th>Concept</th>
10252e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <th>Description</th>
10262e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  </tr>
10272e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <tr>
10282e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <td><strong>Source</strong></td>
10292e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10302e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <td>A role defined in HDP. A <em>source</em> is a  health device that
10312e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormicktransmits medical data (weight scale, glucose meter, thermometer, etc.) to a
10322e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormicksmart device such as an Android phone or tablet. </td>
10332e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  </tr>
10342e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <tr>
10352e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <td><strong>Sink</strong></td>
10362e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10372e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <td>A role defined in HDP. In HDP, a <em>sink</em> is the smart device that
10382e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickreceives the medical data. In an Android HDP application, the sink is
10392e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickrepresented by a {@link android.bluetooth.BluetoothHealthAppConfiguration}
10402e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickobject.</td>
10412e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  </tr>
10422e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <tr>
10432e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <td><strong>Registration</strong></td>
10442e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <td>Refers to registering a sink for a particular health device.</td>
10452e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  </tr>
10462e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <tr>
10472e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <td><strong>Connection</strong></td>
10482e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10492e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick    <td>Refers to opening a channel between a health device and a smart device
10502e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormicksuch as an Android phone or tablet.</td>
10512e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  </tr>
10522e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick</table>
10532e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10542e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<h4>Creating an HDP Application</h4>
10552e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10562e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<p>Here are the basic steps involved in creating an Android HDP application:</p>
10572e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<ol>
10582e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10592e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <li>Get a reference to the {@link android.bluetooth.BluetoothHealth} proxy
10602e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickobject. <p>Similar to regular headset and A2DP profile devices, you must call
10612e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick{@link android.bluetooth.BluetoothAdapter#getProfileProxy getProfileProxy()}
10622e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickwith a {@link android.bluetooth.BluetoothProfile.ServiceListener} and the {@link
10632e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickandroid.bluetooth.BluetoothProfile.ServiceListener#HEALTH} profile type to
10642e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickestablish a connection with the profile proxy object.</p> </li>
10652e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10662e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <li>Create a {@link android.bluetooth.BluetoothHealthCallback} and register an
10672e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickapplication configuration 
10682e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick({@link android.bluetooth.BluetoothHealthAppConfiguration})
10692e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickthat acts as a health
10702e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormicksink.</li>
10712e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10722e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <li>Establish a connection to a health device.  Some devices will initiate the
10732e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickconnection.  It is unnecessary to carry out this step for those devices.</li>
10742e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10752e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <li>When connected successfully to a health device, read/write to the health
10762e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickdevice using the file descriptor. <p>The received data needs to be interpreted
10772e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickusing a health manager which implements the IEEE 11073-xxxxx
10782e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickspecifications.</p></li>
10792e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10802e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick  <li>When done, close the health channel and unregister the application.  The
10812e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickchannel also closes when there is extended inactivity.</li>
10822e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick</ol>
10832e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick
10842e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormick<p>For a complete code sample that illustrates these steps, see <a
10852e32a78eadfe8b98d89a376b8ccbea52e32a749cKatie McCormickhref="{@docRoot}resources/samples/BluetoothHDP/index.html">Bluetooth HDP (Health
10866a52c632530fa39de570c9a6630264178c20e58eKatie McCormickDevice Profile)</a>. </p>
1087