Search code examples
listswiftuipicker

SwiftUI List is working but not the picker


I have this view. The list works fine by showing the data. The picker is not working. It does not display any data. Both use the same objects and functions. I do not know the reason for the picker not showing data. I want to use the picker. I placed the List just to try to determine the problem but I still don't know.

 import SwiftUI

struct GameListPicker: View {

@ObservedObject var gameListViewModel = GameListViewModel()
@State private var selectedGameList = ""

var body: some View {
    
    VStack{        
    
        List(gameListViewModel.gameList){gameList in
        HStack {
            Text(gameList.gameName)
            }
        }
        .onAppear() {self.gameListViewModel.fetchData()}
    
        Picker(selection: $selectedGameList, label: Text("")){
        ForEach(gameListViewModel.gameList) { gameList in
            Text(gameList.gameName)
            }
        }
        .onAppear() {self.gameListViewModel.fetchData()}}
     }
}

This is the GameListViewModel

import Foundation
import Firebase

class GameListViewModel: ObservableObject{

@Published var gameList = [GameListModel]()
let db = Firestore.firestore()

func fetchData() {

    db.collection("GameData").addSnapshotListener {(querySnapshot, error) in
    guard let documents = querySnapshot?.documents else {
      print("No documents")
      return
    }

    self.gameList = documents.map { queryDocumentSnapshot -> GameListModel in
      let data = queryDocumentSnapshot.data()
      let gameName = data["GameName"] as? String ?? ""
      return GameListModel(id: gameName, gameName: gameName)
      }
    }
  }
}

This is the GameListModel

import Foundation

struct GameListModel: Codable, Hashable,Identifiable {

var id: String
//var id: String = UUID().uuidString
var gameName: String

}

Thanks in advance for any help


Solution

  • Picker is not designed to be dynamic, so it is not refreshed when data updated, try to force-rebuild picker when data changed, like below

        Picker(selection: $selectedGameList, label: Text("")){
        ForEach(gameListViewModel.gameList) { gameList in
            Text(gameList.gameName)
            }
        }.id(gameListViewModel.gameList)       // << here !!