Presentation Delay do INP: Tamanho do DOM, Trabalho de Layout e Otimização de Renderização

Aprenda como encontrar e melhorar problemas de INP causados pelo presentation delay

Arjen Karel Core Web Vitals Consultant
Arjen Karel - linkedin
Last update: 2026-03-04

Problemas de Interaction to Next Paint (INP) causados pelo presentation delay

Esta página faz parte da nossa série sobre Interaction to Next Paint (INP). O INP mede o tempo total desde a interação do usuário até a próxima atualização visual. O presentation delay é a terceira e última fase do INP, seguindo o input delay e o processing time. Se você é novo no INP, leia nosso guia sobre como identificar e corrigir problemas de INP primeiro.

Em resumo: O Interaction to Next Paint (INP) mede quanto tempo leva para um usuário ver uma mudança visual em uma página após interagir com ela. Este INP pode ser dividido em 3 componentes: "input delay", "processing time" e "presentation delay".

O presentation delay é o principal contribuinte para o INP total, representando em média cerca de 42% do tempo total do INP. Otimizar seu pipeline de renderização e simplificar sua estrutura HTML é a maior alavanca para melhorar o INP.

Presentation Delay: Já clicou em um botão e se perguntou por que demorou uma fração de segundo a mais para ver o resultado? Isso é o Interaction to Next Paint (INP) em ação. O presentation delay é a última etapa do processo de interação, entrando em ação após o seu clique ter sido processado, mas antes de você ver quaisquer mudanças visuais.

Entendendo o presentation delay

A apresentação é a fase final de uma interação. O presentation delay representa o tempo que o navegador leva para renderizar as atualizações visuais que seguem a interação. O presentation delay começa quando os manipuladores de eventos da interação terminam de ser executados e termina quando o próximo quadro (contendo as mudanças visuais) é pintado. O presentation delay pode ser afetado por vários fatores, incluindo a complexidade do layout, o tamanho do DOM e a quantidade de trabalho de renderização necessária.

O Interaction to Next Paint (INP) pode ser dividido em 3 subpartes: "Input Delay", "Processing Time" e "Presentation Delay".

Presentation delay e o INP

O presentation delay é a última fase do INP. Em média, o presentation delay compõe cerca de 42% do tempo total do INP, tornando-se o maior contribuinte individual para interações lentas.

No CoreDash, coletamos milhões de pontos de dados do Core Web Vitals a cada hora. Com base nesses dados, o presentation delay representa 42% do Interaction to Next Paint. Isso é mais do que o processing time (40%) e significativamente mais do que o input delay (18%). Apesar de ser o maior contribuinte, o presentation delay é frequentemente a fase mais difícil de otimizar porque envolve o pipeline de renderização do navegador, e não o código da sua aplicação.

Exemplo de presentation delay: Imagine que você está no seu telefone navegando em um site de e-commerce em busca de um novo par de sapatos. Você toca na imagem de um produto para ver mais detalhes. No entanto, o seu telefone é um pouco mais antigo e tem dificuldade em acompanhar. Você toca na imagem (Interação). O telefone leva algum tempo para processar a solicitação e atualizar a exibição (Processing Time). O site precisa renderizar a nova página com a imagem maior e os detalhes. Finalmente, leva um tempo considerável para que os novos detalhes do produto e a imagem apareçam na sua tela (Presentation Delay). Esse atraso no INP pode ser frustrante para os usuários e é por isso que é importante corrigi-lo.

O que causa um alto presentation delay?

O presentation delay engloba todo o trabalho que o navegador realiza depois que seus manipuladores de eventos terminam e antes que os pixels apareçam na tela. Isso inclui recálculo de estilo, computação de layout, pintura (painting) e composição (compositing). Vários fatores contribuem para um alto presentation delay:

Grande tamanho do DOM

Um DOM grande ou profundamente aninhado é uma das causas mais comuns de alto presentation delay. Toda vez que o navegador precisa atualizar o estado visual da página após uma interação, ele deve recalcular os estilos, computar o layout e repintar os elementos afetados. O custo de cada uma dessas etapas aumenta proporcionalmente com o número de nós do DOM que são afetados.

