簡體   English   中英

Swift - 將 firestore 集合的所有文檔保存在對象列表中

[英]Swift - Save all documents of firestore collection in a list of objects

我想檢索 firestore 集合的所有文檔,然后將其寫入 object 然后 append 它是我的對象列表。 之后,我將其顯示在 UITableView 中。

這就是我所擁有的,它可以正常工作,但是當我運行它時,什么也沒有顯示。

列表結構:

struct RewardsStruct {
//var rewardKey: String
var Reward: String
var noPoints: String
var QRimageURL: ImageURL = ImageURL(url: nil, didLoad: false)
var Desc: String
var isvalid: Bool  

}

這是我的檢索代碼:

private func getRewards() {
    var rewardsList = [RewardsStruct]()
    let db = Firestore.firestore()
    
    db.collection("Rewards").getDocuments { (snapshot, error) in
        if error != nil {
            print(error)
        } else {
            for document in (snapshot?.documents)! {
                 let code = RewardsStruct( Reward: document.data()["Reward"] as! String , noPoints: document.data()["noPoints"] as! String , QRimageURL: document.data()["QRimageURL"] as! ImageURL, Desc:document.data()["Desc"] as! String, isvalid: (document.data()["isvalid"] != nil) )
                
                    self.rewardsList.append(code)
                    DispatchQueue.main.async {
                        self.CodeTable.reloadData()
                    }
                
            }
        }
    }
    
}

ViewController 中代碼的 rest 作為一些請求

class RewardsVC: UIViewController {

var rewardsList = [RewardsStruct]()

var reward:RewardsStruct!

@IBOutlet weak var infoView: UIView!
@IBOutlet weak var ViewLabel: UILabel!
@IBOutlet weak var CodeTable: UITableView!

override func viewDidLoad() {
    super.viewDidLoad()
    
    CodeTable.delegate = self
    CodeTable.dataSource = self
    ViewLabel.isHidden = true

    infoView.makeCornerRounded(cornerRadius: 30, maskedCorners: [.layerMinXMinYCorner, .layerMaxXMinYCorner])
}

override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)
    rewardsList.removeAll()
    getRewards()
    

}


private func getRewards() {
    ....
  

}

extension RewardsVC: UITableViewDelegate, UITableViewDataSource{

func tableView(_ tableView: UITableView, estimatedHeightForRowAt indexPath: IndexPath) -> CGFloat {
    CodeTable.backgroundColor = UIColor(named: "#F5F5F5")
    return 60
    
}

func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
    return 125
}

func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    print("List number of rows")
    print(rewardsList.count)
    return rewardsList.count
    }

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    
let cell = tableView.dequeueReusableCell(withIdentifier: "RewardsCell") as! RewardsCell
    let object = rewardsList[indexPath.row]
    
    cell.Reward.text = object.Reward
    cell.Desc.text = object.Desc
    cell.noPoints.text = "-" + object.noPoints + " Points"
    
    return cell
}

   
    
func addShadow(backgroundColor: UIColor = .white, cornerRadius: CGFloat = 12, shadowRadius: CGFloat = 5, shadowOpacity: Float = 0.1, shadowPathInset: (dx: CGFloat, dy: CGFloat), shadowPathOffset: (dx: CGFloat, dy: CGFloat)) {
    
} }

這是我的 FireStore:

FireStore 結構

試試這個示例代碼,以...save all documents of firestore collection in a list of objects...

getRewards(...)被稱為異步 function,需要一種方法來“等待”結果可用,然后才能使用它們。

有很多方法可以做到這一點,這里我提供一個示例代碼,它使用完成處理程序將getRewards(...)的結果(或錯誤)傳遞回調用 function。 請注意,代碼未經測試,因為我沒有您的數據庫(甚至 Firestore)。

// -- here some error type for testing
enum FireError: Error {
    case decodingError
    case badError
    // ...
}

// -- here completion handler
private func getRewards(completion: @escaping ([RewardsStruct], FireError?) -> ()) {

    var rewardsList = [RewardsStruct]()
    let db = Firestore.firestore()
    
    db.collection("Rewards").getDocuments { (snapshot, error) in
        if error != nil {
            print(error)
            completion([], FireError.badError)  // <-- here
        } else {
            for document in (snapshot?.documents)! {
                 let code = RewardsStruct(Reward: document.data()["Reward"] as! String , noPoints: document.data()["noPoints"] as! String , QRimageURL: document.data()["QRimageURL"] as! ImageURL, Desc:document.data()["Desc"] as! String, isvalid: (document.data()["isvalid"] != nil) )                    
                 self.rewardsList.append(code)
            }
            completion(rewardsList, nil)  // <-- here
        }
    }
}

像這樣使用 function:

    override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)
    
    getRewards() { results, error in  // <-- here
        if error == nil {
            rewardsList.removeAll()
            rewardsList = results
            DispatchQueue.main.async {
                self.CodeTable.reloadData()
            }
        } else {
            // todo deal with errors
        }
    }
}

或者,您也可以使用此代碼,而不使用完成處理程序,因為getRewards(...)在您的 UIViewController 中。

private func getRewards() {
    let db = Firestore.firestore()
    
    db.collection("Rewards").getDocuments { (snapshot, error) in
        if error != nil {
            print(error)
        } else {
            self.rewardsList.removeAll()  // <-- here
            for document in (snapshot?.documents)! {
                 let code = RewardsStruct(Reward: document.data()["Reward"] as! String , noPoints: document.data()["noPoints"] as! String , QRimageURL: document.data()["QRimageURL"] as! ImageURL, Desc:document.data()["Desc"] as! String, isvalid: (document.data()["isvalid"] != nil) )
                 self.rewardsList.append(code)  // <-- here
            }
            DispatchQueue.main.async {    // <-- here
                self.CodeTable.reloadData()
            }
        }
    }
}

並像這樣使用它:

override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)
    getRewards()
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM