为Swift UI视图创建自定义修饰符

Lui*_*uis 5 ios swift swiftui

想知道如何为Swift UI视图创建修饰符吗?

例如,假设我有一些这样定义的视图:

struct LabelView: View {
   let font1: Font = .header
   let font2: Font = .body

   var body: Some View {
     // two views, where one uses font1 and other uses font2
   }
}
Run Code Online (Sandbox Code Playgroud)

如何创建一个允许类似以下内容的修饰符:

LabelView()
  .font1(.callout)
  .font2(.body)
Run Code Online (Sandbox Code Playgroud)

我正在尝试学习如何以苹果公司通过Swift UI推动的声明性方式编写API,但是似乎文档还不完善。我试过创建某种类型,ViewModifier但是我不太确定该怎么做,因为它需要我返回_ModifiedContent<_, _>并且不确定如何执行。基本上,可以使用声明性语法(如内置SwiftUI视图中的语法)来修改视图的属性。

ars*_*ius 11

由于 dfd 在评论中链接到,您可以创建使用苹果提供的修饰符的自定义修饰符。您也可以创建自己的方法来修改vars。

注意:您不能在此处使用变异方法,因为函数构建器返回不可变值。你会得到一个编译器错误。您需要制作一份副本self并返回。

extension LabelView {
    func font1(_ font1: Font) -> Self {
        var copy = self
        copy.font1 = font1
        return copy
    }
}
Run Code Online (Sandbox Code Playgroud)

您还可以创建使用键路径更新变量的通用版本:

extension View {
    func modifying<T>(_ keyPath: WritableKeyPath<Self, T>, value: T) -> Self {
        var copy = self
        copy[keyPath: keyPath] = value
        return copy
    }
}
Run Code Online (Sandbox Code Playgroud)

两个版本的用法:

struct LabelView: View {
    var font1: Font = .headline
    var font2: Font = .body
    var body: some View { ... }
}

LabelView()
    .modifying(\.font2, value: .callout)
    .font1(.largeTitle)
Run Code Online (Sandbox Code Playgroud)

结果如下:

结果视图