从网络延迟入手:让数据更早到达
网络请求是页面首屏与交互中最常见的延迟来源。一次完整请求往往要经历 DNS 解析、TCP 连接、TLS 握手、HTTP 请求发送与服务端响应等多个阶段,每个阶段都可能成为卡顿的瓶颈。要降低这部分的延迟,首先应开启 HTTP/2 或 HTTP/3,利用多路复用与连接迁移减少握手开销;同时部署 CDN,将静态资源分发到离用户更近的节点,大幅缩短物理距离带来的往返时间。其次是减少请求数量,合并小体积资源,避免无谓的串行等待。对于关键请求,可以在页面加载早期通过 `` 和 `` 提前完成域名解析与连接建立。服务端也需要精简响应体,只返回当前页面必要的数据,并开启压缩算法,从根源上压缩传输体积。通过这些手段,用户按下按钮后收到的数据反馈可以更早出现,感知上的卡顿自然被消除。
渲染路径瘦身:降低主线程压力
浏览器从 HTML 到屏幕像素需要经历解析、样式计算、布局、绘制和合成等步骤,其中任何一步耗时过长都会导致帧率下降。为了减少卡顿,首要任务是缩减渲染路径长度:简化 DOM 层级,避免过深或过宽的节点树;减少全局 CSS 规则,让样式计算更快完成。JavaScript 的频繁读写布局属性,比如先修改样式再立即读取 `offsetHeight`,会造成“强制同步布局”,触发不必要的重排,必须改为分离读写或使用 `requestAnimationFrame` 统一调度。动画效果尽量使用 `transform` 和 `opacity`,因为它们可以交由合成器处理,不占用主线程。另外,将长任务拆分成多个可中断的短小任务,或使用 `Web Worker` 处理耗时计算,能够保证主线程每帧都有空闲时间处理输入和绘制。当每帧预算都控制在 16.6ms 内,页面滚动和点击响应就会立刻变得流畅自然,卡顿感明显减少。

图片和字体加载:用“懒”策略提升流畅度
图片和字体往往是页面体量中的大头。默认情况下,浏览器会立即请求所有图片,即使它们还在屏幕之外,这既浪费带宽又拖慢首屏解析。给 `` 添加 `loading="lazy"` 和 `decoding="async"`,可以让屏外图片延迟到接近视口时才加载,同时解码过程不再阻塞渲染。对于不同屏幕尺寸,应使用 `srcset` 和 `sizes` 提供适当压缩比的候选图,避免手机加载桌面级高清大图。字体资源的加载同样容易引发“不可见文字闪烁”或布局偏移,使用 `font-display: swap` 可以先显示回退字体,然后无缝替换为自定义字体;更进一步可以将字体按常用字符子集化,只加载页面真正需要的字形。对于首屏内的关键图片,则可以适当使用预加载,但非关键图片必须坚持懒加载,让网络通道优先传输文本、脚本和样式等核心资源,从而缩短可交互时间,减少因图片解析导致的滚动和动画卡顿。
缓存与预加载:为下一次交互提前准备
延迟优化不仅关注首次渲染,更要为后续操作做好准备。合理设置 HTTP 缓存头(`Cache-Control`、`ETag`)能让重复访问直接命中本地缓存,跳过网络请求;而使用 Service Worker 可以在离线或弱网状态下快速返回缓存的页面壳与资源,大幅降低二次加载时间。同时要区分“预加载”和“预取”:关键资源使用 `preload` 提示浏览器提前下载,非关键但即将需要的资源使用 `prefetch` 在空闲时获取,避免抢占首屏带宽。更进一步,可以基于用户行为预测,比如在鼠标悬停到下一页面链接时提前拉取该页数据,或在输入框聚焦前预加载搜索接口。所有缓存与预取策略都必须搭配版本管理与缓存失效机制,防止用户拿到陈旧内容。当大多数资源都不需要真正从网络重新传输时,页面交互的确定性大幅提升,点击后无需长时间等待,卡顿感也随之消失,整体体验获得质的改善。


