Skip to content
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

Fix: Failed to execute 'animate' on 'Element': Non numeric offset provided #1991

Conversation

walaszczykm
Copy link
Contributor

Hello 👋 I couldn't find the related issue, and while it's an on-line fix, I have decided to open PR directly 🙂

During development, I encountered an error being thrown from framer-motion library

TypeError: Failed to execute 'animate' on 'Element': Non numeric offset provided

I have to dig a little deeper into the library source code to trace the bug and found it originaes from the native Browser Element.animate call on this line: https://github.com/framer/motion/blob/f06854066a1de33561578ce2c4fd785e78fdf3be/packages/framer-motion/src/animation/waapi/index.ts#L17

Direct reproduction was hard at first as after analyzing what type of arguments I get to this function from my app, no combination was causing the error to happen, but customers were facing it sometimes. Fortunately, the report came from Sentry, meaning I had OS and browser versions available.

After spawning Android 8 and Chrome Web View 60 on the simulator I tried to re-run this minimal reproduction step of calling element.animate directly, providing some example sets of values from my app.

And then, I caused exactly that error, by providing offset: undefined explicitly as a value.

{
        "opacity": [ 0, 1 ],
        "offset": undefined
}

The same values does not cause an error on currently fresh browsers versions

Looking quickly at the WAAPI docs, I have found:

  • On MDN:
The offset of the keyframe specified as a number between 0.0 and 1.0 inclusive or null.

https://developer.mozilla.org/en-US/docs/Web/API/Web_Animations_API/Keyframe_Formats

  • On W3C WAAPI Spec:
The offset of a keyframe is a value in the range [0, 1] or the special value null.

https://www.w3.org/TR/web-animations-1/#keyframes-section

This means according to spec, the value should never be explicitly set to undefined, which is currently happening if you don't provide value for argument times of animateStyle, which is being directly passed as value for offset key in keyframes definition: https://github.com/framer/motion/blob/f06854066a1de33561578ce2c4fd785e78fdf3be/packages/framer-motion/src/animation/waapi/index.ts#L18

It looks like all modern browsers filter out such value treating it the same way as it would never be provided, but older browsers might still interpret the spec strictly and don't provide any additional handling throwing error to throw.

Because of some issues with lib.dom.ts definitions, passing null instead of default undefined was a little problematic, I am proposing to provide offset conditionally only if times is truthy meaning from number[] | undefined union we are left with just number[].

Here is the gif showcasing the error happening in Android simulator 👇

CleanShot 2023-03-02 at 16 27 19

@mattgperry
Copy link
Collaborator

Excellent PR, thanks for the fix!

@mattgperry mattgperry merged commit 1d1afca into motiondivision:main Mar 5, 2023
@walaszczykm walaszczykm deleted the fix/waapi-animate-style-non-numeric-offset-provided branch March 5, 2023 10:28
@walaszczykm
Copy link
Contributor Author

@mattgperry Thanks for releasing this already in a new patch version.

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.

2 participants