SwiftUI |如何覆盖 viewWillAppear 等生命周期方法

Posted

技术标签:

【中文标题】SwiftUI |如何覆盖 viewWillAppear 等生命周期方法【英文标题】:SwiftUI | How to override life cycle methods like viewWillAppear 【发布时间】:2020-02-04 06:15:57 【问题描述】:

在我现有的应用程序中,所有视图控制器上的 UI 配置很少,例如设置自定义导航栏、设置全屏背景图像等等。为此,在viewWillAppear 的基本视图控制器中进行配置,所有视图控制器都继承自它。因此,无需在子视图控制器中执行任何操作即可进行配置

如何使用 SwiftUI 实现类似的实现?

SwiftUI 在 View 上提供了 onAppear()onDisappear() 方法,它是 Struct,不支持继承。如果我制作扩展方法或协议,我必须从所有视图中调用方法。

感谢任何帮助...

【问题讨论】:

在 SwiftUI 中,您不应该考虑继承。请改用 composition @Sweeper 我同意你的看法。但最后,我们需要可重用的解决方案。您能否提供一些示例,如何使用组合解决上述问题? 改变设计没有万能的解决方案。根据您所说,设置导航栏、设置背景图像等操作都应在body 属性中完成。创建一个执行这些操作的视图,但它的初始化程序需要 viewBuilder 以允许您传递不同的内容。这有点像 Button 的工作原理。 【参考方案1】:

制作您自己的容器视图。您可以使用@ViewBuilder 使您的视图表现得像VStackHStack,其中需要一个充满子视图的内容闭包。

例如,这是一个自定义容器,它为主要内容提供粉红色背景,并在其下方放置一个工具栏:

import SwiftUI

struct CustomContainer<Content: View>: View 
    init(@ViewBuilder content: () -> Content) 
        self.content = content()
    

    let content: Content

    var body: some View 
        VStack(spacing: 0) 
            content
                .frame(maxWidth: .infinity, maxHeight: .infinity)
                .background(Color(hue: 0, saturation: 0.3, brightness: 1))
            Toolbar()
        
    


struct Toolbar: View 
    var body: some View 
        HStack 
            Spacer()
            button("person.3.fill")
            Spacer()
            button("printer.fill")
            Spacer()
            button("heart.fill")
            Spacer()
            button("bubble.left.fill")
            Spacer()
         //
            .frame(height: 44)
    

    private func button(_ name: String) -> some View 
        Image(systemName: name)
            .resizable()
            .aspectRatio(contentMode: .fit)
            .padding(4)
            .frame(width: 40, height: 40)
    

然后这是一个使用它的视图:

struct HelloView: View 
    var body: some View 
        CustomContainer 
            VStack 
                Text("hello")
                Text("khawar")
            
        
    


import PlaygroundSupport
PlaygroundPage.current.setLiveView(HelloView())

结果:

【讨论】:

谢谢@rob。这是个好主意。问题的目的是讨论并为一个基本问题提出更好的解决方案。看看SwiftUI有没有其他方法,否则我会接受你的回答。

以上是关于SwiftUI |如何覆盖 viewWillAppear 等生命周期方法的主要内容,如果未能解决你的问题,请参考以下文章

即使在 SwiftUI 中调整矩形大小,如何将点转换为 Rectangle 的点?

如何在swiftui中的navigationitems下面创建一个弹出菜单

SwiftUI 覆盖阻止列表滚动事件

SwiftUI 将覆盖添加到整个屏幕

SwiftUI 中可覆盖的 ButtonStyle

键盘不覆盖 SwiftUI 中的视图