zoukankan      html  css  js  c++  java
  • Android 开发中 iBeacon的使用

    iBeacon的工作原理是基于Bluetooth Low Energy(BLE)低功耗蓝牙传输技术,iBeacon基站不断向四周发送蓝牙信号,当智能设备进入设定区域时,就能够收到信号。只要满足iBeacon技术标准的都可以使用,所以Android也能够支持iBeacon。Google在Android4.3中支持BLE技术

    定位一直是非常关键的功能。通过iBeacon基站的部署能够实现室内导航,同时通过蓝牙推送信息,iBeacon在商场零售或者一些公共服务领域如体育馆、博物馆能提供非常棒的体验。尤其是蓝牙不错传输距离、低功耗、以及信号加密使得iBeacon在移动支付领域也非常有前景。总之,iBeacon的潜力似乎是无穷大,也受到了越来越多的关注。

    要了解iBeacon是如何工作首先我们要了解BLE。BLE(也称为Bluetooth Smart)最早追溯到Nokia于2006年提出的Wibree,后来融合进了蓝牙标准,成为Bluetooth4.0的一部分。目前我们经常能看到3种蓝牙设备:

    • Bluetooth:只支持传统模式的蓝牙设备
    • Bluetooth Smart Ready:支持传统和低功耗两种模式设备
    • Bluetooth Smart:只支持低功耗蓝牙设备

    estimote-ibeacon-teardown2

    BLE与传统的蓝牙相比最大的优势是功耗降低90%,同时传输距离增大(超过100米)、安全和稳定性提高(支持AES加密和CRC验证)。iBeacon同时有一些自己的特点:

    • 无需配对,一般蓝牙设备印象中都需要配对工作。iBeacon无需配对,因为它是采用蓝牙的广播频道传送信号。
    • 程序可以后台唤醒,iBeacon的信息推送需要App支持。但是我们接收iBeacon信号无需打开App,只要保证安装了,同时手机蓝牙打开。

    iBeacon是如何工作呢?实际上iBeacon基站通过蓝牙的广播频道不断向外发送位置信息,发送频率越快越耗电。也就是说iBeacon并不推送消息,而只是用于定位,推送消息的功能必须由App来完成。苹果定义了iBeacon 其中32位广播的数据格式。

    estimote-ibeacon-teardown3

    • UUID:厂商识别号
    • Major:相当于群组号,同一个组里Beacon有相同的Major
    • Minor:相当于识别群组里单个的Beacon
    • TX Power:用于测量设备离Beacon的距离

    UUID+Major+Minor就构成了一个Beacon的识别号,有点类似于网络中的IP地址。TX Power用于测距,iBeacon目前只定义了大概的3个粗略级别:

    • 非常近(Immediate): 大概10厘米内
    • 近(Near):1米内
    • 远(Far):1米外

    这里主要是对其用法做一个介绍:

    首先是获取BluetoothAdapter对象:

    1. final BluetoothManager bluetoothManager =  
    2.                 (BluetoothManager) getSystemService(Context.BLUETOOTH_SERVICE);  
    3.         mBluetoothAdapter = bluetoothManager.getAdapter();  
    4.         mBluetoothAdapter.startLeScan(mLeScanCallback);  


    然后就是它的回调,在这里对搜索到的iBeacon设备距手机的信号强度做了一个排序

    1. private BluetoothAdapter.LeScanCallback mLeScanCallback =  
    2.             new BluetoothAdapter.LeScanCallback() {  
    3.   
    4.         @Override  
    5.         public void onLeScan(final BluetoothDevice device, int rssi, byte[] scanRecord) {  
    6.             final iBeacon ibeacon = iBeaconClass.fromScanData(device,rssi,scanRecord);  
    7.             addDevice(ibeacon);  
    8.             Collections.sort(mLeDevices, new Comparator<iBeacon>() {  
    9.                 @Override  
    10.                 public int compare(iBeacon h1, iBeacon h2) {  
    11.                     return h2.rssi - h1.rssi;  
    12.                 }  
    13.             });  
    14.         }  
    15.     };  

    最后把搜索到的数据添加到集合中去

    1. private ArrayList<iBeacon> mLeDevices = new ArrayList<iBeacon>();  
    2.     private void addDevice(iBeacon device) { //更新beacon信息  
    3.         if(device==null) {  
    4.             Log.d("DeviceScanActivity ", "device==null ");  
    5.             return;  
    6.         }  
    7.           
    8.         for(int i=0;i<mLeDevices.size();i++){  
    9.             String btAddress = mLeDevices.get(i).bluetoothAddress;  
    10.             if(btAddress.equals(device.bluetoothAddress)){  
    11.                 mLeDevices.add(i+1, device);  
    12.                 mLeDevices.remove(i);  
    13.                 break;  
    14.             }   
    15.         }  
    16.         mLeDevices.add(device);  
    17.           
    18.     }  

    我们在iBbeaconClass类中对其进行数据的解析处理,参考:https://github.com/AltBeacon/android-beacon-library

      1. public class iBeaconClass {  
      2.   
      3.     static public  class iBeacon{  
      4.         public String name;  
      5.         public int major;  
      6.         public int minor;  
      7.         public String proximityUuid;  
      8.         public String bluetoothAddress;  
      9.         public int txPower;  
      10.         public int rssi;  
      11.     }  
      12.     public static iBeacon fromScanData(BluetoothDevice device, int rssi,byte[] scanData) {  
      13.   
      14.         int startByte = 2;  
      15.         boolean patternFound = false;  
      16.         while (startByte <= 5) {  
      17.             if (((int)scanData[startByte+2] & 0xff) == 0x02 &&  
      18.                 ((int)scanData[startByte+3] & 0xff) == 0x15) {            
      19.                 // yes!  This is an iBeacon   
      20.                 patternFound = true;  
      21.                 break;  
      22.             }  
      23.             else if (((int)scanData[startByte] & 0xff) == 0x2d &&  
      24.                     ((int)scanData[startByte+1] & 0xff) == 0x24 &&  
      25.                     ((int)scanData[startByte+2] & 0xff) == 0xbf &&  
      26.                     ((int)scanData[startByte+3] & 0xff) == 0x16) {  
      27.                 iBeacon iBeacon = new iBeacon();  
      28.                 iBeacon.major = 0;  
      29.                 iBeacon.minor = 0;  
      30.                 iBeacon.proximityUuid = "00000000-0000-0000-0000-000000000000";  
      31.                 iBeacon.txPower = -55;  
      32.                 return iBeacon;  
      33.             }  
      34.             else if (((int)scanData[startByte] & 0xff) == 0xad &&  
      35.                      ((int)scanData[startByte+1] & 0xff) == 0x77 &&  
      36.                      ((int)scanData[startByte+2] & 0xff) == 0x00 &&  
      37.                      ((int)scanData[startByte+3] & 0xff) == 0xc6) {  
      38.                      
      39.                     iBeacon iBeacon = new iBeacon();  
      40.                     iBeacon.major = 0;  
      41.                     iBeacon.minor = 0;  
      42.                     iBeacon.proximityUuid = "00000000-0000-0000-0000-000000000000";  
      43.                     iBeacon.txPower = -55;  
      44.                     return iBeacon;  
      45.             }  
      46.             startByte++;  
      47.         }  
      48.   
      49.   
      50.         if (patternFound == false) {  
      51.             // This is not an iBeacon  
      52.             return null;  
      53.         }  
      54.   
      55.         iBeacon iBeacon = new iBeacon();  
      56.   
      57.         iBeacon.major = (scanData[startByte+20] & 0xff) * 0x100 + (scanData[startByte+21] & 0xff);  
      58.         iBeacon.minor = (scanData[startByte+22] & 0xff) * 0x100 + (scanData[startByte+23] & 0xff);  
      59.         iBeacon.txPower = (int)scanData[startByte+24]; // this one is signed  
      60.         iBeacon.rssi = rssi;  
      61.   
      62.         // AirLocate:  
      63.         // 02 01 1a 1a ff 4c 00 02 15  # Apple's fixed iBeacon advertising prefix  
      64.         // e2 c5 6d b5 df fb 48 d2 b0 60 d0 f5 a7 10 96 e0 # iBeacon profile uuid  
      65.         // 00 00 # major   
      66.         // 00 00 # minor   
      67.         // c5 # The 2's complement of the calibrated Tx Power  
      68.   
      69.         // Estimote:          
      70.         // 02 01 1a 11 07 2d 24 bf 16   
      71.         // 394b31ba3f486415ab376e5c0f09457374696d6f7465426561636f6e00000000000000000000000000000000000000000000000000  
      72.   
      73.         byte[] proximityUuidBytes = new byte[16];  
      74.         System.arraycopy(scanData, startByte+4, proximityUuidBytes, 0, 16);   
      75.         String hexString = bytesToHexString(proximityUuidBytes);  
      76.         StringBuilder sb = new StringBuilder();  
      77.         sb.append(hexString.substring(0,8));  
      78.         sb.append("-");  
      79.         sb.append(hexString.substring(8,12));  
      80.         sb.append("-");  
      81.         sb.append(hexString.substring(12,16));  
      82.         sb.append("-");  
      83.         sb.append(hexString.substring(16,20));  
      84.         sb.append("-");  
      85.         sb.append(hexString.substring(20,32));  
      86.         iBeacon.proximityUuid = sb.toString();  
      87.   
      88.         if (device != null) {  
      89.             iBeacon.bluetoothAddress = device.getAddress();  
      90.             iBeacon.name = device.getName();  
      91.         }  
      92.   
      93.         return iBeacon;  
      94.     }  
      95.   
      96.     public static String bytesToHexString(byte[] src){    
      97.         StringBuilder stringBuilder = new StringBuilder("");    
      98.         if (src == null || src.length <= 0) {    
      99.             return null;    
      100.         }    
      101.         for (int i = 0; i < src.length; i++) {    
      102.             int v = src[i] & 0xFF;    
      103.             String hv = Integer.toHexString(v);    
      104.             if (hv.length() < 2) {    
      105.                 stringBuilder.append(0);    
      106.             }    
      107.             stringBuilder.append(hv);    
      108.         }    
      109.         return stringBuilder.toString();    
      110.     }    
  • 相关阅读:
    Asp.Net Web API 2第八课——Web API 2中的属性路由
    Asp.Net Web API 2第七课——Web API异常处理
    Asp.Net Web API 2第六课——Web API路由和动作选择
    Asp.Net Web API 2第五课——Web API路由
    开始学习python
    BMI 小程序 购物车
    深浅copy 文件操作
    字典 dict 集合set
    基本数据类型 (str,int,bool,tuple,)
    python 运算符
  • 原文地址:https://www.cnblogs.com/Free-Thinker/p/6098929.html
Copyright © 2011-2022 走看看