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:只支持低功耗蓝牙设备

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

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

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

  • 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. @Override
  4. public void onLeScan(final BluetoothDevice device, int rssi, byte[] scanRecord) {
  5. final iBeacon ibeacon = iBeaconClass.fromScanData(device,rssi,scanRecord);
  6. addDevice(ibeacon);
  7. Collections.sort(mLeDevices, new Comparator<iBeacon>() {
  8. @Override
  9. public int compare(iBeacon h1, iBeacon h2) {
  10. return h2.rssi - h1.rssi;
  11. }
  12. });
  13. }
  14. };

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

  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. for(int i=0;i<mLeDevices.size();i++){
  8. String btAddress = mLeDevices.get(i).bluetoothAddress;
  9. if(btAddress.equals(device.bluetoothAddress)){
  10. mLeDevices.add(i+1, device);
  11. mLeDevices.remove(i);
  12. break;
  13. }
  14. }
  15. mLeDevices.add(device);
  16. }

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

  1. public class iBeaconClass {
  2. static public  class iBeacon{
  3. public String name;
  4. public int major;
  5. public int minor;
  6. public String proximityUuid;
  7. public String bluetoothAddress;
  8. public int txPower;
  9. public int rssi;
  10. }
  11. public static iBeacon fromScanData(BluetoothDevice device, int rssi,byte[] scanData) {
  12. int startByte = 2;
  13. boolean patternFound = false;
  14. while (startByte <= 5) {
  15. if (((int)scanData[startByte+2] & 0xff) == 0x02 &&
  16. ((int)scanData[startByte+3] & 0xff) == 0x15) {
  17. // yes!  This is an iBeacon
  18. patternFound = true;
  19. break;
  20. }
  21. else if (((int)scanData[startByte] & 0xff) == 0x2d &&
  22. ((int)scanData[startByte+1] & 0xff) == 0x24 &&
  23. ((int)scanData[startByte+2] & 0xff) == 0xbf &&
  24. ((int)scanData[startByte+3] & 0xff) == 0x16) {
  25. iBeacon iBeacon = new iBeacon();
  26. iBeacon.major = 0;
  27. iBeacon.minor = 0;
  28. iBeacon.proximityUuid = "00000000-0000-0000-0000-000000000000";
  29. iBeacon.txPower = -55;
  30. return iBeacon;
  31. }
  32. else if (((int)scanData[startByte] & 0xff) == 0xad &&
  33. ((int)scanData[startByte+1] & 0xff) == 0x77 &&
  34. ((int)scanData[startByte+2] & 0xff) == 0x00 &&
  35. ((int)scanData[startByte+3] & 0xff) == 0xc6) {
  36. iBeacon iBeacon = new iBeacon();
  37. iBeacon.major = 0;
  38. iBeacon.minor = 0;
  39. iBeacon.proximityUuid = "00000000-0000-0000-0000-000000000000";
  40. iBeacon.txPower = -55;
  41. return iBeacon;
  42. }
  43. startByte++;
  44. }
  45. if (patternFound == false) {
  46. // This is not an iBeacon
  47. return null;
  48. }
  49. iBeacon iBeacon = new iBeacon();
  50. iBeacon.major = (scanData[startByte+20] & 0xff) * 0x100 + (scanData[startByte+21] & 0xff);
  51. iBeacon.minor = (scanData[startByte+22] & 0xff) * 0x100 + (scanData[startByte+23] & 0xff);
  52. iBeacon.txPower = (int)scanData[startByte+24]; // this one is signed
  53. iBeacon.rssi = rssi;
  54. // AirLocate:
  55. // 02 01 1a 1a ff 4c 00 02 15  # Apple's fixed iBeacon advertising prefix
  56. // e2 c5 6d b5 df fb 48 d2 b0 60 d0 f5 a7 10 96 e0 # iBeacon profile uuid
  57. // 00 00 # major
  58. // 00 00 # minor
  59. // c5 # The 2's complement of the calibrated Tx Power
  60. // Estimote:
  61. // 02 01 1a 11 07 2d 24 bf 16
  62. // 394b31ba3f486415ab376e5c0f09457374696d6f7465426561636f6e00000000000000000000000000000000000000000000000000
  63. byte[] proximityUuidBytes = new byte[16];
  64. System.arraycopy(scanData, startByte+4, proximityUuidBytes, 0, 16);
  65. String hexString = bytesToHexString(proximityUuidBytes);
  66. StringBuilder sb = new StringBuilder();
  67. sb.append(hexString.substring(0,8));
  68. sb.append("-");
  69. sb.append(hexString.substring(8,12));
  70. sb.append("-");
  71. sb.append(hexString.substring(12,16));
  72. sb.append("-");
  73. sb.append(hexString.substring(16,20));
  74. sb.append("-");
  75. sb.append(hexString.substring(20,32));
  76. iBeacon.proximityUuid = sb.toString();
  77. if (device != null) {
  78. iBeacon.bluetoothAddress = device.getAddress();
  79. iBeacon.name = device.getName();
  80. }
  81. return iBeacon;
  82. }
  83. public static String bytesToHexString(byte[] src){
  84. StringBuilder stringBuilder = new StringBuilder("");
  85. if (src == null || src.length <= 0) {
  86. return null;
  87. }
  88. for (int i = 0; i < src.length; i++) {
  89. int v = src[i] & 0xFF;
  90. String hv = Integer.toHexString(v);
  91. if (hv.length() < 2) {
  92. stringBuilder.append(0);
  93. }
  94. stringBuilder.append(hv);
  95. }
  96. return stringBuilder.toString();
  97. }
  98. }

