5

私はオブジェクティブ C の初心者です。私のアプリは 1 つのビーコンで正しく動作します。「estimote SDK」を使用しています。2つか3つのビーコンを使用したいので、多くの問題があります。各ビーコンのビューをプッシュしたい。

複数のビーコンでそれを行う方法がわかりません。

  1. 複数のビーコン マネージャーを使用する必要があるかどうかはわかりません。(ESTBeaconManager* beaconManager)

  2. 異なるリージョンを didRangeBeacons:(NSArray *)beacons inRegion:(ESTBeaconRegion *)region に渡す方法がわかりません

  3. 1 つのビーコンを通知のみに使用し、他の 2 つのビーコンを使用して、近くにいるときに 2 つの異なるビューをポップすることはできますか。(ビーコンごとに 1 つの異なるビュー)

ご協力いただきありがとうございます。

よろしくお願いします。

コード:

#import "ESTViewController.h"
#import "PresentViewController.h"
#import <ESTBeaconManager.h>
#import <AudioToolbox/AudioToolbox.h>

@interface ESTViewController () <ESTBeaconManagerDelegate>

@property (nonatomic, strong) ESTBeaconManager* beaconManager;
@property (nonatomic, strong) ESTBeaconManager* beaconManager2;
@property (nonatomic, strong) ESTBeaconManager* beaconManager3;

@property (nonatomic, strong) ESTBeacon* selectedBeacon;


@end

@implementation ESTViewController

- (void)viewDidLoad
{
    [super viewDidLoad];

    // should i create one manager instance or more ?

    self.beaconManager = [[ESTBeaconManager alloc] init];
    self.beaconManager.delegate = self;
    self.beaconManager.avoidUnknownStateBeacons = NO;

    //self.beaconManager2 = [[ESTBeaconManager alloc] init];
    //self.beaconManager2.delegate = self;
    //self.beaconManager2.avoidUnknownStateBeacons = NO;

    //self.beaconManager3 = [[ESTBeaconManager alloc] init];
    //self.beaconManager3.delegate = self;
    //self.beaconManager3.avoidUnknownStateBeacons = NO;



    // My Differents regions


    region = [[ESTBeaconRegion alloc] initWithProximityUUID:ESTIMOTE_PROXIMITY_UUID
                                                      major:12800 minor:228 identifier:@"Icy Marshmellow"];

    region2 = [[ESTBeaconRegion alloc] initWithProximityUUID:ESTIMOTE_PROXIMITY_UUID
                                                       major:12800 minor:128 identifier:@"Mint Cocktail"];

    region3 = [[ESTBeaconRegion alloc] initWithProximityUUID:ESTIMOTE_PROXIMITY_UUID
                                                       major:12800 minor:328 identifier:@"Blueberry Pie"];


    // Should i do it for each region with one ESTBeaconManager or 3 ?

    [self.beaconManager requestStateForRegion:region];
    [self.beaconManager requestStateForRegion:region2];
    [self.beaconManager requestStateForRegion:region3];


}

// NOTIFICATION METHOD :

-(void)beaconManager:(ESTBeaconManager *)manager
      didEnterRegion:(ESTBeaconRegion *)region
{
    // iPhone/iPad entered beacon zone

    // present local notification
    UILocalNotification *notification = [[UILocalNotification alloc] init];
    notification.alertBody = @"Hello blabla blabla";
    notification.soundName = UILocalNotificationDefaultSoundName;

    [[UIApplication sharedApplication] presentLocalNotificationNow:notification];
}

-(void)beaconManager:(ESTBeaconManager *)manager
       didExitRegion:(ESTBeaconRegion *)region
{
    // iPhone/iPad left beacon zone

    // present local notification
    UILocalNotification *notification = [[UILocalNotification alloc] init];
    notification.alertBody = @"bye bye";
    notification.soundName = UILocalNotificationDefaultSoundName;

    [[UIApplication sharedApplication] presentLocalNotificationNow:notification];
}



- (void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];
    [self.beaconManager startRangingBeaconsInRegion:region];
    [self.beaconManager startMonitoringForRegion:region];

    //[self.beaconManager2 startRangingBeaconsInRegion:region2];
    //[self.beaconManager2 startMonitoringForRegion:region2];

    //[self.beaconManager3 startRangingBeaconsInRegion:region3];
    //[self.beaconManager3 startMonitoringForRegion:region3];


}

  - (void)viewWillDisappear:(BOOL)animated {
    [super viewWillDisappear:animated];

    [self.beaconManager stopRangingBeaconsInRegion:region];
    [self.beaconManager stopMonitoringForRegion:region];

    //[self.beaconManager2 stopRangingBeaconsInRegion:region2];
    //[self.beaconManager2 stopMonitoringForRegion:region2];

    //[self.beaconManager3 stopRangingBeaconsInRegion:region3];
    //[self.beaconManager3 stopMonitoringForRegion:region3];

}

