【问题标题】:Can't display data from firebase documents on a tableview无法在 tableview 上显示来自 firebase 文档的数据
【发布时间】:2021-11-03 10:12:38
【问题描述】:

我有一个存储表格视图数据的数组,我需要我的应用程序从 firebase 检索数据,然后将其附加到数据数组中以显示到我的表格视图中。但由于某种原因,在我添加行 assignmentstableview.reloadData() 后,表格视图中的所有单元格都紧密地打包在一起。当我删除assignmentstableview.reloadData() 时,数据根本不显示。任何人都知道如何从 firebase 文档中检索数据,然后将其显示在我的 tableview 上?代码如下:

import Firebase
import FirebaseAuth


class AssignmentsViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
    
    struct assignmentmodal {
        let name: String
        let duedate: String
        let imagename: String
    }
    
    var data: [assignmentmodal] = []
    
    
    @IBOutlet weak var titleLabel: UILabel!
    
    @IBOutlet weak var titleView: UIView!
    
    
    @IBOutlet weak var plusbtn: UIButton!
    
    @IBOutlet weak var codeLabel: UILabel!
    
    @IBOutlet weak var assignmentstableview: UITableView!
    
    
    override func viewDidLoad() {
        super.viewDidLoad()
        syncAssignments()
        data.append(assignmentmodal(name: "test2", duedate: "test2", imagename: ""))
        titleLabel.text = "\(ClassesViewController.shared.chosenClass)"
        print(ClassesViewController.shared.chosenClass)
        let gradientFirstColor = UIColor(hex: "9d81e0").cgColor
        let gradientSecondColor = UIColor(hex: "6d5cd3").cgColor
        let gradientLayer = CAGradientLayer()
        gradientLayer.frame = titleView.bounds
        gradientLayer.colors = [gradientFirstColor, gradientSecondColor]
        gradientLayer.cornerRadius = 21
        gradientLayer.masksToBounds = true
        titleView.layer.insertSublayer(gradientLayer, at: 0)
        displayInfo(classname: ClassesViewController.shared.chosenClass)
        setTableView()
        titleView.layer.cornerRadius = 21
        
        
        // Do any additional setup after loading the view.
    }
    
    @IBAction func unwindsegue(_ sender: Any) {
        print("button works")
        performSegue(withIdentifier: "unwind", sender: self)
    }
    
    override func viewDidAppear(_ animated: Bool) {
        syncAssignments()
    }
    let db = Firestore.firestore()
    let user = Auth.auth().currentUser
    func syncAssignments() {
        db.collection("Classes").document(ClassesViewController.shared.chosenClass).collection("Assignments").getDocuments() { (querySnapshot, err) in
            if let err = err {
                print("Error getting documents: \(err)")
            } else {
                for document in querySnapshot!.documents {
                    if let name = document.get("name"), let duedate = document.get("due date") {
                        print("\(name)")
                        print("\(duedate)")
                        self.data.append(assignmentmodal(name: "\(name)", duedate: "\(duedate)", imagename: ""))
                        self.assignmentstableview.reloadData()
                        self.setTableView()
                    }
                }
            }
        }
    }
    
    func setTableView() {
        assignmentstableview.backgroundColor = UIColor.clear
        assignmentstableview.delegate = self
        assignmentstableview.dataSource = self
        
        assignmentstableview.register(AssignmentCellTableViewCell.self, forCellReuseIdentifier: "Cell")
    }
    
    
    
    
    @IBAction func plusAssignment(_ sender: Any) {
        
    }
    
    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return data.count
    }
    
    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let assignments = data[indexPath.row]
        let cell = assignmentstableview.dequeueReusableCell(withIdentifier: "Cell", for: indexPath) as! AssignmentCellTableViewCell
        cell.image.image = UIImage(named: assignments.imagename)
        cell.assignmentname.text = assignments.name
        cell.duedate.text = assignments.duedate
        print("\(assignments.name)")
        print("\(assignments.duedate)")
        return cell
    }
    
    func displayInfo(classname: String) {
        let db = Firestore.firestore()
        db.collection("Classes").whereField("name", isEqualTo: classname)
            .getDocuments() { (querySnapshot, err) in
                if let err = err {
                    print("Error getting documents")
                } else {
                    for document in querySnapshot!.documents {
                        if let teacher = document.get("teacher"), let code = document.get("code") {
                            print(code)
                            self.codeLabel.text = "\(code)"
                            
                            let user = Auth.auth().currentUser
                            if let email = user?.email {
                                print("\(email)")
                                let docRef = db.collection("Users").document("limkiran522@gmail.com")
                                docRef.getDocument { (document, error) in
                                    if let document = document, document.exists, let username = document.get("username") {
                                        if username as! String == teacher as! String {
                                            self.plusbtn.isHidden = false
                                        }
                                        else {
                                            self.plusbtn.isHidden = true
                                        }
                                    } else {
                                        print("Document does not existdisplay")
                                    }
                                }
                            }
                        }
                    }
                }
        }
        
    }
    
    

    /*
    // MARK: - Navigation

    // In a storyboard-based application, you will often want to do a little preparation before navigation
    override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
        // Get the new view controller using segue.destination.
        // Pass the selected object to the new view controller.
    }
    */
    
    
    
}

