useState()
hook to create a variable that holds the hovering state.useCallback()
hook to memoize two handler functions that update the state.useCallback()
hook to create a callback ref and create or update the listeners for the 'mouseover'
and 'mouseout'
events.useRef()
hook to keep track of the last node passed to callbackRef
to be able to remove its listeners.const useHover = () => {
const [isHovering, setIsHovering] = React.useState(false);
const handleMouseOver = React.useCallback(() => setIsHovering(true), []);
const handleMouseOut = React.useCallback(() => setIsHovering(false), []);
const nodeRef = React.useRef();
const callbackRef = React.useCallback(
node => {
if (nodeRef.current) {
nodeRef.current.removeEventListener('mouseover', handleMouseOver);
nodeRef.current.removeEventListener('mouseout', handleMouseOut);
}
nodeRef.current = node;
if (nodeRef.current) {
nodeRef.current.addEventListener('mouseover', handleMouseOver);
nodeRef.current.addEventListener('mouseout', handleMouseOut);
}
},
[handleMouseOver, handleMouseOut]
);
return [callbackRef, isHovering];
};
const MyApp = () => {
const [hoverRef, isHovering] = useHover();
return <div ref={hoverRef}>{isHovering ? 'Hovering' : 'Not hovering'}</div>;
};
ReactDOM.render(<MyApp />, document.getElementById('root'));
Subscribe to get resources directly to your inbox. You won't receive any spam! ✌️