缓存图像swift



我尝试从我的firebase存储中缓存URL中的图像。如果我在函数"中打印我的url;downloadImage";我可以看到我得到了图片的URL。但是我在函数getImage中打印我的url,然后什么都不显示。

我的图像服务:

import Foundation
import UIKit
import Firebase
class ImageService {

static let cache = NSCache<NSString, UIImage>()
static let storage = Storage.storage()
static let db = Firestore.firestore()

// Downloading image with URL
static func downloadImage(withURL url:URL, completion: @escaping (_ image:UIImage?, _ url:URL)->()) {
let dataTask = URLSession.shared.dataTask(with: url) { data, responseURL, error in
var downloadedImage:UIImage?

if let data = data {
downloadedImage = UIImage(data: data)

}
if downloadedImage != nil {
cache.setObject(downloadedImage!, forKey: url.absoluteString as NSString)

}
DispatchQueue.main.async {
completion(downloadedImage, url)

}
}
dataTask.resume()
}
// Get the downloaded image
static func getImage(withURL url:URL?, completion: @escaping (_ image:UIImage?, _ url:URL)->()) {
if let _url = url {
if let image = cache.object(forKey: _url.absoluteString as NSString) {
completion(image, _url)
print("HEJSAN(String(describing: url))")
} else {
downloadImage(withURL: _url, completion: completion)
}
}
}

// Set the retrieved image for the UIImageView
static func setImage(imageView image: UIImageView, imageURL url: String) {
getImage(withURL: URL(string: url)) { retrievedImage, error in
image.image = retrievedImage
}
}

这就是我尝试在我的VC:中显示它的方式

override func viewDidLoad() {
super.viewDidLoad()        
ImageService.setImage(imageView: logoImage, imageURL: "https://firebasestorage.googleapis.com/v0/b/shutappios.appspot.com/o/LogoImage%2FShutAppLogo.jpg?alt=media&token=13216931-418f-486a-9702-2985b262ab08")
}

我不确定是否能很好地理解你的问题,但根据你所说的,第一次调用getImage时,它将执行downloadImage是正常的,因为缓存中还没有图像,但第二次调用时会有图像。也许这里的问题是,你试图在下载完成之前从缓存中获取图像,因为它的代码发生在后台。异步确实意味着,如果你试图在那之后立即获得现金,而不需要等待。更有可能的是,它还没有准备好,所以如果你想确保这不会发生,我认为你需要在你的setImage函数中添加完成,比如:

static func setImage(
imageView image: UIImageView,
imageURL url: String,
completion: (() -> ())? = nil) {
getImage(withURL: URL(string: url)) { retrievedImage, error in
image.image = retrievedImage
completion?()
}
}

在这个例子中,它将按预期从getImage打印日志——第一次是下载,第二次是从缓存中获取。

ImageService.setImage(imageView: imageView, imageURL: imageURL) {
ImageService.setImage(imageView: self.imageView, imageURL: imageURL)
} 

请注意,这只是一个例子,让你了解这背后的问题,我希望它能帮助你!

最新更新