In v1, we were exposing dispatch in the view function and it was up to the developers to map messages to the right root type.
type Msg =
| SubPageMsg of SubPage.Msg
let view model dispatch =
SubPage.view model.SubModel (SubPageMsg >> dispatch)
This was possible because we weren't strongly typing the views (everything is ViewElement).
dispatch is a function internal to Fabulous and it's better to not leak it for the view function where it can be misused.
To avoid this, in v2 we're strongly typing the widgets (eg. ContentPage<SubPage.Msg>) and Fabulous takes care of dispatching internally without exposing it to the developers.
But this strong typing prevents composing widgets of different msg types.
NavigationPage([
MainPage.view model.MainPageModel
DetailPage.view model.DetailPageModel // Error: Expected to be ContentPage<MainPage.Msg>, but was ContentPage<DetailPage.Msg>
])
So to change the msg type from one to another (ContentPage<MainPage.Msg> => ContentPage<DetailPage.Msg>), having a mapping function would be necessary
type Msg =
| MainMsg of MainPage.Msg
| DetailMsg of DetailPage.Msg
NavigationPage([
Widget.map MainMsg (MainPage.view model.MainPageModel)
Widget.map DetailMsg (DetailPage.view model.DetailPageModel)
])
In v1, we were exposing
dispatch
in theview
function and it was up to the developers to map messages to the right root type.This was possible because we weren't strongly typing the views (everything is
ViewElement
).dispatch
is a function internal to Fabulous and it's better to not leak it for theview
function where it can be misused.To avoid this, in v2 we're strongly typing the widgets (eg.
ContentPage<SubPage.Msg>
) and Fabulous takes care of dispatching internally without exposing it to the developers.But this strong typing prevents composing widgets of different msg types.
So to change the msg type from one to another (
ContentPage<MainPage.Msg>
=>ContentPage<DetailPage.Msg>
), having a mapping function would be necessary