There are times when we want some React state that should always hold a boolean value, and should only allow toggling between true and false.
This is a thin wrapper around
React.useState to solve for this purpose. It carries greater semantic meaning, and prevents us from accidentally setting a non-boolean value in the future.
The nice thing about this hook is that the
toggleIsOn function can be passed straight to a click-handler; there's no need for an intermediary arrow that sets the value to the opposite of the value (and no opportunity for accidentally setting it to a non-boolean value!).
This hook uses
React.useCallback in order to preserve the reference to the setter function; without this wrapper, the
toggle function would be recreated on every render.
The cost of creating this function is minimal, but recreating it means that it would be a new reference. This would break memoization of children elements.
For example, say we have this code:
A button can be clicked to increment a counter bit of state. Whenever that button is clicked,
App will re-render.
SomeBigComponent is wrapped with
React.memo, it will only re-render when its props change. And it only has one prop, the
React.useCallback in our
useToggle hook, that
toggleIsOn function would change on every render! This means that
SomeBigComponent would re-render even when the user is incrementing the count by clicking the button.
In practice, this likely won't be a huge performance problem in most cases, but because
useToggle is generic and reusable, it doesn't hurt to bake this in.