![](/img/trans.png)
[英]How to load data into a view in SwiftUI with firebase/firestore
[英]SwiftUI and MVVM: How to display data from Firebase/Firestore in View?
我正在从 Firebase 数据库中获取一些数据,并希望将它们显示在视图中。 到目前为止,获取部分有效,但未显示数据。 由于我是 MVVM 模式的新手,所以我有点困惑我的错误在哪里。 我想我遗漏了一些关于异步调用的信息,但我不确定。
为了获取数据,我创建了一个FirestoreManager :
class FirebaseManager {
private let db = Firestore.firestore()
func getUploadedDecks() -> [FlashcardDeck]{
var uploadedDecks = [FlashcardDeck]()
db.collection(K.FSCollectionName).getDocuments { (querySnapshot, error) in
guard let documents = querySnapshot?.documents else {
fatalError("error downloading documents")
}
for document in documents{
if let deck = try? document.data(as: FlashcardDeck.self) {
uploadedDecks.append(deck)
print(deck.title) // <----- prints the ID correctly
}
}
}
return uploadedDecks
}
视图模型:
class DownloadViewModel: ObservableObject {
@Published var decks = [FlashcardDeck]()
@Published var show = false
func fetchDecks(){
self.decks = FirebaseManager().getUploadedDecks()
}
}
视图:此处仅显示“正在加载...”文本字段。
struct DownloadDecksView: View {
@ObservedObject var viewModel: DownloadViewModel
var body: some View {
VStack{
if viewModel.decks == [] {
Text("loading...")
} else {
ForEach(viewModel.decks) { elem in
Flashcard(elem)
}
}
.onAppear {
viewModel.fetchDecks()
}
}
主视图:
struct HomeView: View {
@StateObject var downloadViewModel = DownloadViewModel()
...
var body: some View {
DownloadDecksView(viewModel: downloadViewModel)
...
}
}
这都是关于异步检索的,所以你需要在回调中返回结果,比如
class FirebaseManager {
private let db = Firestore.firestore()
func getUploadedDecks(completion: @escaping ([FlashcardDeck]) -> ()) {
db.collection(K.FSCollectionName).getDocuments { (querySnapshot, error) in
guard let documents = querySnapshot?.documents else {
fatalError("error downloading documents")
}
var uploadedDecks = [FlashcardDeck]()
for document in documents{
if let deck = try? document.data(as: FlashcardDeck.self) {
uploadedDecks.append(deck)
}
}
completion(uploadedDecks) // << here !!
}
// no return !!
}
并将其用作
class DownloadViewModel: ObservableObject {
@Published var decks = [FlashcardDeck]()
@Published var show = false
func fetchDecks(){
FirebaseManager().getUploadedDecks() { [weak self] decks in
DispatchQueue.main.async {
// always update UI-linked properties on main queue
self?.decks = decks
}
}
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.