Android檢測IBeacon熱點的方法
IBeacon是BLE的一種,搜索iBeacon基站關(guān)鍵在于設(shè)備掃描到的scanRecord數(shù)組,識別是否有下面加粗斜體的02 15這兩個數(shù)字。如果有,搜索到的藍(lán)牙設(shè)備就是IBeacon。
// AirLocate:
// 02 01 1a 1a ff 4c 00 02 15 # Apple's fixed iBeacon advertising prefix
// e2 c5 6d b5 df fb 48 d2 b0 60 d0 f5 a7 10 96 e0 # iBeacon profile uuid
// 00 00 # major
// 00 00 # minor
// c5 # The 2's complement of the calibrated Tx Power
下面分步驟來實現(xiàn)檢測IBeacon熱點。
一、獲得手機藍(lán)牙控制權(quán)限
在manifest 文件中寫上:
<uses-permission android:name="android.permission.BLUETOOTH"/> <uses-permission android:name="android.permission.BLUETOOTH_ADMIN"/>
二、檢測手機是否支持藍(lán)牙,并獲取mBluetoothAdapter 對象
if (!getPackageManager().hasSystemFeature(
PackageManager.FEATURE_BLUETOOTH_LE))
{
Toast.makeText(this, R.string.ble_not_supported, Toast.LENGTH_SHORT)
.show();
finish();
}
final BluetoothManager bluetoothManager = (BluetoothManager) getSystemService(Context.BLUETOOTH_SERVICE);
mBluetoothAdapter = bluetoothManager.getAdapter();
if (mBluetoothAdapter == null)
{
Toast.makeText(this, R.string.error_bluetooth_not_supported,
Toast.LENGTH_SHORT).show();
finish();
return;
}
三、實現(xiàn)LeScanCallback回調(diào)接口
設(shè)備每次檢測到一個藍(lán)牙設(shè)備,就會回調(diào)這個接口中的onLeScan()方法,并且傳入掃描到的device,rssi,scanRecord等參數(shù)。
private BluetoothAdapter.LeScanCallback mLeScanCallback = new BluetoothAdapter.LeScanCallback()
{
@Override
public void onLeScan(final BluetoothDevice device, int rssi,
byte[] scanRecord)
{
//在這里處理掃描到的參數(shù)
//判斷是不是IBeacon設(shè)備,做相應(yīng)的處理。
}
};
四、處理掃描到的參數(shù)的方法
public class iBeaconClass
{
static public class iBeacon
{
public String name;
public int major;
public int minor;
public String proximityUuid;
public String bluetoothAddress;
public int txPower;
public int rssi;
}
/**
* 將掃描到的信息傳入這個方法
* 該方法會判斷掃描到的設(shè)備是不是IBeacon
* 如果是就返回一個IBeacon對象
* 如果不是就返回null
* @param device
* @param rssi
* @param scanData
* @return
*/
public static iBeacon fromScanData(BluetoothDevice device, int rssi,
byte[] scanData)
{
int startByte = 2;
boolean patternFound = false;
while (startByte <= 5)
{
if (((int) scanData[startByte + 2] & 0xff) == 0x02
&& ((int) scanData[startByte + 3] & 0xff) == 0x15)
{
// yes! This is an iBeacon
patternFound = true;
break;
} else if (((int) scanData[startByte] & 0xff) == 0x2d
&& ((int) scanData[startByte + 1] & 0xff) == 0x24
&& ((int) scanData[startByte + 2] & 0xff) == 0xbf
&& ((int) scanData[startByte + 3] & 0xff) == 0x16)
{
iBeacon iBeacon = new iBeacon();
iBeacon.major = 0;
iBeacon.minor = 0;
iBeacon.proximityUuid = "00000000-0000-0000-0000-000000000000";
iBeacon.txPower = -55;
return iBeacon;
} else if (((int) scanData[startByte] & 0xff) == 0xad
&& ((int) scanData[startByte + 1] & 0xff) == 0x77
&& ((int) scanData[startByte + 2] & 0xff) == 0x00
&& ((int) scanData[startByte + 3] & 0xff) == 0xc6)
{
iBeacon iBeacon = new iBeacon();
iBeacon.major = 0;
iBeacon.minor = 0;
iBeacon.proximityUuid = "00000000-0000-0000-0000-000000000000";
iBeacon.txPower = -55;
return iBeacon;
}
startByte++;
}
if (patternFound == false)
{
// This is not an iBeacon
return null;
}
iBeacon iBeacon = new iBeacon();
iBeacon.major = (scanData[startByte + 20] & 0xff) * 0x100
+ (scanData[startByte + 21] & 0xff);
iBeacon.minor = (scanData[startByte + 22] & 0xff) * 0x100
+ (scanData[startByte + 23] & 0xff);
iBeacon.txPower = (int) scanData[startByte + 24]; // this one is signed
iBeacon.rssi = rssi;
// AirLocate:
// 02 01 1a 1a ff 4c 00 02 15 # Apple's fixed iBeacon advertising prefix
// e2 c5 6d b5 df fb 48 d2 b0 60 d0 f5 a7 10 96 e0 # iBeacon profile
// uuid
// 00 00 # major
// 00 00 # minor
// c5 # The 2's complement of the calibrated Tx Power
// Estimote:
// 02 01 1a 11 07 2d 24 bf 16
// 394b31ba3f486415ab376e5c0f09457374696d6f7465426561636f6e00000000000000000000000000000000000000000000000000
byte[] proximityUuidBytes = new byte[16];
System.arraycopy(scanData, startByte + 4, proximityUuidBytes, 0, 16);
String hexString = bytesToHexString(proximityUuidBytes);
StringBuilder sb = new StringBuilder();
sb.append(hexString.substring(0, 8));
sb.append("-");
sb.append(hexString.substring(8, 12));
sb.append("-");
sb.append(hexString.substring(12, 16));
sb.append("-");
sb.append(hexString.substring(16, 20));
sb.append("-");
sb.append(hexString.substring(20, 32));
iBeacon.proximityUuid = sb.toString();
if (device != null)
{
iBeacon.bluetoothAddress = device.getAddress();
iBeacon.name = device.getName();
}
return iBeacon;
}
private static String bytesToHexString(byte[] src)
{
StringBuilder stringBuilder = new StringBuilder("");
if (src == null || src.length <= 0)
{
return null;
}
for (int i = 0; i < src.length; i++)
{
int v = src[i] & 0xFF;
String hv = Integer.toHexString(v);
if (hv.length() < 2)
{
stringBuilder.append(0);
}
stringBuilder.append(hv);
}
return stringBuilder.toString();
}
}
五、開啟藍(lán)牙
mBluetoothAdapter.enable();
六、開始掃描
mBluetoothAdapter.startLeScan(mLeScanCallback);
代碼改自鏈接地址
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
- android獲取ibeacon列表的方法
- Android提高之BLE開發(fā)Android手機搜索iBeacon基站
- Android藍(lán)牙開發(fā)深入解析
- 詳解Android——藍(lán)牙技術(shù) 帶你實現(xiàn)終端間數(shù)據(jù)傳輸
- Android Bluetooth藍(lán)牙技術(shù)使用流程詳解
- Android單片機與藍(lán)牙模塊通信實例代碼
- 分享Android 藍(lán)牙4.0(ble)開發(fā)的解決方案
- android實現(xiàn)藍(lán)牙文件發(fā)送的實例代碼,支持多種機型
- Android手機通過藍(lán)牙連接佳博打印機的實例代碼
- Android基于ibeacon實現(xiàn)藍(lán)牙考勤功能
相關(guān)文章
Android開發(fā)之圖形圖像與動畫(三)Animation效果的XML實現(xiàn)
使用XML來定義Tween Animation動畫的XML文件在工程中res/anim目錄,這個文件必須包含一個根元素,感興趣的友可以了解一下,希望本文對你有所幫助2013-01-01
Android控件Spinner實現(xiàn)下拉列表及監(jiān)聽功能
這篇文章主要介紹了Android控件Spinner實現(xiàn)下拉列表及監(jiān)聽功能,這是在Web開發(fā)中一個必不可少的交互性組件,而在Android中的對應(yīng)實現(xiàn)就是Spinner。需要的朋友可以參考下2018-07-07
Android開發(fā)中的文件操作工具類FileUtil完整實例
這篇文章主要介紹了Android開發(fā)中的文件操作工具類FileUtil,結(jié)合完整實例形式分析了Android文件操作的常用技巧,包括文件的獲取、遍歷、搜索、復(fù)制、刪除、判斷等功能,需要的朋友可以參考下2017-11-11
2013年 移動App設(shè)計13項注意細(xì)節(jié)總結(jié)
在過去的一年里,移動成主流也讓眾多的移動應(yīng)用如雨后春筍般層出不窮,在眾多開發(fā)者從中獲利的同時競爭也愈演愈烈,如何才能保證自己立于不敗之地接下來介紹移動App設(shè)計的13大精髓感興趣的朋友可以了解下啊2013-01-01
Android實現(xiàn)數(shù)據(jù)按照時間排序
這篇文章主要為大家詳細(xì)介紹了Android實現(xiàn)數(shù)據(jù)按照時間排序的方法,具有一定的參考價值,感興趣的小伙伴們可以參考一下2018-09-09

