elm 0.18 中的局部更新
Locally scoped updates in elm 0.18
我有一个带有许多页面和路由的 elm 0.18 网络应用程序。在 main.elm
中我定义了我的更新函数。
update : Msg -> Model -> ( Model, Cmd Msg )
update msg model =
case msg of
FirstUpdateAction ->
...
每个动作都经过这个函数,而且越来越大。是否可以为嵌套在整体结构中的较小模块创建更新函数?
例如,我有一个允许用户更改密码的设置页面。有三个 fields/states(passwordOld、passwordNew、passwordConfirm)具有与 onInput
和 onBlur
事件关联的更新操作。这些状态和操作仅与用户设置页面相关,当用户离开页面时,与模型的其余部分无关。
如何为用户设置设置范围?
您可以将代码分解为独立的子模块,每个子模块都有自己的消息类型、更新和查看功能。
例如,您可以有一个文件 SubmoduleA.elm 如下所示:
module SubmoduleA exposing (Model, Msg, update, view)
type Msg = SubMessageA
| SubMessageB
[..]
type alias model =
{ fieldA : TypeA
, fieldB : TypeB
, [..]
}
update msg model =
case msg of
MessageA ->
{model | fieldA = [..] } ! []
[..]
view model =
div [id "submoduleAView"]
[..]
此模块将像这样连接到您的主程序:
module Main exposing (..)
import SubmoduleA exposing (Model, Msg, update, view)
type Msg = MessageA
| MessageB
| ToSubmoduleA (SubmoduleA.Msg)
[..]
type alias model =
{ fieldA : TypeA
, fieldB : TypeB
, [..]
, subModuleA : SubmoduleA.Model
}
update msg model =
case msg of
MessageA ->
{model | fieldA = [..] } ! []
[..]
ToSubmoduleA msg =
let (newSubmoduleA, newSubmoduleACmd) = SubmoduleA.update msg (.subModuleA model)
in { model | subModuleA = newSubmoduleA } ! [Cmd.map ToSubmoduleA newSubmoduleACmd]
view model =
div [id "mainView"]
[ ..
, Html.map ToSubmoduleA <| SubmoduleA.view (.subModuleA model)
]
这样,与您的子模块相关的所有信息和状态都封装在您的子模块中,而您的主更新函数中只有一个案例负责消息的正确路由。
我有一个带有许多页面和路由的 elm 0.18 网络应用程序。在 main.elm
中我定义了我的更新函数。
update : Msg -> Model -> ( Model, Cmd Msg )
update msg model =
case msg of
FirstUpdateAction ->
...
每个动作都经过这个函数,而且越来越大。是否可以为嵌套在整体结构中的较小模块创建更新函数?
例如,我有一个允许用户更改密码的设置页面。有三个 fields/states(passwordOld、passwordNew、passwordConfirm)具有与 onInput
和 onBlur
事件关联的更新操作。这些状态和操作仅与用户设置页面相关,当用户离开页面时,与模型的其余部分无关。
如何为用户设置设置范围?
您可以将代码分解为独立的子模块,每个子模块都有自己的消息类型、更新和查看功能。
例如,您可以有一个文件 SubmoduleA.elm 如下所示:
module SubmoduleA exposing (Model, Msg, update, view)
type Msg = SubMessageA
| SubMessageB
[..]
type alias model =
{ fieldA : TypeA
, fieldB : TypeB
, [..]
}
update msg model =
case msg of
MessageA ->
{model | fieldA = [..] } ! []
[..]
view model =
div [id "submoduleAView"]
[..]
此模块将像这样连接到您的主程序:
module Main exposing (..)
import SubmoduleA exposing (Model, Msg, update, view)
type Msg = MessageA
| MessageB
| ToSubmoduleA (SubmoduleA.Msg)
[..]
type alias model =
{ fieldA : TypeA
, fieldB : TypeB
, [..]
, subModuleA : SubmoduleA.Model
}
update msg model =
case msg of
MessageA ->
{model | fieldA = [..] } ! []
[..]
ToSubmoduleA msg =
let (newSubmoduleA, newSubmoduleACmd) = SubmoduleA.update msg (.subModuleA model)
in { model | subModuleA = newSubmoduleA } ! [Cmd.map ToSubmoduleA newSubmoduleACmd]
view model =
div [id "mainView"]
[ ..
, Html.map ToSubmoduleA <| SubmoduleA.view (.subModuleA model)
]
这样,与您的子模块相关的所有信息和状态都封装在您的子模块中,而您的主更新函数中只有一个案例负责消息的正确路由。