iOS: Track user location - ios

I've used location services in many apps, but this new app has a problem on iOS 8.0 and up. I am not getting the notification on the app's first load prompting to allow location services. However, on my iOS 7.1 device I get the prompt.
Here is what I have in my appDelegate in didFinishLaunchingWithOptions:
self.locationManager = [CLLocationManager new];
[self.locationManager setDelegate:self];
if ([self.locationManager respondsToSelector:#selector(requestAlwaysAuthorization)]) {
[self.locationManager requestAlwaysAuthorization];
}
[self initializeRegionMonitoring];
And the initializeRegionMonitoring method is:
-(void) initializeRegionMonitoring {
NSLog(#"initialize region monitoring");
self.locationManager = [[CLLocationManager alloc] init];
self.locationManager.delegate = self;
// radius of region being monitored
CLLocationDistance radius = 25; // 20 metre sensitivity
CLLocationCoordinate2D coordinate;
coordinate.latitude = 25.886099;
coordinate.longitude = -80.165124;
self.someRegion = [[CLCircularRegion alloc] initWithCenter:coordinate radius:radius identifier:#"Qualex"];
self.someRegion.notifyOnEntry = YES;
self.someRegion.notifyOnExit = YES;
[self.locationManager startMonitoringForRegion:self.someRegion];
// notify changes when the device has moved x meters
self.locationManager.distanceFilter = 20; // or set to 20 meters
self.locationManager.desiredAccuracy = kCLLocationAccuracyBest;
self.locationManager.activityType = CLActivityTypeAutomotiveNavigation;
[self.locationManager startUpdatingLocation];
[self.locationManager startMonitoringSignificantLocationChanges];
}
I also have set the NSLocationAlwaysUsageDescription in my info.plist, so there must be something I've forgotten, right? Thanks for the help!
Edit:
I'm also registering for remote notifications at the same time, that's never been a problem before but I thought it might be some useful extra information.
Also, when terminated the app then re-run the notification to allow location services pops up, but goes away instantly. Just flashes on the screen. I have no idea why it would dismiss without clicking one of the options on the alert.

Before iOS 8, you could request location permission simply by instantiating a CLLocationManager object and attempting to start location tracking. On iOS 8 and above, this does not present a permission prompt; you must request authorization manually with either the requestAlwaysAuthorization or requestWhenInUseAuthorization methods.
That being said, on iOS 8, if you call either of those methods, then the CLLocationManager instance on which you called it is released, the location permission prompt will dismiss itself. What's happening here is that you are creating a location manager, requesting permission (iOS starts to try to present the permission dialog), calling initializeRegionMonitoring, and setting the self.locationManager property to a new location manager instance. This causes the first one you created to get released by ARC, so the permission prompt is dismissed before it even gets a chance to appear.
Removing the line self.locationManager = [[CLLocationManager alloc] init]; in your initializeRegionMonitoring method should fix the issue.

Related

Why does the device stop recieving locations on iOS after two minutes gps on?

// Create a location manager object
self.locationManagerTest = [[CLLocationManager alloc] init];
// Set the delegate
self.locationManagerTest.delegate = self;
// Request location authorization
[self.locationManagerTest requestAlwaysAuthorization];
// Specify the type of activity your app is currently performing
self.locationManagerTest.activityType = CLActivityTypeOtherNavigation;
// Start location updates
[self.locationManagerTest startUpdatingLocation];
1.after 2 weeks struggling on this problem finally solved it. Just needed to check apple documentation. I just needed to add two lines:
self.locationManagerTest = [[CLLocationManager alloc] init];
// Set the delegate
self.locationManagerTest.delegate = self;
// Request location authorization
[self.locationManagerTest requestWhenInUseAuthorization];
// Set an accuracy level. The higher, the better for energy.
self.locationManagerTest.desiredAccuracy = kCLLocationAccuracyThreeKilometers;
// Enable automatic pausing
self.locationManagerTest.pausesLocationUpdatesAutomatically = NO;
// Specify the type of activity your app is currently performing
self.locationManagerTest.activityType = CLActivityTypeFitness;
// Enable background location updates
self.locationManagerTest.allowsBackgroundLocationUpdates = YES;
// Start location updates
[self.locationManagerTest startUpdatingLocation];
in Capabilities/Background modes/ turn on location updates
and info.plist add this key "Privacy - Location Always Usage Description"
hope this helped

Is there anyway to monitor CLBeaconRegion without using CLLocationManager

In my current app i am using
self.locationManager = [[CLLocationManager alloc] init];
if ([_locationManager respondsToSelector:#selector(requestAlwaysAuthorization)])/
[_locationManager requestAlwaysAuthorization];
//self.locationManager.allowsBackgroundLocationUpdates = YES;
self.locationManager.delegate = self;
[self.locationManager startMonitoringForRegion:tempRegio
[self.locationManager startRangingBeaconsInRegion:beaconRegion];
in this case nowhere i need to know user's location still my app asks that it will use you current location even when you're not using this app
Which is annoying for end user plus it constantly display purple arrow on the statubar indicating that the app uses GPS (Which it does not )
My question is
Can we have mechanism where we can scan the beacon without use of CLLocationManager
1 possible solution is to use CBCentralManager but i do not find a proper way where i can use it to detect beacons/ibeacons
Thanks

iOS 8 CLLocationManager enterRegion: not getting called if use requestWhenInUseAuthorization

I'm trying to get being called the delegate method locationManager:didEnterRegion in iOS 8 for custom region. Here is the code:
self.locationManager = [[CLLocationManager alloc] init];
self.locationManager.delegate = self;
if ([self.locationManager respondsToSelector:#selector(requestWhenInUseAuthorization)]) {
[self.locationManager requestWhenInUseAuthorization];
}
CLCircularRegion *region = [[CLCircularRegion alloc] initWithCenter:CLLocationCoordinate2DMake(20, 20) radius:1000 identifier:#"asda"];
region.notifyOnEntry = YES;
region.notifyOnExit = YES;
[self.locationManager startMonitoringForRegion:region];
It does call method locationManager:didStartMonitoringForRegion, but it doesn't call "enter" or "exit" region methods.
The one more strange thing is that it DOES work if I use requestAlwaysAuthorization for locationManager. But I need to get it worked with "When In Use".
Note: In iOS7 it works for both WhenInUse and Always Authorization methods.
region monitoring - it's not working with requestWhenInUseAuthorization
check Apple Docs:
".. “when-in-use” ... Apps cannot use any services that automatically relaunch the app, such as region monitoring or the significant location change service"
You must call requestAlwaysAuthorization!!!
https://developer.apple.com/library/ios/documentation/CoreLocation/Reference/CLLocationManager_Class/index.html#//apple_ref/occ/instm/CLLocationManager/requestWhenInUseAuthorization

Get User location alert does not stay on screen in iOS 8

I am trying to get authorization from user before fetching his location. I am using this code for that:
self.locationManager = [[CLLocationManager alloc] init];
[self.locationManager setDelegate:self];
if ([self.locationManager respondsToSelector:#selector(requestAlwaysAuthorization)]) {
// iOS8+
// Sending a message to avoid compile time error
[self.locationManager requestAlwaysAuthorization];
}
[self showIndicatorView];
self.getCityService = [[GetCitiesService alloc] initServiceWithDelegate:self isLocalCall:NO];
[self.getCityService fetchCities];
I see the alert on screen but before I allow it or not, it disappear form screen and app is not authorized.
I want my code to stop until user gives permission.
Apparently in iOS 8 SDK, requestAlwaysAuthorization (for background location) or requestWhenInUseAuthorization (location only when foreground) call on CLLocationManager is needed before starting location updates.
There also needs to be NSLocationAlwaysUsageDescription or NSLocationWhenInUseUsageDescription key in Info.plist with a message to be displayed in the prompt. Adding these solved my problem.
Hope it helps someone else.
EDIT: For more extensive information, have a look at: http://nevan.net/2014/09/core-location-manager-changes-in-ios-8/
You code looks really weird, since you seem to be calling the requestAlwaysAuthorization twice. Once on self.locationManager and once via the sendAction.
You code should look like:
self.locationManager = [[CLLocationManager alloc] init];
[self.locationManager setDelegate:self];
if ([self.locationManager respondsToSelector:#selector(requestAlwaysAuthorization)]) {
// iOS8+
// Sending a message to avoid compile time error
[self.locationManager requestAlwaysAuthorization];
}

iOS App gets invalid user location

when I'm trying to show the user location on my map it shows the location is somewhere in the ocean (lat = 0.000 , lon = 0.000) , I have set the simulated location to be in london and still nothing.
when i try to compile the app on my iphone its doesn't ask for permission to get user current location , just when i enable the app for using location services in the iphone settings , the app shows the user current location.
any idea why it does it?
this is my viewDidLoad :
_locationManager = [[CLLocationManager alloc] init];
_locationManager.delegate = self;
_locationManager = [[CLLocationManager alloc] init];
if(IS_OS_8_OR_LATER) {
[_locationManager requestWhenInUseAuthorization];
[_locationManager requestAlwaysAuthorization];
}
_locationManager.distanceFilter = kCLDistanceFilterNone; // whenever we move
_locationManager.desiredAccuracy = kCLLocationAccuracyBest;
[_locationManager startUpdatingLocation];
There is no need to adding both they both do different things
[_locationManager requestWhenInUseAuthorization];
[_locationManager requestAlwaysAuthorization];
requestWhenInUseAuthorization
use [_locationManager requestWhenInUseAuthorization]; when you want to get location updates when app is Active of foreground mode and not when in background .
requestAlwaysAuthorization
use [_locationManager requestAlwaysAuthorization]; when you want to get location updates Even when your app is in background mode. So OS would ask for permissions accordingly
Adding Keys to info.Plist
It is now mandetory to add either NSLocationWhenInUseUsageDescription or NSLocationAlwaysUsageDescription Key to your info.Plist depending upon which permission you are asking for .
The value to this key should be a NSString explaining user why the app wants to use location services something like "We need your location for XYZ reason"
If iOS does not find above key in your Plist file , it will ignore location request.
Hope this helps. By the way I reccomand you to watch WWDC 2014 video "Whats new in Core Location", all iOS8 changes have been nicely explained.
Other Changes in Code
Also one more thing i see in your code , You are creating new instance of _locationManager in 3rd line , Means you are creating new object after assigning delegate to locationManager, should not do that too.

Resources