Swift无法从父级更新视图

时间:2019-12-10 16:50:12

标签: ios swift swiftui

因此,我有一个SwiftUI视图,该视图在父ViewControllers viewDidLoad()方法中实例化。

它看起来像这样:

class ChildViewController: UIViewController {
    private var historyView: HistoryView?
    private var models: [HistoryModel]?
    ...

    override func viewDidLoad() {
        super.viewDidLoad()

        historyView = HistoryView(models: models)
        let historyViewHost = UIHostingController(rootView: historyView)
        view.addSubview(historyViewHost.view)
        historyViewHost.didMove(toParent: self)
        historyViewHost.view.frame = view.frame
    }
    ...
}

在某个时候,我需要在historyView中更新模型,我这样做是这样的:

func updateHistory() {
    let updatedModels = requests.map({ HistoryModel.fromRequest(request: $0) })

    historyView!.historyCellModels = updatedModels
}

问题是视图中的模型实际上没有更新。我并不是说视图不会显示新模型,但实际上它甚至都无法获得新模型列表。

每次单击按钮时,我的HistoryView也会更新,当我单击该按钮时,我在视图的构造中设置了一个断点,并且从调试器中可以看到模型没有更新。我的updateHistory方法中也有一个断点,在那里我可以看到父对象中的模型已更新,只是没有传递给孩子。

我想到可能正在创建视图的两个实例,而我只是在更新错误的一个。因此,当我在historyView中有一个断点时,便查看了它的内存,并写下了它在内存中的位置。然后在父视图中的断点处,我去查看historyView的内存,它指向0x00!但是,甚至更陌生的是historyView并不为零!我什至对它进行了强制转换,使该程序没有问题。

因此,我认为调试器一定是在骗我,只是没有提供正确的信息。所以我去了一些旧的可信赖的印刷声明。当我添加如下打印语句时:

    func updateHistory() {
        let updatedModels = requests.map({ HistoryCellModel.fromRequest(request: $0) })

        print(updatedModels.count)
        historyView!.historyCellModels = updatedModels
        print(historyView?.historyCellModels.count)
    }

然后创建一个新模型,并调用它将输出的更新函数:

11
Optional(10)

那怎么可能!

我的HistoryView看起来像这样:

struct HistoryView: View {
    @State var historyCellModels: [HistoryModel]

    var body: some View {
        List(historyCellModels) { ... }    
    }
}

我清楚地将两个变量设置为相等,视图为非null,只有一个实例...我真的不确定下一步要解决的错误是什么。有什么明显的我可能会丢失的东西吗?

1 个答案:

答案 0 :(得分:1)

npm install设计为只能在SwiftUI视图本身中使用( )(建议始终声明为私有)。

所以这是一种方法...

改为使用

@State

其中

struct HistoryView: View {
    @ObservedObject var historyCellModels: HistoryViewModel

    init(models: HistoryViewModel) {
       historyCellModels = models
    }
    ...

现在可以了

import Combine

class HistoryViewModel: ObservableObject {
    @Published var historyCellModels: [HistoryModel]
}

class ChildViewController: UIViewController {
    private var models: HistoryViewModel = HistoryViewModel()
    ...

所有方法都应该起作用。