useClick
useClick toggles or opens a floating surface in response to pointer clicks, touchscreen taps, and keyboard activation on the anchor element.
It attaches listeners directly to the anchor element (or context element for virtual anchors) and updates node.open.value. Pair it with useOutsideClick and useEscapeKey when the surface should close on outside clicks or Escape key presses.
Type
function useClick(node: FloatingNode, options?: UseClickOptions): void;
type UseClickContext = FloatingNode;
interface UseClickOptions {
enabled?: MaybeRefOrGetter<boolean>;
event?: MaybeRefOrGetter<"click" | "mousedown">;
toggle?: MaybeRefOrGetter<boolean>;
ignoreMouse?: MaybeRefOrGetter<boolean>;
ignoreKeyboard?: MaybeRefOrGetter<boolean>;
ignoreTouch?: MaybeRefOrGetter<boolean>;
}
Options
| Name | Type | Default | Notes |
|---|---|---|---|
enabled | MaybeRefOrGetter<boolean> | true | Reactive toggle. Setting to false disables interaction and removes all DOM event listeners from the anchor element. |
event | MaybeRefOrGetter<"click" | "mousedown"> | "click" | Which pointer DOM event triggers opening or toggling. "mousedown" fires immediately on press for mouse and pen devices, while touch input still safely uses the trailing click. |
toggle | MaybeRefOrGetter<boolean> | true | Whether subsequent clicks toggle the open state. When false, clicking opens the surface if closed, but never closes it if already open. |
ignoreMouse | MaybeRefOrGetter<boolean> | false | When true, ignores mouse and mouse-like pointer interactions. Touch and pen devices continue to trigger normally. |
ignoreKeyboard | MaybeRefOrGetter<boolean> | false | When true, disables Enter and Space keyboard activation and ignores synthetic clicks generated by keyboard events. |
ignoreTouch | MaybeRefOrGetter<boolean> | false | When true, ignores touch tap gestures. Mouse and pen devices continue to trigger normally. |
Returns
useClick returns void. It manages event listeners directly on node.refs.anchorEl (or the underlying contextElement for virtual anchors) and automatically synchronizes when reactive options or elements change.
Details
Pointer and Touch Handling
- Primary Button Only: Only primary clicks (
e.button === 0) trigger activation. Auxiliary clicks (middle mouse button) and secondary clicks (context menu right-click) are ignored. - Modality Tracking:
useClicktracks the input device modality ("mouse","touch","pen") viapointerdown. - Cancellation Safety: If a touch gesture is cancelled before release (e.g. when the user starts scrolling or dragging away, firing
pointercancel),useClickresets its internal interaction state so subsequent gestures are not blocked.
click vs mousedown Activation
event: "click"(default): Opening or toggling occurs on the standard DOMclickevent.event: "mousedown": Triggers immediately on press for mouse and pen devices, skipping the latency of waiting for mouse release. This is ideal for fast-response interfaces such as menus, toolbars, and contextual popovers.- Touch Safety with
mousedown: Whenevent: "mousedown"is used, touch devices do not trigger prematurely on touch-emulatedmousedownevents;useClickwaits for the trailingclickevent to ensure natural touch scrolling. - Deduplication: When
event: "mousedown"handles the press event,useClickautomatically swallows the trailingclickevent from the same gesture to prevent double-toggling.
Keyboard Activation Semantics
When ignoreKeyboard is false (the default):
- Native Buttons: Elements that natively dispatch synthetic
clickevents upon pressing Space or Enter (<button>,<input type="button">,<input type="submit">,<input type="reset">,<input type="image">,<summary>) are detected automatically.useClickavoids duplicating actions onkeydownand allows the native click emission to handle toggling. - Native Links: Links with an
hrefattribute (<a href="...">) natively activate on Enter.useClickpermits standard link navigation on Enter without double-toggling, while still supporting Space key activation. - Custom / ARIA Buttons: Custom trigger elements (such as
<div role="button" tabindex="0">or<a>withouthref) are fully supported. Pressing Enter triggers immediately onkeydown, while pressing Space triggers onkeyup(faithfully matching native browser button semantics). - Typeable Elements: If the anchor is a form control that accepts text entry (
<input type="text">,<textarea>,<select>), Space and Enter are passed through without toggling the floating node. - Synthetic Keyboard Clicks: When
ignoreKeyboard: true, synthetic click events dispatched by keyboard activation (wheree.detail === 0and no pointer gesture occurred) are ignored.
Virtual Anchors
useClick supports VirtualElement anchors. If the virtual anchor provides a contextElement property, useClick automatically resolves and binds DOM event listeners to that element.
Example
<script setup lang="ts">
import { ref } from "vue";
import { useClick, useEscapeKey, useFloatingNode, useOutsideClick, usePosition } from "v-float";
const anchorEl = ref<HTMLElement | null>(null);
const floatingEl = ref<HTMLElement | null>(null);
const node = useFloatingNode({ anchorEl, floatingEl });
usePosition(node, {
placement: "bottom-start",
middlewares: {
offset: 8,
flip: true,
shift: { padding: 8 },
},
});
useClick(node);
useOutsideClick(node);
useEscapeKey(node);
</script>
<template>
<button ref="anchorEl" type="button">Toggle Menu</button>
<div v-if="node.open.value" ref="floatingEl" class="dropdown">
<button type="button" @click="node.open.value = false">Profile</button>
<button type="button" @click="node.open.value = false">Settings</button>
<button type="button" @click="node.open.value = false">Logout</button>
</div>
</template>
See Also
useHover- Open on pointer hover with delay and safe polygon trackinguseOutsideClick- Close on outside pointer interactionsuseEscapeKey- Close on Escape key pressuseFocus- Open on keyboard focus and close on bluruseFloatingNode- Shared node coordinating element refs and open state- Build Popovers and Dropdowns - Click and dismissal workflow