【问题标题】:How to broadcast iBeacon with the BluetoothLeScanner class?如何使用 BluetoothLeScanner 类广播 iBeacon?
【发布时间】:2018-01-25 08:49:26
【问题描述】:

我想使用来自android.bluetooth.leBluetoothLeAdvertiser 类通过android 传输iBluetooth。但似乎我无法设置某些 制造商规范数据 字段以匹配 iBeacon 的字段。


iBeacon 结构

Thisthis 告诉您 iBeacon 的 制造商规格数据 值需要包含哪些内容。基本上:

Apple Company Identifier (Little Endian), 0x004c = 76
data type, 0x02 => iBeacon
data length, 0x15 = 21
uuid: 585CDE931B0142CC9A1325009BEDC65E
major: [0000]
minor: 0000
meaured power at 1 meter: 0xc5 = -59




我一直在关注this tutorial,其中包含以下步骤:
  1. 使用AdvertiseData.Builder.addManufacturerData() 创建AdvertiseData 对象(我认为这应该是制造商规格数据,有关问题请参见下文)

    protected void setAdvertiseData() {
    
      AdvertiseData.Builder mBuilder = new AdvertiseData.Builder();
    
      ByteBuffer mManufacturerData = ByteBuffer.allocate(24);
    
      byte[] uuid = getIdAsByte(UUID.fromString("0CF052C2-97CA-407C-84F8-B62AAC4E9020"));
    
      mManufacturerData.put(0, (byte)0xBE); // Beacon Identifier
    
      mManufacturerData.put(1, (byte)0xAC); // Beacon Identifier
    
      for (int i=2; i<=17; i++) {
    
        mManufacturerData.put(i, uuid[i-2]); // adding the UUID
    
      }
    
      mManufacturerData.put(18, (byte)0x00); // first byte of Major
      mManufacturerData.put(19, (byte)0x09); // second byte of Major
      mManufacturerData.put(20, (byte)0x00); // first minor
      mManufacturerData.put(21, (byte)0x06); // second minor
      mManufacturerData.put(22, (byte)0xB5); // txPower
      mBuilder.addManufacturerData(224, mManufacturerData.array()); // using google's company ID
      mAdvertiseData = mBuilder.build();
    }
    
  2. 使用AdvertiseSettings.Builder 创建AdvertiseSettings

    protected void setAdvertiseSettings() {
      AdvertiseSettings.Builder mBuilder = new AdvertiseSettings.Builder();
      mBuilder.setAdvertiseMode(AdvertiseSettings.ADVERTISE_MODE_LOW_POWER);
      mBuilder.setConnectable(false);
      mBuilder.setTimeout(0);
      mBuilder.setTxPowerLevel(AdvertiseSettings.ADVERTISE_TX_POWER_MEDIUM);
      mAdvertiseSettings = mBuilder.build();
    }
    
  3. 使用 BluetoothLeAdvertiser 广播 AdvertiseSettings 和 AdvertiseData。 (这也需要一个回调,告诉蓝牙传输是否有效,没有问题)

    mBluetoothLeAdvertiser.startAdvertising(mAdvertiseSettings, mAdvertiseData, mAdvertiseCallback);
    




这些步骤的问题是:




起初我在关注this 教程,并正在传输一个 Alt-Beacon。也许BluetoothLeAdvertiser 类假设我仍在传输结构不同于iBeacon 的Alt-Beacon。

Alt-Beacon 结构:



其他资源:

更新代码

