So, I am trying to get my Location inside a function of my ViewController.swift.
The Code I use works when i try it like this:
import UIKit
import CoreLocation
class ViewController: UIViewController, CLLocationManagerDelegate {
var manager : CLLocationManager!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
manager = CLLocationManager()
manager.delegate = self
manager.desiredAccuracy = kCLLocationAccuracyHundredMeters
manager.requestAlwaysAuthorization()
manager.startUpdatingLocation()
}
func locationManager(manager: CLLocationManager!, didUpdateLocations locations: [AnyObject]!) {
var locValue : CLLocationCoordinate2D
locValue = manager.location.coordinate
println("Coordinates = \(locValue.longitude) + \(locValue.latitude)")
manager.stopUpdatingLocation()
}
But what I am trying to do is get it while pressing a button which toggles a function:
var manager : CLLocationManager!
override func viewDidLoad() {
super.viewDidLoad()
manager = CLLocationManager()
manager.delegate = self
manager.desiredAccuracy = kCLLocationAccuracyHundredMeters
manager.requestAlwaysAuthorization()
manager.startUpdatingLocation()
}
func locationManager(manager: CLLocationManager!, didUpdateLocations locations: [AnyObject]!) {
var locValue: CLLocationCoordinate2D = manager.location.coordinate
println("locations = \(locValue.longitude) \(locValue.latitude)")
manager.stopUpdatingLocation()
}
#IBAction func refresh() {
getWeatherData()
refreshButton.hidden = true
acitivityIndicatorView.hidden = false
acitivityIndicatorView.startAnimating()
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
}
func getWeatherData() -> Void {
func locationManager(manager: CLLocationManager, didUpdateLocations locations: [AnyObject]!) {
var locValue: CLLocationCoordinate2D = manager.location.coordinate
println("locations = \(locValue.longitude) \(locValue.latitude)")
manager.stopUpdatingLocation()
While using a breakpoint i realized it gets to func locationManager but it jumps to the end of my getweatherdata() function.
I can't see why it doesn't work.
What you are doing is not possible. Inly thing you can do is call manager.startUpdatingLocation() inside refresh() and wait till didUpdateLocations get called with the updated location data.
#IBAction func refresh() {
manager.startUpdatingLocation()
refreshButton.hidden = true
acitivityIndicatorView.hidden = false
activityIndicatorView.hidesWhenStopped = true
acitivityIndicatorView.startAnimating()
}
func locationManager(manager: CLLocationManager!, didUpdateLocations locations: [AnyObject]!) {
var locValue: CLLocationCoordinate2D = manager.location.coordinate
println("locations = \(locValue.longitude) \(locValue.latitude)")
manager.stopUpdatingLocation()
refreshButton.hidden = false
acitivityIndicatorView.stopAnimating()
}
Related
I have the function "locationManager" where I create and set longitude and latitude. What I want to do is be able to get that location when the button is pushed. How can I get longitude and latitude into the #IBAction for when I press that button? Than you so much for your help!
import UIKit
import CoreLocation
class ViewController: UIViewController, CLLocationManagerDelegate {
let locationManager = CLLocationManager()
override func viewDidLoad() {
super.viewDidLoad()
setupLocationManager()
}
func setupLocationManager() {
locationManager.delegate = self
locationManager.desiredAccuracy = kCLLocationAccuracyNearestTenMeters
locationManager.requestWhenInUseAuthorization()
locationManager.startUpdatingLocation()
}
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
if let location = locations.last {
if location.horizontalAccuracy > 0 {
locationManager.stopUpdatingLocation()
let longitude = location.coordinate.longitude
let latitude = location.coordinate.latitude
print("longitude = \(longitude)")
print("latitude = \(latitude)")
}
}
}
func locationManager(_ manager: CLLocationManager, didFailWithError error: Error) {
print("Location update failed, \(error)")
}
#IBAction func buttonPressed(_ sender: UIButton) {
// print(longitude)
}
}
Define your location variable if class scope
fileprivate var mylocation:CLLocation?
set mylocation in
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
if let location = locations.last {
if location.horizontalAccuracy > 0 {
locationManager.stopUpdatingLocation()
myLocation = location
}
}
}
now you can access location when button tap
#IBAction func buttonPressed(_ sender: UIButton) {
let longitude = myLocation.coordinate.longitude
let latitude = myLocation.coordinate.latitude
print("longitude = \(longitude)")
print("latitude = \(latitude)")
}
Is there any way to reduce the number of times the locationManager updates? Currently is updated over 100 times in 30 seconds! My app collects the coordinates of the user and pushes this to a database, But I'm collecting too many coordinates.
Can I reduce the number of times the app updates user location?
func locationManager(_ manager: CLLocationManager, didUpdateLocations
locations: [CLLocation]) {
let lat = LocationManager.sharedInstance.location.coordinate.latitude
let long = LocationManager.sharedInstance.location.coordinate.longitude
}
Use CLLocationManager's distanceFilter property.
import UIKit
import MapKit
import CoreLocation
class ViewController: UIViewController, MKMapViewDelegate, CLLocationManagerDelegate {
// MARK: - Variables
let locationManager = CLLocationManager()
// MARK: - IBOutlets
#IBOutlet weak var mapView: MKMapView!
// MARK: - IBAction
// MARK: - Life cycle
override func viewDidLoad() {
super.viewDidLoad()
/* delegate */
mapView.delegate = self
locationManager.delegate = self
locationManager.requestWhenInUseAuthorization()
}
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
/* checking location authorization */
checkLocationAuthorizationStatus()
if CLLocationManager.locationServicesEnabled() {
locationManager.startUpdatingLocation()
locationManager.allowsBackgroundLocationUpdates = true
locationManager.pausesLocationUpdatesAutomatically = false
locationManager.desiredAccuracy = kCLLocationAccuracyBest
locationManager.distanceFilter = 20.0 // 20.0 meters
}
}
// MARK: - Authorization
func checkLocationAuthorizationStatus() {
if CLLocationManager.authorizationStatus() == .authorizedWhenInUse || CLLocationManager.authorizationStatus() == .authorizedAlways {
} else {
locationManager.requestWhenInUseAuthorization()
}
}
// MARK: - CLLocationManager delegate methods
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
guard let mostRecentLocation = locations.last else {
return
}
print(mostRecentLocation)
}
}
How i can draw user's route in `mapView?
My map is work, but route is not drawing.
No errors.
For example:
User's route
My code:
class ViewController: UIViewController, CLLocationManagerDelegate, MKMapViewDelegate {
#IBOutlet weak var mapView: MKMapView!
var locationManager: CLLocationManager!
override func viewDidLoad() {
super.viewDidLoad()
locationManager = CLLocationManager()
locationManager.desiredAccuracy = kCLLocationAccuracyBest
locationManager.delegate = self
locationManager.requestAlwaysAuthorization()
locationManager.requestWhenInUseAuthorization()
locationManager.startUpdatingLocation()
locationManager.startUpdatingHeading()
mapView.delegate = self
mapView.showsUserLocation = true
mapView.mapType = MKMapType(rawValue: 0)!
mapView.userTrackingMode = MKUserTrackingMode(rawValue: 2)!
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func locationManager(manager: CLLocationManager!, didUpdateToLocation newlocation: CLLocation!, fromLocation oldLocation: CLLocation!) {
print("present location : \(newlocation.coordinate.latitude), \(newlocation.coordinate.longitude)")
if let oldLocationNew = oldLocation as CLLocation?{
let oldCoordinates = oldLocationNew.coordinate
let newCoordinates = newlocation.coordinate
var area = [oldCoordinates, newCoordinates]
var polyline = MKPolyline(coordinates: &area, count: area.count)
mapView.add(polyline)
}
}
func mapView(_ mapView: MKMapView, rendererFor overlay: MKOverlay) -> MKOverlayRenderer {
let pr = MKPolylineRenderer(overlay: overlay)
pr.strokeColor = UIColor.red
pr.lineWidth = 5
return pr
}
}
But it doesn't work.
I asume you used the following delegate to get the last position?
func locationManager(manager: CLLocationManager!,
didUpdateToLocation newlocation: CLLocation!,
fromLocation oldLocation: CLLocation!) {
The delegate above is deprecated in iOS 6. Now the following should be used:
func locationManager(_ manager: CLLocationManager,
didUpdateLocations locations: [CLLocation]) {
In order to get the last position, simply get the last object of the array:
locations.lastObject
Try the following code to draw user's route:
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
guard let newLocation = locations.last else {
return
}
guard let oldLocation = oldLocation else {
// Save old location
self.oldLocation = newLocation
return
}
let oldCoordinates = oldLocation.coordinate
let newCoordinates = newLocation.coordinate
var area = [oldCoordinates, newCoordinates]
let polyline = MKPolyline(coordinates: &area, count: area.count)
mapView.add(polyline)
// Save old location
self.oldLocation = newLocation
}
I'm new to swift - currently, my current location is only output once in the console when I first call setupLocationManager() on init through override func awakeFromNib(). When I want it to output my new location by calling locationManager.startUpdatingLocation() when I click a button with the method updateLocation(), it prints an error. Any way to fix this? All help is appreciated.
import Cocoa
import CoreLocation
class StatusMenuController: NSObject, CLLocationManagerDelegate {
#IBOutlet weak var statusMenu: NSMenu!
let statusItem = NSStatusBar.system().statusItem(withLength: NSVariableStatusItemLength)
var locationManager:CLLocationManager!
var currentLocation:CLLocation?
#IBAction func quitClicked(_ sender: NSMenuItem) {
NSApplication.shared().terminate(self)
}
#IBAction func updateClicked(_ sender: NSMenuItem) {
updateLocation()
}
func updateLocation() {
locationManager.startUpdatingLocation()
}
override func awakeFromNib() {
statusItem.menu = statusMenu
let icon = NSImage(named: "statusIcon")
icon?.isTemplate = true
statusItem.image = icon
statusItem.menu = statusMenu
setupLocationManager()
}
func setupLocationManager(){
locationManager = CLLocationManager()
locationManager?.delegate = self
//self.locationManager?.requestAlwaysAuthorization()
locationManager?.desiredAccuracy = kCLLocationAccuracyNearestTenMeters
locationManager?.startUpdatingLocation()
}
// Below method will provide you current location.
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
if currentLocation == nil {
currentLocation = locations.last
locationManager?.stopMonitoringSignificantLocationChanges()
let locationValue:CLLocationCoordinate2D = manager.location!.coordinate
print(locationValue)
locationManager?.stopUpdatingLocation()
}
}
// Below Method will print error if not able to update location.
func locationManager(_ manager: CLLocationManager, didFailWithError error: Error) {
print("Error")
}
}
There is an if condition in the code which suspends updating the location after the location is set once (if currentLocation == nil). You have to reset currentLocation to nil before restarting the manager.
#IBAction func updateClicked(_ sender: NSMenuItem) {
currentLocation = nil
updateLocation()
}
The delegate Methods of CLLocationManager
didChangeAuthorizationStatus
and
didUpdateToLocation
are not getting called.
Location Always Usage Description key is already added in info.plist and I am getting notification also when i launch app for the first time.
I am able to see the google map, but i am not able to see current location, When i change location, its not getting updated. Basicaaly delegate methods are not getting called.
//code
import UIKit
import GoogleMaps
class ViewController: UIViewController,GMSMapViewDelegate {
#IBOutlet weak var mapViewTest: GMSMapView!
let locationManager = CLLocationManager()
var currentLocation :CLLocation = CLLocation(latitude: 0.0, longitude: 0.0)
var currentLatitude : Double = 0.0
var currentLongitude : Double = 0.0
override func viewDidLoad()
{
super.viewDidLoad()``
locationManager.delegate = self
if (CLLocationManager.locationServicesEnabled())
{
locationManager.desiredAccuracy = kCLLocationAccuracyBest
locationManager.allowsBackgroundLocationUpdates = true
locationManager.requestAlwaysAuthorization()
locationManager.startUpdatingLocation()
}
// Do any additional setup after loading the view, typically from a nib.
}
}
extension ViewController : CLLocationManagerDelegate
{
func locationManager(manager: CLLocationManager, didChangeAuthorizationStatus status: CLAuthorizationStatus)
{
if status == .authorizedAlways
{
if(CLLocationManager .locationServicesEnabled())
{
locationManager.startUpdatingLocation()
mapViewTest.isMyLocationEnabled = true
mapViewTest.settings.myLocationButton = true
}
}
}
func locationManager(manager: CLLocationManager, didUpdateToLocation newLocation: CLLocation, fromLocation oldLocation: CLLocation)
{
mapViewTest.camera = GMSCameraPosition(target: (newLocation.coordinate), zoom: 15, bearing: 0, viewingAngle: 0)
currentLocation = newLocation
currentLatitude = newLocation.coordinate.latitude
currentLongitude = newLocation.coordinate.longitude
}
func locationManager(manager: CLLocationManager, didFailWithError error: NSError)
{
print("Errors: " + error.localizedDescription)
}
}
From your code you are working with Swift 3, and in Swift 3 CLLocationManagerDelegate method's signature is changed like this.
func locationManager(_ manager: CLLocationManager, didChangeAuthorization status: CLAuthorizationStatus) {
}
//func locationManager(_ manager: CLLocationManager, didUpdateTo newLocation: CLLocation,
from oldLocation: CLLocation) is deprecated with below one
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
}
func locationManager(_ manager: CLLocationManager, didFailWithError error: Error) {
}
Check Apple Documentation on CLLocationManagerDelegate for more details.
After checking your code i found some changes you needs to do as follow,
note : I have only added the code having issue here that of location manager
import UIKit
import CoreLocation
class ViewController: UIViewController {
let locationManager = CLLocationManager()
var currentLocation :CLLocation = CLLocation(latitude: 0.0, longitude: 0.0)
var currentLatitude : Double = 0.0
var currentLongitude : Double = 0.0
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
locationManager.delegate = self
if (CLLocationManager.locationServicesEnabled())
{
locationManager.desiredAccuracy = kCLLocationAccuracyBest
locationManager.allowsBackgroundLocationUpdates = true
locationManager.requestAlwaysAuthorization()
locationManager.startUpdatingLocation()
}
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
}
extension ViewController : CLLocationManagerDelegate {
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
}
func locationManager(_ manager: CLLocationManager, didFinishDeferredUpdatesWithError error: Error?) {
print("Errors: " + (error?.localizedDescription)!)
}
}
Also add below lines in .plist file if not added,
<key>NSLocationWhenInUseUsageDescription</key>
<string>$(PRODUCT_NAME) location use</string>
<key>NSLocationAlwaysUsageDescription</key>
<string>$(PRODUCT_NAME) always uses location </string>
Add these two properties in your info.plist
NSLocationWhenInUseUsageDescription
NSLocationAlwaysUsageDescription
you need to put the mapview delegate to self.
try this:
override func viewDidLoad() {
super.viewDidLoad()
// User Location Settings
locationManager.delegate = self
locationManager.requestWhenInUseAuthorization()
locationManager.desiredAccuracy = kCLLocationAccuracyBest
locationManager.startUpdatingLocation()
// Google Maps Delegate
mapView.delegate = self
}
// View will appear
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
// Google maps settings
mapView.isMyLocationEnabled = true
mapView.settings.myLocationButton = true
// Get location if autorized
if (CLLocationManager.authorizationStatus() == CLAuthorizationStatus.authorizedWhenInUse) {
let (latitude, longitude) = self.getLocation()
mapView.camera = GMSCameraPosition.camera(
withLatitude: latitude,
longitude: longitude,
zoom: 14)
}
}
//Get the user location
func getLocation() -> (latitude: CLLocationDegrees, longitude: CLLocationDegrees) {
let latitude = (locationManager.location?.coordinate.latitude)!
let longitude = (locationManager.location?.coordinate.longitude)!
return (latitude, longitude)
}