發送地理位置在社交應用里面是很常用的需求。最近也需要在自己的應用里面加入這個功能
首先我們需要獲取自己的地理位置,這里用到 CLLocationManager 這個類,調用如下代碼
locationManager = CLLocationManager()
locationManager.requestAlwaysAuthorization()
locationManager.delegate = self // 在成功獲取位置后,就會把位置回調給 self
locationManager.distanceFilter = kCLDistanceFilterNone
locationManager.desiredAccuracy = kCLLocationAccuracyBest
locationManager.startUpdatingLocation() // 在執行這個方法之后,系統就會不斷獲取手機所在的位置并且把這個位置回調給應用
我們在回調方法里面獲取該這個地理位置
func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
locationManager.stopUpdatingLocation() // 注意這個地方需要關閉定位,不然會不斷的回調這個方法
manager.delegate = nil; // 不加這段代碼可能還是會調用幾次
let location = locations[0] //這個就是我們當前所在的位置 類型為:CLLocation ,里面包含了經度和緯度
}
如果要達到微信那種預覽位置效果的話,我們需要通過位置獲取一張截圖, 因為我們不可能放一個 mapView 到消息列表上,這樣內存肯定受不了。
所以我們使用 MKMapSnapshotter, 這個類可以獲取地圖上的一小塊截圖,代碼如下
let mapShoot = MKMapSnapshotter(options: options)
mapShoot.start { (mapshoot, error) in
let image = mapshoot!.image // 這就是我們需要的位置截圖
let finalImageRect = CGRect(x: 0, y: 0, width: image.size.width, height: image.size.height)
// 如果想在地圖上加入一個大頭針,可以直接繪制上去,就像下面一樣
let pin = MKPinAnnotationView()
let pinImage = pin.image
UIGraphicsBeginImageContextWithOptions(image.size, true, image.scale)
image.draw(at: CGPoint(x: 0, y: 0))
pinImage?.draw(at: CGPoint(x: finalImageRect.size.width/2, y: finalImageRect.size.height/2))
let finalImage = UIGraphicsGetImageFromCurrentImageContext()
self.locationDelegate.locationImageCallBack(location: location,image: finalImage)
}
之后的就只需要處理發送位置和接收位置消息了。 如果想看源碼可以點擊傳送門 源碼 在 dev 分支