右边有 2 个值的函数是什么意思? (型号 -> Html 消息)

What does a function with 2 values on the right side mean? (Model -> Html msg)

我在指南中遇到过:

viewValidation : Model -> Html msg
viewValidation model =
  let
    (color, message) =
      if model.password == model.passwordAgain then
        ("green", "OK")
      else
        ("red", "Passwords do not match!")
  in
    div [ style [("color", color)] ] [ text message ]

所以这是一个接受Model的函数。 Html msg 在我看来通常就像我们在调用带有参数 msg 的函数 Html 一样。

不过,

msg 似乎在 viewValidation 函数的任何其他部分都没有发挥任何作用。那么它是什么意思,在这种情况下有什么用?

Html Msg 只是一个类型参数,就像 List Int 一样。虽然 List Int 表示包含类型 Int 元素的列表,但类似地 Html Msg 描述了一些 HTML 可以 treat/emit 类型 Msg 的消息。

例如,如果您的 HTML 中有一个按钮,它可能如下所示:

button [ onClick DoSomething ] [ text "caption" ]

其中 DoSomethingMsg 类型的情况。

不要将类型定义与代码的正常执行混为一谈。 Html不是函数,它是一个接受参数的类型,为视图函数定义一个类型。

Html msg 是您可以拥有的最一般的定义,因为 msg 本身就是一个变量,所以这个 returns Html 与您的消息类型无关目前正在使用。这可能是因为它没有创建事件消息,或者是因为视图函数将消息作为参数。

因为评论建立 Html () 将是一个非常狭窄的类型,限制为 return 没有。

最常见的情况是视图函数 returning Html Msg - 即 Html 带有基于用户交互的消息。

由于 Elm 鼓励组件化,因此您还需要牢记 Html.map。它的类型签名是 Html.map : (a -> b) -> Html a -> Html b。在组件的上下文中,这更容易读作

Html.map : (Child.Msg -> Parent.Msg) -> Html Child.Msg -> Html Parent.Msg

请注意,当您在父组件中定义消息时,您将拥有类似的内容:

type Msg = ChildMsg Child.Msg

这意味着 ChildMsg 具有类型签名:

ChildMsg : Child.Msg -> Parent.Msg

所以我的视图函数有很多

parentView model = 
  -- childView model.child |> Html.map ChildMsg
  Html.map ChildMsg (childView model.child)