【iOS】SwiftUI Section

Section 可以将视图在逻辑上分隔开,通常用于容器中,比如 Stack、List、Form 等。Section 不提供额外的视觉效果,但是可以添加自定义的 header 和 footer 视图。

比如用 Section 可以实现以下的效果,其中每个颜色是一个 Section:

首先定义一个结构 ColorData,用于存储每个 Section 的数据:

struct ColorData: Identifiable {
    let id = UUID()
    let name: String
    let color: Color
    let variations: [ShadeData]

    struct ShadeData: Identifiable {
        let id = UUID()
        var brightness: Double
    }

    init(color: Color, name: String) {
        self.name = name
        self.color = color
        self.variations = stride(from: 0.0, to: 0.5, by: 0.1)
            .map { ShadeData(brightness: $0) }
    }
}

然后定义一个 SectionHeaderView 显示在每个 Section 的上方:

struct SectionHeaderView: View {
    var colorData: ColorData

    var body: some View {
        HStack {
            Text(colorData.name)
                .font(.headline)
                .foregroundColor(colorData.color)
            Spacer()
        }
        .padding()
        .background(Color.primary
                        .colorInvert()
                        .opacity(0.75))
    }
}

最后定义若干 ColorData,显示在 LazyVStack 和 ScrollView 中:

struct ColorSelectionView: View {
    let sections = [
        ColorData(color: .red, name: "Reds"),
        ColorData(color: .green, name: "Greens"),
        ColorData(color: .blue, name: "Blues"),
        ColorData(color: .pink, name: "Pinks"),
        ColorData(color: .yellow, name: "Yellows"),
        ColorData(color: .orange, name: "Oranges"),
        ColorData(color: .purple, name: "Purples"),
        ColorData(color: .gray, name: "Grays")
    ]

    var body: some View {
        ScrollView {
            LazyVStack(spacing: 1) {
                ForEach(sections) { section in
                    Section(header: SectionHeaderView(colorData: section)) {
                        ForEach(section.variations) { variation in
                            section.color
                                .brightness(variation.brightness)
                                .frame(height: 20)
                        }
                    }
                }
            }
        }
    }
}

实现效果如下:

默认情况下 Section 的 header 会随着内容一起滚动,如果需要固定 header,可以在容器中指定固定 header 到顶部。

LazyVStack(spacing: 1, pinnedViews: [.sectionHeaders]) {
	// ...
}

实现效果如下:

相关文章

当我们远离最新的 iOS 16 更新版本时,我们听到了困扰 Apple...
欧版/美版 特别说一下,美版选错了 可能会永久丧失4G,不过只...
一般在接外包的时候, 通常第三方需要安装你的app进行测...
前言为了让更多的人永远记住12月13日,各大厂都在这一天将应...