您可以使用 Photos Framework 和 UIImagePickerControllerDelegate 方法修改 PHAsset(例如添加位置元数据)。没有第三方图书馆的开销,没有创建重复的照片。适用于 iOS 8.0+
在didFinishPickingMediaWithInfo委托方法中,调用UIImageWriteToSavedPhotosAlbum首先保存图片。这也将创建我们将修改其 EXIF GPS 数据的 PHAsset:
func imagePickerController(picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : AnyObject]) {
if let myImage = info[UIImagePickerControllerOriginalImage] as? UIImage {
UIImageWriteToSavedPhotosAlbum(myImage, self, Selector("image:didFinishSavingWithError:contextInfo:"), nil)
}
}
完成选择器功能将在保存完成或失败并出现错误后运行。在回调中,获取新创建的 PHAsset。然后,创建一个 PHAssetChangeRequest 来修改位置元数据。
func image(image: UIImage, didFinishSavingWithError: NSErrorPointer, contextInfo:UnsafePointer<Void>) {
if (didFinishSavingWithError != nil) {
print("Error saving photo: \(didFinishSavingWithError)")
} else {
print("Successfully saved photo, will make request to update asset metadata")
// fetch the most recent image asset:
let fetchOptions = PHFetchOptions()
fetchOptions.sortDescriptors = [NSSortDescriptor(key: "creationDate", ascending: true)]
let fetchResult = PHAsset.fetchAssetsWithMediaType(PHAssetMediaType.Image, options: fetchOptions)
// get the asset we want to modify from results:
let lastImageAsset = fetchResult.lastObject as! PHAsset
// create CLLocation from lat/long coords:
// (could fetch from LocationManager if needed)
let coordinate = CLLocationCoordinate2DMake(myLatitude, myLongitude)
let nowDate = NSDate()
// I add some defaults for time/altitude/accuracies:
let myLocation = CLLocation(coordinate: coordinate, altitude: 0.0, horizontalAccuracy: 1.0, verticalAccuracy: 1.0, timestamp: nowDate)
// make change request:
PHPhotoLibrary.sharedPhotoLibrary().performChanges({
// modify existing asset:
let assetChangeRequest = PHAssetChangeRequest(forAsset: lastImageAsset)
assetChangeRequest.location = myLocation
}, completionHandler: {
(success:Bool, error:NSError?) -> Void in
if (success) {
print("Succesfully saved metadata to asset")
print("location metadata = \(myLocation)")
} else {
print("Failed to save metadata to asset with error: \(error!)")
}