O Google recomenda manter seu DOM com menos de 1.400 elementos, com uma profundidade máxima de 32 níveis e não mais que 60 elementos filhos por nó pai (veja a auditoria de tamanho do DOM do Lighthouse). Quando o seu DOM excede esses limites, o navegador gasta muito mais tempo no recálculo de estilo e na computação de layout após cada interação.

Considere este cenário: um usuário clica em um botão que alterna uma classe CSS em um elemento contêiner. Se esse contêiner tiver 5.000 nós descendentes, o navegador deve recalcular os estilos potencialmente para todos eles, mesmo que apenas alguns elementos realmente mudem visualmente. Esse recálculo de estilo acontece de forma síncrona antes da próxima pintura, aumentando diretamente o presentation delay.

Para técnicas específicas de como reduzir seu DOM, leia nosso guia sobre como corrigir o tamanho excessivo do DOM.

Trabalho excessivo de layout

Layout (também chamado de "reflow") é o processo onde o navegador calcula a posição e as dimensões de cada elemento visível na página. Após uma interação que modifica o DOM ou altera as propriedades CSS que afetam a geometria (width, height, margin, padding, top, left), o navegador deve realizar o layout antes de poder pintar o quadro atualizado.

Dois padrões são particularmente prejudiciais para o presentation delay:

Layout síncrono forçado (Forced synchronous layout) ocorre quando o JavaScript lê uma propriedade de layout (como offsetHeight ou getBoundingClientRect()) após fazer uma mudança no DOM que invalida o layout. O navegador é forçado a realizar o layout de forma síncrona, dentro do seu manipulador de eventos, para retornar um valor preciso. Esse trabalho de layout então se torna parte do processing time, mas qualquer layout subsequente acionado por mais mudanças no DOM se torna parte do presentation delay.

Layout thrashing é o padrão repetido de escrever no DOM e depois ler propriedades de layout em um loop. Cada leitura força o navegador a recalcular o layout, e cada escrita invalida o layout novamente. Isso pode causar dezenas ou até centenas de cálculos de layout desnecessários por interação. Aqui está um exemplo de layout thrashing e como corrigi-lo:

// RUIM: Layout thrashing dentro de um loop
function resizeItems() {
  const items = document.querySelectorAll('.item');
  items.forEach(item => {
    // Lê (força o layout)
    const parentWidth = item.parentElement.offsetWidth;
    // Escreve (invalida o layout)
    item.style.width = parentWidth + 'px';
  });
}

// BOM: Agrupar leituras, depois agrupar escritas
function resizeItems() {
  const items = document.querySelectorAll('.item');
  // Ler todos os valores primeiro
  const widths = Array.from(items).map(
    item => item.parentElement.offsetWidth
  );
  // Depois escrever todos os valores
  items.forEach((item, i) => {
    item.style.width = widths[i] + 'px';
  });
}

Renderização do lado do cliente em Single Page Applications (SPAs)

A renderização de HTML do lado do cliente pode impactar significativamente o presentation delay, particularmente em Single Page Applications (SPAs). Quando uma interação do usuário aciona uma mudança de rota ou uma grande atualização da interface do usuário (UI), o framework SPA deve:

  1. Executar o algoritmo de diffing do virtual DOM para determinar o que mudou
  2. Aplicar as mutações resultantes do DOM ao DOM real
  3. Acionar o recálculo de estilo e o layout para todos os elementos afetados
  4. Pintar o quadro atualizado

Em aplicações React, o processo de reconciliação do virtual DOM faz parte do processing time, mas as mutações resultantes no DOM e seu custo de renderização recaem sobre o presentation delay. Quanto mais nós do DOM a sua árvore de componentes produzir, mais cara será a reconciliação e o trabalho de renderização subsequente.

