【问题标题】:Firestore- Showing data in TableviewFirestore - 在 Tableview 中显示数据
【发布时间】:2018-05-05 18:29:30
【问题描述】:

我正在尝试将我的 Firestore 数据显示到我的 Tableview 中,但我似乎无法让它显示出来。

protocol DocumentSerializeable {
    init?(dictionary:[String:Any])
}

struct Sourse {
    var name: String
    var content: String
    var timeStamp: Date

    var dictionary: [String: Any] {
        return [
            "name": name,
            "content": content,
            "timestamp": timeStamp
        ]
    }
}


extension Sourse : DocumentSerializeable {
    init?(dictionary: [String : Any]) {
        guard let name = dictionary["name"] as? String,
            let content = dictionary["content"] as? String,
            let timeStamp = dictionary["timeStamp"] as? Date else {return nil}

        self.init(name: name, content: content, timeStamp: timeStamp)

    }
}

class SourseListTableViewController: UITableViewController {

    var db: Firestore!

    var sourseArray = [Sourse]()

    private var document: [DocumentSnapshot] = []

    override func viewDidLoad() {
        super.viewDidLoad()
        self.tableView.delegate = self
        self.tableView.dataSource = self

        //initalize Database
        db = Firestore.firestore()
        loadData()

    }

起初我在下面尝试了这段代码,没有错误,但表格视图中没有加载任何内容。

func loadData() {
    db.collection("sourses").getDocuments() {
        snapshot, error in
        if let error = error {
            print("\(error.localizedDescription)")
        } else {
            self.sourseArray = snapshot!.documents.flatMap({Sourse(dictionary: $0.data())})
            DispatchQueue.main.async {
                self.tableView.reloadData()
            }
        }
    }
}

经过一些研究(从Firestore - Append to tableView when view is loaded 读取)我在下面尝试了这段代码,但我收到错误“无法将类型'(名称:字符串,内容:字符串,时间戳:日期?)'的值转换为预期的参数类型'Sourse'”所以我尝试从所有代码中删除日期,但我仍然无法让它工作。

func loadData() {
        db.collection("sourses").getDocuments() {
            snapshot, error in
            if let error = error {
                print("\(error.localizedDescription)")
            } else {
                for document in snapshot!.documents {

                    let data = document.data()
                    let name = data["name"] as? String ?? ""
                    let content = data["content"] as? String ?? ""
                    let timeStamp = data["timeStamp"] as? Date 

                    let newSourse = (name:name, content:content, timeStamp: timeStamp)
                    self.sourseArray.append(newSourse)
                }
            }
        }
    }

这是我的 numberOfRows/CellForRow 以确保它不是 tableview 本身。我还用我的故事板仔细检查了“单元标识符”。

override func numberOfSections(in tableView: UITableView) -> Int {
        return 1
    }

    override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        // #warning Incomplete implementation, return the number of rows
        return sourseArray.count
    }


    override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCell(withIdentifier: "SourseTableViewCell", for: indexPath)

        let sourse = sourseArray[indexPath.row]

        cell.textLabel?.text = "\(sourse.name)"
        cell.detailTextLabel?.text = "\(sourse.content)"

        return cell
    }

【问题讨论】:

    标签: ios swift uitableview google-cloud-firestore


    【解决方案1】:

    您需要在解析您的Snapshot 后重新加载您的tableView。强制打开 Snapshot 也不是一个好主意:

    .getDocuments { (snapshot, error) in
    
        if let error = error {
    
            print(error.localizedDescription)
    
        } else {
    
            if let snapshot = snapshot {
    
                for document in snapshot.documents {
    
                    let data = document.data()
                    let name = data["name"] as? String ?? ""
                    let content = data["content"] as? String ?? ""
                    let timeStamp = data["timeStamp"] as? Date ?? Date()
                    let newSourse = Sourse(name:name, content:content, timeStamp: timeStamp)
                    self.sourseArray.append(newSourse)
                }
                self.tableView.reloadData()
            }
        }
    

    【讨论】:

    • 感谢您的回复!过去几天我一直在研究这个问题。非常感激!!我没有问题地实施了“重新加载数据”。但是当我从快照中删除强制解包时,我收到错误“可选类型'QuerySnapshot的值?'没有打开;你是不是要使用“!”或者 '?'?”此外,当我尝试解析 Date 对象时,我收到此错误,“使用未解析的标识符 'date'”知道为什么吗?
    • 确保你写了if let snapshot = snapshot { /...,它会打开它(即检查它不是零,所以你的应用程序不会崩溃!
    • 我实现了,但后来我得到了这个错误“闭包参数列表的上下文类型需要 2 个参数,不能隐式忽略”
    • 检查您的确切语法。我已经修改了我的答案以在 .getDocuments { 之后显示整个代码
    • 我明白你现在所说的应该是这样的(error.localizedDescription)") } else { if let snapshot = snapshot { for document in snapshot.documents { let data = document.data() ...... 除了我得到两个错误“使用未解析的标识符”外它有效'date'" 和使用未解析的标识符 'timeStamp'
    【解决方案2】:

    rbaldwin 告诉我,他的回答是正确的,我只是发布完整的 loaddata 函数以作记录。

    func loadData() {
        db.collection("sourses").getDocuments() { (snapshot, error) in
    
            if let error = error {
    
                print(error.localizedDescription)
    
            } else {
    
                if let snapshot = snapshot {
    
                    for document in snapshot.documents {
    
                        let data = document.data()
                        let name = data["name"] as? String ?? ""
                        let content = data["content"] as? String ?? ""
                        let timeStamp = data["timeStamp"] as? Date ?? Date()
                        let newSourse = Sourse(name:name, content:content, timeStamp: timeStamp)
                        self.sourseArray.append(newSourse)
                    }
                    self.tableView.reloadData()
                }
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-11-12
      • 2020-06-09
      • 1970-01-01
      • 2017-11-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-01-04
      相关资源
      最近更新 更多