所以我找到了一个关于使用iBeacons的好教程,我创建了一个接收器和一个广播器,但是当我运行代码时,我看不到有任何信标被广播。有没有人有一个很好的解决方案可以解决我的问题?
import UIKit
import CoreLocation
import CoreBluetooth
import Foundation
/// ibeacon class
class iBeaconConfiguration
{
// You can use uuidgen in terminal to generate new one.
static let uuid = UUID(uuidString: "7FA08BC7-A55F-45FC-85C0-0BF26F899530")!
private init() {}
}
如果您想知道,上面的课程仅适用于UUID
class BroadcastViewController: UIViewController {
fileprivate var broadcasting: Bool = false
fileprivate var beacon: CLBeaconRegion?
fileprivate var peripheralManager: CBPeripheralManager?
@IBOutlet var statusLabel: UILabel!
@IBOutlet var triggerButton: UIButton!
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
self.setNeedsStatusBarAppearanceUpdate()
}
override func viewDidLoad() {
super.viewDidLoad()
statusLabel = UILabel()
triggerButton = UIButton(frame: CGRect(x: 130, y: 10, width: 100, height: 50))
triggerButton.backgroundColor = UIColor.blue
triggerButton.addTarget(self, action: #selector(broadcastBeacon(sender:)), for: .touchUpInside)
self.view.addSubview(triggerButton)
let button = UIButton(frame: CGRect(x: 10, y: 10, width: 50, height: 50))
button.backgroundColor = UIColor.red
button.addTarget(self, action: #selector(dismiss1), for: .touchUpInside)
self.view.addSubview(button)
self.view.backgroundColor = UIColor.white
let UUID: UUID = iBeaconConfiguration.uuid
let major: CLBeaconMajorValue = CLBeaconMajorValue(arc4random() % 100 + 1)
let minor: CLBeaconMinorValue = CLBeaconMinorValue(arc4random() % 2 + 1)
self.beacon = CLBeaconRegion(proximityUUID: UUID, major: major, minor: minor, identifier: "tw.darktt.beaconDemo")
self.peripheralManager = CBPeripheralManager(delegate: self, queue: nil)
}
deinit
{
self.beacon = nil
self.peripheralManager = nil
}
override func didReceiveMemoryWarning()
{
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
@IBAction func dismiss1() {
//self.dismiss(animated: true, completion: nil)
present(ReceiverViewController(), animated: true, completion: nil)
}
}
// MARK: - Status Bar -
extension BroadcastViewController {
override var preferredStatusBarStyle: UIStatusBarStyle
{
if self.broadcasting {
return .lightContent
}
return .default
}
override var preferredStatusBarUpdateAnimation: UIStatusBarAnimation
{
return .fade
}
override var prefersStatusBarHidden: Bool
{
return false
}
}
//MARK: - Actions -
extension BroadcastViewController {
@IBAction fileprivate func broadcastBeacon(sender: UIButton) -> Void
{
let state: CBManagerState = self.peripheralManager!.state
if (state == .poweredOff && !self.broadcasting) {
let OKAction: UIAlertAction = UIAlertAction(title: "OK", style: .cancel, handler: nil)
let alert: UIAlertController = UIAlertController(title: "Bluetooth OFF", message: "Please power on your Bluetooth!", preferredStyle: .alert)
alert.addAction(OKAction)
self.present(alert, animated: true, completion: nil)
return
}
let titleFromStatus: (Void) -> String = {
let title: String = (self.broadcasting) ? "Start" : "Stop"
return title + " Broadcast"
}
let buttonTitleColor: UIColor = (self.broadcasting) ? UIColor.blue : UIColor.white
sender.setTitle("nil", for: .normal)
sender.setTitleColor(buttonTitleColor, for: .normal)
let labelTextFromStatus: (Void) -> String = {
let text: String = (self.broadcasting) ? "Not Broadcast" : "Broadcasting..."
return text
}
self.statusLabel.text = "broadcast started"
let animations: () -> Void = {
let backgroundColor: UIColor = (self.broadcasting) ? UIColor.white : UIColor.blue
self.view.backgroundColor = backgroundColor
self.broadcasting = !self.broadcasting
self.setNeedsStatusBarAppearanceUpdate()
}
let completion: (Bool) -> Void = {
finish in
self.advertising(start: self.broadcasting)
}
UIView.animate(withDuration: 0.25, animations: animations, completion: completion)
}
// MARK: - Broadcast Beacon
func advertising(start: Bool) -> Void
{
if self.peripheralManager == nil {
return
}
if (!start) {
self.peripheralManager!.stopAdvertising()
return
}
let state: CBManagerState = self.peripheralManager!.state
if (state == .poweredOn) {
let UUID:UUID = (self.beacon?.proximityUUID)!
let serviceUUIDs: Array<CBUUID> = [CBUUID(nsuuid: UUID)]
// Why NSMutableDictionary can not convert to Dictionary<String, Any>
var peripheralData: Dictionary<String, Any> = self.beacon!.peripheralData(withMeasuredPower: 1) as NSDictionary as! Dictionary<String, Any>
peripheralData[CBAdvertisementDataLocalNameKey] = "iBeacon Demo"
peripheralData[CBAdvertisementDataServiceUUIDsKey] = serviceUUIDs
self.peripheralManager!.startAdvertising(peripheralData)
}
}
}
// MARK: - CBPeripheralManager Delegate -
extension BroadcastViewController: CBPeripheralManagerDelegate {
func peripheralManagerDidUpdateState(_ peripheral: CBPeripheralManager)
{
let state: CBManagerState = peripheralManager!.state
if state == .poweredOff {
self.statusLabel.text = "Bluetooth Off"
if self.broadcasting {
self.broadcastBeacon(sender: self.triggerButton)
}
}
if state == .unsupported {
self.statusLabel.text = "Unsupported Beacon"
}
if state == .poweredOn {
self.statusLabel.text = "Not Broadcast"
}
}
}
除此之外,我还阅读了苹果在其网站上提供的文档,但我对此并不是很了解。我也可能喜欢10个不同的Github项目并尝试过它们,但它们都是用早期版本的swift编写的。
答案 0 :(得分:0)
假设你有一个iBeacon扫描应用程序正在运行(否则,如果你的设备正确播放,那将很难知道)......
我建议开始简单...得到&#34;开始播放&#34;部分工作,然后添加额外的东西。
创建一个新项目(或将新VC添加到当前项目中)。添加&#34;开始&#34;和&#34;停止&#34;按钮,您将连接到下面的@IBAction
个功能。
将此作为新VC的课程:
//
// BroadcasterViewController.swift
//
// Created by Don Mag on 3/16/18.
//
import UIKit
import CoreLocation
import CoreBluetooth
class BroadcasterViewController: UIViewController, CBPeripheralManagerDelegate {
var myBeacon: CLBeaconRegion!
var beaconData: NSDictionary!
var peripheralMgr: CBPeripheralManager!
let myRegionID = "myRegionID"
@IBAction func startBeacon(_ sender: Any) {
// don't do anything if myBeacon already exists
guard myBeacon == nil else { return }
let beaconUUID = "7FA08BC7-A55F-45FC-85C0-0BF26F899530"
let beaconMajor: CLBeaconMajorValue = 123
let beaconMinor: CLBeaconMinorValue = 456
let uuid = UUID(uuidString: beaconUUID)!
myBeacon = CLBeaconRegion(proximityUUID: uuid, major: beaconMajor, minor: beaconMinor, identifier: "MyIdentifier")
beaconData = myBeacon.peripheralData(withMeasuredPower: nil)
peripheralMgr = CBPeripheralManager(delegate: self, queue: nil, options: nil)
}
@IBAction func stopBeacon(_ sender: Any) {
// don't do anything if there's no peripheral manager
guard peripheralMgr != nil else { return }
peripheralMgr.stopAdvertising()
peripheralMgr = nil
beaconData = nil
myBeacon = nil
}
func peripheralManagerDidUpdateState(_ peripheral: CBPeripheralManager) {
if peripheral.state == .poweredOn {
peripheralMgr.startAdvertising(beaconData as! [String: AnyObject]!)
} else if peripheral.state == .poweredOff {
peripheralMgr.stopAdvertising()
}
}
}
在&#34;广播公司&#34;上运行该应用设备,然后点击开始按钮。然后运行你的&#34;扫描仪&#34;应用程序在另一台设备上,看看你是否找到了新的&#34;设备作为iBeacon&#34;
注意:我确定您知道,您的扫描仪必须正在扫描您在广播公司上使用的beaconUUID
。在此示例代码中,我使用了您在问题中发布的相同UUID字符串。
这对我来说很好 - 所以希望它会为你做同样的事情。如果此部分正常工作,那么您可以实现应用程序的其余部分 - UI,状态标签,任何其他选项 - 并添加一些错误处理(蓝牙未启用或未授予权限,等)。
答案 1 :(得分:0)
您无法在iBeacon广告中添加任何额外内容,并将其识别为此类内容。这两行是一个问题,必须删除:
#!/usr/bin/perl
use warnings;
use strict;
my $input = '...';
my $expected = '...';
$input =~ s/ =/:/g;
$input =~ s/\[(.*)\]/}\n$1: {/g;
$input =~ s/^/config.n8_v2_BB_RSI_SL = {\n/;
$input =~ s/(?<!\{)$/,/mg;
$input =~ s/,\n}//;
$input =~ s/,\n}/ }/g;
$input =~ s/,$/ }\n};/;
$input eq $expected or die 'Different';
第一行尝试将广播名称添加到广告中。你不能这样做,因为这种信息包里没有额外的空间。
第二行尝试将GATT服务UUID添加到广告中。这根本不符合逻辑。 iBeacon广告是蓝牙LE制造商广告,其不广告GATT服务。添加此选项会导致广告无效或导致广告API失败。
显示的代码可能存在其他问题。我建议在应用程序开始时简化代码以开始转换,这样您就可以消除任何可能的UI错误。我会使用像Locate这样的Android检测器,这样即使您的ProximityUIID错误也可以看到广告。与iOS不同,Android可以看到任何信标广告。