Maps & Location

RSS for tag

Learn how to integrate MapKit and Core Location to unlock the power of location-based features in your app.

Maps & Location Documentation

Post

Replies

Boosts

Views

Activity

CLLocationManager: getting kCLErrorDenied in widget
I am having some problem with accessing the CLLLocationManager location from my widget. It works fine with Xcode 15 running on a iOS17 simulator. But running it on a iOS17 device gives me an error in the delegate: To access the location manager, I have this class: class WidgetLocationManager: NSObject, CLLocationManagerDelegate { var locationManager: CLLocationManager? private var handler: ((CLLocation?) -> Void)? override init() { super.init() DispatchQueue.main.async { print("WidgetLocationManager: init") self.locationManager = CLLocationManager() if self.locationManager!.authorizationStatus == .notDetermined { print("WidgetLocationManager: init - auth status is Undetermined") } else { print("WidgetLocationManager: init - auth status = \(self.locationManager!.authorizationStatus)") } } } func fetchLocation(handler: @escaping (CLLocation?) -> Void) { self.handler = handler self.locationManager = CLLocationManager() self.locationManager!.delegate = self self.locationManager!.requestLocation() } func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) { if let lastLocation = locations.last { if (CLLocationCoordinate2DIsValid(lastLocation.coordinate) == true && abs(lastLocation.timestamp.timeIntervalSinceNow) < 60 && lastLocation.horizontalAccuracy < 200.0 && lastLocation.horizontalAccuracy > 0.0) { self.handler!(locations.last!) } } } func locationManager(_ manager: CLLocationManager, didFailWithError error: Error) { print("WidgetLocationManager: locationManager didFailWithError = \(error)") self.handler!(nil) } } When run on device, I get an error: WidgetLocationManager: locationManager didFailWithError = Error Domain=kCLErrorDomain Code=1 "(null)" Code = 1 in CLError is kCLErrorDenied ("Access to location or ranging has been denied by the user") This is despite getting the following output in the init method: WidgetLocationManager: init - auth status = CLAuthorizationStatus(rawValue: 4) The weird thing is that it works fine in the simulator. On device, I've tried deleting and reinstalling the app a couple of times, restarting the device, making sure the privacy setting is correct etc. Also, on the iOS17 device, when I am in the "Add Widget" page, the location manager runs fine in the preview screen, and shows the 'current location' to the user. But as soon as I add the widget to the home screen, it starts giving me this problem where the location can't be found, and I have to display an error message in the widget. I have the following keys in the Info.plist for the widget: NSLocationAlwaysAndWhenInUseUsageDescription NSLocationWhenInUseUsageDescription NSWidgetWantsLocation The app target also has the following keys in the Info.plist: NSLocationWhenInUseUsageDescription NSLocationAlwaysAndWhenInUseUsageDescription Any idea for what I can try to fix this problem? Thanks.
2
0
920
Sep ’23
locationManager didUpdateLocations stops updating when phone is still
I built an autopilot for my boat, and took it further by writing an IOS app to control it via bluetooth with my phone. Everything was working great, until I thought I'd add the ability to navigate a route. Here's what has me stumped... I've got location manager generating updates, as long as the phone is moving (ever so slightly) in my hand. I've got the display setup to never sleep, and the phone is plugged in to power. If I put the phone down, I get a few new locations, then the location freezes. The didUpdateLocations delegate is called, but the location never changes. I've tried a number of settings but no matter what I try, none have solved the still phone issue. My current design uses self.locationManager?.requestLocation() sent on at programmable interval, so that I get updates with reasonable spacing. The updates come, but the location is identical if the phone is still (laying on the dash of the boat). If I just "wiggle" the phone a bit, locations come with a new value. If I keep "wiggling the phone, I get new locations every call to requestLocation. Seems like there is some kind of inactivity timer associated with didUpdataLocations that prevents retrieving new locations. It just re-sends the previous location. This issue has nothing to do with using requestLocation, since I had the same issue when didUpdateLocations was running on its own timing. I added the code and logic to support requestLocation in an attempt to force a new location. Has anyone experienced this or have any idea how to force a "new" location when the phone is still? I'm using Xcode Version 14.3.1 (14E300c) The phone is an iPhone 12 and the deployment target is set to 15.3 Here's how I currently configure location manager... This is one of a number of attempts, but all have the same issue. if locationManager == nil{ print("****** instantiating locationManager ******") locationManager = CLLocationManager() locationManager!.distanceFilter = kCLDistanceFilterNone // locationManager!.distanceFilter = 3 locationManager!.desiredAccuracy = kCLLocationAccuracyNearestTenMeters locationManager!.delegate = self locationManager!.showsBackgroundLocationIndicator = true locationManager!.startUpdatingLocation() locationManager!.startUpdatingHeading() locationManager!.allowsBackgroundLocationUpdates = true } }
2
0
617
Sep ’23
Using Core Location in App Intent
I would like to retrieve the user's current location when they are logging some information with my App Intent. When the app has been just run, this works just fine, but if it has been force quit or not run recently, the Core Location lookup times out. I have tried logging the information and using the Core Location background mode, and I can verify that the background mode is triggering because there is an indicator on the status bar, but the background mode does not seem to fire the delegate. Is there a good way to debug this? When I run the app, everything works just fine, but I can't confirm that delegate calls are going through because I can't debug from an App Intent launch. Here is the perform method from my App Intent func perform() async throws -> some ProvidesDialog { switch PersistenceController.shared.addItem(name: name, inBackground: true) { case .success(_): return .result(dialog: "Created new pin called \(name)") case .failure(let error): return .result(dialog: "There was a problem: \(error.localizedDescription)") } } addItem calls LocationManager.shared.getCurrentCoordinates: func getCurrentCoordinates(inBackground: Bool = false, callback: @escaping (CLLocation?) -> Void) { if lastSeenLocation != nil { callback(lastSeenLocation) return } if inBackground { locationManager.allowsBackgroundLocationUpdates = true locationManager.showsBackgroundLocationIndicator = false } let status = CLLocationManager.authorizationStatus() guard status == .authorizedAlways || status == .authorizedWhenInUse else { DispatchQueue.main.async { [weak self] in self?.callback?(nil) self?.locationManager.allowsBackgroundLocationUpdates = false } return } self.callback = callback locationManager.startUpdatingLocation() } The CLLocationManager delegate didUpdateLocations then calls the callback with the location and sets allowsBackgroundLocationUpdates to false. And the callback saves the location data to Core Data. What is the best practice for using Core Location in an App Intent?
0
0
453
Sep ’23
didRangeBeacons detects old beacons, and some inconsistencies in documentation
I have had some trouble with that "didRangeBeacons" was called with beacons that were not present. They were preset some minutes before. And these calls never seemed to stop coming. iOS must be storing the beacons somehow. My first idea was to update the deprecated "locationManager:didRangeBeacons:inRegion" to "locationManager:didRangeBeacons:satisfyingConstraint". But the type "CLBeaconIdentityConstraint" is also deprecated, use " CLBeaconIdentityCondition" instead. How can the type be deprecated, but not the function using it? I see no API functions for this new "CLBeaconIdentityCondition" type, e.g. something like "start/stopRangingBeaconsSatisfyingCondition" or "locationManager:didRangeBeacons:satisfyingCondition:".
0
0
256
Sep ’23
What is the right way to display user location on map
Hello, I am currently working on an app for a client. The concept is straightforward: the app allows users to view the location of other users on a map, even when they are not actively using the app. However, this feature is limited to a selected group of people, specifically those who have joined the same group as the user. To achieve this, I collect location data in the background. The primary objective of this app is to connect users with nearby individuals who can assist them with tasks or jobs. However, I encountered an issue during the app review process. The review team deemed it inappropriate for deployment because it displays users' locations on a map, without the necessary privacy safeguards in place. Nevertheless, the main purpose of the app is to allow users to be visible on the map, and people who download the app intend to be included in this display. Here is the comment provided by the reviewer: Your app enables the display of nearby users' locations on a map, but does not have the required privacy precautions in place. Additionally, here is the specific requirement: Require users to manually check-in each time they wish to have their location displayed on a map; there should be no option to enable automatic check-ins. If I understand correctly, this means that users would be required to open the app in order to appear on the map. However, this contradicts the purpose of the app, as users prefer to be passively visible without actively opening the app. On the other hand, I have noticed tracking apps like Life360 and others that provide similar functionalities. They display users' locations on a map in near-real-time. What am I missing to ensure the validity of my app? The reviewer mentioned being unable to provide any hints, so I am hopeful that someone here can assist me.
2
2
738
Jun ’23
Can't render MKPolylineRenderer in a MKMapView on emulator since iOS 16.4 / Xcode Version 14.3 (14E222b)
Hi, I updated Xcode to version 14.3 (14E222b) which comes with iOS 16.4 Also macOS has the latest update Ventura 13.3 (22E252) Mac hardware is a MacBook Pro M1 Max After the update in MapKit (Not SwiftUI) MKPolylineRenderer won't render any more in an iOS 16.4 emulator (but still works fine on a physical device). In the terminal I see many lines like this: "Compiler failed to build request" "PSO error: reading from a rendertarget is not supported" I don't see these lines on a physical device and the polylines render fine on a physical device. Has anybody else seen this? Anything I can do? Thanks Gerd P.S. workaround: works for me when I choose the target "My Mac (Designed for iPad)"
5
0
1.2k
Apr ’23
iOS Geolocation updates stop after 5 hours
@Gualtier Malde, My app has not been able to send location updates in the background past 5hrs even after implementing all the changes you specified The debugger spits out nothing .... allowsBackgroundLocationUpdates must be set to TRUE distanceFilter must not be set desiredAccuracy must be kCLLocationAccuracyHundredMeters or better. If you’re using numeric values, it must be set to less than 1000 meters (We set it to 100m) We have been losing hundreds of enterprise clients as a result of this, is there something we can do to ensure the behaviour is similar or same to iOS <16.4?
1
0
485
Sep ’23
Clustering stop working after removing all annotations
Hi!I noticed a strange behavior on MapKit when using the iOS 11 clustering feature.If you add some annotations on a map (with same clusteringIdentifier and same displayPriority) MapKit will correctly merge together annotations that are close.The problem is that if you remove all the annotations and then you add them back the map will no more merge the annotation together. It’s like the clustering feature simply stop working.I don’t really know if it is a bug or if I miss something.Someone else have noticed this?Alan
6
0
4.9k
Dec ’17
SwiftUI MapKit map style inconsistency
I am switchingt to the new WWDC 2023 SwiftUI map with user location and a few map annotations. I find if I use .mapStyle(.imagery(elevation: .flat)) as the map style, the map will be loaded with a reasonably zoomed area. However, if I use .mapStyle(.imagery(elevation: .realistic)) on the same map, the simulator will give me a view of the entire planet. I have to manually zoom in everytime to find the user location and annotations, which is not very convenient. This is the only map style configuration that does this. I am not very sure if this is a feature or a inconsistency bug. If this is a feature, I cannot see the purpose of it.
0
0
572
Aug ’23
CLLocationManager crashes when requestLocation is called from a widget
Hey yall--seemingly once in a blue moon whenever fetchLocation gets called in here from a widget that is requesting location, it calls on the manager's requestLocation, the widget will crash. Crash stack backtrace shows this: And this is the affected code: import Foundation import CoreLocation class WidgetLocationFetcher: NSObject, CLLocationManagerDelegate { let manager = CLLocationManager() private var handler: ((CLLocation?) -> Void)? override init() { super.init() DispatchQueue.main.async { self.manager.delegate = self self.manager.requestWhenInUseAuthorization() } } func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) { self.handler?(locations.last!) self.handler = nil } func locationManager(_ manager: CLLocationManager, didFailWithError error: Error) { print(error) self.handler?(nil) self.handler = nil } func fetchLocation(handler: @escaping (CLLocation?) -> Void) { self.handler = handler self.manager.requestLocation() } } I am not too sure what could even be causing this, although I am running watchOS 10 beta 8 and iPadOS 17 beta 8 on the devices experiencing this crash. Has anyone ever solved this issue?
1
0
471
Aug ’23
MKMapSnapshotter/VectorKit crash since iOS 16
We "recently" started getting crashes when taking a satelite map snapshot in app using MKMapSnapshotter. We realized that all crashes have a common denominator that they all happened on iOS 16. The code that creates the snapshot has been unaltered and working without crashes since 2018 up until the release of iOS 16. This is likely some bug in the SDK. let options = MKMapSnapshotter.Options() let location = CLLocationCoordinate2D(latitude: latitude, longitude: longitude) options.mapType = .satelliteFlyover options.size = size options.camera = MKMapCamera(lookingAtCenter: location, fromDistance: distance, pitch: 0, heading: 0) let snapshotter = MKMapSnapshotter(options: options) snapshotter.start(completionHandler: completionHandler) Crashed: com.apple.maps.snapshotter 0 VectorKit 0x95d8f0 ggl::Renderer::removeDebugRenderer(std::__1::shared_ptr<ggl::DebugRenderer> const&) + 40 1 VectorKit 0x5cc588 md::DebugConsoleManager::~DebugConsoleManager() + 120 2 VectorKit 0x5cc588 md::DebugConsoleManager::~DebugConsoleManager() + 120 3 VectorKit 0x14e4f4 std::__1::unique_ptr<md::DebugConsoleManager, std::__1::default_delete<md::DebugConsoleManager> >::reset(md::DebugConsoleManager*) + 32 4 VectorKit 0x1b4a48 -[GGLImageCanvas .cxx_destruct] + 36 5 libobjc.A.dylib 0x14a4 object_cxxDestructFromClass(objc_object*, objc_class*) + 116 6 libobjc.A.dylib 0x621c objc_destructInstance + 80 7 libobjc.A.dylib 0xf9d0 _objc_rootDealloc + 80 8 VectorKit 0x145958 -[GGLImageCanvas dealloc] + 44 9 VectorKit 0x6eacc md::MapEngine::~MapEngine() + 1644 10 VectorKit 0x133e6c md::MapEngine::~MapEngine() + 16 11 VectorKit 0x33b30 -[VKMapSnapshotCreator softDealloc] + 352 12 VectorKit 0x33778 __42-[VKMapSnapshotCreator renderNextSnapshot]_block_invoke + 904 13 libdispatch.dylib 0x24b4 _dispatch_call_block_and_release + 32 14 libdispatch.dylib 0x3fdc _dispatch_client_callout + 20 15 libdispatch.dylib 0xb694 _dispatch_lane_serial_drain + 672 16 libdispatch.dylib 0xc214 _dispatch_lane_invoke + 436 17 libdispatch.dylib 0x16e10 _dispatch_workloop_worker_thread + 652 18 libsystem_pthread.dylib 0xdf8 _pthread_wqthread + 288 19 libsystem_pthread.dylib 0xb98 start_wqthread + 8
7
1
2.2k
Jan ’23
MapKitJS - Service Requests
Hi everyone, I just implemented MapKitJS into my Ionic Vue app. At the same time I noticed a disproportionate amount of service calls (see image) without implementing dedicated calls to the Apple Maps Server API for example for autocompletion. Therefore the question arrised: Are those service calls mentioned in the MapKitJS Dashboard something differenent to the Apple Maps Server API, due to both disclaimed with 25k service calls free per month. Added to that, what causes those services calls in the MapKitJS implementation and how can it be made more efficent to make optimal use of the Apple Maps Server API calls? Thanks for clarifing and helping out.
0
1
588
Aug ’23
CLMonitor Limitations
Hello all! Apple presented the all-new Core Location Monitor at WWDC 2023. It changes the logic of monitoring for iBeacons with a new approach of adding CLCondition-s for monitoring iBeacon values like UUID, major, and minor. This, I suppose (please do feel free to correct me) is meant to replace current (now deprecated) startMonitoring implementation. Now, we it's a fact that it is impossible to monitor more than 20 regions at once. Question: does the new CLMonitor let us bypass this limit? If not, what's the maximum number of CLConditions we can add to a CLMonitor?
0
0
458
Aug ’23
MapKit - Look Around - isNavigationEnabled not working?
I'm adding Look Around into my app, but settings isNavigationEnabled to true or false does nothing. This bool is set to true by default, and my understanding is that it will enable the user to navigate around the location. I tried setting it to false and that didn't change the experience as the user was able to rotate the camera 360 degrees, but not move around freely in the area. Is this by design or am I missing something? Note: I'm on the latest Xcode 14 beta (beta 6). Here is my basic implementation: let lookAroundRequest = MKLookAroundSceneRequest(coordinate: location.coordinate!) lookAroundRequest.getSceneWithCompletionHandler { lookAroundScene, error in guard error == nil, lookAroundScene != nil else { return } let lookAroundVC = MKLookAroundViewController(scene: lookAroundScene!) lookAroundVC.pointOfInterestFilter = .includingAll self.present(lookAroundVC) }
3
0
1.5k
Aug ’22