useDeferredValue creates a deferred version of a value that React can update later (at lower priority). While the deferred value is being computed, the UI continues showing the old value — keeping the interface responsive.
How it works step-by-step:
query updates immediately (urgent)useDeferredValue(query) creates deferredQuery — it updates later (non-urgent)Results component uses deferredQuery → doesn't block typingComplete code example:
1import { useState, useDeferredValue, useMemo } from "react";23function SearchResults({ query }: { query: string }) {4 const deferredQuery = useDeferredValue(query);5 const isStale = query !== deferredQuery;67 // Expensive computation with deferred value8 const results = useMemo(() => {9 if (!deferredQuery) return [];10 // Simulate expensive filtering11 return allItems.filter(item =>12 item.name.toLowerCase().includes(deferredQuery.toLowerCase())13 );14 }, [deferredQuery]);1516 return (17 <div style={{ opacity: isStale ? 0.5 : 1, transition: "opacity 0.2s" }}>18 <p>{results.length} results</p>19 <ul>20 {results.map(item => (21 <li key={item.id}>{item.name}</li>22 ))}23 </ul>24 </div>25 );26}2728function App() {29 const [query, setQuery] = useState("");3031 return (32 <div>33 <input34 value={query}35 onChange={e => setQuery(e.target.value)}36 placeholder="Search..."37 />38 <SearchResults query={query} />39 </div>40 );41}
When to use:
useDeferredValue vs useTransition: | Feature | useDeferredValue | useTransition | |---------|------------------|---------------| | Wraps | A value (like a prop) | A state update function | | Use case | Deferred re-rendering | Deferred state transitions | | Can be interrupted | Yes | Yes | | Shows stale data | Yes (old value while new computes) | Yes (old UI while new renders) |
Key points: