Hook
useHaptics
useHaptics wraps the web's narrow Vibration API in safe named presets. It reports support honestly, never throws, and remains a no-op on iOS and browsers without navigator.vibrate.
Preview
Vibration API
This browser has no vibration capability, so every preset is a safe no-op.
Installation
pnpm dlx shadcn@latest add https://pwaui.com/r/use-haptics.jsonUsage
"use client"
import { useHaptics } from "@/hooks/use-haptics"
export function SaveButton() { const haptics = useHaptics()
function save() { haptics.tap() // Save from this same user gesture. }
return <button onClick={save}>Save</button>}Returns
supported- Whether navigator.vibrate is available. A true value means the API exists, not that the user necessarily felt feedback.
vibrate(pattern)- Requests a custom duration or vibration/pause sequence and returns whether the browser accepted it.
tap()- A single 10ms acknowledgement.
success()- A 10–40–20ms success sequence.
warning()- A 30–40–30ms warning sequence.
error()- A 40–60–40ms error sequence.
Behavior notes
- Call a preset from a click, press, or other user activation. Browsers may reject vibration requested from background or automatic work.
- Use feedback sparingly: tap can acknowledge a deliberate TabBar selection; warning or error can reinforce a consequential ActionSheet choice. Do not wire every control by default.
- The methods return false when unsupported, blocked, or rejected and never substitute audio or another workaround.
- No preset is wired into existing components; consumers decide which actions deserve tactile feedback.
Platform support
| Platform | Available | Notes |
|---|---|---|
| Android Chrome | Yes | Usually available after a user gesture; device and browser settings can still suppress the motor. |
| iOS / iPadOS Safari | No | The Vibration API is not exposed, including in Home Screen apps. |
| Desktop browsers | Mostly no | Support is uncommon and hardware-dependent; treat it as an optional enhancement. |