Android 开发中 iBeacon的使用的更多相关文章

  1. Android学习探索之Java 8 在Android 开发中的应用

    前言: Java 8推出已经将近2年多了,引入很多革命性变化,加入了函数式编程的特征,使基于行为的编程成为可能,同时减化了各种设计模式的实现方式,是Java有史以来最重要的更新.但是Android上, ...

  2. android开发中fragment获取context

    在用到fragment时无法使用.this来指定当前context内容,android开发中fragment获取context,可以使用getActivity().getApplicationCont ...

  3. java中的反射机制在Android开发中的用处

    JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法:对于任意一个对象,都能够调用它的任意一个方法和属性:这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反 ...

  4. Android开发中的输入合法性检验

    Why ? 合法性检查对于程序的健壮性具有重要作用.在Android开发中,良好的合法性检查设计机制可以使程序更加清晰,产生bug更少,交互更加友好. What ? 合法性检查的目的在于确定边界.对于 ...

  5. 在android开发中使用multdex的方法-IT蓝豹为你整理

    Android系统在安装应用时,往往需要优化Dex,而由于处理工具DexOpt对id数目的限制,导致其处理的数目不能超过65536个,因此在Android开发中,需要使用到MultiDex来解决这个问 ...

  6. 怎样实现了捕获应用中的日志在android开发中

    怎样实现了捕获应用中的日志在android开发中,大家可研究一下. Process mLogcatProc = null; BufferedReader reader = null; try { mL ...

  7. Android开发中Eclispe相关问题及相应解决(持续更新)

    1.Eclipse项目中的Android Private Libraries没有自动生成. 一般而言,在Android开发中,项目中引用到的jar包会放到项目目录中的libs中,引入库会放到Andro ...

  8. Android开发中的问题及相应解决(持续更新)

    最近博客写的少了,以后还得经常更新才行. ------------------------------------------------------------ 1.特定业务需求下try cath ...

  9. 关于Android开发中的证书和密钥等问题

    关于Android开发中的证书和密钥等问题 引言 除了Android发布应用签名时需要用到证书外,在进行google Map Api开发和Facebook SDK API开发等时都需要申请API Ke ...

随机推荐

  1. jQuery开发技术笔记

    HTML DOM 加载步骤    1. 解析 HTML 结构     2.加载外部脚本和样式表文件     3.解析并执行脚本代码     4.构造 HTML DOM 模型     5.加载图片等外部 ...

  2. php Imagick库readImage()报Postscript delegate failed 解决方法(失效)

    需要安装 ghostscript http://www.ghostscript.com/download/gsdnld.html

  3. iOS: 神奇的addSubView

    看着addSubView, 本以为是添加多个对象, 但通过测试代码, 发现同一个对象在addSubView中只会添加一次. 想想, 视图对象是通过引用得到的. 在视图的子视图集中, 只保存一个相应的对 ...

  4. iOS: 学习笔记, Swift名字空间

    在Swift中, 名字空间是用class(extension)嵌套来实现的, 下面用一个简单例子来进行展示 // // main.swift // SwiftNameSpace // // Creat ...

  5. linux下date命令实现时间戳与日期的转换

    1.查看指定时间的时间戳    查看当前时间  #date +%s    查看指定时间  #date -d 2008-01-01 +%s   1199116800  #date -d 20080101 ...

  6. 练习2 I题 - 水仙花数

      Time Limit:1000MS     Memory Limit:32768KB     64bit IO Format:%I64d & %I64u   Description 春天是 ...

  7. hexdump——Linux系统的二进制文件查看工具

    hexdump是Linux下的一个二进制文件查看工具,可以将二进制文件转换为ASCII.10进制.16进制或8进制进行查看. 首先我们准备一个测试用的文件test,十六进制如下: 00 01 02 0 ...

  8. 对rsync进行封装的shell脚本

    抓取 #!/bin/bash . push.sh # 错误处理:尝试查找备份文件 function onError() { local errFile="err" local se ...

  9. golang开发android环境搭建_window

    golang开发android环境搭建介绍 一 安装依赖软件: git:版本管理 go:  go开发环境(版本>=1.5),可直接下载window版的go安装包. android studio: ...

  10. JBoss for luna

    Redhat官方手顺 貌似已经404了,搬运地址 我的Eclipse是Luna,每次进入Eclipse Market去装 http://marketplace.eclipse.org/content/ ...