I’m working on a game where you transition between different states, and for some of these I’d like to have a fading animation between each stage.
I have have a graph of what we call scenes in the game, where each scene has a set of nodes (we call those frames), a set of edges (called choices, taking you to the next frame). We represent it as a graph. So the aim is that when a choice is clicked, we transition to the new frame.
My initial thinking was simply to check that if the node ID is different from the current frame, it should set the animation opacity to zero
animation : FrameId -> Animator.Timeline FrameId -> Html.Attribute Msg animation frameId timeline = Animator.Inline.opacity timeline <| \currentFrame -> if currentFrame == frameId then Animator.at 1 else Animator.at 0
Then I set up the following render function
render : List (Element.Attribute Msg) -> Frame -> Element.Element Msg render attributes frame = let node = frame.node choices = IntDict.toList frame.outgoing |> List.filterMap (\( id, choice ) -> case choice of Prompt str -> Just ( id, str ) ) in case node.label of Display text -> Element.column (attributes ++ [ Element.spacing 24, Element.scrollbarX ]) [ textPrompt text , listChoices choices ]
Later I render it with
-- latest is the current Frame id from Animation.current, frame is the node. render [ Element.htmlAttribute <| animation latest model.frameState ] frame
Now I’m curious how I can at the same time fade out the old page? With my current setup the new page only fades in and the old doesn’t transition “out”.
I thought maybe I could use an attribute like
Element.below (render [ Element.htmlAttribute <| animation oldFrameId model.frameState ] oldFrame) but this doesn’t render correctly.