@ObservedObject не запускает перерисовку, если в условном

#swift #swiftui

#swift #swiftui

Вопрос:

У меня есть следующий код:

 import SwiftUI

struct RootView: View {
    @ObservedObject var authentication: AuthenticationModel
    
    var body: some View {
        ZStack {
            if self.authentication.loading {
                Text("Loading")
            } else if self.authentication.userId == nil {
                SignInView()
            } else {
                ContentView()
            }
        }
    }
}
  

Однако @ObservedObject изменения, похоже, не запускают переключение на другие представления. Я могу «исправить» это путем рендеринга

     var body: some View {
        VStack {
            Text("(self.authentication.loading ? "true" : "false") (self.authentication.userId ?? "0")")
        }.font(.largeTitle)
        ZStack {
            if self.authentication.loading {
                Text("Loading")
            } else if self.authentication.userId == nil {
                SignInView()
            } else {
                ContentView()
            }
        }
    }
  

и внезапно он начинает работать. Почему @ObservedObject , похоже, не запускается повторный запуск, если наблюдаемые свойства используются только в условных выражениях?

Код для AuthenticationModel :

 import SwiftUI
import Combine
import Firebase
import FirebaseAuth

class AuthenticationModel: ObservableObject {
    @Published var userId: String?
    @Published var loading = true
    
    init() {
        // TODO: Properly clean up this handle.
        Auth.auth().addStateDidChangeListener { [unowned self] (auth, user) in
            self.userId = user?.uid
            self.loading = false
        }
    }
}
  

Комментарии:

1. Можете ли вы показать код (по крайней мере, частичный) для AuthenticationModel ?

2. @NewDev Конечно, обновил сообщение.

3. Я не могу воспроизвести код, который вы показали (я использовал DispatchQueue.main.asyncAfter вместо Auth )

4. Трудно сказать. Я предполагаю, что вы создаете экземпляр let auth = AuthenticationModel(...) и передаете его: RootView(authentication: auth) ? Возможно, ошибка не в коде, который вы показали.

5. Да, это так. Я также не уверен на 100%, что ошибка находится в приведенном выше коде, но я думаю, что удаление [unowned self] работает на данный момент. Поскольку это постоянный прослушиватель аутентификации, это не так уж плохо. Я в основном удивлен, потому что приложение прямо сейчас не намного больше, чем эти представления, поскольку это новый проект, но я, возможно, вернусь к этой проблеме и опубликую, если что-нибудь выясню.

Ответ №1:

Я думаю, проблема может заключаться в том, что вы не создаете экземпляр AuthenticationModel . Можете ли вы попробовать следующее в rootView?:

 @ObservedObject var authentication = AuthenticationModel()