Android检测IBeacon热点的方法

2020-11-04 15:56:59 浏览数 (2)

IBeacon是BLE的一种,搜索iBeacon基站关键在于设备扫描到的scanRecord数组,识别是否有下面加粗斜体的02 15这两个数字。如果有,搜索到的蓝牙设备就是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

下面分步骤来实现检测IBeacon热点。

一、获得手机蓝牙控制权限

在manifest 文件中写上:

代码语言:javascript复制
<uses-permission android:name="android.permission.BLUETOOTH"/ 
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN"/ 

二、检测手机是否支持蓝牙,并获取mBluetoothAdapter 对象

代码语言:javascript复制
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;
    }

三、实现LeScanCallback回调接口

设备每次检测到一个蓝牙设备,就会回调这个接口中的onLeScan()方法,并且传入扫描到的device,rssi,scanRecord等参数。

代码语言:javascript复制
private BluetoothAdapter.LeScanCallback mLeScanCallback = new BluetoothAdapter.LeScanCallback()
  {
    @Override
    public void onLeScan(final BluetoothDevice device, int rssi,
        byte[] scanRecord)
    {
      //在这里处理扫描到的参数
      //判断是不是IBeacon设备,做相应的处理。
    }
  };

四、处理扫描到的参数的方法

代码语言:javascript复制
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;
}
/**
* 将扫描到的信息传入这个方法
* 该方法会判断扫描到的设备是不是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();
}
}

五、开启蓝牙

mBluetoothAdapter.enable();

六、开始扫描

mBluetoothAdapter.startLeScan(mLeScanCallback);

代码改自链接地址

以上就是本文的全部内容,希望对大家的学习有所帮助。

0 人点赞