Internally, a throttle keeps track of two things:
update
needs to be applied before it will allow the next command to be executed (we'll call this the "counter")update
sets the counter to 0
(we'll call this the "stored command")create : Basics.Int -> Throttle msg
Create a throttle that will ensure that commands will be executed at most once per n
applications of update
. We'll call n
the "counter maximum". The counter is initially set to 0
to ensure the execution of the first command is not delayed (see try
).
throttle : Throttle msg
throttle =
Throttle.create n
update : Throttle msg -> ( Throttle msg, Platform.Cmd.Cmd msg )
0
and there is a stored command:Returns a Throttle
whose counter is set to the counter maximum, and the stored command
0
and there is not a stored command:Returns an identical Throttle
and Cmd.none
(note: As this case accomplishes nothing, if performance is a concern and you're using a subscription to update your throttle, use ifNeeded
and this will never happen.)
0
:Returns a throttle with a counter equal to the old counter minus one, and Cmd.none
try : Platform.Cmd.Cmd msg -> Throttle msg -> ( Throttle msg, Platform.Cmd.Cmd msg )
Try to execute a command.
If model.throttle
's counter is 0
, newThrottle
is a Throttle
whose counter is set to the counter maximum, and cmd
is doSomething
.
If model.throttle
's counter is not 0
, newThrottle
is a Throttle
with doSomething
set as the stored command, and cmd
is Cmd.none
.
update msg model =
case msg of
MouseMoved ->
let
( newThrottle, cmd ) =
Throttle.try
doSomething
model.throttle
in
( { model | throttle = newThrottle }, cmd )
ifNeeded : Platform.Sub.Sub msg -> Throttle msg -> Platform.Sub.Sub msg
If the throttle's counter is 0
and there is no stored command, return Sub.none
, otherwise, return the subscription that was passed in.
This allows you to use high frequency subscriptions for throttling and not worry about it running when it's not needed.