useIntersectionObserver
A hook that detects when elements enter or exit the viewport using the Intersection Observer API.
useIntersectionObserver
The useIntersectionObserver
hook provides an easy way to detect when an element enters or exits the viewport using the browser’s Intersection Observer API. This is useful for implementing lazy loading, infinite scrolling, animations on scroll, and tracking element visibility.
Installation
Install the useIntersectionObserver hook using:
File Structure
Parameters
Prop | Type | Default |
---|---|---|
root | Element | null | null (browser viewport) |
rootMargin | string | 0px |
threshold | number | number[] | 0 |
triggerOnce | boolean | false |
skip | boolean | false |
Return Value
Prop | Type | Default |
---|---|---|
ref | RefObject<T> | - |
isIntersecting | boolean | - |
entry | IntersectionObserverEntry | null | - |
Examples
Lazy Loading Images
Load images only when they scroll into view to improve page load performance:
Animations on Scroll
Trigger animations when elements scroll into view:
Section 1
This content fades in when it enters the viewport, enhancing the user experience with subtle animations triggered by scrolling.
Section 2
This content fades in when it enters the viewport, enhancing the user experience with subtle animations triggered by scrolling.
Section 3
This content fades in when it enters the viewport, enhancing the user experience with subtle animations triggered by scrolling.
Section 4
This content fades in when it enters the viewport, enhancing the user experience with subtle animations triggered by scrolling.
Section 5
This content fades in when it enters the viewport, enhancing the user experience with subtle animations triggered by scrolling.
Tracking Visibility for Analytics
Monitor when elements are viewed for analytics purposes:
Use Cases
- Lazy Loading: Load images, videos, or components only when needed
- Infinite Scrolling: Load more content when the user reaches the bottom
- Animations on Scroll: Trigger animations when elements enter the viewport
- Visibility Tracking: Monitor which elements are visible for analytics
- Auto-playing Media: Start/stop videos or audio when in/out of view
- Smart Navigation: Highlight navigation items based on visible sections
- Delayed Loading: Defer non-critical content loading until needed
- Performance Optimization: Reduce initial page load time and resources
Intersection Observer Options
Threshold
The threshold
option controls at what percentage of the target’s visibility the observer’s callback should be executed:
0
(default): Callback is invoked as soon as even 1 pixel is visible1.0
: Callback is invoked when 100% of the target is visible- Array of values: Callback is invoked for each threshold crossed
Root Margin
The rootMargin
option adds margin around the root element, effectively increasing or decreasing the area considered for intersection:
Trigger Once
The triggerOnce
option stops observing the element after it’s been intersected once:
Accessibility
When implementing features with the Intersection Observer, consider these accessibility best practices:
- Ensure content is accessible even if JavaScript is disabled
- Provide proper fallbacks for browsers that don’t support Intersection Observer
- Don’t rely solely on scroll events for critical functionality
- For lazy-loaded images, always provide appropriate
alt
text - Consider users who may have disabled animations (prefers-reduced-motion)
- Avoid content that suddenly appears, which can be disorienting
Browser Support
The Intersection Observer API is supported in all modern browsers. For older browsers, consider using a polyfill or the hook’s built-in fallback behavior, which sets isIntersecting
to true
when the API isn’t available.
Best Practices
- Use the
triggerOnce
option for one-time actions like animations or lazy loading - Set appropriate
threshold
values based on your use case - Use
rootMargin
to start loading content before it’s actually visible - Keep observed elements simple to avoid performance issues
- Use the full entry data for advanced calculations like position or timing
- Combine with CSS transitions/animations for smooth visual effects
- Unobserve elements when they’re no longer needed