Skip to content

Fix animation frames #138

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open

Conversation

lydell
Copy link

@lydell lydell commented Jun 1, 2025

When Elm’s virtual DOM crashes, you get an error in the browser console many times per second. This is because Elm generally draws on the next animation frame using requestAnimationFrame, and if it crashes during rendering it gets stuck in an infinite requestAnimationFrame loop. That’s really annoying. This PR makes sure it doesn’t get stuck in a loop on error.

When changing the code to not get caught in a loop if there is an exception, I also noticed that the whole requestAnimationFrame was a bit off. Basically, if you also subscribe to Browser.Events.onAnimationFrame, you could end up with update and view being 1 frame out of sync, and some frames could be skipped. I made a demo showing these animation frame oddities. This PR fixes that, too, except the demo cases where the animation frames come via a port – I don’t think that is solvable.

The old implementation was really clever: When rendering, it basically always ran requestAnimationFrame one time extra, just in case there is a Browser.Events.onAnimationFrame, so that there’s always a render queued up for the next animation frame ready to go, without having to wait until the next frame. But if there is no Browser.Events.onAnimationFrame subscription, the system only resulted in one extra requestAnimationFrame call (it’s not like Elm is constantly doing things on every single animation frame, many times per second). While I appreciate the cleverness of the old implementation, it unfortunately resulted in update and view being 1 frame out of sync, and some frames could be skipped, as mentioned above. The new implementation instead wraps requestAnimationFrame to keep track of whether we are currently in an animation frame or not.

Note to those following along: This PR is included in https://github.com/lydell/browser/tree/safe, which is part of https://github.com/lydell/elm-safe-virtual-dom. This is only related to “safe virtual DOM” in the form that if the rendering crashes, it won’t loop in a tight requestAnimationFrame loop.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

1 participant