React Component to lazy load images.
npm i loadable-image
Or via yarn
yarn add loadable-image
<AsyncImage />
accepts all props of <img />
tag.
import { AsyncImage } from 'loadable-image'
...
<AsyncImage
src='https://picsum.photos/1900'
style={{ width: 150, height: 150 }}
/>
You can pass your own loader
and error
components as props to AsyncImage
component.
import { AsyncImage } from 'loadable-image'
...
<AsyncImage
src='https://picsum.photos/1900'
style={{ width: 150, height: 150 }}
loader={<div style={{ background: '#888' }}/>}
error={<div style={{ background: '#eee' }}/>}
/>
Since under the hood <AsyncImage />
is just a picture
element. You can pass an array of different Sources
as a prop. And browser will pick the first one that it supports.
import { AsyncImage } from 'loadable-image'
...
<AsyncImage
src="./image.jpg"
sources={[
{ type:"image/avif", srcSet:"./image.avif" },
{ type:"image/webp", srcSet:"./image.webp" }
]}
style={{ width: 200, height: 200 }}
/>
To make image responsive you can use aspectRatio
property in style
prop. This way you can specify only width
or height
as 100%
and the other one as auto
.
Note that if you support older browsers you might need to use aspectRatio
padding-hack.
import { AsyncImage } from 'loadable-image'
...
<AsyncImage
src='https://picsum.photos/1900'
style={{ width: "100%", height: "auto", aspectRatio: 16 / 9 }}
/>
Under the hood AsyncImage
uses transitions-kit library
it's a collection Transition components built on top of react-transition-group its a small library maintained by React team for animating between different views.
You can pass your own Transition
as a prop to AsyncImage
component.
Here’s how you can implement a Blur
transition that replaces a low-resolution image
with a high-resolution
one
import { Blur } from 'transitions-kit'
import { AsyncImage } from 'loadable-image'
...
<AsyncImage
src='./original-image.jpg'
style={{ width: 150, height: 150 }}
Transition={props => <Blur radius={10} {...props}/>}
loader={<img src='./extra-small-1x1.jpg' />}
/>
By default AsyncImage
uses Fade
transition.
import { Fade } from 'transitions-kit'
import { AsyncImage } from 'loadable-image'
...
<AsyncImage
src='https://picsum.photos/1900'
style={{ width: 150, height: 150 }}
loader={<div style={{ background: '#888' }}/>}
Transition={Fade}
/>
There are plenty different already predefined Transition components such as Grow
, Zoom
, Slide
, Blur
, Fade
etc. in transitions-kit.
Feel free to try any of them.
import { Grow } from 'transitions-kit'
import { AsyncImage } from 'loadable-image'
...
<AsyncImage
src='https://picsum.photos/1900'
style={{ width: 150, height: 150 }}
loader={<div style={{ background: '#888' }}/>}
Transition={Grow}
/>
<AsyncImage />
accepts all standard props for HtmlImageElement
and the following:
Property | Type | Description |
---|---|---|
className | String |
NOTE: CSS from style object has a higher priority |
style | CSSProperties |
CSSStyleDeclaration object |
rootMargin | string by default: '600px 0px' |
Margin around the root. Specifies when to trigger an image download. |
loader | ReactElement |
React element to display a loading state. |
error | ReactElement |
React element to display an error state. |
sources | Array<SourceProps> |
An array of options for <source /> element. |
timeout | Number or Object |
The duration for the transition, in milliseconds. You may specify a single timeout for all transitions, or individually with an object. |
Transition | ComponentType<TransitionProps> |
Custom Transition component. Check out transitions-kit's predefined components |
- Forward the ref: The transition components require the first child element to forward its ref to the DOM node. This is usually done with React.forwardRef.
- Single element: The transition components require only one child element (React.Fragment is not allowed).