Para mitigar isso em aplicações React e Next.js:

  • Use React.memo() para evitar novas renderizações desnecessárias de componentes filhos que recebem as mesmas props.
  • Use useDeferredValue() para valores que acionam renderizações caras, permitindo que o React priorize atualizações mais urgentes.
  • Mantenha as árvores de componentes rasas. Hierarquias de componentes profundamente aninhadas produzem um DOM profundamente aninhado, o que aumenta o custo da reconciliação e da renderização no navegador.
  • Use bibliotecas de virtualização (como react-window ou @tanstack/react-virtual) para listas longas, para que o DOM contenha apenas os itens visíveis.

Reduzindo o presentation delay

Minimizar o tamanho do DOM

O maior ganho para o presentation delay é manter o seu DOM pequeno:

  • Remova os elementos HTML não utilizados, especialmente divs de encapsulamento profundamente aninhadas.
  • Use virtualização de lista para listas longas (renderize apenas os itens visíveis mais um pequeno buffer).
  • Achate estruturas profundamente aninhadas onde for possível.
  • Use CSS Grid e Flexbox em vez de divs aninhadas para o layout.
// Virtualizar listas longas para reduzir o tamanho do DOM
// Antes: 10.000 itens no DOM

<ul>
  {allItems.map(item => 
     <li key="{item.id}">{item.name}</li>)
   }
</ul>

// Depois: apenas os itens visíveis no DOM (usando react-window)
import { FixedSizeList } from 'react-window';
<fixedsizelist height="{600}" 
               itemcount="{allItems.length}" 
               itemsize="{50}" width="100%">  
  {({ index, style }) => (
    <div style="{style}">{allItems[index].name}</div>
  )}
</fixedsizelist>

Use content-visibility para renderizar de forma preguiçosa (lazy-render) o conteúdo fora da tela

A propriedade CSS content-visibility diz ao navegador para pular a renderização do conteúdo fora da tela até que o usuário role perto dele. Isso reduz a quantidade de trabalho de renderização durante as interações, limitando o escopo do recálculo de estilo e layout à parte visível da página.

/* Aplica content-visibility a seções abaixo da dobra */
.below-fold-section {
  content-visibility: auto;
  contain-intrinsic-size: auto 500px;
}

/* Aplica a itens individuais em listas longas */
.list-item {
  content-visibility: auto;
  contain-intrinsic-size: auto 80px;
}

A propriedade contain-intrinsic-size fornece uma altura estimada para que o navegador possa calcular o tamanho da barra de rolagem corretamente sem renderizar o conteúdo. Isso evita mudanças de layout (layout shifts) quando o usuário rola a página e o conteúdo se torna visível.

Para mais estratégias de otimização de CSS que reduzem o custo de renderização, veja nosso guia sobre como remover CSS não utilizado.

Minimizar o trabalho de layout acionado por interações

Ao criar interações, prefira propriedades CSS que não acionem o layout. Propriedades como transform e opacity podem ser manipuladas pelo compositor da GPU sem acionar o layout ou a pintura. Em vez de animar top, left, width ou height, use transform: translate() e transform: scale(). Para a lista completa de propriedades CSS que acionam o layout, consulte o guia de desempenho de renderização do web.dev.

Use a propriedade CSS will-change para indicar ao navegador que um elemento será animado. Isso permite que o navegador crie uma camada de compositor separada para o elemento, isolando sua renderização do resto da página:

/* Promover elementos para sua própria camada de compositor */
.animated-element {
  will-change: transform, opacity;
}

/* Alternar visibilidade com opacity em vez de display */
.modal {
  opacity: 0;
  pointer-events: none;
  transform: translateY(10px);
  transition: opacity 0.2s, transform 0.2s;
}

.modal.active {
  opacity: 1;
  pointer-events: auto;
  transform: translateY(0);
}

Identificando presentation delays longos

Para identificar presentation delays longos, você pode usar o perfilador de desempenho do Chrome. Abra o DevTools (Ctrl+Shift+I), navegue até a aba Performance, clique em gravar e interaja com a página.

