根据观察到的变量的更新来更新@Published变量 [英] Updating a @Published variable based on changes in an observed variable

查看:79
本文介绍了根据观察到的变量的更新来更新@Published变量的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个可以观察到的AppState:

I have an AppState that can be observed:

class AppState: ObservableObject {

    private init() {}
    static let shared = AppState()

    @Published fileprivate(set) var isLoggedIn = false

}

视图模型应根据状态( isLoggedIn )决定显示哪个视图:

A View Model should decide which view to show based on the state (isLoggedIn):

class HostViewModel: ObservableObject, Identifiable {

    enum DisplayableContent {
        case welcome
        case navigationWrapper
    }

    @Published var containedView: DisplayableContent = AppState.shared.isLoggedIn ? .navigationWrapper : .welcome

}

最后, HostView 观察 containedView 属性并基于该属性显示正确的视图.

In the end a HostView observes the containedView property and displays the correct view based on it.

我的问题是,上面的代码未观察到 isLoggedIn ,我似乎也找不到解决方法.我非常确定这是一种简单的方法,但是经过4小时的试用和测试后,错误,我希望这里的社区能够帮助我.

My problem is that isLoggedIn is not being observed with the code above and I can't seem to figure out a way to do it. I'm quite sure that there is a simple way, but after 4 hours of trial & error I hope the community here can help me out.

推荐答案

有效的解决方案:

在使用Combine的两个星期之后,我现在又重新处理了以前的解决方案(请参阅编辑历史记录),这是我现在能想到的最好的解决方案.这仍然不完全是我的初衷,因为 contained 不是同时属于订户和发布者,但是我认为始终需要 AnyCancellable .如果有人知道实现我的愿景的方法,请仍然让我知道.

After two weeks of working with Combine I have now reworked my previous solution again (see edit history) and this is the best I could come up with now. It's still not exactly what I had in mind, because contained is not subscriber and publisher at the same time, but I think the AnyCancellable is always needed. If anyone knows a way to achieve my vision, please still let me know.

class HostViewModel: ObservableObject, Identifiable {

    @Published var contained: DisplayableContent
    private var containedUpdater: AnyCancellable?

    init() {
        self.contained = .welcome
        setupPipelines()
    }

    private func setupPipelines() {
        self.containedUpdater = AppState.shared.$isLoggedIn
            .map { $0 ? DisplayableContent.mainContent : .welcome }
            .assign(to: \.contained, on: self)
    }

}

extension HostViewModel {

    enum DisplayableContent {
        case welcome
        case mainContent
    }

}

这篇关于根据观察到的变量的更新来更新@Published变量的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