ios 是否可以在应用程序启动之前检查CoreData值,并根据SwiftUI项目中的值显示视图?

vpfxa7rd  于 2023-05-19  发布在  iOS
关注(0)|答案(2)|浏览(169)

我正在使用的应用程序有两个视图,登录视图和主页视图。应用首次启动时,将从登录视图开始。用户必须使用名称和ID注册,然后单击“下一步”按钮,这将将用户导航到主视图。当用户使用名称和ID注册时,数据将保存到CoreData中。用户注册后,每次下次用户启动我想要的应用程序时,应用程序都会以主视图启动。

import SwiftUI

@main
struct BJITXpressApp: App {
    let persistenceController = PersistenceController.shared

    var body: some Scene {
        WindowGroup {
            LoginView()
                .environment(\.managedObjectContext, persistenceController.container.viewContext)
        }
    }
}

在应用程序启动时,应用程序将从CoreData检查注册数据,如果找到数据,应用程序将从 Home View 启动。
我在登录视图.onAppear上尝试了以下策略

struct LoginView: View {
    @Environment(\.managedObjectContext) var context
    @State private var name: String = ""
    @State private var employeeId: String = ""
    @State var isShowingHomeView = false
    
    var body: some View {
        NavigationView{...}
        .onAppear{
            checkFirstUse()
        }
        .fullScreenCover(isPresented: $isShowingHomeView){
            HomeView()
        }

但这样一来,应用程序首先从登录视图开始,然后如果它在Coredata中找到数据,则导航到HomeView。而不是开始->登录->检查CoreData ->主页视图,我希望它像开始->检查CoreData ->主页视图

nkoocmlb

nkoocmlb1#

加载核心数据是异步的,并且可能产生错误。您必须在UI显示和核心数据可用之间的时间段内提供一些UI。您不得阻止UI等待Core Data完成加载。它可以任意长。
您当前的方法接近:启动->登录视图->检查核心数据->主页视图。但是,您需要的是Starts -> LoadingView -> Check CoreData -> HomeView|登录视图。
您需要创建一个新的LoadingView。可能是空白的。更常见的做法是显示进度指示器。但它必须是某种东西,因为存在这样一种状态,你必须在每一种可能的状态下展示某种东西。
在我的一个项目中,我对LoadingView使用了以下方法:

struct LoadingView<Content: View, Model>: View {
    enum LoadState {
        case loading
        case loaded(Model)
        case error(Error)
    }

    @ViewBuilder let content: (Model) -> Content
    let loader: () async throws -> Model

    @State var loadState = LoadState.loading

    var body: some View {
        ZStack {
            Color.white
            switch loadState {
            case .loading: Text("Loading")
            case .loaded(let model): content(model)
            case .error(let error): Text(verbatim: "Error: \(error)")
            }
        }
        .task {
            do {
                loadState = .loaded(try await loader())
            } catch {
                loadState = .error(error)
            }
        }
    }
}

在我有Text的地方,你可能会想要更专业的东西(这来自于一个个人爱好项目)。
在这个项目中,我有这样的视图:

struct DailyView: View {
    var body: some View {
        LoadingView() { model in
            LoadedDailyView(model: model)
        } loader: {
            try await DailyModel()
        }
    }
}

所以实际的视图总是需要一个模型,加载器一完成它就得到它。这远不是唯一的办法。你可以使用你现在拥有的东西。这只是我用来激发灵感的一种方法。

hpcdzsge

hpcdzsge2#

通过以下操作解决了问题

enum LoginState {
    case isChecking
    case isLoggedIn
    case isNotLoggedIn
    case isWeekend
}

class ViewSelector: ObservableObject {
    @Published var loginState: LoginState = .isChecking
    
    init() {
        
        let isWeekend = isSundayOrMonday()
        if isWeekend{
            loginState = .isWeekend
        }else {
            let isLoggedIn =
            PersistenceController.shared.isRegisterDataAvailable()
            loginState = isLoggedIn ? .isLoggedIn : .isNotLoggedIn
        }
    } 

struct BJITXpressApp: App {
    let persistenceController = PersistenceController.shared
    
    @StateObject var viewModel = ViewSelector()

    var body: some Scene {
        WindowGroup {
            Group {
                if viewModel.loginState == .isChecking {
                    // Show a loading view or any other appropriate view while checking the login state
                    Text("Checking...")
                } else if viewModel.loginState == .isWeekend{
                    WeekendView()
                } else if viewModel.loginState == .isLoggedIn {
                    HomeView()
                        .environment(\.managedObjectContext, persistenceController.container.viewContext)
                } else if viewModel.loginState == .isNotLoggedIn {
                    LoginView()
                        .environment(\.managedObjectContext, persistenceController.container.viewContext)
                }
            }
        }
    }
}

相关问题