页面在登录状态改变时刷新的问题

huangapple go评论66阅读模式
英文:

The issue of refreshing the page when the login status changes

问题

I am developing an app using SwiftUI, and I'm planning to implement a feature where the app checks the login status upon entering and displays either the login page or the main page accordingly. After logging in on the login page, the app should navigate to the main interface. But I met a problem.

我正在使用SwiftUI开发一个应用程序,计划在进入应用程序时检查登录状态,并根据情况显示登录页面或主页面。在登录页面登录后,应用程序应导航到主界面。但我遇到了一个问题。

I attempted to achieve this using the following approach, but when I change the 'ifLogin' state to true in 'LoginPage()', the page doesn't transition to 'HomeView()'.
Alternatively, are there any better ways to achieve it? I would greatly appreciate it.

我尝试使用以下方法来实现这一目标,但当我在'LoginPage()'中将'ifLogin'状态更改为true时,页面不会切换到'HomeView()'。或者,有没有更好的方法来实现它?我将不胜感激。

struct ContentView: View {
    @ObservedObject var loginVM: LoginVM()
    var body: some View {
        NavigationStack{
            if loginVM.loginInfo.isLogin {
                HomeView()
            }else{
                LoginPage()
            }
        }
    }
}
import SwiftUI

struct LoginPage: View {
    @ObservedObject var loginVM = LoginVM()
    var body: some View {
        VStack{
            Button("Login"){
                loginVM.changeIsLogin()
            }
        }
    }
}
import SwiftUI

class LoginVM: ObservableObject {
    @Published var loginInfo = Login(isLogin: false)
    
    func changeIsLogin(){
        loginInfo.changeLoginState()
    }
}
import Foundation

struct Login {
    var isLogin: Bool
    
    mutating func changeLoginState() {
        isLogin.toggle()
    }
    
    init(isLogin: Bool) {
        self.isLogin = isLogin
    }
}
英文:

I am developing an app using SwiftUI, and I'm planning to implement a feature where the app checks the login status upon entering and displays either the login page or the main page accordingly. After logging in on the login page, the app should navigate to the main interface. But I met a problem.

I attempted to achieve this using the following approach, but when I change the 'ifLogin' state to true in 'LoginPage()', the page doesn't transition to 'HomeView()'.
Alternatively, are there any better ways to achieve it? I would greatly appreciate it.

struct ContentView: View {
    @ObservedObject var loginVM : LoginVM()
    var body: some View {
        NavigationStack{
            if loginVM.loginInfo.isLogin {
                HomeView()
            }else{
                LoginPage()
            }
        }
    }
}
import SwiftUI

struct LoginPage: View {
    @ObservedObject var loginVM = LoginVM()
    var body: some View {
        VStack{
            Button("Login"){
                loginVM.changeIsLogin()
            }
        }
    }
}
import SwiftUI

class LoginVM: ObservableObject {
    @Published var loginInfo = Login(isLogin: false)
    
    func changeIsLogin(){
        loginInfo.changeLoginState()
    }

}
import Foundation

struct Login {
    var isLogin: Bool
    
    mutating func changeLoginState() {
        isLogin.toggle()
    }
    
    init(isLogin: Bool) {
        self.isLogin = isLogin
    }

}

答案1

得分: 0

你犯了一个常见错误:创建了两个不同(独立)的LoginVM实例。

始终使用一个实例。要么将其注入到环境中,要么通过视图层次结构传递它。

自SwiftUI 2以来,@State的引用类型等效物是@StateObject,而@Binding的等效物是@ObservedObject

struct ContentView: View {
    @StateObject var loginVM = LoginVM()

    var body: some View {
        NavigationStack{
            if loginVM.loginInfo.isLogin {
                HomeView()
            }else{
                LoginPage(loginVM: loginVM)
            }
        }
    }
}

struct LoginPage: View {
    @ObservedObject var loginVM : LoginVM

    var body: some View {
        VStack{
            Button("Login"){
                loginVM.changeIsLogin()
            }
        }
    }
}

语法@ObservedObject var loginVM : LoginVM()无论如何都是错误的,无法编译。

英文:

You made a common mistake: You created two different (independent) instances of LoginVM.

Use always one instance. Either inject it into the environment or pass it through the view hierarchy.

And since SwiftUI 2 the reference type equivalent of @State is @StateObject and the equivalent of @Binding is @ObservedObject.

struct ContentView: View {
    @StateObject var loginVM = LoginVM()

    var body: some View {
        NavigationStack{
            if loginVM.loginInfo.isLogin {
                HomeView()
            }else{
                LoginPage(loginVM: loginVM)
            }
        }
    }
}

struct LoginPage: View {
    @ObservedObject var loginVM : LoginVM

    var body: some View {
        VStack{
            Button("Login"){
                loginVM.changeIsLogin()
            }
        }
    }
}

The syntax @ObservedObject var loginVM : LoginVM() is wrong anyway and doesn't compile.

huangapple
  • 本文由 发表于 2023年5月28日 23:02:45
  • 转载请务必保留本文链接:https://go.coder-hub.com/76352114.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定