The component listens to the context. Each context update triggers a rerender. Can I stop listening to the context if I already got the right value?
I want to stop further component update when this context changes
For example
const {contextValue, setContextValue}= useContext(MyContext)
if (contextValue == 'stop listen') {stop listening}
Is it possible?
2
Answers
Consumers of
useContext()
will always re-render whenever the context value changes."Even if an ancestor uses React.memo or shouldComponentUpdate, a rerender will still happen starting at the component itself using useContext."
There’s a good chance that if you don’t always want context changes to trigger a component re-render, then some other means of maintaining that state is better for your use case.
See the useContext React docs for more information.
There is no way to wrangle a
useContext
invocation into a custom hook that wouldn’t cause a rerender when the context value changes. However we can achieve similar functionality in a higher order component.Provided you pass a memoized component to
withContextValue
you’ll receive a component that will rerender on every context value change but the memoized component will not rerender unlike in the case whereuseContext
was invoked inside the memoized component.The above pattern can be unwieldy to work with and doesn’t eliminate rerenders completely. For a better developer experience you may want to try a subscription pattern where each consumer of a context gets to define what changes cause a rerender. Famously
react-redux
uses this pattern.Define your context value as a mutable object.
You can then define any equality function to limit rerenders on a consumer-by-consumer basis just like with Redux’s
useSelector
.Mind you this pattern will stop unnecessary rerenders but will not stop the component from reading an up-to-date context value if something else causes a rerender. If you need to stop receiving new values you’ll want to wrap the hook in an extra layer of memoization.