Tip: Indoor-outdoor transitions are demonstrated in the Indoor-outdoor code example (Objective-C) and Indoor-outdoor code example (Swift).


IndoorAtlas SDK controls the platform location scanning, and you only need to provide the necessary permissions as explained in SDK setup.


As a prerequisite, please read our overview of Outdoor-Indoor transitions.

This article helps you to deploy the most accurate Indoor-Outdoor transitions. If you don't do the outdoor-fingerprinting instructed in the linked article, IndoorAtlas defaults to a less accurate method. 



Like automatic floor detection, indoor-outdoor transitions are signaled with the IARegion events.


Obj C:


// Handling region enter events
- (void)indoorLocationManager:(IALocationManager *)manager didEnterRegion:(IARegion *)region
{
    switch (region.type) {
        case kIARegionTypeVenue:
            // Triggered when near a new location
            NSLog(@"Entered venue %@", region.identifier);
            break;
        case kIARegionTypeFloorPlan:
            // Triggered when entering the mapped area of the given floor plan
            NSLog(@"Entered floor plan %@", region.identifier);
            break;
    }
}

// Handling region exit events
- (void)indoorLocationManager:(IALocationManager *)manager didExitRegion:(IARegion *)region
{
    // Leaving a previously entered region
    switch (region.type) {
        case kIARegionTypeVenue:
            // Triggered when moving away from the vicinity of a location
            NSLog(@"Exit venue %@", region.identifier);
            break;
        case kIARegionTypeFloorPlan:
            // Notice that a change of floor plan (e.g., floor change)
            // is signaled by an exit-enter pair so ending up here
            // does not yet mean that the device is outside any mapped area
            NSLog(@"Exit floor plan %@", region.identifier);
            break;
    }
}


Swift:


// Handling region enter events
func indoorLocationManager(_ manager: IALocationManager, didEnter region: IARegion) {

    switch region.type {
    case .iaRegionTypeVenue:
        // Triggered when near a new location
        print("Entered venue \(region.identifier)")
    case .iaRegionTypeFloorPlan:
        // Triggered when entering the mapped area of the given floor plan
        print("Entered floor plan \(region.identifier)")
    default:
        break
    }
}

// Handling region exit events
func indoorLocationManager(_ manager: IALocationManager, didExitRegion region: IARegion) {

    // Leaving a previously entered region
    switch region.type {
    case .iaRegionTypeVenue:
        // Triggered when moving away from the vicinity of a location
        print("Exit venue \(region.identifier)")
    case .iaRegionTypeFloorPlan:
        // Notice that a change of floor plan (e.g., floor change)
        // is signaled by an exit-enter pair so ending up here
        // does not yet mean that the device is outside any mapped area
        print("Exit floor plan \(region.identifier)")
    default:
        break
    }
}



The IALocationManager delegate must be set before using these events.


Obj C:


self.locationManager.delegate = self;


Swift:


locationManager.delegate = self



Location and floor plan regions


In the above code snippet, there are two types of region entry events. 

  • The kIARegionTypeFloorPlan entry events are triggered when the user actually enters the mapped area of the floor plan. In almost all cases, this corresponds to physically entering the building. 
  • The kIARegionTypeVenue events are emitted a lot earlier, between 100 and 200 meters of the location (a.k.a. venue). This is meant as a heads-up to enable pre-loading of data. The venue entry events are also useful in the case when one wishes to disable automatic indoor-outdoor detection.



Floor plan and venue regions



Disabling indoor-outdoor detection


In some venues there may be areas where indoor-outdoor detection falsely detects outdoor when the user is indoors. If you prefer that the positioning is accurate indoors (at the cost of not detecting that the user goes outdoor), you can disable indoor-outdoor detection. This is done with lockIndoors:true;

If lockIndoors is enabled when the user approaches a venue, the correct venue is still automatically detected automatically. After starting indoor positioning, GPS is no longer scanned.

Note that lockFloor and lockIndoors can be used together but it is redundant in most cases: Locking positioning to specific floor also implicitly locks positioning indoors. 



Obj C:


// Lock positioning indoors (i.e., enable indoor-only mode)
IALocationManager *manager = [IALocationManager sharedInstance];
[manager lockIndoors:true];

// Unlock positioning indoors (disable indoor-only mode)
[manager lockIndoors:false];