In elm, is something like the below possible
foo : Int -> Html
foo inputNum =
addToNumHistory inputNum ;
display inputNum
where the aim of the above is to execute multiple lines of code?
If not, is this because the above is an example of a side effect?
If something like the above syntax is not possible, how would one go about executing two functions/lines of code simultaneously, as in the above, or as a result of a given input (case branch) ?
The above is a bad example. The following uses the Elm Architecture:
--Model
type alias Model =
{ number : Int
, numberHistory : List Int
}
type Action
= Number Int
--Update
update : Action -> Model
update action =
case action of
Number num->
addToNumHistory num
addToNumHistory : Int -> Model -> Model
addToNumHistory num modelHistory =
{ model
| number = num
, numberHistory = num :: model.numberHistory
}
--View
view : Signal.Address Action -> Model -> Html
view action model =
div []
[ field
"text"
address
Number model.number
"Enter lucky number here pal!"
model.number
]
Given this, am I right in presuming that to 'execute multiple lines' in such a fashion as to alter an underlying model, one would simply use/extend the model - for example, to effect a change analogous to the following:
--Update
update : Action -> Model
update action =
case action of
Number num->
addToNumHistory num;
addToChangeHistory
one would simply extend the model as follows:
--Model
type alias Model =
{ number : Int
, numberHistory : List Int
, changeHistory : List Date
}
--Update
update : Action -> Model
update action =
case action of
Number num->
addToNumHistoryWithChangeHistory num
addToNumHistoryWithChangeHistory : Int -> Model -> Model
addToNumHistory num modelHistory =
{ model
| number = num
, numberHistory = num :: model.numberHistory
, changeHistory = getCurrentDate :: model.changeHistory
}
getCurrentDate : Date
In this specific case, you don't need to have side-effects.
I've had to add two utility functions to create a functioning example.
onInput
to handle 'input'
eventparseInt
to retrieve Int
from a String
The rest is a basic Elm Architecture lifecycle as of 0.16
Please consider this minimal example I made for use with StartApp.Simple:
import Html exposing (text, input, div, Html, Attribute)
import Html.Attributes exposing (value)
import Html.Events exposing (on, targetValue)
import String
import Signal exposing (Address)
import StartApp.Simple as StarApp
--Utils
onInput : Address a -> (String -> a) -> Attribute
onInput address f =
on "input" targetValue (\v -> Signal.message address (f v))
parseInt : String -> Int
parseInt string =
case String.toInt string of
Ok value ->
value
Err error ->
0
--Model
type alias Model =
{ number : Int
, numberHistory : List Int
}
initModel : Model
initModel =
{ number = 0
, numberHistory = []
}
--Update
type Action
= UpdateNumber String
update : Action -> Model -> Model
update action model =
case action of
UpdateNumber num ->
addToNumHistory (parseInt num) model
addToNumHistory : Int -> Model -> Model
addToNumHistory num model =
{ model
| number = num
, numberHistory = num :: model.numberHistory
}
--View
view : Signal.Address Action -> Model -> Html
view address model =
div
[]
[ input
{- On every 'input' event,
grab the value of input field and send to UpdateNumber
-}
[ onInput address UpdateNumber, value (toString model.number) ]
[]
, div [] [ text (toString model.number) ]
, div
[]
( model.numberHistory
|> List.reverse
|> List.map (toString)
|> List.map text
)
]
main : Signal Html
main =
StarApp.start
{ view = view
, update = update
, model = initModel
}