为什么“ ViewModifier”协议具有“ associatedtype”和“ typealias”?

问题描述

据我所知,ViewModifier协议的定义如下:

protocol ViewModifier {

    // content view type passed to body()
    typealias Content

    // type of view returned by body()
    associatedtype Body : View

    // only requirement
   func body(content: Self.Content) -> Self.Body

}

我的问题是:

为什么Self.ContenttypealiasSelf.Bodyassociatedtype? 有什么区别?

解决方法

为什么Self.ContenttypealiasSelf.Bodyassociatedtype?有什么区别?

由于Contenttypealias,因此ViewModifier协议的作者在编写协议时会选择别名的类型。 (您看不到别名的类型,因为该类型是_ViewModifier_Content<Self>。当SDK中的标识符以_开头时,Apple会从文档和生成的接口中忽略该标识符。)

由于Bodyassociatedtype,因此在编写符合ViewModifier协议的类型时可以选择别名。您可以将Body设置为任意类型,但要满足两个条件:

  • 您必须选择符合View的类型(因为ViewModifier协议约束Body符合View)。

  • 您必须能够创建或获取您选择的任何类型的实例,因为您必须从body方法返回它的实例。 (或者您可能会崩溃或挂起以避免完全返回,但这通常不是您想要的……)

因此,当您实现符合ViewModifier的类型时,就无法影响Content的含义。它始终表示_ViewModifier_Content<Self>。但是您可以通过选择Body方法的返回类型来选择body的含义。

在这里,我将强制Body表示EmptyView

struct EmptyModifier: ViewModifier {
    func body(content: Content) -> EmptyView {
        EmptyView()
    }
}

在这里,我将强制Body表示Color

struct RedModifier: ViewModifier {
    func body(content: Content) -> Color {
        Color.red
    }
}

通常,我们使用some View作为类型,这意味着Swift会为我们推断出确切的类型并将其保密:

struct FrameModifier: ViewModifier {
    var color: Color
    var width: CGFloat

    func body(content: Content) -> some View {
        return content
            .padding(width)
            .border(color,width: width)
    }
}

在这里,我们对Body类型的了解仅在于它符合View。 Swift尽力阻止我们在编译时发现真实类型。

,
  • typealias仅更改类型的名称。没什么。

  • associatedtype是在协议实现中包含泛型的一种方式。


public protocol ViewModifier {

    /// The type of view representing the body of `Self`.
    associatedtype Body : View

    /// Returns the current body of `self`. `content` is a proxy for
    /// the view that will have the modifier represented by `Self`
    /// applied to it.
    func body(content: Self.Content) -> Self.Body

    /// The content view type passed to `body()`.
    typealias Content
}

在上面的示例中,Body是符合View的具体类型,并由body(content:)返回类型来推断。

Content只是作为content参数传递的类型的另一个名称。


rob mayoff的

This answer更详细地解释了ViewModifier

因此,这告诉我们,当我们编写自己的ViewModifier时,我们的body 方法将收到某种View(具体类型由 框架,我们可以将其命名为Content),然后返回某种形式 的View(我们将选择特定的返回类型)。

这意味着您不知道Content是什么,您只需对其进行操作-为方便起见,它被称为Content,因此您不必处理_ViewModifier_Content<Self>

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...