navigator.vibrate()必须在用户点击事件同步执行才有效,且单值参数最可靠;需HTTPS、系统触感开启、真机测试,并提供视觉反馈fallback。

按钮点击事件里直接调用 navigator.vibrate() 才有效
不是加了代码就震,而是必须在用户手指点下去那一瞬间同步执行。放在 setTimeout、Promise.then、页面加载完成回调里,全都会静默失败——不报错,也不震。
- ✅ 正确写法:
button.addEventListener('click', () => navigator.vibrate(150)) - ⚠️ 错误写法:
document.addEventListener('DOMContentLoaded', () => navigator.vibrate(200))或setTimeout(() => navigator.vibrate(100), 0) - iOS Safari 首次合法触发后,后续调用才可能被允许;Android 多数机型只认“第一次”手势激活,切后台再切回来可能需重新点一次
navigator.vibrate() 参数怎么传才跨平台可靠
iOS 和 Android 对参数支持差异很大,盲目传数组容易在 iPhone 上完全失效。
- 单值最稳:
navigator.vibrate(150)—— iOS/Android 都支持,推荐用于确认、错误等短反馈 - 数组慎用:
navigator.vibrate([200, 100, 300])—— Android 可能生效,iOS 直接返回false且无提示 - 清空震动队列:
navigator.vibrate(0)或navigator.vibrate([]),但部分旧版 Android 不支持空数组 - 别传超长值:
navigator.vibrate(3000)在 iPhone 上会被硬截成 500ms,在小米 MIUI 上可能只震 1 秒,毫无预警
为什么点了没反应?优先排查这四件事
90% 的“不震动”问题和代码无关,而是环境或配置卡住了。
- 确认 HTTPS:HTTP 页面中
navigator.vibrate被浏览器直接禁用 - 检查系统设置:iOS 需开启「设置 > 辅助功能 > 触感反馈」;Android 某些厂商(如华为 EMUI)会全局屏蔽网页振动
- 真机测试:模拟器基本不模拟硬件震动,Chrome DevTools 的 Sensors 面板仅验证逻辑是否触发,不能代替实测
- 别信
navigator.permissions.query({name: 'vibrate'}):这个权限没标准定义,多数浏览器不实现,查了也白查
没震动时该 fallback 做什么
不能只留 console.warn,用户需要可感知的替代反馈。
立即学习“前端免费学习笔记(深入)”;
- 视觉反馈优先:给按钮加
scale(0.95)动画 + class 切换(比如加is-pressed),比弹 alert 更自然 - 适配动效偏好:
matchMedia('(prefers-reduced-motion: reduce)')返回 true 时,连视觉反馈也跳过 - 绝对不要播“震动音效”:扬声器外放既失真,又可能在静音模式下突兀出声,干扰用户
- iOS 用户可直接跳过震动逻辑——Safari 没有标准替代接口,Haptic Feedback 仅限原生应用或特定 PWA 场景,网页不可用



















