Skip to content

useLongPress ​

Long-press detection for any element. Powers <orio-long-press>; use it directly when you need the behavior without the wrapper's scale feedback.

Live Demo ​

Hold here

Usage ​

ts
const target = ref<HTMLElement | null>(null);

const { isPressing, isHolding } = useLongPress(target, {
  delay: 600,
  onStart: () => log.value.unshift("start"),
  onCancel: () => log.value.unshift("cancel"),
  onTrigger: (event, source) => log.value.unshift(`trigger (${source})`),
});

Options ​

OptionTypeDefaultDescription
delayMaybeRefOrGetter<number>500Hold time in ms
moveToleranceMaybeRefOrGetter<number>10Movement in px that cancels
forceTouchMaybeRefOrGetter<boolean>trueSafari force click triggers immediately
disabledMaybeRefOrGetter<boolean>falseIgnore presses; cancels an active one
onStart(event: PointerEvent) => void—Primary pointer went down
onCancel() => void—Press ended without triggering
onTrigger(event, source: "hold" | "force") => voidrequiredHold reached delay, or force click

Returns ​

KeyTypeDescription
isPressingReadonly<Ref<boolean>>true from pointerdown until trigger or cancel
isHoldingReadonly<Ref<boolean>>true from pointerdown until the finger lifts or the press is cancelled — outlives the trigger

Notes ​

  • The click after a trigger is swallowed (capture phase on window, so it also covers a release over an overlay the trigger opened). Keyboard clicks pass through; Ctrl+click never starts a press.
  • Nested targets: only the innermost handles a press.
  • While isHolding, selectstart and contextmenu on the target are prevented; on trigger any selection inside the target is cleared. Bind user-select: none / -webkit-touch-callout: none to isHolding for iOS.
  • Not to be confused with usePressAndHold, which repeats a callback while held.