ユーザーが家を出るたびに警告する小さなジオフェンス(100メートル)をセットアップしようとしています。これを行うには、次のようにユーザーに現在の場所を要求します。
- (void)requestUsersCurrentLocation
{
if (self.locationManager == nil) self.locationManager = [[CLLocationManager alloc] init];
self.locationManager.delegate = self;
self.locationManager.desiredAccuracy = kCLLocationAccuracyBest;
self.locationManager.distanceFilter = 100;
[self.locationManager startUpdatingLocation];
}
CLLocationManagerのデリゲートメソッドを使用して、アプリケーションがユーザーの現在の場所を特定できたかどうかを確認します。attemptToRegisterGeofenceAlertForLocation:
私のテストでは、これは正しく機能し、アプリケーションは私のメソッドの呼び出しに進みます
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations
{
CLLocation *location = [locations lastObject];
NSDate *eventDate = location.timestamp;
NSTimeInterval howRecent = [eventDate timeIntervalSinceNow];
if (abs(howRecent) < 15.0)
{
[self.locationManager stopUpdatingLocation];
if([self attemptToRegisterGeofenceAlertForLocation:location])
{
[[NSNotificationCenter defaultCenter] postNotificationName:kGeofenceSetupSuccess object:nil];
}
else
{
[[NSNotificationCenter defaultCenter] postNotificationName:kGeofenceSetupFailure object:nil];
}
}
}
ここまでは順調ですね。これが、ユーザーの現在の場所の周りに比較的小さなジオフェンスを登録するための私のカスタム関数です。
- (BOOL)attemptToRegisterGeofenceAlertForLocation:(CLLocation *)location
{
// Do not create regions if support is unavailable or disabled
if (![CLLocationManager regionMonitoringAvailable]) return NO;
// Check the authorization status
if (([CLLocationManager authorizationStatus] != kCLAuthorizationStatusAuthorized) && ([CLLocationManager authorizationStatus] != kCLAuthorizationStatusNotDetermined)) return NO;
// Clear out any old regions to prevent buildup.
if ([self.locationManager.monitoredRegions count] > 0)
{
for (id obj in self.locationManager.monitoredRegions)
{
[self.locationManager stopMonitoringForRegion:obj];
}
}
// If the overlay's radius is too large, registration fails automatically,
// so clamp the radius to the max value.
CLLocationDegrees radius = 100; // meters?
if (radius > self.locationManager.maximumRegionMonitoringDistance)
{
radius = self.locationManager.maximumRegionMonitoringDistance;
}
// Create the region to be monitored.
CLRegion *region = [[CLRegion alloc] initCircularRegionWithCenter:location.coordinate radius:radius identifier:kGeofenceIdentifier];
[self.locationManager startMonitoringForRegion:region];
return YES;
}
ユーザーがジオフェンス領域を終了すると、次のように応答します。
- (void)locationManager:(CLLocationManager *)manager didExitRegion:(CLRegion *)region
{
if([region.identifier isEqual:kGeofenceIdentifier])
{
if([[UIApplication sharedApplication] applicationState] == UIApplicationStateBackground)
{
// Fire a UILocationNotification
}
else
{
// Fire a UIAlertView
}
}
}
アプリケーションがユーザーの場所を取得でき、ジオフェンスが正しく登録されていると判断しましたが、実際のデバイス(3G対応のiPhone)でトリガーすることはできません。私はジオフェンス地域を離れ、何の通知も受け取らずに数マイル移動しました。場所を大幅に変更することで、シミュレーターでアラートを受信することに成功しました。
私は何が間違っているのですか?