【问题标题】:Firebase RTDB data not showing up in SwiftUI List viewFirebase RTDB 数据未显示在 SwiftUI 列表视图中
【发布时间】:2021-01-05 19:05:00
【问题描述】:

我正在关注一个关于将 Firebase 数据放入 SwiftUI 中的列表视图的互联网教程,但该教程使用了 Firestore,所以我现在只能靠自己了。我拥有所有数据,但是当我打开 PlayerListView 时,列表为空。但是,当我打印时,所有数据都打印得很完美。

这是我所拥有的:

import SwiftUI
import Firebase

struct Player: Identifiable {
  var id: String = UUID().uuidString
  var username: String
  var score: Int
}

struct PlayerListView: View {
  @ObservedObject var viewModel = PlayerViewModel()
  @Binding var showLeaderboard: Bool

  var body: some View {
    NavigationView {
        List(viewModel.players) { player in
        VStack(alignment: .leading) {
          Text(player.username)
            .font(.headline)
          Text("\(player.score)")
            .font(.subheadline)
        }
      }
      .navigationBarTitle("Players")
        .onAppear() {
            self.viewModel.fetchData() { player in
                print(player)
            }
        }
    }
    .onTapGesture {
      self.showLeaderboard.toggle()
    }
  }
}
class PlayerViewModel: ObservableObject {
  @Published var players = [Player]()
  let ref = Database.database().reference().child("users")
    
  func fetchData(completion: @escaping(Array<Player>) -> Void) {
    ref.observeSingleEvent(of: .value, with: {(snapshot: DataSnapshot) in
      if let result = snapshot.children.allObjects as? [DataSnapshot] {
        for child in result {
          let orderID = child.key
          self
            .ref
            .child(orderID)
            .queryOrdered(byChild: "score")
            .observeSingleEvent(of: .value, with: {(snapshot: DataSnapshot) in
              let value = snapshot.value as? NSDictionary
              self.players.append(
                Player(id: .init(), 
                       username: value?["username"] as? String ?? "", 
                       score: value?["score"] as? Int ?? 0))
              completion(self.players)
            })
          }
        }
      })  
  }
}

【问题讨论】:

  • 你试过在主线程上发布players数组:DispatchQueue.main.async { self.players.append(...) }
  • 刚试了下还是没有显示

标签: swift firebase listview firebase-realtime-database swiftui


【解决方案1】:

我已经稍微简化了您的代码(例如,不需要实现完成处理程序),并修复了一些问题。

最大的问题是您没有将玩家 ID 映射到 Player 结构的 id 属性。由于List 要求其元素是可识别的,因此所有元素都必须具有唯一的 ID。然而,所有玩家都有相同的 ID(一个空字符串) - 这导致 List 视图中的条目重复。

这是更新后的代码:

import SwiftUI
import Firebase

struct Player: Identifiable {
  var id: String = UUID().uuidString
  var username: String
  var score: Int
}

struct PlayerListView: View {
  @ObservedObject var viewModel = PlayerViewModel()
  
  var body: some View {
    NavigationView {
      List(viewModel.players) { player in
        VStack(alignment: .leading) {
          Text(player.username)
            .font(.headline)
          Text("\(player.score)")
            .font(.subheadline)
        }
      }
      .navigationBarTitle("Players")
      .onAppear() {
        self.viewModel.fetchData()
      }
    }
  }
}
import Foundation
import Firebase

class PlayerViewModel: ObservableObject {
  @Published var players = [Player]()
  let ref = Database.database().reference().child("users")
  
  func fetchData() {
    ref.observeSingleEvent(of: .value, with: {(snapshot: DataSnapshot) in
      if let result = snapshot.children.allObjects as? [DataSnapshot] {
        for child in result {
          let orderID = child.key
          self
            .ref
            .child(orderID)
            .queryOrdered(byChild: "score")
            .observeSingleEvent(of: .value, with: {(snapshot: DataSnapshot) in
              let value = snapshot.value as? NSDictionary
              self.players.append(
                Player(id: value?["id"] as? String ?? UUID().uuidString,
                       username: value?["username"] as? String ?? "",
                       score: value?["score"] as? Int ?? 0))
            })
        }
      }
    })
  }
}

这是我的测试数据的样子:

这是模拟器中 UI 的快照:

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-09-26
    • 2021-06-16
    • 1970-01-01
    • 1970-01-01
    • 2020-04-18
    • 2021-08-13
    相关资源
    最近更新 更多