There are two basic ways to interact with time in Elm:
- As a one off “let me know when so much time has elapsed” via a command
- As a subscription for “let me know every time this interval has elapsed”.
Via a command
Here’s how a minimal executable version of the game you described might look like using the command: https://ellie-app.com/cjLDLyz3WKYa1
The interesting part is this line in the update
:
UserClickedStart ->
( InProgress, notifyIn TimeIsUp 5000 )
which sets the model into the InProgress
state and kicks off a timer that will notify us when 5 seconds have passed. The implementation of notifyIn
looks like:
notifyIn : Msg -> Float -> Cmd Msg
notifyIn msg time =
Process.sleep time
|> Task.attempt (\_ -> msg)
Via a subscription
Here’s how it might look like using a subscription: https://ellie-app.com/cjLMnNvFVmSa1. An advantage here is that we know about time changes all along rather than just when the timer is done. This means we’re able to decrement the number in the view.
The interesting part is the subscriptions
function which triggers a Tick
message every second when the game is in the InProgress
state.
subscriptions : Model -> Sub Msg
subscriptions model =
case model of
Initial -> Sub.none
InProgress _ -> Time.every 1000 (\_ -> Tick)
Won -> Sub.none
Lost -> Sub.none