#swiftui
#swiftui
Вопрос:
Я пытаюсь сохранить результат выбора в пользовательских значениях по умолчанию. Операция сохранения пользователя по умолчанию выполняется в классе UserData с помощью метода saveBase.
Я успешно попробовал аналогичную технику с помощью кнопки, но мой вызов после выбора выдает известную ошибку:
Тип ‘()’ не может соответствовать представлению.
struct aboutView: View {
@EnvironmentObject var userData: UserData
@State private var baseEntry: Int = 0
let base = ["Level 1", "Level 2","Level 3","Level 4"]
var body: some View {
Text("comment")
Text("comment")
Text("comment")
Section {
Picker(selection: $baseEntry, label: Text("Select Base >")) {
ForEach(0 ..< self.base.count) {
Text(self.base[$0]).tag($0)
}
self.userData.saveBase(baseEntry: self.baseEntry)
}
}
.padding()
}
}
class UserData: ObservableObject {
@Published var baseCurr: Int
func saveBase(baseEntry: Int) -> () {
baseCurr = baseEntry
let defaults = UserDefaults.standard
defaults.set(self.baseCurr, forKey: "base")
}
}
Ответ №1:
В body
вы можете использовать только представления — вы не можете выполнять такие операции, как:
self.userData.saveBase(baseEntry: self.baseEntry)
Вы можете использовать onChange
для сохранения значения:
Picker(selection: $baseEntry, label: Text("Select Base >")) {
ForEach(0 ..< self.base.count) {
Text(self.base[$0]).tag($0)
}
.onChange(of: baseEntry) {
self.userData.saveBase(baseEntry: $0)
}
}
Обратите внимание, что вы также можете использовать @AppStorage
для автоматизации сохранения / чтения из UserDefaults:
@AppStorage("base") var baseEntry = 0
и использовать в сборщике так же, как @State
переменную:
Picker(selection: $baseEntry, label: Text("Select Base >")) {
Комментарии:
1. @AppStorage отлично работает, но не обновляет мой параметр, хранящийся в классе UserData (userData.BaseCurr). .onChange обладает наибольшим потенциалом, но поскольку мы используем локальный частный параметр состояния (baseEntry), он не обновляется userData.BaseCurr
2. @GalenSmith Вам, вероятно, не нужна отдельная
@State
переменная в представлении. Просто сделайтеPicker(selection: $userData.baseCurr
и наблюдайте, как.onChange(of: userData.baseCurr) {
3. Средство выбора (выделение: $userData.BaseCurr, метка: текст («Валюта>»)) { ForEach(0 ..< self.baseCurrencies.count) { Текст (self.baseCurrencies[$0]).тег ($ 0). не может соответствовать ‘Equatable } . onChange(of: self.userData.BaseCurr: Int) { self.userData.saveBase() —> выдает сообщение: не удается преобразовать значение типа ‘Int’ в ожидаемый тип аргумента ‘()’.
4. Использование @GalenSmith
.onChange(of: userData.baseCurr) { userData.saveBase(baseEntry: $0) }
5. Спасибо pawello2222 за помощь. Я наконец-то заработал. Я использовал userData.BaseCurr как в сборщике, так и в onChange. Если метод user data.saveBase вызывается без параметров, SwiftUI выдает две ошибки, перечисленные выше; если я оставлю @State private var baseEntry: $0 в качестве заполнителя в вызове, все работает нормально.