Avoiding flash of unwanted animation on first render in React
Thomas Ledoux
Posted on April 29, 2021
While developing my personal website, I noticed that my mobile menu appeared for a split second and then moved out of the screen.
My mobile menu is placed on the right side of the screen by using the following CSS:
.navigation {
transform: translateX(100%)
}
To make the menu come into the screen smoothly, I used the following CSS:
.navigation {
transition-property: transform;
transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
transition-duration: 150ms;
}
By adding this transition in my initial CSS, the menu will be transformed to the right side of the screen but with a duration of 150ms, so this will be clearly visible when the page loads.
To avoid this behaviour, I had to find a way to only apply the transition once the React app is already mounted.
For this use case, I found a custom useIsMounted
hook useful.
import { useRef, useEffect } from 'react';
const useIsMounted = () => {
const isMounted = useRef(false);
useEffect(() => {
isMounted.current = true;
return () => isMounted.current = false;
}, []);
return isMounted;
};
export default useIsMounted;
Then in my component, I can easily import this hook and use it:
const Navigation = () => {
const isMounted = useIsMounted();
return (<div className={`navigation ${isMounted ? 'mounted' : ''}`}></div>)
}
My CSS then becomes this:
.navigation.mounted {
transition-property: transform;
transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
transition-duration: 150ms;
}
And that's it! No more unwanted animations on page load.
This will also help to increase your Cumulative Layout Shift (https://web.dev/cls) if you were encountering the same thing as I was, because your layout will not shift anymore, so it's a win-win!
You can see the end result here: https://thomasledoux.be (I use Tailwind on my site, so the example code is not exactly the same).
Posted on April 29, 2021
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.