// My problem is here , i dont know how i can pass differents regions here


-(void)beaconManager:(ESTBeaconManager *)manager
     didRangeBeacons:(NSArray *)beacons
            inRegion:(ESTBeaconRegion *)region
{
    if([beacons count] > 0)
    {

        if(!self.selectedBeacon)
        {
            // initialy pick closest beacon
            self.selectedBeacon = [beacons objectAtIndex:0];
        }
        else
        {
            for (ESTBeacon* cBeacon in beacons)
            {
                // update beacon it same as selected initially
                if([self.selectedBeacon.major unsignedShortValue] == [cBeacon.major unsignedShortValue] &&
                   [self.selectedBeacon.minor unsignedShortValue] == [cBeacon.minor unsignedShortValue])
                {
                    self.selectedBeacon = cBeacon;
                }
            }
        }



        switch (self.selectedBeacon.proximity)
        {
            case CLProximityUnknown:
            {

                self.rangeStatusImageView.image = [UIImage imageNamed:@"logo_signal.jpg"];
                self.descriptionStateLabel.text = @"Signal lost";
                break;
            }
            case CLProximityImmediate:
            {
                [self performSegueWithIdentifier: @"presentSegue" sender: self];
                break;
            }
            case CLProximityNear:
            {
                self.rangeStatusImageView.image = [UIImage imageNamed:@"logo_near_bleu.jpg"];
                self.descriptionStateLabel.text = @"Come closer";
                break;

            }
            case CLProximityFar:
            {
                self.rangeStatusImageView.image = [UIImage imageNamed:@"logo_far_clair.jpg"];
                self.descriptionStateLabel.text = @"Welcome";
                break;
            }

            default:
                break;
        }


    }
}

- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];

}

@end

編集

わかりました私は自分のコードに取り組みましたが、今では 1 つのリージョンでそれを行っています。私のビーコン配列には 3 つのビーコンがあります。

region = [[ESTBeaconRegion alloc] initWithProximityUUID:ESTIMOTE_PROXIMITY_UUID identifier:@"multibeacons"];

私は初期設定でメジャーまたはマイナーを使用しません。

ViewDidAppearsで私は:

[self.beaconManager startRangingBeaconsInRegion:region];

このようなデリゲート:

-(void)beaconManager:(ESTBeaconManager *)manager
     didRangeBeacons:(NSArray *)beacons
            inRegion:(ESTBeaconRegion *)region
{

// I used a sort , sorting by distance
    NSSortDescriptor *sortDescriptor;
    sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"distance" ascending:YES];
    NSArray *sortDescriptors = [NSArray arrayWithObject:sortDescriptor];

