Best Practice für die Verwendung von FetchedResults zum Auffüllen eines SwiftUI-Pickers

Nov 25 2020

Ich arbeite zurzeit mit CoreData FetchedResultsund SwiftUIs PickerView. Dabei ist ein Problem aufgetreten, als ich die FetchedResults zum Auffüllen einer PickerView verwendet habe:

Ich kann natürlich die FetchedResults verwenden, um die PickerView zu füllen, aber welche Lösung ist die beste (auch aus UI / UX-Perspektive), um den @State für das ausgewählte Ergebnis zu definieren?

@FetchRequest(sortDescriptors: [NSSortDescriptor(keyPath: \User.lastName, ascending: true)], animation: .default) private var users: FetchedResults<User>
@State var user: User = User()

// ...

Picker(selection: $user, label: Text("User")) {
    ForEach(users) { user in
        Text(lastName).tag(user)
    }
}

Dies funktioniert, ist jedoch wahrscheinlich nicht die eleganteste Methode , um ein neues leeres Benutzerobjekt zu erstellen und es als Standard festzulegen.

Hat jemand von euch eine bessere Idee / Best Practice zur Lösung dieses wahrscheinlich oft auftretenden Problems?

Antworten

2 davidev Nov 25 2020 at 17:14

Wenn Sie nicht ständig einen Dummy-Benutzer () erstellen möchten, was, wie bereits erwähnt, keine gute Vorgehensweise ist, müssen Sie Ihre FetchRequest in Ihrer ausführen init()oder Ihr FetchedResult an eine andere Ansicht übergeben.

Hier ist eine Lösung mit einer anderen Ansicht

struct ContentView : View {
    
    @FetchRequest(sortDescriptors: [NSSortDescriptor(keyPath: \User.lastName, ascending: true)], animation: .default) private var users: FetchedResults<User>

    var body : some View {
        PickerView(users: Array(users))
    }
}

struct PickerView : View {

    var users : [User]
    @State var selectedUser : User?
    
    init(users: [User]) {
        self.users = users
        self._selectedUser = State(initialValue: users.first)
    }
    
    var body : some View {
        Picker(selection: $selectedUser, label: Text("Users")) {
            ForEach(users) { user in
                Text(user.lastName ?? "").tag(user as User?)
            }
        }

    }
}

Bearbeiten:

Eigentlich können Sie Ihre Person einfach als optional deklarieren. Sie müssen also keine Standardeinstellung angeben. Beim Abrufen wird automatisch zum ersten Element in der Auswahl verschoben. Wenn Sie eine andere auswählen möchten, können Sie diese Methode oben verwenden. In Bezug auf die FetchRequest in init () wurde hier vor einigen Monaten eine Antwort veröffentlicht