Layout thrashing: reflows repetidos em um frame e como pará-los
O que acontece
O navegador tenta recalcular o layout uma vez por frame. Mas se seu código escreve um estilo, depois lê uma propriedade de geometria (offsetWidth, getBoundingClientRect) e escreve de novo — em um laço — cada leitura força um layout novo e síncrono da página. Um laço sobre 100 elementos pode disparar 100 reflows completos em um frame.
O custo é proporcional ao tamanho do DOM, então o mesmo código que vai bem em uma página pequena destrói o INP em uma página com milhares de nós.
Como reconhecer
- O presentation delay (trabalho de renderização após o manipulador) domina o detalhamento do INP.
- O DevTools Performance mostra muitos blocos roxos de Layout dentro de um frame, muitas vezes marcados como “Forced reflow”.
- O código alterna leituras (offsetTop, clientHeight, getComputedStyle) e escritas (style, classList) dentro de um laço.
Como corrigir
- Agrupe primeiro todas as leituras e depois todas as escritas — nunca as intercale em um laço.
- Mova as escritas para requestAnimationFrame para que ocorram logo antes da próxima pintura.
- Prefira soluções CSS (classes, transforms, flex/grid) a medir e posicionar elementos em JS.
Problema
items.forEach((el) => {
el.style.width = base + "px" // write
const h = el.offsetHeight // read → forced reflow, every iteration
el.style.height = h * 2 + "px" // write
})
Correção
const heights = items.map((el) => el.offsetHeight) // all reads
requestAnimationFrame(() => {
items.forEach((el, i) => { // all writes
el.style.width = base + "px"
el.style.height = heights[i] * 2 + "px"
})
})
Escaneie seu site gratuitamente →