我的细胞类:


import UIKit

class AssignmentCellTableViewCell: UITableViewCell {
    
    lazy var backview: UIView = {
        let view = UIView(frame: CGRect(x: 10, y: 6, width: 340, height: 110))
        view.backgroundColor = UIColor.white
        return view
    }()
    
    lazy var image: UIImageView = {
        let image = UIImageView(frame: CGRect(x: 4, y: 15, width: 80, height: 80))
        image.contentMode = .scaleAspectFill
        return image
    }()
    
    lazy var assignmentname: UILabel = {
        let assignmentname = UILabel(frame: CGRect(x: 116, y: 8, width: backview.frame.width - 88, height: 25))
        assignmentname.textAlignment = .left
        assignmentname.font = UIFont.boldSystemFont(ofSize: 20)
        return assignmentname
    }()
    
    lazy var duedate: UILabel = {
        let duedate = UILabel(frame: CGRect(x: 116, y: 42, width: backview.frame.width - 88, height: 25))
        duedate.textAlignment = .left
        duedate.font = UIFont.systemFont(ofSize: 10)
        return duedate
    }()

    override func awakeFromNib() {
        super.awakeFromNib()
        // Initialization code
    }
    
    override func layoutSubviews() {
        backview.layer.cornerRadius = 15
        backview.clipsToBounds = true
        backview.layer.borderColor = UIColor.systemGray5.cgColor
        backview.layer.borderWidth = 1
        image.layer.cornerRadius = 40
        image.clipsToBounds = true
    }

    override func setSelected(_ selected: Bool, animated: Bool) {
        super.setSelected(selected, animated: animated)
        addSubview(backview)
        backview.addSubview(image)
        backview.addSubview(assignmentname)
        backview.addSubview(duedate)
        // Configure the view for the selected state
    }

}

这就是细胞被挤在一起时的样子:

【问题讨论】:

  • 没有人知道你的 Firestore 人的数据结构。

标签: ios swift google-cloud-firestore


【解决方案1】:

我建议你切换self.assignmentstableview.reloadData()self.setTableView()的调用,你需要在重新加载表的数据之前调用代理。

其实你的函数func setTableView()只需要调用一次,应该在self.assignmentstableview.reloadData()之前调用

如果这不起作用,则问题可能与您的 Firestore 有关。

【讨论】:

  • 试过了,但没有运气,谢谢
猜你喜欢
  • 2017-11-20
  • 1970-01-01
  • 1970-01-01
  • 2017-07-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多