#ios #swift #swiftui
#iOS #swift #swiftui
Вопрос:
Xcode 12 iOS 14 beta 8
У меня есть представление SwiftUI, которое может представлять три разных листа в зависимости от состояния приложения. Вместо трех отдельных.модификаторы листа и три разных @State
свойства для обработки этих листов, я подумал, что использование перечисления для определения того, какой лист представить, было бы элегантным решением…но это не работает.
Вот перечисление:
enum SheetType: Int, Identifiable {
case welcome
case notification
case assignment
var id: Int { rawValue }
}
SheetType
должно соответствовать идентификатору из-за .sheet(item:content:)
модификатора в представлении:
struct MainTabView: View {
@State var sheetType: SheetType?
var body: some View {
Text("Hello World!")
.onAppear(perform: checkForSheet)
.sheet(item: $sheetType) { _ in
sheetView
}
}
}
При MainTabView
появлении checkForSheet
ищет условия, которые гарантировали бы представление определенного листа, и, если какие-либо совпадают, устанавливает sheetType
свойство следующим образом: sheetType = .welcome
. Затем следует вызвать sheetView
, который возвращает соответствующий лист.
Проблема в том, что независимо от того, где в коде я обновляю значение sheetType
, оно остается нулевым. Я вижу изменение значения на долю секунды в отладчике, но затем оно переключается обратно на ноль, прежде чем может быть представлен лист. Я в полной растерянности. Есть ли что-то очевидное, чего мне не хватает, или это просто еще одна ошибка?
РЕДАКТИРОВАТЬ 1:
Благодаря коду Asperi я смог представить лист, но проблема в том, что sheetView
свойство, которое возвращает правильный лист, также не работает. Вместо этого я изменил его на функцию и изменил .sheet
модификатор:
.sheet(item: $sheetType) { type in
createSheetView(of: type)
}
Вот код для createSheetView(of:)
. Я подтвердил в отладчике, что значение sheetType
равно .welcome
, но оператор switch по-прежнему возвращает значение по умолчанию, которое бесполезно EmptyView
.
func createSheetView(of type: SheetType) -> some View {
switch sheetType {
case .welcome: return AnyView(WelcomeSplashView())
case .notification: return AnyView(NotificationPermissionView(notificationAccessWasGranted: .constant(false)))
default:
return AnyView(EmptyView())
}
}
РЕДАКТИРОВАТЬ 2:
Я идиот. Я забыл изменить оператор switch с switch sheetType
(который является @State
свойством представления) на новый switch type
(который принимает параметр функции). Теперь это работает 🙂
Ответ №1:
Вот некоторый реплицированный код, который работает с Xcode 12b5
enum SheetType: Int, Identifiable {
case welcome
case notification
case assignment
var id: Int { rawValue }
}
struct MainTabView: View {
@State var sheetType: SheetType?
var body: some View {
Text("Hello World!")
.onAppear(perform: checkForSheet)
.sheet(item: $sheetType) { _ in
Text("sheetView")
}
}
func checkForSheet() {
sheetType = .welcome // << make sure to update always in main queue
}
}
Комментарии:
1. Хм… Я поиграл с этим кодом, и похоже, что причиной проблемы является наличие условного представления внутри листа. Спасибо, что указали мне правильное направление!
2. Я добавил еще немного кода к своему исходному сообщению, если у вас есть время взглянуть еще раз. Спасибо!