安卓蓝牙通讯
需要說明的是,該通訊是安卓手機與藍牙模塊之間的通訊。
通訊的步驟如下
通過得到的BluetoothSocket對象,進行數據的讀寫。
下面我就分別寫下這幾個步驟。
1,得到本地的藍牙適配器并且打開藍牙
1.1得到本地藍牙適配器:
1.2打開藍牙
// 如果藍牙沒有打開,通過這個Activity打開if (!adapter.isEnabled()) {Intent intent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);startActivity(intent);}Intent enable = new Intent(BluetoothAdapter.ACTION_REQUEST_DISCOVERABLE);// 300為可以被其他藍牙設備搜索到的時間,單位為秒enable.putExtra(BluetoothAdapter.EXTRA_DISCOVERABLE_DURATION, 300); startActivityForResult(enable, DISCOVERY_REQUEST);2,掃描周圍的設備
通過BluetoothAdapter 的startDiscovery()進行掃描,找到一個設備,就會發出一條廣播,所以找到的新設備要在廣播接收器里面進行接收。
掃描的時間會比較長,一般會持續十多秒。
3,通過廣播接收器找到掃描到的新設備。
前面已經說了,如果adapter發現新的設備,就會發出廣播。因此我們需要在廣播接收器里面得到新設備。
BluetoothDevice對象就是發現的新設備,BluetoothDevice有好多方法,比如通過bluetoothdevice.getName()獲取新設備名稱。通過bluetoothdevice.getAddress()獲取設備的硬件地址,比如“00:11:22:AA:BB:CC”。當然還有其他的方法,這里不再多說。
發現的新設備可以顯示到一個列表里面。這里只是說明原理,列表顯示在源碼里面。
當然,最后需要對廣播接收器進行注冊。
IntentFilter filter = new IntentFilter(BluetoothDevice.ACTION_FOUND); registerReceiver(mReceiver, filter);4,得到BluetoothSocket。
需要說明的是,這里手機是作為客戶端來使用。如果是作為服務端,得到Socket的方法會有所不同。
無論手機是作為客戶端還是服務端,在和其他設備連接過程中,都需要UUID,下面簡單地介紹下UUID。
UUID
UUID 含義是通用唯一識別碼 (Universally Unique Identifier),這 是一個軟件建構的標
準,也是被開源軟件基金會 (Open Software Foundation, OSF) 的組織應用在分布式計算環境 (Distributed Computing Environment, DCE) 領域的一部分。
在藍牙 3.0 及一下版本中,UUID 被用于唯一標識一個服務,比如文件傳輸服務,串口服務、打印機服務等,如下:
藍牙串口服務
SerialPortServiceClass_UUID = ‘{00001101-0000-1000-8000-00805F9B34FB}’
LANAccessUsingPPPServiceClass_UUID = ‘{00001102-0000-1000-8000-00805F9B34FB}’
撥號網絡服務
DialupNetworkingServiceClass_UUID = ‘{00001103-0000-1000-8000-00805F9B34FB}’
信息同步服務
IrMCSyncServiceClass_UUID = ‘{00001104-0000-1000-8000-00805F9B34FB}’
SDP_OBEXObjectPushServiceClass_UUID = ‘{00001105-0000-1000-8000-00805F9B34FB}’
文件傳輸服務
OBEXFileTransferServiceClass_UUID = ‘{00001106-0000-1000-8000-00805F9B34FB}’
IrMCSyncCommandServiceClass_UUID = ‘{00001107-0000-1000-8000-00805F9B34FB}’
因為我們和藍牙模塊進行通訊,所以選擇藍牙串口服務的UUID。
通過UUID建立連接
private static String uuid = "00001101-0000-1000-8000-00805F9B34FB"; try{ //device為BluetoothDevice 對象,即掃描到的新設備對象 BluetoothSocket mmSocket=device.createRfcommSocketToServiceRecord(UUID.fromString(uuid)); } catch(IOException e){ }得到BluetoothSocket 之后,就可以在兩臺設備之間建立連接,在連接之前,我們最好取消上面開啟的掃描功能功能。
//adapter是BluetoothAdapter 的對象。 adapter.cancelDiscovery();進行連接:
try{ //這個方法是阻塞式的,所以最好開一個線程進行連接。在這里可以寫一個回調,連接成功后,就可以通過該socket讀寫數據了,詳細的代碼見源碼。mmSocket.connect(); }catch(Exception e){ //連接過程中若拋出異常,則關閉socket。try {mmSocket.close();} catch (Exception e1) {Log.e("close", e1.toString());} }5,通過BluetoothSocket 對象讀寫數據。
收到數據后,通過Handler 發送message來刷新界面。
public class ConnectedThread extends Thread {private final BluetoothSocket mmSocket;private final InputStream mmInStream;private final OutputStream mmOutStream;public String datas;public Message message;public Handler handler;//輸入輸出流的初始化public ConnectedThread(BluetoothSocket socket,Handler handlers) {mmSocket = socket;this.handler=handlers;InputStream tmpIn = null;OutputStream tmpOut = null;try {tmpIn = socket.getInputStream();tmpOut = socket.getOutputStream();} catch (IOException e) {}mmInStream = tmpIn;mmOutStream = tmpOut;}/*** 接收數據,線程*/public void run() {byte[] buffer = new byte[2048];int bytes;while (true) {try {bytes = mmInStream.read(buffer);String str= new String(buffer,"ISO-8859-1");str=str.substring(0,bytes);datas=str;message=new Message();message.what=Constant.DATAS;handler.sendMessage(message);} catch (IOException e) {break;}}}public void write(byte[] bytes) {try {mmOutStream.write(bytes);} catch (IOException e) {}}}6,其他
關于將手機作為服務端我沒有嘗試過,下面是連接的代碼:
private static String uuid = "00001101-0000-1000-8000-00805F9B34FB"; //adapter是BluetoothAdapter 的對象。 BluetoothServerSocket =adapter.listenUsingRfcommWithServiceRecord("blue",UUID.fromString(uuid));//連接之前會一直等待,所以要開啟一個線程 while (true) { try { BluetoothSocket socket = mmServerSocket.accept(); } catch (IOException e) { break; } }拿到BluetoothSocket之后,就可以進行通訊了,通訊的代碼和作為客戶端連接設備應該是一樣的。我沒有嘗試過。
7,源碼下載
源碼下載
總結
- 上一篇: 老鼠的旅行
- 下一篇: centos7.5 挂载超过2T的大硬盘