0% completed
In this lesson, you'll learn everything about the useTransition hook and how you can implement it in your React apps. By the end of this lesson, you'll have learned about the important role concurrency with this hook plays in building apps with a good user experience.
useTransition is a React Hook designed to help manage concurrency by allowing you to mark certain state updates as non-urgent. This is useful in cases where an application needs to handle both urgent and non-urgent updates simultaneously without affecting UI responsiveness.
In traditional React rendering, all state updates are processed synchronously, meaning that heavy operations (such as filtering large lists) can cause UI lag. With useTransition, React can prioritize urgent updates (like user interactions) while deferring non-urgent updates, ensuring a smoother user experience.
The useTransition hook works by:
The useTransition Hook returns two values:
startTransition(callback) – A function that wraps non-urgent state updates.isPending – A boolean that indicates whether a transition is still in progress.Here’s the basic syntax:
const [isPending, startTransition] = useTransition();
To use it, wrap non-urgent updates inside startTransition:
startTransition(() => { // Non-urgent state update });
Lets look at an example that uses the useTransition hook to prevent UI lag in search filtering.
Consider an application where a user types into a search box to filter a large list of items. Without useTransition, filtering would be synchronous, causing UI lag when processing large datasets.
import { useState } from "react"; const ItemList = ({ items }) => { const [query, setQuery] = useState(""); const [filteredItems, setFilteredItems] = useState(items); const handleSearch = (e) => { setQuery(e.target.value); // Immediately updating state setFilteredItems(items.filter(item => item.includes(e.target.value))); }; return ( <div> <input type="text" value={query} onChange={handleSearch} placeholder="Search..." /> <ul> {filteredItems.map(item => <li key={item}>{item}</li>)} </ul> </div> ); };
In this code, there is a problem. And the problem is; as the user types, the filtering process happens immediately, causing noticeable UI lag, especially for large lists.
To solve this problem, we use the useTransition hook:
import { useState, useTransition } from "react"; const ItemList = ({ items }) => { const [query, setQuery] = useState(""); const [filteredItems, setFilteredItems] = useState(items); const [isPending, startTransition] = useTransition(); // Using useTransition const handleSearch = (e) => { setQuery(e.target.value); startTransition(() => { // Marking filtering as a non-urgent update setFilteredItems(items.filter(item => item.includes(e.target.value))); }); }; return ( <div> <input type="text" value={query} onChange={handleSearch} placeholder="Search..." /> {isPending && <p>Updating list...</p>} {/* Show loading indicator during transition */} <ul> {filteredItems.map(item => <li key={item}>{item}</li>)} </ul> </div> ); };
Here, we've made a significant improvement. Now, React prioritizes user input (query state update) while deferring the filtering process, preventing UI lag and ensuring a smooth typing experience.
1. Improves User Experience by Prioritizing Urgent Updates: React ensures that interactions like typing remain smooth, preventing UI lag caused by expensive computations or large data operations.
2. Reduces UI Freezing in Expensive Computations: Since non-urgent updates are deferred, React prevents slow state updates from blocking UI interactions.
3. Provides a Pending State to Improve Perceived Performance: With the isPending flag, you can show feedback (e.g., a loading indicator) while the transition is still in progress, enhancing perceived performance.
There are some things you need to factor in before or while using this hook, such as:
1. Not Suitable for Every Update
useTransition is designed for state updates that do not require an immediate UI response.startTransition.2. Can Cause Inconsistent UI if Used Incorrectly
3. Requires React 18 or Later
useTransition is available starting from React 18. Applications using older versions must upgrade to utilize concurrency features.1. Use for Non-Urgent Updates Only
2. Always Handle the Pending State (isPending)
"Updating list..." when filtering a large dataset.3. Avoid Wrapping Every Update in startTransition
useTransition where necessary to prevent unnecessary delays......
.....
.....