我是编程新手,目前正在构建一个应用程序,用于从Firebase收集数据。
我认为当视图被拉下时实现这种令人耳目一新的动画会很好。现在我有一个问题,就是什么都没有刷新(刚开始时工作正常)。同样,每次应用启动时,tableView最初都是空的,当您进行下推时会重新加载,但是是错误的。
我真的很挣扎。谁能在我的代码中看到任何错误?
class ViewController: BaseViewController, UITableViewDelegate, UITableViewDataSource {
@IBOutlet var newsfeedTableView: UITableView!
@IBOutlet weak var activityIndicatorView: UIActivityIndicatorView!
private let refreshControl = UIRefreshControl()
var ref: DatabaseReference!
var posts = [String]()
var timeRef = [String]()
var userRef = [String]()
override func viewDidLoad() {
super.viewDidLoad()
addSlideMenuButton()
setupTableView()
ref = Database.database().reference()
ref.child("posts").observe( .childAdded, with: { snapshot in
let newPost = snapshot.value as? NSDictionary
let post_title:String = newPost!["post_title"] as? String ?? "error"
let newPostTime = snapshot.value as? NSDictionary
let post_time:String = newPostTime!["post_time"] as? String ?? "error collecting timestamp"
let newPostUser = snapshot.value as? NSDictionary
let post_user:String = newPostUser!["post_user"] as? String ?? "Team"
self.posts.insert(post_title, at: 0)
self.timeRef.insert(post_time, at: 0)
self.userRef.insert(post_user, at: 0)
self.newsfeedTableView.reloadData()
})
}
private func setupTableView() {
if #available(iOS 10.0, *) {
newsfeedTableView.refreshControl = refreshControl
} else {
newsfeedTableView.addSubview(refreshControl)
}
refreshControl.addTarget(self, action: #selector(refreshNewsFeedTableView(_:)), for: .valueChanged)
}
@objc private func refreshNewsFeedTableView(_ sender: Any) {
//self.refreshControl.beginRefreshing()
self.newsfeedTableView.reloadData()
self.refreshControl.endRefreshing()
self.activityIndicatorView.stopAnimating()
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return posts.count
}
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as! NewsfeedCell
cell.customTextLabel?.text = posts[indexPath.row]
cell.customTimeLabel?.text = timeRef[indexPath.row]
cell.customNameLabel?.text = userRef[indexPath.row]
return cell
}
}
class NewsfeedCell: UITableViewCell {
@IBOutlet weak var customTextLabel: UILabel!
@IBOutlet weak var customNameLabel: UILabel!
@IBOutlet weak var customTimeLabel: UILabel!
}
答案 0 :(得分:2)
这里
@objc private func refreshNewsFeedTableView(_ sender: Any)
您无需执行任何API请求即可获取数据,然后重新加载表并结束刷新,并且由于您在此处使用了观察
ref.child("posts").observe( .childAdded, with: { snapshot in
然后,您将获取任何新数据,如果需要实施刷新,则将所有数据库代码插入函数中,并将observe
替换为observeSingleEvent
,然后从viewDidLoad
进行调用,然后通过刷新选择器方法
ref.child("posts").observeSingleEvent( .value, with: { snapshot in
请注意,建议的方法将一次获取所有子项,因此不要忘记清理observeSingleEvent
回调中的数组以避免重复的值,也可以考虑制作一个dataSource数组而不是3
self.posts.insert(post_title, at: 0)
self.timeRef.insert(post_time, at: 0)
self.userRef.insert(post_user, at: 0)
可能是创建模型
struct Item {
let post:String
let time:String
let user:String
}
答案 1 :(得分:1)
我能在代码中看到的唯一问题是,您正在使用.childAdded来观察Firebase的事件,但根据Firebase文档:
child_added 事件通常在检索以下内容的列表时使用 数据库中的项目。与返回整个值的值不同 该位置的内容 child_added 每次触发一次 现有的孩子,然后每次将新的孩子添加到 指定的路径。向事件回调传递了一个快照,其中包含 新孩子的数据。出于订购目的,它还会经过一秒钟 包含上一个子项的键的参数。
因此,如果要接收任何特定节点的所有数据,则需要使用 value 事件,而不要使用 child_added ,如下所示:
value 事件用于读取内容的静态快照 在给定的数据库路径上,因为它们在读取时已存在 事件。它用初始数据触发一次,每次都触发一次 数据改变。事件回调传递了一个快照,其中包含 该位置上的所有数据,包括子数据。在代码示例中 以上,value返回了您应用中的所有博客文章。每次一个 添加了新的博客文章,回调函数将返回所有 帖子。
答案 2 :(得分:0)
在DispatchQueue.main中重新加载UItableView,请尝试以下代码。
override func viewDidLoad() {
super.viewDidLoad()
addSlideMenuButton()
setupTableView()
ref = Database.database().reference()
ref.child("posts").observe( .childAdded, with: { snapshot in
let newPost = snapshot.value as? NSDictionary
let post_title:String = newPost!["post_title"] as? String ?? "error"
let newPostTime = snapshot.value as? NSDictionary
let post_time:String = newPostTime!["post_time"] as? String ?? "error collecting timestamp"
let newPostUser = snapshot.value as? NSDictionary
let post_user:String = newPostUser!["post_user"] as? String ?? "Team"
self.posts.insert(post_title, at: 0)
self.timeRef.insert(post_time, at: 0)
self.userRef.insert(post_user, at: 0)
DispatchQueue.main.async() {
self.newsfeedTableView.reloadData()
}
})
}