I am using a react App, with a context holdling a wordlist. I have a child component of the context , which uses a context function which edits the current word (setting the wordlist). When I do that with useContext, it renders the child component (All of them!).
export default function EditWordlistElem({content,elemId}){
const {editWordlist} = useWordlist(); // using context
const {newValue,setNewValue} = useState(content); // holds edited value
return (<div>
{/* Some code for getting edited value*/}
<button onClick={()=>editWordlist(newValue,elemId))>
Edit
</button>
</div>);
}
My point is, that i don't actually need the updated edit funciton every the whole time the child component is up, but only on editing (for exampmle on a button press).
However trying accessing the context conditionally, or inside a callback is illegal with react hooks.
From https://reactjs.org/docs/hooks-rules.html
Only Call Hooks at the Top Level
Don’t call Hooks inside loops, conditions, or nested functions.
How can i get the context value Only on a button click , so it won't render this component on every context change?
If your hook is subscribing with useContext to the WordList values, it will re-render every time the word list is updated. From there, any components that subscribe to that hook will also re-render, causing the whole child tree to re-render.
One way to optimize that functionality is to use two Context providers. One to store the actual values in state, and one to store the dispatch/setter functions including editWordlist. Since the editWordlist reference should not change, you can call this function without subscribing to the values.
See: https://kentcdodds.com/blog/how-to-optimize-your-context-value for a more detailed explanation of this pattern.
Lastly, if you are using React 19, they have introduced the use function which can load a context value without following the rules of hooks.