Answer the question
In order to leave comments, you need to log in
How to implement image substitution with native loading="lazy" support?
Hello everyone and Happy New Year)) I decided to make a component for lazy loading of images, for this I use react-intersection-observer. With its help, I track a picture that has not yet loaded and replace it with a loader. I wanted to do the same with native loading="lazy", but the trouble is that I don't understand what event the browser generates and when and how to track it. I started digging towards react-mutation-observer, but it did not work out. Perhaps everything is much simpler?)) Any ideas? Thank you in advance!
export function LazyImage(props: LazyImageProps) {
const {
src,
height,
width,
alt,
styles,
rootMargin = '0px',
threshold = 0,
loadImmediately
} = props;
const supportsNativeLazyLoading = 'loading' in HTMLImageElement.prototype;
const { ref, inView } = useInView({
rootMargin,
threshold,
triggerOnce: true
});
const [srcPath, setSrcPath] = useState(null);
const preloadImage = (url: string) => {
return new Promise((resolve, reject) => {
const image = new Image();
image.onload = resolve;
image.onerror = reject;
image.src = url;
});
};
useEffect(() => {
const checkPreloader = async () => {
try {
await preloadImage(src);
// eslint-disable-next-line no-empty
} catch (error) {
} finally {
setSrcPath(src);
}
};
if (supportsNativeLazyLoading) {
setSrcPath(src);
return;
}
if (loadImmediately || inView) checkPreloader();
}, [supportsNativeLazyLoading, src, loadImmediately, inView]);
return srcPath ? (
<S.Image
loading={!loadImmediately ? 'lazy' : 'eager'}
src={srcPath}
alt={alt}
height={height}
width={width}
css={styles}
/>
) : (
<S.Preloader
ref={!supportsNativeLazyLoading ? ref : null}
height={height}
width={width}
/>
);
}
Answer the question
In order to leave comments, you need to log in
Didn't find what you were looking for?
Ask your questionAsk a Question
731 491 924 answers to any question