使用 AltBeacon 格式在广告时添加自定义数据

Add custom data while advertising by using AltBeacon format

我正在学习 Android 应用程序开发,同时构建与物理网络交互的应用程序。我想根据 AltBeacon 规范做广告,并以 stringbytes 的形式添加小负载。我遇到了 Beacon.Builder Javadoc,但它写得不好。我应该使用上面 javadoc 中的哪个函数,或者还有其他可用的函数吗?

我的目标是使用我的应用程序做广告并传输特定字符串。如果其他设备有我的应用程序,那么它应该显示带有该字符串的通知。我所有的代码都取自 this.

标准蓝牙信标布局(iBeacon、AltBeacon、Eddystone-UID)旨在传输唯一的数字标识符,而不是字符串。 (Eddystone-URL 有点例外,因为它旨在传输编码的 URL 字符串。)

但是,当然可以传输在信标传输中编码的字符串。请注意,这有一些限制:

  1. space数量有限。信标传输中只有大约 20 个可用字节 space 可用,如果使用像 ASCII 这样的编码,则为 20 个字符,如果使用 UTF-8,则可能更少,具体取决于字符。

  2. 您需要一定数量的匹配字节才能确定(有一定合理的确定性)广告是否为 "yours" 并且应该被解码为字符串。使用两个字节的匹配值将使您有 65536 分之一的机会意外地将其他人的信标解码为字符串。

  3. 如果要在iOS上接收和解码,就不能真正使用iBeacon,因为必须使用16字节的UUID进行匹配,剩下两个字节给握住绳子。

这是一个示例,说明如何使用修改后的 AltBeacon 布局执行此操作,前两个字节匹配标识符 0x8b9c 用于确保它是您的信标,第二个 18 字节标识符用于存储编码字符串.显示传输最长为 18 个字符的 ASCII 字符串的代码片段:

public static final Identifier MY_MATCHING_IDENTIFIER = Identifier.fromInt(0x8b9c);
...
mBeaconManager.getBeaconParsers().clear();
BeaconParser customBeaconParser = new BeaconParser().setBeaconLayout("m:2-3=beac,i:4-5,i:6-23,p:24-24,d:25-25");
mBeaconManager.addBeaconParser(customBeaconParser);
String stringToTransmit = "Only 18 chars fit!";
byte[] stringToTransmitAsAsciiBytes = stringToTransmit.getBytes(StandardCharsets.US_ASCII);
Beacon beacon = new Beacon.Builder().setId1(MY_MATCHING_IDENTIFIER.toString())
            .setId2(Identifier.fromBytes(stringToTransmitAsAsciiBytes, 0, 18, false).toString())
            .setTxPower(-59).build();
mBeaconTransmitter = new BeaconTransmitter(this, customBeaconParser);
mBeaconTransmitter.startAdvertising(beacon);

这里正在接收:

@Override
public void didRangeBeaconsInRegion(Collection<Beacon> beacons, Region region) {
    for (Beacon beacon : beacons) {
        if (beacon.getId1().equals(MY_MATCHING_IDENTIFIER)) {
            byte[] bytes = beacon.getId2().toByteArray();
            String receivedString = null;
            try {
                receivedString = new String(bytes, 0, bytes.length, "ASCII");
            } catch (UnsupportedEncodingException e) {
                Log.d(TAG, "Cannot decode ASII");
            }
            Log.d(TAG, "I just received: "+receivedString);
        }
    }
}

编辑: 确保如上所示清除信标解析器,否则您的代码将尝试使用默认的信标解析器。请参阅上面的代码更改。