如何使用 Firebase 数据库中存储的 url 作为 UIImageView 中的图像

Posted

技术标签:

【中文标题】如何使用 Firebase 数据库中存储的 url 作为 UIImageView 中的图像【英文标题】:How to use a stored url from Firebase Database as an image in an UIImageView 【发布时间】:2020-06-10 04:37:31 【问题描述】:

我不熟悉编码并尝试构建 ios 应用程序。我将用户上传的图像存储到我的 firebase 存储中,然后将 URL 保存为字符串(“https//.....)。我可以在使用 print(snapshot ). 它打印、捕捉 (profileImageUrl) https://firebasestorage.... 如何使用此快照获取 ImageView 以显示最近保存的个人资料图片?

import UIKit
import Firebase
import SDWebImage


class EditProfileViewController: UIViewController 

@IBOutlet weak var ProfileImage: UIImageView!

        var selectedImage: UIImage?

        var ref:DatabaseReference?

        var databaseHandle:DatabaseHandle = 0

        var postProfileImage = [String]()

let dbref = Database.database().reference()
let uid = Auth.auth().currentUser?.uid


        override func viewDidLoad() 
            super.viewDidLoad()
           self.ref?.child("users").child(Auth.auth().currentUser!.uid).child("profileImageUrl").observe(.value, with:  (snapshot) in
                print(snapshot)
           )


            ProfileImage.layer.borderWidth = 3.0
            ProfileImage.layer.masksToBounds = false
            ProfileImage.layer.borderColor = UIColor.white.cgColor
            ProfileImage.layer.cornerRadius = ProfileImage.frame.size.width / 2
            ProfileImage.clipsToBounds = true

            let tapGesture = UITapGestureRecognizer(target: self, action: #selector(EditProfileViewController.handleSelectProfileImageView))
            ProfileImage.addGestureRecognizer(tapGesture)
            ProfileImage.isUserInteractionEnabled = true


        @objc func handleSelectProfileImageView() 
        let pickerController = UIImagePickerController()
        pickerController.delegate = self
        present(pickerController, animated: true, completion: nil)

                    

@IBAction func Cancel(_ sender: UIBarButtonItem) 
    dismiss(animated: true, completion: nil)



let user = Auth.auth().currentUser

let fileData = NSData()


@IBAction func DoneButton(_ sender: UIBarButtonItem) 
guard let imageSelected = self.ProfileImage.image else 
    print ("Avatar is nil")
    return


    var dict: Dictionary<String, Any> = [
        "profileImageUrl": "",

    ]

guard let imageData = imageSelected.jpegData(compressionQuality: 0.4) else 
    return

    let storageRef = Storage.storage().reference(forURL: "(I have my storage url here")
    let imageName = NSUUID().uuidString
    let storageProfileRef = storageRef.child("Profile_Images").child(Auth.auth().currentUser!.uid).child("\(imageName).png")

let metadata = StorageMetadata()
metadata.contentType = "image/jpeg"
storageProfileRef.putData(imageData, metadata: metadata, completion:
     (StorageMetadata, error) in
        if (error != nil) 
            return
        

        storageProfileRef.downloadURL  (url, error) in
            if let metaImageUrl = url?.absoluteString 
                dict["profileImageUrl"] = metaImageUrl

                Database.database().reference().child("users").child(Auth.auth().currentUser!.uid).updateChildValues(dict, withCompletionBlock:  
                    (error, ref) in
                    if error == nil 
                        print("Done")
                    
                    

                )
            
        

)


    dismiss(animated: true, completion: nil)

      

 
     extension EditProfileViewController: UIImagePickerControllerDelegate, UINavigationControllerDelegate 
       func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) 
           //print("did Finish Picking Media")
           if let image = info[UIImagePickerController.InfoKey(rawValue: "UIImagePickerControllerOriginalImage")] as? UIImage
               selectedImage = image
               ProfileImage.image = image
           
           dismiss(animated: true, completion: nil)
       
   

我真的需要一些帮助!

【问题讨论】:

【参考方案1】:

您可以向 UIImageView 添加扩展,如下所示:

extension UIImageView 
    func load(url: URL, onLoadCompletion: ((_ isImageLoaded: Bool) -> Void)? = nil) 
        self.image = nil
        DispatchQueue.global().async  [weak self] in
            if let data = try? Data(contentsOf: url) 
                if let image = UIImage(data: data) 
                    DispatchQueue.main.async 
                        self?.image = image
                        onLoadCompletion?(true)
                    
                 else 
                    onLoadCompletion?(false)
                
             else 
                onLoadCompletion?(false)
            
        
    

假设您的图像视图出口是这样的:

@IBOutlet weak var imageView: UIImageView!

下面是添加loader时的用法:

if let url = URL(string: "https://firebase-storage-url") 
    // show a loader here if needed
    imageView.load(url: url)  (imageLoaded) in
        if imageLoaded 
            // hide loader
         else 
            // show a place holder image
            // hide loader
        
    
 else 
    // show a default image

以下是没有任何额外工作,只加载图像的用法:

if let url = URL(string: "https://firebase-storage-url") 
    imageView.load(url: url)

【讨论】:

嘿,谢谢您的帮助。 UIImage 没有加载,我得到一个 NSErrorFailingURLStringKey。我不知道这是否相关,但我真的需要快速帮助。 此错误有时来自 Firebase API。你能告诉我堆栈跟踪或让我知道你的代码中哪一行出现了这个问题以及完整的消息是什么? 不知道这是不是你想看到的。对不起,我对此很陌生。任务 . HTTP 加载失败,0/0 字节(错误代码:-1003 [12:8])

以上是关于如何使用 Firebase 数据库中存储的 url 作为 UIImageView 中的图像的主要内容,如果未能解决你的问题,请参考以下文章

如何在实时数据库firebase android中存储下载图像url

如何从 Firebase 存储下载 URL 中删除查询字符串

使用 Cloud Functions 的下载 URL 从 Firebase 存储中删除文件

如何将多个图像上传到 Firebase 存储并返回多个下载 URL

如何将图像上传到firebase存储然后将图像url存储在firestore中?

如何将 Url 从 Firebase Storage 存储到 ArrayList 中?