我想在给定图片网址的情况下将图片附加到我的本地通知中。这是创建附件的扩展程序:
import UserNotifications
extension UNNotificationAttachment {
static func create(identifier: String, image: UIImage, options: [NSObject : AnyObject]?) -> UNNotificationAttachment? {
let fileManager = FileManager.default
let tmpSubFolderName = ProcessInfo.processInfo.globallyUniqueString
let tmpSubFolderURL = URL(fileURLWithPath: NSTemporaryDirectory()).appendingPathComponent(tmpSubFolderName, isDirectory: true)
do {
try fileManager.createDirectory(at: tmpSubFolderURL, withIntermediateDirectories: true, attributes: nil)
let imageFileIdentifier = identifier+".png"
let fileURL = tmpSubFolderURL.appendingPathComponent(imageFileIdentifier)
guard let imageData = UIImagePNGRepresentation(image) else {
return nil
}
try imageData.write(to: fileURL)
let imageAttachment = try UNNotificationAttachment.init(identifier: imageFileIdentifier, url: fileURL, options: options)
return imageAttachment } catch {
print("error " + error.localizedDescription)
}
return nil
}
}
当我安排新通知时,我会这样使用它:
// url of the image such as http://www.unsplash.com/image.png
let data = try? Data(contentsOf: url)
guard let myImage = UIImage(data: data!) else { return }
if let attachment = UNNotificationAttachment.create(identifier: key, image: myImage, options: nil) {
content.attachments = [attachment]
}
创建这样的通知会冻结应用程序几秒钟,因为应用程序会同步下载图像。我也试过使用DispatchQueue
,但它没有改变任何东西。我做错了什么?
答案 0 :(得分:2)
您的代码下载图像,解析它以创建UIImage,将图像转换回PNG数据块,然后将此数据写入临时文件。
您可以跳过创建UIImage
的步骤并将其转换回文件。
尝试使用URLSession
和URLDataTask
:
let fileURL = ...
let task = URLSession.shared.dataTask(with: url) { (data, _, _) in
do {
try imageData.write(to: fileURL)
let attachment = UNNotificationAttachment.create(identifier: key, image: myImage, options: nil)
// call closure to call back with attachment and/or error
}
catch let ex {
// call closure with error
}
}
task.resume()
我遗漏了一些错误处理和其他细节,但这应该让你大致了解异步执行它需要什么。 URLSession
使用GCD执行异步网络。
答案 1 :(得分:-1)
使用Alamofire异步下载图像,然后尝试显示它。
let destination: DownloadRequest.DownloadFileDestination = {
_, _ in
var documentsURL = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0]
documentsURL.appendPathComponent("image.jpg")
return (documentsURL, [.removePreviousFile, .createIntermediateDirectories])
}
Alamofire.download(url, to: destination).response {
response in
// do whatever you want with your image, for example if it is an audio file:
do {
self.player = try AVAudioPlayer(contentsOf: URL(string: "\(response.destinationURL!)")!)
self.player.volume = 1.0
self.player.play()
} catch {
print(error)
}
}