2013-10-14 68 views
15

我正在爲iOS編寫一個應用程序,要求應用程序同時宣告iOS iBeacon以及同時宣傳外設服務。有必要公佈該服務,而不是僅僅在外設上發現,因爲用例需要中央(用BLE說法)在被iOS喚醒(但仍然在後臺)由於接近iBeacon而連接到外設。在中央後臺運行的應用只能通過可用服務發現外設,而不是發現所有外設[];我的代碼用於宣傳服務或iBeacon,但我還沒有想出如何在同一時間做到這一點。 iBeacon可能會使用38bytes可用空間中的21bytes,並且沒有足夠的空間來宣傳信標以及服務?iOS CoreBluetooth/iBeacon:同時發佈iBeacon和外設服務

此作品(燈塔):

self.beaconRegion = [[CLBeaconRegion alloc] initWithProximityUUID:uuid 
    major:1 
    minor:1 
    identifier:@"bentboolean"]; 
NSMutableDictionary *dict = [[self.beaconRegion peripheralDataWithMeasuredPower:nil] mutableCopy];  
[self.peripheralManager startAdvertising:dict ]; 

這工作(服務):

NSMutableDictionary *dict = [[NSMutableDictionary alloc] init]; 
[dict setValue:@[serviceUUID] forKey:CBAdvertisementDataServiceUUIDsKey]; 
[self.peripheralManager startAdvertising:dict ]; 

添加兩人在一起,試圖在同一時間不工作,宣傳這兩種服務。它只廣告燈塔,而不是服務:

self.beaconRegion = [[CLBeaconRegion alloc] initWithProximityUUID:uuid 
    major:1 
    minor:1 
    identifier:@"bentboolean"]; 
NSMutableDictionary *dict = [[self.beaconRegion peripheralDataWithMeasuredPower:nil] mutableCopy]; 
[dict setValue:@[serviceUUID] forKey:CBAdvertisementDataServiceUUIDsKey]; 
[self.peripheralManager startAdvertising:dict ]; 

感謝您的參觀!

+0

嗨,你有沒有解決這個問題?我不認爲這是可能的,由於藍牙的能力... – CW0007007

回答

-1

我能得到這個要和一個單獨的CLLocationManager和CLBeaconRegion爲單獨的reciever和信標兩種:

#import "GRBothViewController.h" 

@interface GRBothViewController() 

@end 

@implementation GRBothViewController 

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil 
{ 
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil]; 
    if (self) { 
     // Custom initialization 
    } 
    return self; 
} 

- (void)viewDidLoad 
{ 
    [super viewDidLoad]; 


    self.locationManager = [[CLLocationManager alloc] init]; 
    self.locationManager.delegate = self; 

    self.locationScanner = [[CLLocationManager alloc] init]; 
    self.locationScanner.delegate = self; 

    [self initBeacon]; 
    [self initRegion]; 
    [self locationManager:self.locationManager didStartMonitoringForRegion:self.scannerRegion]; 
} 

- (void)initBeacon { 
    NSLog(@"Starting beacon"); 

    NSUUID *uuid = [[NSUUID alloc] initWithUUIDString: @"23542266-18D1-4FE4-B4A1-23F8195B9D39"]; 
    self.beaconRegion = [[CLBeaconRegion alloc] initWithProximityUUID:uuid 
                   major:1 
                   minor:1 
                  identifier:@"com.thisisgrow.Grow"]; 
    [self transmitBeacon:self]; 
} 

- (IBAction)transmitBeacon:(id)sender { 
    self.beaconPeripheralData = [self.beaconRegion peripheralDataWithMeasuredPower:nil]; 
    self.peripheralManager = [[CBPeripheralManager alloc] initWithDelegate:self 
                    queue:nil 
                    options:nil]; 
} 

-(void)peripheralManagerDidUpdateState:(CBPeripheralManager *)peripheral { 
    if (peripheral.state == CBPeripheralManagerStatePoweredOn) { 
     NSLog(@"Powered On"); 
     [self.peripheralManager startAdvertising:self.beaconPeripheralData]; 
    } else if (peripheral.state == CBPeripheralManagerStatePoweredOff) { 
     NSLog(@"Powered Off"); 
     [self.peripheralManager stopAdvertising]; 
    } 
} 

- (void)locationManager:(CLLocationManager *)manager didStartMonitoringForRegion:(CLRegion *)region { 
    [self.locationManager startRangingBeaconsInRegion:self.beaconRegion]; 
} 

- (void)initRegion { 
    NSUUID *uuid = [[NSUUID alloc] initWithUUIDString:@"23542266-18D1-4FE4-B4A1-23F8195B9D39"]; 
    _scannerRegion = [[CLBeaconRegion alloc] initWithProximityUUID:uuid identifier:@"com.thisisgrow.Grow"]; 
    _scannerRegion.notifyEntryStateOnDisplay = YES; 
    [_locationScanner startMonitoringForRegion:self.scannerRegion]; 
} 

- (void)locationManager:(CLLocationManager *)manager didEnterRegion:(CLRegion *)region { 
    //SCANNER 
    [self.locationScanner startRangingBeaconsInRegion:self.scannerRegion]; 
} 

-(void)locationManager:(CLLocationManager *)manager didExitRegion:(CLRegion *)region { 
    //SCANNER HAS LEFT THE AREA 
    [self.locationScanner stopRangingBeaconsInRegion:self.scannerRegion]; 
} 

-(void)locationManager:(CLLocationManager *)manager didRangeBeacons:(NSArray *)beacons inRegion:(CLBeaconRegion *)region { 
    CLBeacon *beacon = [[CLBeacon alloc] init]; 
    NSLog(@"Beacons: %d", [beacons count]); 
    if(beacons && [beacons count]>0){ 
     beacon = [beacons firstObject]; 
    } 
    else{ 

    } 
} 

唯一這裏限制是該設備無法檢測本身。

+0

我看到了另一個有趣的觀察:即使*另一個*應用程序作爲iBeacon廣告,您的應用程序無法檢測到它。更重要的是,如果外部iBeacon存在廣告相同的標識符,您的應用程序仍然無法檢測到它。換句話說,廣告iBeacon ID集可以阻止任何相同ID集的檢測。 – davidgyoung

+0

但是,將設備作爲iBeacon使用時,如果要將其用於此目的,它足夠簡單,可以爲設備自動生成唯一的UUID(即使在啓動時也可以)。 對我來說,最主要的限制因素是:1)用作iBeacon的設備不會在背景AT ALL中廣播; 2)除了在onEnter上喚醒時,應用程序無法在後臺爲各個iBeacon設置範圍onLeave事件只有在進入或離開UUID區域時纔會觸發。 – d2burke

+0

@ d2burke您提到用作iBeacon的設備根本不會在後臺廣播。你知道這是否是這種情況,即使應用程序使用藍牙外設後臺模式? – darrinm

0

在我的實踐中,iBeacon & BLE服務不能同時做廣告。

如果廣告與iBeacon混合使用,BLE服務無法在前臺廣告。 iBeacon無法在後臺投放廣告。

iBeacon & BLE服務可以逐個做廣告,例如, iBeacon宣傳0.5秒,然後 BLE服務宣傳30.0秒。

希望這會有幫助