All hooks / Events and input
useClickOutside
Calls handler when the user presses outside an element: mouse, touch, or pen. Returns a callback ref to put on the element.
Listens to pointerdown on the document, so it fires before focus moves and works for touch. Uses composedPath(), so presses inside shadow DOM count as inside.
Import
import { useClickOutside } from '@vincent.ri/react-tils'
// or only this hook
import { useClickOutside } from '@vincent.ri/react-tils/useClickOutside'Usage
const [open, setOpen] = useState(false)
const ref = useClickOutside<HTMLDivElement>(() => setOpen(false), open)
// The ref wraps the button too, so pressing it toggles instead of closing and reopening.
return (
<div ref={ref}>
<button onClick={() => setOpen(!open)}>Menu</button>
{open && <Menu />}
</div>
)Live demo
Open the menu, then click anywhere else.
When to use it
Closing a dropdown, popover, or menu when the user presses elsewhere.
When not to
You can use the native <dialog> or the popover attribute, which close on outside click and Escape with no JS. Content rendered in a portal is outside the element: put the ref on a wrapper that contains both, or ignore those targets in the handler. Put the ref on a wrapper around the toggle button too: if the button is outside, pressing it closes the menu and its click then reopens it.
API
function useClickOutside<T extends Element = HTMLElement>(handler: (event: PointerEvent) => void, enabled?: boolean): (element: T | null) => void| Parameter | Description |
|---|---|
handler | Called with the PointerEvent. Can change every render. |
enabled | Listen only while true, e.g. while the menu is open. Default true. |
Returns A callback ref. Pass it to the element's ref prop.
Browser support
| Uses | Chrome | Edge | Firefox | Safari | Chrome Android | Safari iOS |
|---|---|---|---|---|---|---|
| Pointer eventsWidely available | 55+ | 12+ | 59+ | 13+ | 55+ | 13+ |
First version with support, from MDN's compatibility data (web-features 3.42.0, @mdn/browser-compat-data 8.1.5).
Coming from another library?
Other libraries call this useClickAway, useOnClickOutside.