Packages

Animations for lustre, utilizing JS requestAnimationFrame and setTimeout

Current section

Files

Jump to
lustre_animation src example_simple.erl
Raw

src/example_simple.erl

-module(example_simple).
-compile([no_auto_import, nowarn_unused_vars]).
-export([update/2, render/1, main/0]).
-export_type([msg/0, model/0]).
-type msg() :: left | right | top | bottom | {tick, float()}.
-type model() :: {model, float(), float(), lustre@animation:animations()}.
-spec init() -> model().
init() ->
{model, 0.5, 0.5, lustre@animation:new()}.
-spec update(model(), msg()) -> {model(), lustre@cmd:cmd(msg())}.
update(Model, Msg) ->
M = case Msg of
left ->
New_animations = lustre@animation:add(
erlang:element(4, Model),
<<"x"/utf8>>,
erlang:element(2, Model),
0.0,
2.5
),
erlang:setelement(4, Model, New_animations);
right ->
New_animations@1 = lustre@animation:add(
erlang:element(4, Model),
<<"x"/utf8>>,
erlang:element(2, Model),
1.0,
2.5
),
erlang:setelement(4, Model, New_animations@1);
top ->
New_animations@2 = lustre@animation:add(
erlang:element(4, Model),
<<"y"/utf8>>,
erlang:element(3, Model),
0.0,
2.5
),
erlang:setelement(4, Model, New_animations@2);
bottom ->
New_animations@3 = lustre@animation:add(
erlang:element(4, Model),
<<"y"/utf8>>,
erlang:element(3, Model),
1.0,
2.5
),
erlang:setelement(4, Model, New_animations@3);
{tick, Time_offset} ->
New_animations@4 = lustre@animation:tick(
erlang:element(4, Model),
Time_offset
),
X = lustre@animation:value(
New_animations@4,
<<"x"/utf8>>,
erlang:element(2, Model)
),
Y = lustre@animation:value(
New_animations@4,
<<"y"/utf8>>,
erlang:element(3, Model)
),
{model, X, Y, New_animations@4}
end,
{M,
lustre@animation:cmd(
erlang:element(4, M),
fun(Field@0) -> {tick, Field@0} end
)}.
-spec render(model()) -> lustre@element:element(msg()).
render(Model) ->
Sp = lustre@element:span([], []),
To_s = fun gleam@float:to_string/1,
lustre@element:'div'(
[],
[lustre@element:'div'(
[lustre@attribute:style(
[{<<"height"/utf8>>, <<"50vh"/utf8>>},
{<<"display"/utf8>>, <<"grid"/utf8>>},
{<<"grid-template-rows"/utf8>>,
<<<<<<(To_s(erlang:element(3, Model)))/binary,
"fr auto "/utf8>>/binary,
(To_s(1.0 - erlang:element(3, Model)))/binary>>/binary,
"fr"/utf8>>},
{<<"grid-template-columns"/utf8>>,
<<<<<<(To_s(erlang:element(2, Model)))/binary,
"fr auto "/utf8>>/binary,
(To_s(1.0 - erlang:element(2, Model)))/binary>>/binary,
"fr"/utf8>>}]
)],
[Sp,
Sp,
Sp,
Sp,
'..@ffi.mjs':text(<<"Move me around"/utf8>>),
Sp,
Sp,
Sp,
Sp]
),
lustre@element:'div'(
[],
[lustre@element:button(
[lustre@event:on_click(left)],
['..@ffi.mjs':text(<<"Move to the Left"/utf8>>)]
),
lustre@element:button(
[lustre@event:on_click(right)],
['..@ffi.mjs':text(<<"Move to the Right"/utf8>>)]
),
lustre@element:button(
[lustre@event:on_click(top)],
['..@ffi.mjs':text(<<"Move to the Top"/utf8>>)]
),
lustre@element:button(
[lustre@event:on_click(bottom)],
['..@ffi.mjs':text(<<"Move to the Bottom"/utf8>>)]
)]
)]
).
-spec main() -> {ok, fun((msg()) -> nil)} | {error, lustre:error()}.
main() ->
_pipe = lustre:application(
{init(), lustre@cmd:none()},
fun update/2,
fun render/1
),
lustre:start(_pipe, <<"#root"/utf8>>).