FID指标高是不是因为点击事件没优化?
最近用Lighthouse测性能,发现FID(首次输入延迟)经常超过100ms,页面点按钮老是卡一下。我明明没写啥复杂逻辑啊,是不是哪里没处理好?
比如这个简单的按钮,点击后只是切换个class,但FID还是很高:
<button id="toggleBtn">切换状态</button>
<div id="content">内容区域</div>
<script>
document.getElementById('toggleBtn').addEventListener('click', () => {
document.getElementById('content').classList.toggle('active');
});
</script>
我试过把事件监听放到DOMContentLoaded里,也加了 passive: true,但FID还是下不来,到底问题出在哪?
FID这个指标本质上是看浏览器主线程有没有被卡住。用户点击了但浏览器没及时响应,根本原因是那一刻主线程正忙着干别的事。你那个按钮逻辑再简单也没用,如果页面加载时主线程被其他东西占用了,照样FID爆炸。
你试的那两个方法基本没对症:
- DOMContentLoaded 只是等DOM解析完,跟主线程阻塞是两码事
- passive: true 是给scroll事件用的,对click的FID毫无影响
常见坑在这几个地方:
页面加载时有没有执行很重的同步JS?比如在head里放了阻塞渲染的脚本,或者有那种几十KB的bundle一次性加载。可以用Performance面板看看有没有Long Tasks,或者直接看Lighthouse的诊断建议,它会告诉你哪个脚本耗时最长。
另外检查下有没有第三方脚本在搞事——统计脚本、广告、聊天组件这些经常在背后偷偷执行,而且你控制不了。
如果确实有长任务,常规做法是拆分。把同步执行的大块代码用setTimeout或requestIdleCallback切成小份,让浏览器有时间喘气。或者把非关键的JS延迟加载,别在首屏加载时全塞进来。
你要是想定位具体是哪个任务导致的FID,用Chrome DevTools的Performance面板录一下,看Main线程那边有没有红色的长条,一目了然。