tableView не обновляется - PullRequest
       1

tableView не обновляется

0 голосов
/ 07 декабря 2018

Я новичок в программировании и в настоящее время создаю приложение, в котором я собираю данные из 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!

    }

Ответы [ 3 ]

0 голосов
/ 07 декабря 2018

Единственная проблема, которую я вижу в коде, это то, что вы используете .childAdded для наблюдения событий из firebase, но в соответствии с документом firebase:

Обычно используется событие child_added при получении списка элементов из базы данных.В отличие от значения, которое возвращает все содержимое местоположения, child_added запускается один раз для каждого существующего дочернего элемента, а затем снова каждый раз, когда в указанный путь добавляется новый дочерний элемент.Обратному вызову события передается снимок, содержащий данные нового дочернего элемента.Для упорядочивания также передается второй аргумент, содержащий ключ предыдущего дочернего элемента.

Итак, если вы хотите получить все данные какого-либо конкретного узла, вам необходимо использовать значение событие, но не child_added , как указано здесь:

Событие значение используется для чтения статического снимка содержимого в данной базе данныхпуть, как они существовали на момент чтения события.Он запускается один раз с начальными данными и снова каждый раз, когда данные изменяются.Обратному вызову события передается снимок, содержащий все данные в этом месте, включая дочерние данные.В приведенном выше примере кода value возвращаются все сообщения блога в вашем приложении.Каждый раз, когда добавляется новое сообщение в блоге, функция обратного вызова возвращает все сообщения.

0 голосов
/ 07 декабря 2018

Перезагрузите UItableView в DispatchQueue.main, попробуйте этот код.

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()
            }

        })
    }
0 голосов
/ 07 декабря 2018

Здесь

@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
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...