10

I'm working on an iOS app that monitors for iBeacon regions. When the app is running in the background, I want it to send a local notification whenever it encounters a particular iBeacon region. Everything works fine, except for one thing: locationManager: didEnterRegion evidently doesn't get called until the user displays the lock screen. So even if the device passed through an iBeacon region while the app was in the background, they don't get the notification until they display the lock screen.

I've also tried using startMonitoringForRegion, and that sort of works -- if the app is running in the background, locationManager: didDetermineState: fires when the device enters the iBeacon region. However, it only does so once -- if the user subsequently exits and reenters the iBeacon region, locationManager: didDetermineState does not fire again.

I'm running an iPhone 5s and using an iPhone 4s as the iBeacon, if that makes any difference.

Correction: This phenomenon is evidently only happening when I use an iPhone 4s as the client. If I use a 5s, the notification is delivered immediately.

Trevor Alyn
  • 687
  • 2
  • 8
  • 20

3 Answers3

5

Just trying to get more info. Have you set notifyEntryStateOnDisplay to YES on the CLBeaconRegion? It sounds like it.

From documentation:

When set to YES, the location manager sends beacon notifications when the user turns on the display and the device is already inside the region. These notifications are sent even if your app is not running. In that situation, the system launches your app into the background so that it can handle the notifications. In both situations, the location manager calls the locationManager:didDetermineState:forRegion: method of its delegate object.

The default value for this property is NO.

Community
  • 1
  • 1
johnyorke
  • 471
  • 5
  • 5
  • notifyEntryStateOnDisplay is set to YES. If I launch the app, then turn on the iBeacon, didDetermineState fires regardless of whether the app is in the foreground or the background, and all is good. However, if I then turn off the iBeacon, wait a minute, and then turn it on again, didDetermineState does not fire again whether the app is in the foreground or the background. I've checked, and I'm not calling stopMonitoringForRegion anywhere. It almost seems like it's designed to only fire once. – Trevor Alyn Oct 30 '13 at 21:31
  • I think I got it -- I was assuming that everything would happen in real time, but according to the following link, you sometimes have to wait a few minutes between turning off and turning back on an iBeacon. Sure enough, when I waited five minutes, the delegate methods started firing again. – Trevor Alyn Oct 30 '13 at 21:39
  • http://stackoverflow.com/questions/19670513/local-notifications-only-received-once-ibeacons – Trevor Alyn Oct 30 '13 at 21:39
1

I had a similar issue as well and tried various code level changes detailed above (and other posts). Ranging worked but the Enter and Exit zone detection did not.

It turned out that I had App Background Refresh off. Once I enabled background app refreshing the Entering and Exiting of the zones worked correctly.

  • Can you please explain how you set App Background Refresh to on ? – fvisticot Jan 11 '14 at 23:58
  • Sure thing. Open the Settings App then click General -> Background App Refresh -> Enable Background App Refresh – draftalyzer Jan 13 '14 at 00:56
  • 2
    FYI, the Background App Refresh requirement has been removed for Beacon and Geofence updates. It was a requirement in iOS 7, but no longer for iOS 8. Your app will not show up in the list of apps for BAR in iOS 8. – Bill Burgess Nov 20 '14 at 20:56
0

I've had the exact same problem. I was sure I've set everything ok.

The solution was very easy: just remove the app from the device completely and run it again in Xcode . It worked for me like a charm.

michal.ciurus
  • 3,616
  • 17
  • 32