进入信标区域时如何在后台作为信标做广告

how to advertise in the background as a beacon when entering a beacon region

我目前正在开发一款严重依赖 iBceaons 的应用程序。

我设法创建了一个信标区域,当进入该区域时,它会在后台唤醒应用进程 10 秒。

下一步是让 phone 它在后台进入区域时自我宣传

目前,当应用程序打开时,它会保持测距并在其位于某个区域时作为信标进行传输
当应用程序在后台时,它会持续 10 秒,但在进入区域时不会作为信标传输

那么有没有办法让 phone 在进入某个区域时在后台作为信标进行传输?

我已经研究过 Apple's background Bluetooth which mentioned that the advertising packet is differs when transmitting in the background. I have also looked at This Solution 但此解决方案不使用核心位置,因此在进入区域时无法唤醒应用程序

import UIKit
import CoreLocation
import CoreBluetooth
class ViewController: 
UIViewController,CLLocationManagerDelegate,CBPeripheralManagerDelegate {

var locationManager: CLLocationManager!
var localBeacon: CLBeaconRegion!
var beaconPeripheralData: NSDictionary!
var peripheralManager: CBPeripheralManager!

let myCustomServiceUUID = CBUUID(string:"5A4BCFCE-174E-4BAC-A814-092E77F6B7E5")

override func viewDidLoad() {
    super.viewDidLoad()
    locationManager = CLLocationManager()
    locationManager.delegate = self
    locationManager.requestAlwaysAuthorization()

    }


}

override func didReceiveMemoryWarning() {
    super.didReceiveMemoryWarning()
}

func locationManager(_ manager: CLLocationManager, didChangeAuthorization status: CLAuthorizationStatus) {
    if status == .authorizedAlways {
        if CLLocationManager.isMonitoringAvailable(for: CLBeaconRegion.self) {
            if CLLocationManager.isRangingAvailable() {
                startScanning()
            }
        }
    }
}

func startScanning() {
    let uuid = UUID(uuidString: "48de4980-968d-11e4-b4a9-0800200c9a66")!
    let beaconRegion = CLBeaconRegion(proximityUUID: uuid, major: 1, minor: 1, identifier: "region1")
       beaconRegion.notifyEntryStateOnDisplay=true;
    locationManager.startMonitoring(for: beaconRegion)
    locationManager.startRangingBeacons(in: beaconRegion)
}

func locationManager(_ manager: CLLocationManager, didRangeBeacons beacons: [CLBeacon], in region: CLBeaconRegion) {

    if(beacons.count > 0) {
        let nearestBeacon:CLBeacon = beacons[0] as CLBeacon

    NSLog("RSSI value is %ld", nearestBeacon.rssi);
        initLocalBeacon() // Here I'm transmitting as a beacon along with ranging when entering or within a region  which works fine the app is open but not transmitting while in background 



    }
}

func locationManager(_ manager: CLLocationManager,didDetermineState state: CLRegionState,for region: CLRegion)    {

    switch state {
    case .inside:
        NSLog("locationManager didDetermineState INSIDE  %@", region.identifier);


    case .outside:
        NSLog("locationManager didDetermineState OUTSIDE  %@", region.identifier);

    case .unknown:
        NSLog("locationManager didDetermineState OTHER  %@", region.identifier);

    }
}

func initLocalBeacon() {
    if localBeacon != nil {
        stopLocalBeacon()
    }

    let localBeaconUUID = "5A4BCFCE-174E-4BAC-A814-092E77F6B7E5"
    let localBeaconMajor: CLBeaconMajorValue = 2
    let localBeaconMinor: CLBeaconMinorValue = 1

    let uuid = UUID(uuidString: localBeaconUUID)!
    localBeacon = CLBeaconRegion(proximityUUID: uuid, major: localBeaconMajor, minor: localBeaconMinor, identifier: "identifer here")

    beaconPeripheralData = localBeacon.peripheralData(withMeasuredPower: -59)
    peripheralManager = CBPeripheralManager(delegate: self, queue: nil, options: nil)
}

func stopLocalBeacon() {
    peripheralManager.stopAdvertising()
    peripheralManager = nil
    beaconPeripheralData = nil
    localBeacon = nil
}

func peripheralManagerDidUpdateState(_ peripheral: CBPeripheralManager) {
    if peripheral.state == .poweredOn {
        peripheralManager.startAdvertising(beaconPeripheralData as! [String: AnyObject]!)
    } else if peripheral.state == .poweredOff {
        //peripheralManager.stopAdvertising()
    }
}
}

我在功能的后台模式中选择了作为 BLE 附件的行为,并在播放列表中添加了隐私 - 蓝牙外设使用说明

抱歉,iOS 不会让您的应用在后台发布符合 iBeacon 规范的 BLE 数据包。正如您在问题中提到的,Apple 改变了在后台发出的背景广告的方式,因此,它们不会触发 CoreLocation enter 事件来唤醒在后台接收应用程序。

有几个不完美的选择:

  1. 您可以在后台使用其他信标广告并唤醒您的应用程序。这不会像 iBeacon 那样快,但它会在几分钟内唤醒您的应用程序。这是执行此操作的设置:https://github.com/Decemberlabs/AltBeacon

  2. 您可以在应用程序在前台时通告 iBeacon,并尝试通过本地通知让用户将应用程序带到前台。

  3. 如果附近有您的应用程序的其他前台副本(基于后台信标检测),您可以使用网络服务在您的应用程序运行的 10 秒内通知他们您的存在的背景。此通知可以告诉他们开始代表您投放广告。