Você pode então analisar a linha do tempo de uma interação e visualizar as diferentes fases, incluindo o presentation delay. Ao examinar as atualizações de renderização que ocorrem após a conclusão dos manipuladores de eventos, você pode apontar quaisquer gargalos que contribuam para um presentation delay longo. Procure por grandes entradas de "Recalculate Style", "Layout" e "Paint" na linha do tempo. Isso representa o trabalho que o navegador faz durante a fase de presentation delay.

Identificando o presentation delay com dados de RUM

O Real User Monitoring (RUM) fornece atualizações em tempo real sobre métricas importantes relacionadas aos Core Web Vitals, como o Interaction to Next Paint e suas subpartes, incluindo o presentation delay. Uma ferramenta de RUM como o CoreDash divide cada interação do INP em suas três fases, permitindo que você veja se o presentation delay é o gargalo para suas páginas e segmentos de usuários específicos.

Medindo o presentation delay com Long Animation Frames (LoAF)

A API Long Animation Frames (LoAF) mostra exatamente o que causa atrasos de renderização durante as interações do usuário. A API fornece dados de tempo para separar o processing time do presentation delay e identificar quais scripts estão desacelerando a renderização.

As principais propriedades da LoAF para entender o presentation delay são:

  • renderStart: quando o navegador começou a fase de renderização (recálculo de estilo, layout, pintura)
  • styleAndLayoutStart: quando a computação de estilo e layout começou
  • duration: duração total do long animation frame
  • blockingDuration: quanto do quadro foi bloqueado por scripts

Atualmente, a LoAF é exclusiva do Chromium (Chrome 123+). Para outros navegadores, use os rastros do painel de Performance do Chrome DevTools para analisar o trabalho de renderização.

A diferença entre o final da execução do script e o final do quadro representa o custo de renderização puro, que é o presentation delay. Veja como observar e registrar esses dados:

// Medir o presentation delay usando a API LoAF
const observer = new PerformanceObserver((list) => {
  for (const entry of list.getEntries()) {
    if (entry.duration > 50) {
      const scriptEnd = Math.max(
        ...entry.scripts.map(s => s.startTime + s.duration)
      );
      const presentationDelay = (
        entry.startTime + entry.duration
      ) - Math.max(scriptEnd, entry.renderStart);

      console.log('Presentation delay breakdown:', {
        totalDuration: entry.duration,
        renderStart: entry.renderStart,
        styleAndLayoutStart: entry.styleAndLayoutStart,
        estimatedPresentationDelay: presentationDelay,
        scriptCount: entry.scripts.length
      });
    }
  }
});

observer.observe({
  type: 'long-animation-frame',
  buffered: true
});

Ferramentas de RUM como o CoreDash integram os dados da LoAF e mostram quais scripts e mudanças no DOM causam atrasos de renderização, com total atribuição de scripts.

Explore as outras fases do INP

Para manter o seu INP sob controle, aborde também as outras duas fases:

  • Input Delay: Minimize o tempo de espera antes que os manipuladores de eventos comecem a ser executados. O input delay é normalmente a menor fase, mas apresenta picos durante a inicialização da página quando a thread principal (main thread) está ocupada.
  • Processing Time: Otimize o código do manipulador de eventos que é executado durante a interação. Na maioria das páginas, é aqui que a maior parte do seu esforço de otimização compensa.

Para um fluxo de trabalho de diagnóstico completo, veja nosso guia sobre como encontrar e corrigir problemas de INP. Para estratégias adicionais de otimização de renderização, explore nossos guias sobre como corrigir o tamanho excessivo do DOM e remover CSS não utilizado. Retorne para a página principal do INP para a visão geral completa.

Fiz o CoreDash pras minhas próprias auditorias.

Menos de 1KB. Hospedado na UE. Sem banner de cookies. Agora com suporte a MCP.

Testa o CoreDash grátis
Presentation Delay do INP: Tamanho do DOM, Trabalho de Layout e Otimização de RenderizaçãoCore Web Vitals Presentation Delay do INP: Tamanho do DOM, Trabalho de Layout e Otimização de Renderização