# FastBle?
Android Bluetooth Low Energy?藍(lán)牙快速開(kāi)發(fā)框架。?
使用簡(jiǎn)單的方式進(jìn)行搜索、連接、讀寫(xiě)、通知的訂閱與取消等一系列藍(lán)牙操作,并實(shí)時(shí)地得到操作反饋。?
Gradle:?
Implementation 'com.clj.fastble:FastBleLib:1.2.1'?
FastBle requires at minimum Java 7 or Android 4.0.?
#?藍(lán)牙操作經(jīng)驗(yàn)及FastBle的兼容性說(shuō)明?
1.BLE是藍(lán)牙4.0里面的低功耗規(guī)范,Android 4.3以上的系統(tǒng)開(kāi)始搭載BLE模塊,所以FastBle也只支持4.3以上。?
2.不排除某些特殊設(shè)備的定制系統(tǒng)去除了BLE模塊的情況,使用之前可以先判斷當(dāng)前設(shè)備是否支持BLE,再進(jìn)行后續(xù)操作。?
3.藍(lán)牙設(shè)備相關(guān)程序必須使用真機(jī)才能運(yùn)行。?
4.?FastBle當(dāng)前版本僅支持對(duì)BLE藍(lán)牙進(jìn)行操作,不支持經(jīng)典藍(lán)牙。?
5.?使用藍(lán)牙功能,必須先聲明藍(lán)牙相關(guān)的權(quán)限。Android 6.0以上的系統(tǒng),需要額外申請(qǐng)位置相關(guān)的權(quán)限,并且是危險(xiǎn)權(quán)限建議在運(yùn)行時(shí)動(dòng)態(tài)獲取。為使使用更靈活,F(xiàn)astBle庫(kù)中并不包含權(quán)限相關(guān)的操作,使用者根據(jù)程序的實(shí)際情況在外層自行嵌套。示例代碼中有相關(guān)代碼演示,供參考。?
5.藍(lán)牙操作與硬件關(guān)聯(lián)很大,開(kāi)發(fā)過(guò)程中要保持和硬件協(xié)議的溝通,某些問(wèn)題的解決需要硬件方面做一些適配。?
6.?BLE的MTU(最大傳輸單元)是20字節(jié),即一次最多能發(fā)送20個(gè)字節(jié),若超過(guò)20個(gè)字節(jié),建議采用分包傳輸?shù)姆绞健?
7.藍(lán)牙連接之后,列出當(dāng)前外設(shè)模塊的所有service,每個(gè)service可能有一個(gè)或多個(gè)的characteristic,每一個(gè)characteristic有其對(duì)應(yīng)的property(即可操作的屬性類(lèi)別),假如一個(gè)characteristic的property對(duì)應(yīng)的是write,那么對(duì)這個(gè)characteristic做notify處理顯然是行不通的。?
8.兩次操作之間最好間隔一小段時(shí)間,如100ms(具體時(shí)間可以根據(jù)自己實(shí)際藍(lán)牙外設(shè)自行嘗試延長(zhǎng)或縮短)。舉例,連接成功之后,延遲100ms進(jìn)行notify,成功之后延遲100ms進(jìn)行write,write成功之后,notify的數(shù)據(jù)回調(diào)接口將返回外設(shè)傳輸過(guò)來(lái)的數(shù)據(jù)。?
9.?FastBle中開(kāi)放的藍(lán)牙操作的相關(guān)方法均要求在主線(xiàn)程中執(zhí)行。?
10.一個(gè)簡(jiǎn)單的使用場(chǎng)景:打開(kāi)藍(lán)牙,在主線(xiàn)程掃描設(shè)備,連接,連接成功并發(fā)現(xiàn)服務(wù)之后,在`onServicesDiscovered`的異步回調(diào)方法中,延時(shí)100ms,再切換到主線(xiàn)程,再去調(diào)用notify、write等方法。這就是一個(gè)基本的操作。?
11.?連接及連接后的過(guò)程中,時(shí)刻關(guān)注BleGattCallback,藍(lán)牙的連接情況會(huì)實(shí)時(shí)反映在其各個(gè)回調(diào)方法中,尤其是`onDisConnected`方法。?
12.連接過(guò)程中,假如外設(shè)突然中斷(或關(guān)閉)了藍(lán)牙,Android設(shè)備維持的BLE連接并不會(huì)馬上回調(diào)`onDisConnected`方法,而是會(huì)延遲一段時(shí)間才會(huì)通知連接斷開(kāi),開(kāi)發(fā)時(shí)需注意,假如對(duì)實(shí)時(shí)性要求較高的程序,可能需要借助其他輔助方法來(lái)判斷設(shè)備是否中斷,比如心跳包等。?
13.?藍(lán)牙應(yīng)用開(kāi)發(fā)中,存在兩種角色,分別是central和peripheral ,中文就是中心和外設(shè)。比如手機(jī)去連接智能設(shè)備,那手機(jī)就是central,智能設(shè)備就是peripheral。?
14.FastBle當(dāng)前版本僅支持中心模式?(central model),即"以App作為中心,連接其他BLE外設(shè)"。把手機(jī)作為外設(shè)目前版本是行不通的。?
15.連接之后的操作有:write,read,notify,indicate,response or not等。indicate和notify的區(qū)別就在于,indicate是一定會(huì)收到數(shù)據(jù),notify有可能會(huì)丟失數(shù)據(jù)(不會(huì)有central收到數(shù)據(jù)的回應(yīng)),write也分為response和no response,如果是response,那么write成功回收到peripheral的確認(rèn)消息,但是會(huì)降低寫(xiě)入的速率,換一個(gè)角度說(shuō)就是?write no response寫(xiě)的速率更快。?
16.?連接斷開(kāi)之后的重連很簡(jiǎn)單,在`void onDisConnected(BluetoothGatt gatt, int status, BleException exception)`調(diào)用`boolean gatt.connect()`方法即可,當(dāng)外設(shè)再次處于可連接狀態(tài)時(shí),就會(huì)自動(dòng)連上。?
17.連接斷開(kāi)之后可以根據(jù)實(shí)際情況進(jìn)行重連,但如果是連接失敗的情況,建議不要立即重連,而是調(diào)用`void closeBluetoothGatt()`清空一下?tīng)顟B(tài),并延遲一段時(shí)間等待復(fù)位,否則會(huì)把gatt阻塞,導(dǎo)致手機(jī)不重啟藍(lán)牙就再也無(wú)法連接任何設(shè)備的嚴(yán)重情況。?
18.?調(diào)用`bleManager.closeBluetoothGatt()`之后,最好不要緊接著調(diào)用`bleManager = null`,因?yàn)锳ndroid原生藍(lán)牙API中的`gatt.close()`方法需要一段時(shí)間保證完成,我們建議延遲一段時(shí)間。延時(shí)操作在Android藍(lán)牙開(kāi)發(fā)中是一個(gè)重要的技巧。?
19.很多Android設(shè)備是可以強(qiáng)制打開(kāi)用戶(hù)手機(jī)藍(lán)牙的,打開(kāi)藍(lán)牙需要一段時(shí)間(部分手機(jī)上需要向用戶(hù)請(qǐng)求)。雖然時(shí)間比較短,但也不能調(diào)用完打開(kāi)藍(lán)牙方法后直接去調(diào)用掃描方法,此時(shí)藍(lán)牙多半是還未開(kāi)啟完畢狀態(tài)。建議的做法是維持一個(gè)藍(lán)牙狀態(tài)的廣播,調(diào)用打開(kāi)藍(lán)牙方法后,在一段時(shí)間內(nèi)阻塞線(xiàn)程,如果在這段時(shí)間內(nèi)收到藍(lán)牙打開(kāi)廣播后,再進(jìn)行后續(xù)操作。而后續(xù)操作過(guò)程中,如果收到藍(lán)牙正在關(guān)閉或關(guān)閉的廣播,也可以及時(shí)對(duì)當(dāng)前的情況做一個(gè)妥善處理。?