我有一个UICollectionViewController
,它充当从我的Firebase数据库中检索和显示数据的Feed。它是窗口的根视图控制器,因此它始终存在。我的问题是每次控制器出现时,其观察节点中的所有子节点都会被添加到集合视图中。这最初很好,但是当我离开控制器并返回时,所有相同的数据都会被追加,从而产生重复数据。这是一些伪代码,代表我与Firebase的互动:
class ViewController: UIViewController {
var children_query: DatabaseQuery!
override func viewDidLoad() {
super.viewDidLoad()
self.children_query = Database.database().reference().child("children").queryOrdered(byChild: "timestamp").queryStarting(atValue: Date().timeIntervalSince1970)
}
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
self.observeAddedChildren()
}
override func viewWillDisappear(_ animated: Bool) {
super.viewWillDisappear(animated)
self.children_query.removeAllObservers()
}
func observeAddedChildren() {
self.children_query.observe(.childAdded, with: { snapshot in
print(snapshot.value)
})
}
}
在这个伪代码中,我只是打印snapshot
而不是处理UI,但重点仍然存在。每次控制器出现时都会打印所有孩子。如何检索仅尚未检索到的数据?感谢。
答案 0 :(得分:1)
我没有使用过Firebase,但是当你将一个块传递给observe
函数时,没有任何迹象表明当视图消失时观察会停止。
所以我想知道多次调用observe
是不是问题。您是否尝试过在ViewDidLoad中调用observe
一次?
或者,有一个属性来记录观察是否已经开始:
var observing: Bool = false
func observeAddedChildren() {
if observing {
return false
}
self.children_query.observe(.childAdded, with: { snapshot in
print(snapshot.value)
})
observing = true
}
编辑:这里有几种方法,因为您可能会将snapshot
项添加到数组或其他集合中,然后您的UICollectionViewDataSource
正在阅读其中的内容阵列。
所以:
viewWillAppear
内清空此数组,然后调用self.collectionView.reloadData()
或snapshot
对象具有唯一标识符属性,则将其放入数组中,然后观察块可以忽略它之前已经看到的项目像这样:
var snapshotIDs : [String] = Array<String>()
func observeAddedChildren() {
self.children_query.observe(.childAdded, with: { snapshot in
if !snapshotIDs.contains(snapshot.uniqueID) {
print(snapshot.value)
snapshotIDs.append(snapshot.uniqueID)
}
})
}