public AdvertiseData getiBeaconData() {
    AdvertiseData.Builder mBuilder = new AdvertiseData.Builder();
    ByteBuffer mManufacturerData = ByteBuffer.allocate(24);

    byte[] uuid = getIdAsByte(UUID.fromString(thisCont.getString( R.string.ble_uuid )) );
    ParcelUuid parced = new ParcelUuid(UUID.fromString(thisCont.getString( R.string.ble_uuid )) );
    /*

R.string.ble_uuid == CDB7950D-73F1-4D4D-8E47-C090502DBD63 这是关于 iBeacon 结构的 http://smlie-blog.blogspot.com/2014/06/bluetooth-ibeacon-packet-format.html */

    //mManufacturerData.put((byte)0x00); //Manufactor Id 1
    //mManufacturerData.put((byte)0x4C); //Manufactor Id 2
   // mManufacturerData.put((byte)0xBE); //ibeconid1
    mManufacturerData.put((byte)0x02); //ibeconid2
    mManufacturerData.put((byte)0x15); //Data length
    for (byte i:uuid) {
        mManufacturerData.put(i); // adding the UUID
    }
    mManufacturerData.put((byte)0x00); //major first
    mManufacturerData.put((byte)0x00); //major second
    mManufacturerData.put((byte)0x00); //minor first
    mManufacturerData.put((byte)0x00); //minor second
    //mManufacturerData.put((byte)0xC5); //TX power

    /*
    mManufacturerData.put((byte)0x1A); // Beacon Identifier was BE  iBeacon = 00
    mManufacturerData.put((byte)0xFF); // Beacon Identifier was AC  iBeacon = 02
    /* the above 2 lines are the ibeacon AD Indicator

    for (byte i:uuid) {
        mManufacturerData.put(i); // adding the UUID
    }
    mManufacturerData.put((byte)0x00); // first byte of Major
    mManufacturerData.put((byte)0x00); // second byte of Major
    mManufacturerData.put((byte)0x00); // first minor
    mManufacturerData.put((byte)0x00); // second minor
    mManufacturerData.put((byte)0xC5); // txPower (RSSI) (from tx)
    mBuilder.addManufacturerData(16, mManufacturerData.array()); // using google's company ID
    */

    mBuilder.addManufacturerData(76, mManufacturerData.array()); // using google's company ID
    //mBuilder.addServiceUuid(parced);
    return mBuilder.build();

}

【问题讨论】:

    标签: android bluetooth-lowenergy ibeacon-android


    【解决方案1】:

    我认为您的代码非常好。一些备注:

    • Apple 的制造商 ID 为 76:mBuilder.addManufacturerData(76, mManufacturerData.array())
    • iBeacon 类型为 0x02:mManufacturerData.put(0, (byte)0x02); // Beacon Identifier
    • 长度为0x15:mManufacturerData.put(1, (byte)0x15); // Beacon Identifier
    • 我不确定这是否有效:UUID.fromString("0CF052C297CA407C84F8B62AAC4E9020")。通常fromString() 方法需要类似:UUID.fromString("F0018B9B-7509-4C31-A905-1A27D39C003D")

    总结一下:

    protected void setAdvertiseData() {
    
         AdvertiseData.Builder mBuilder = new AdvertiseData.Builder()
    
         ByteBuffer mManufacturerData = ByteBuffer.allocate(23);
    
         byte[] uuid = getIdAsByte(UUID.fromString("0CF052C297CA407C84F8B62AAC4E9020"));
    
         mManufacturerData.put(0, (byte)0x02);
         mManufacturerData.put(1, (byte)0x15); 
    
         for (int i=2; i<=17; i++) {
           mManufacturerData.put(i, uuid[i-2]); // adding the UUID
         }
    
         mManufacturerData.put(18, (byte)0x00); // first byte of Major
         mManufacturerData.put(19, (byte)0x09); // second byte of Major
         mManufacturerData.put(20, (byte)0x00); // first minor
         mManufacturerData.put(21, (byte)0x06); // second minor
         mManufacturerData.put(22, (byte)0xB5); // txPower
    
         mBuilder.addManufacturerData(76, mManufacturerData.array()); 
         mAdvertiseData = mBuilder.build();
    }
    

    【讨论】:

    • 正确,我保留了 Alt-Beacon 值,因为它们在我从中获取代码的教程中。我尝试将信标标识符设置为 2 个字节(0x00,0x02)。当我尝试添加 0x15(带有 00,02)时,我遇到了缓冲区溢出,我也遇到了 0xFF 和 0x00(对于长度)
    • 不添加。更换我提到的部件。
    • 我的意思是索引 1 处的字节。 -> mManufacturerData.put(1, (byte)0xAC); -> 替换为 mManufacturerData.put(1, (byte)0x15);
    • 刚刚尝试了这些值,这个信标仍然在 nrfConnect(蓝牙接收应用)中显示为 AltBeacon
    • 你能用你当前的代码更新你的问题吗?你能在 nrf 应用程序中呈现广告框架的原始视图吗?如果您更改制造商 ID,它就不能再成为 Altbeacon。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-04-02
    • 2015-11-16
    • 2022-01-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-07-14
    相关资源
    最近更新 更多