// if breakpoint here 3 beacons in array
    self.beaconsArray = [beacons sortedArrayUsingDescriptors:sortDescriptors];

    if([self.beaconsArray count] > 0)
    {

        if(!self.selectedBeacon)
        {
            // initialy pick closest beacon
            self.selectedBeacon = [beacons objectAtIndex:0];
            currentBeaconMinor = self.selectedBeacon.minor;
        }
        else
        {
            for (ESTBeacon* cBeacon in self.beaconsArray)
            {
                // update beacon it same as selected initially
                if([self.selectedBeacon.major unsignedShortValue] == [cBeacon.major unsignedShortValue] &&
                   [self.selectedBeacon.minor unsignedShortValue] == [cBeacon.minor unsignedShortValue])
                {
                    self.selectedBeacon = cBeacon;
                    currentBeaconMinor = self.selectedBeacon.minor;
                }
            }
        }

私は距離で並べ替え、現在の BeaconMinor 値を持っています。ビーコンの配列には、ブレークポイントを配置すると、3 つのビーコンが内部に表示されます。

スイッチの近接では、私は次のようにしています:

switch (self.selectedBeacon.proximity)
        {

            case CLProximityImmediate:
            {

                if ([currentBeaconMinor floatValue] == 128)
                {
                    NSLog(@"128 128 128");
                    //[self performSegueWithIdentifier: @"presentSegue1" sender: self];
                }

                else if ([currentBeaconMinor floatValue] == 228)
                {
                    NSLog(@"228 228 228");
                    //[self performSegueWithIdentifier: @"presentSegue2" sender: self];
                }
                else if ([currentBeaconMinor floatValue] == 328)
                {
                    NSLog(@"328 328 328");
                    //[self performSegueWithIdentifier: @"presentSegue3" sender: self];
                }

                break;
            }

しかし、それはまだうまくいきません :((( 私は怒っています。私のアプリは最初に最も近いビーコンを選択します。その後、アプリは常に同じビーコンを保持し、決して変更しません。ビーコンをデバイスの近くに移動しますが、nslog は常に同じマイナー番号を送信します. 助けてくれませんか? 何か間違ったことをしているに違いありません.

4

2 に答える 2

5

各ビーコンには、UUID、メジャー番号、マイナー番号の 3 つの情報があります。ビーコン リージョンを作成するときは、少なくとも UUID を指定する必要があります。オプションで、メジャー値とマイナー値を指定できます。iOS がバックグラウンドでスキャンするビーコン リージョンの数には制限があるため (20 だと思います)、一般的には、リージョン登録をできるだけ広く行い、興味があるかどうかを通知するタイミングを決定するのが最善です。目に見えるビーコンで。

すべての Estimote ビーコンは同じ UUID を持っているため、UUID だけで地域を登録すると、Estimote ビーコンの範囲内にいるときはいつでもアプリに通知されます。あなたの 3 つのビーコンはすべてメジャー 12800 を使用していることがわかります。そのため、UUID とメジャーを指定するリージョンを作成するだけで、それらの値を持つビーコンが表示されるたびに通知を受けることができます。 3 つのビーコンのそれぞれに特定の地域を登録します。

すべてのリージョンを管理するために必要なEstBeaconManagerインスタンスは 1 つだけです。

リージョンに出入りするたびに、メソッドdidEnterRegiondidExitRegionメソッドが呼び出されます。また、didRangeBeacons現在ビーコンの範囲を設定している場合は、メソッドが呼び出されます。

これらのデリゲート メソッドでは、実行するアクションを決定するために、メジャーとマイナーの値を調べる必要があります。リージョン ID 文字列を調べて、どのビーコンが表示されているかを判断することもできます。

複数のビーコンが範囲内にある可能性があるため、実行するアクションを決定するために近接を調べる必要がある場合があることに注意してください。

最後に、3 つのリージョンを定義しますが、それらすべてを測距/監視しているわけではないためviewWillAppear

- (void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];
    [self.beaconManager startRangingBeaconsInRegion:region];
    [self.beaconManager startMonitoringForRegion:region];

    [self.beaconManager startRangingBeaconsInRegion:region2];
    [self.beaconManager startMonitoringForRegion:region2];

    [self.beaconManager startRangingBeaconsInRegion:region3];
    [self.beaconManager startMonitoringForRegion:region3];


}
于 2014-05-19T01:06:10.450 に答える
3

これまで Estimote SDK を使用したことがありません。私は、Estimote ビーコンを標準的な iBeacon として扱い、Apple の Location Manager フレームワークを使用しています。

あなたはとても混乱しているように見えます。

Estimote SDK を簡単に見たところ、Apple のロケーション マネージャーに非常によく似ていました。

ロケーション マネージャーでビーコン リージョンを作成し、ロケーション マネージャーにそのビーコン リージョンの測距を開始するように依頼します (これにより、推定距離の読み取り値が通知されるか、startMonitoringForRegion を使用して、リージョンの出入りイベントについて通知を受けるように依頼します。

両方を同時に行うことができます。Estimate API を見てみると、同じアプローチを使用しているように見えます。

ビーコン リージョンを作成してから、startRangingBeaconsInRegion および/または startMonitoringForRegion を呼び出して、範囲および/またはリージョンの開始/終了の通知を要求する必要があります。

次に、ビーコンが範囲に出入りするとき (startMonitoringForRegion)、または距離が変わるとき (startRangingBeaconsInRegion) にデリゲート メソッドが呼び出されるのを待ちます。

ドキュメントを見ると、requestStateForRegion を呼び出すと、Estimote ビーコン マネージャーが locationManager:didDetermineState:forRegion: デリゲート メソッドを 1 回だけ呼び出すようになります。

あなたのコードでは、領域を監視したり、ビーコンの範囲を設定したりするように要求していないため、3 つの領域すべてが「範囲外」状態を返します。

これらの requestStateForRegion を呼び出さないでください。startMonitoringForRegion および/または startRangingBeaconsInRegion を呼び出し、ビーコンのステータスが変化したときにシステムが通知するのを待ちます。

于 2014-05-19T00:57:22.077 に答える