L'INP dans les Core Web Vitals : ce que c'est et comment l'améliorer

Ce que mesure l'INP, en quoi il diffère du FID et laquelle des trois phases corriger en premier.

Arjen Karel Core Web Vitals Consultant
Arjen Karel - linkedin
Last update: 2026-11-08

Qu'est-ce que l'Interaction to Next Paint (INP) ?

L'Interaction to Next Paint (INP) est le Core Web Vital (CWV) qui mesure la réactivité : le délai entre un clic, un tap ou l'appui sur une touche et la frame suivante à l'écran, mesuré sur l'interaction la plus lente d'une visite. Un bon INP est de 200 millisecondes ou moins au 75e percentile. L'INP a remplacé le First Input Delay (FID) le 12 mars 2024.

Pour le visiteur, un mauvais INP ressemble à un bouton qui ne réagit pas tout de suite : il tape sur le menu, rien ne change, alors il tape à nouveau. L'INP est l'un des trois Core Web Vitals, aux côtés du LCP et du CLS, et Google les utilise comme signal de classement.

Sur une page où l'on clique beaucoup, l'INP ignore une valeur aberrante toutes les 50 interactions. Une visite sans le moindre clic, tap ou appui sur une touche n'a pas d'INP.

INP vs FID : qu'est-ce qui a changé en mars 2024 ?

L'INP a remplacé le First Input Delay (FID) parmi les Core Web Vitals le 12 mars 2024. Le FID mesurait uniquement l'attente avant que le navigateur ne commence à traiter la première interaction d'une visite. L'INP chronomètre chaque interaction, de l'input jusqu'à la frame suivante à l'écran.

L'INP prend donc aussi en compte le travail que le FID ignorait : les event handlers exécutés après cette attente, ainsi que le style, le layout et le paint avant que l'écran ne change. Un clic dont le handler démarre après 10 ms puis s'exécute pendant 300 ms passait le FID, mais échoue à l'INP.

First Input Delay (FID)Interaction to Next Paint (INP)
InteractionsLa premièreChaque clic, tap et appui sur une touche
Ce qui est mesuréInput delayInput delay, processing duration et presentation delay
Bon100 ms ou moins200 ms ou moins
Valeur par visiteLe délai du premier inputL'interaction la plus lente

Quelles interactions l'INP mesure-t-il ?

L'INP mesure les clics, les taps et les appuis sur une touche, claviers virtuels compris. Chaque touche enfoncée lors de la saisie dans un champ de formulaire constitue une interaction distincte. Le scroll, le survol et le zoom ne comptent pas comme des interactions.

Le code lié au scroll peut tout de même ralentir un clic. Un clic sur un lien d'ancrage qui déclenche une animation de scroll en JavaScript est une interaction, et le code du scroll s'exécute à l'intérieur. Un handler qui s'exécute à chaque événement de scroll occupe le main thread : un tap effectué pendant que le visiteur scrolle doit donc attendre. La propriété CSS scroll-behavior: smooth assure un scroll fluide sans aucun script.

Les trois phases d'une interaction INP (sous-parties)

Chaque interaction mesurée par l'INP se compose de trois sous-parties successives : l'input delay, la processing duration et le presentation delay. L'INP d'une interaction correspond à leur somme, et la sous-partie la plus longue indique où commence le fix. Chrome DevTools affiche ces trois phases dans l'insight INP breakdown d'une trace.

Panneau Performance de Chrome DevTools, un tap sur une page de test : INP 379 ms, décomposition INP avec 1 ms d'input delay, 369 ms de processing duration et 9 ms de presentation delay

Un tap sur le filtre « All » d'une page de test simulant un site de locations de vacances, enregistré dans le panneau Performance : 369 des 379 ms correspondent à la processing duration, en grande partie du layout que le click handler force en boucle. Sans enregistrement, ce même tap prend 320 ms : la trace elle-même ralentit le tap.

  • Input delay : l'input attend la fin de la tâche déjà en cours sur le main thread. Il s'agit généralement d'un script exécuté pendant le chargement : un tag manager, un widget de chat ou un framework encore en cours d'hydratation.
  • Processing duration (aussi appelée processing time) : les event handlers de l'interaction s'exécutent. Un handler est lent lorsqu'il en fait trop à la fois : par exemple un tag analytics qui se déclenche au clic, ou un script qui lit les dimensions des éléments après chaque modification et force le layout en boucle.
  • Presentation delay : après les handlers, le navigateur recalcule les styles et le layout, puis peint la frame suivante. Un DOM volumineux ralentit cette étape, tout comme un re-render qui modifie une grande partie de la page. Les autres tâches exécutées avant cette frame comptent également ici.

Core Web Vitals Visualizer : INP de 480 ms pour un pointerdown pendant le chargement de la page, avec le détail INP suivant : input delay 2 ms, processing time 0 ms et presentation delay 478 ms

Un tap pendant que la page chargeait encore, dans le Core Web Vitals Visualizer. Le handler a pris 0 ms ; la frame suivante a ensuite attendu 478 ms pendant le travail de chargement de la page, et toute attente après le handler compte comme du presentation delay.

Qu'est-ce qu'un bon score INP ?

Un bon INP est de 200 millisecondes ou moins. Entre 200 et 500 millisecondes, il est à améliorer, et au-delà de 500 millisecondes, il est mauvais. Google retient le 75e percentile (p75) des chargements de page, séparément sur mobile et desktop.

Barre de performance INP : BON ≤200 ms, À AMÉLIORER 200 à 500 ms, MAUVAIS >500 ms

Au p75, trois chargements de page sur quatre doivent avoir un INP de 200 ms ou moins, téléphones lents compris. Les mobiles échouent en premier : un processeur plus lent exécute le même JavaScript plus longtemps, ce qui occupe le main thread plus souvent quand le visiteur tape sur l'écran.

Dans CoreDash, l'INP sur mobile était environ deux fois plus élevé que sur desktop. Ce tableau regroupe les chargements de page de 149 projets du 11 octobre au 7 novembre 2026 :

INP au p75MobileDesktop
Toutes les interactions170 ms89 ms
Pendant le chargement de la page285 ms125 ms
Après le chargement158 ms84 ms

D'après ces mêmes données, les frappes au clavier sur desktop étaient plus lentes que les clics et les taps : 121 contre 85 ms.

Selon le State of Web Vitals, 91,8 % des sites affichent un bon INP sur mobile.

Comment mesurer l'Interaction to Next Paint (INP)

L'INP utilisé par Google provient de vrais visiteurs sous Chrome : le Chrome UX Report (CrUX), affiché par PageSpeed Insights et Search Console. Un outil de real user monitoring (RUM) vous indique quel clic est lent sur quelle page, et Chrome DevTools vous montre pourquoi.

Search Console et PageSpeed Insights

Le rapport Core Web Vitals de Search Console regroupe par problème les URL qui échouent à l'INP, avec des exemples d'URL pour chaque groupe. « INP issue: longer than 200ms (mobile) » signifie que les visites sur mobile pour ce groupe d'URL similaires ont un INP supérieur à 200 ms au 75e percentile ; « INP issue: longer than 500ms (mobile) » indique plus de 500 ms. Votre site peut vous sembler rapide alors que le rapport le donne en échec : beaucoup de vos visiteurs utilisent des téléphones plus lents que le vôtre, et ils interagissent aussi pendant que la page charge encore. PageSpeed Insights affiche l'INP au p75 sur les 28 derniers jours pour une URL, ou pour l'ensemble du site si cette URL a trop peu de visites dans Chrome. Un fix met du temps à apparaître dans les deux outils : Search Console prend jusqu'à 28 jours.

Google Search Console, rapport Core Web Vitals sur mobile pour acme-inp.com : INP issue: longer than 200ms (mobile), à améliorer, 1 240 URL concernées, en hausse sur trois mois

URL concernées par jour pour un problème d'INP dans Search Console.

Real user monitoring

CrUX donne un seul chiffre par URL ou groupe d'URL. Un script RUM sur votre propre site mesure chaque visite. Dans CoreDash, je regarde d'abord l'INP p75 sur mobile, ventilé par élément cliqué et par état de chargement.

Les outils RUM mesurent désormais aussi l'INP dans Safari et Firefox. CrUX, et avec lui Google, ne prend en compte que Chrome : les chiffres peuvent donc différer.

Vos propres clics dans Chrome DevTools

Ouvrez le panneau Performance de Chrome DevTools. Ses métriques en direct affichent l'INP de votre session au fil de vos clics, avec l'historique de chaque interaction et de ses trois sous-parties. Réglez le CPU sur un ralentissement 4x pour que votre ordinateur se comporte comme un téléphone, et cliquez aussi pendant que la page charge encore. Pour voir ce qui a tourné, enregistrez une trace pendant que vous cliquez : la piste Interactions repère l'interaction et la piste Main montre les tâches associées. L'extension Core Web Vitals Visualizer affiche cette même décomposition directement sur la page.

La bibliothèque web-vitals consigne dans la console chaque interaction qui augmente l'INP, avec l'élément et les sous-parties :

<script type="module">
  import {onINP} from 'https://unpkg.com/web-vitals@6/dist/web-vitals.attribution.js?module';
  onINP(console.log, {reportAllChanges: true});
</script>

Lighthouse

Un audit Lighthouse classique n'a pas d'INP : il charge la page sans jamais cliquer. La métrique de lab la plus proche est le Total Blocking Time (TBT), soit la durée pendant laquelle le main thread a été bloqué durant le chargement. L'INP est généralement bien inférieur au TBT, mais réduire le TBT permet aussi d'améliorer l'INP. Pourquoi Lighthouse et vos field data affichent des chiffres différents : Lighthouse vs field data.

Comment améliorer l'INP

Les interactions les plus lentes sur mobile déterminent votre INP. Repérez-les dans vos field data (Search Console ou outil RUM), regardez leur sous-partie la plus longue et réduisez-la : moins de JavaScript pendant le chargement pour l'input delay, moins de travail dans l'event handler pour la processing duration, moins d'éléments à afficher pour le presentation delay. Le guide INP pas à pas vous guide du rapport Search Console jusqu'à la ligne de code.

WordPress

Sur un site WordPress, commencez par les scripts de plugins chargés par chaque page, car chacun d'eux peut faire attendre un tap. Le Script Manager de Perfmatters et Asset CleanUp déchargent les scripts d'un plugin sur les pages qui ne l'utilisent pas, comme un plugin de formulaire sur vos pages produit. Pour ce qui reste lent après cela, demandez une trace à un développeur : un enregistrement du tap lent avec un CPU ralenti à 4x, et le nom du script qui s'y exécute.

Les réglages de Delay JavaScript (Delay JavaScript execution dans WP Rocket, Delay JavaScript dans Perfmatters, Load JS Deferred réglé sur Delayed dans LiteSpeed Cache) bloquent les scripts jusqu'à la première interaction et les exécutent alors tous d'un coup. Cela fait gagner des points sur Lighthouse, car Lighthouse ne touche jamais à la page. Un vrai visiteur tape sur le menu et attend pendant que le navigateur télécharge et exécute tout ; or l'INP retient le tap le plus lent de la visite. Laissez ces réglages désactivés pour l'INP.

WP Core Web Vitals, le plugin de corewebvitals.io, diffère les scripts dans leur ordre d'origine et exécute les outils d'analytics, les pixels et les widgets de chat après le chargement de la page, sans attendre le moindre tap.

Shopify

Chaque application Shopify alourdit chaque clic : vous l'installez pour une fonctionnalité, et son script se charge sur des pages et des clics qui n'ont rien à voir avec elle. Dans l'éditeur de thème, sous App embeds, désactivez les applications une par une et remesurez le tap lent après chacune. Les app blocks placés dans une section restent actifs quand vous désactivez l'app embed : supprimez-les dans cette section. Une application désinstallée peut laisser son code dans les snippets du thème : recherchez son nom dans le thème.

Les réglages de l'application changent rarement ce qui s'exécute lors d'un clic. C'est le code du thème qui en décide : ce que fait l'ajout au panier, quand le cart drawer s'affiche, quels scripts d'application sont chargés. Cette partie est un travail de développeur : le handler de l'ajout au panier met à jour l'écran en premier et fait le reste ensuite, et le cart drawer ne rend que ce qui a changé.

Input delay : moins de JavaScript pendant le chargement

Un tap pendant le chargement attend le script qui s'exécute à ce moment-là. Le panneau Coverage des DevTools indique le code exécuté jusque-là : un script encore largement inutilisé après avoir parcouru la page peut être supprimé, et une grande partie de ce qui reste peut attendre que la page ait fini de charger. Avez-vous vraiment besoin d'un widget de chat pendant les 500 premières millisecondes du chargement ? Lancez-le après l'événement load, quand le navigateur est inactif :

window.addEventListener('load', () => {
  const whenIdle = window.requestIdleCallback || ((cb) => setTimeout(cb, 1));
  whenIdle(() => {
    const script = document.createElement('script');
    script.src = '/js/chat-widget.js';
    document.head.appendChild(script);
  });
});

async et defer évitent qu'un script ne bloque le parser HTML, mais le script s'exécute tout de même pendant le chargement ; ils aident donc davantage le LCP que l'INP. D'autres façons d'exécuter un script plus tard figurent dans 16 méthodes pour différer ou planifier du JavaScript.

Le navigateur attend la fin d'un listener touchstart ou wheel qui n'est pas passif avant de faire défiler la page. Ajouter { passive: true } supprime cette attente, mais l'INP ne mesurant pas le scroll, cela ne réduira pas votre INP.

Découpez vos propres long tasks (toute tâche de plus de 50 ms sur le main thread) pour que le navigateur puisse traiter un tap en attente entre deux. Rendez la main au main thread (yield) après environ 50 ms de travail, peu importe le temps que prend un élément :

function yieldToMain() {
  if (globalThis.scheduler?.yield) {
    return scheduler.yield();
  }
  return new Promise((resolve) => setTimeout(resolve, 0));
}

async function processItems(items) {
  let lastYield = performance.now();
  for (const item of items) {
    processItem(item);
    if (performance.now() - lastYield > 50) {
      await yieldToMain();
      lastYield = performance.now();
    }
  }
}

scheduler.yield() fonctionne sous Chrome et Firefox ; Safari utilise le fallback setTimeout. En savoir plus dans rendre la main au main thread (yield).

Processing duration : mettez d'abord l'écran à jour

Un event handler rapide exécute d'abord ce que voit le visiteur et reporte tout le reste après le paint suivant. Un tag placé dans le click handler s'exécute avant que l'écran ne puisse changer. En le déplaçant après la mise à jour, le visiteur voit le résultat en premier et le tag s'exécute tout de même :

button.addEventListener('click', () => {
  showConfirmation(); // ce que voit le visiteur
  requestAnimationFrame(() => {
    setTimeout(() => {
      // s'exécute après le paint de la frame suivante
      dataLayer.push({ event: 'cta_click' });
    }, 0);
  });
});

Un requestIdleCallback() à cet endroit plante sur tous les iPhone : Safari ne le prend pas en charge, donc le handler génère une erreur après l'exécution de showConfirmation(). Le clic semble fonctionner, mais l'événement est perdu. La version adaptée à Tag Manager se trouve dans planifier les événements dataLayer ; sur le site d'un client, déplacer dataLayer.push() après le paint a réduit l'INP de 100 ms.

Pour un formulaire ou un ajout au panier qui attend le serveur, confirmez immédiatement à l'écran que le tap a fonctionné (« Ajout au panier… ») et laissez la requête se terminer ensuite.

Le clic lent que je rencontre le plus souvent concerne les filtres de produits : le handler met à jour la liste, lit sa nouvelle hauteur, modifie un élément en fonction de cette hauteur, puis lit à nouveau la hauteur. Chaque lecture après une modification oblige le navigateur à recalculer le layout dans le handler. Sur une page de test simulant un site de locations de vacances WordPress, un tap sur le filtre « All » prenait 320 ms, dont 298 ms de layout forcé par le script du thème. En faisant lire toutes les hauteurs au script en premier, ou en confiant ce rôle au CSS, ce même tap prenait 16 ms, soit une seule frame. Ces deux cas ont été mesurés dans Chrome en largeur mobile avec un CPU ralenti à 4x. Le guide sur le forced reflow détaille le fix pour les thèmes, plugins, applications et votre propre code.

Presentation delay : un DOM plus léger, moins de re-renders

Un DOM volumineux ralentit chaque frame après l'exécution des handlers. Lighthouse le liste sous « Optimize DOM size » : comment réduire la taille du DOM.

Sur les pages longues, content-visibility: auto permet au navigateur d'ignorer le rendu des sections hors du viewport jusqu'à ce que le visiteur scrolle à proximité :

.product-reviews,
.site-footer {
  content-visibility: auto;
  contain-intrinsic-size: auto 600px;
}

Donnez à chaque section de ce type un contain-intrinsic-size proche de sa hauteur réelle. Sans cela, une section ignorée a une hauteur de zéro pixel, et la barre de défilement saute à mesure que les sections s'affichent.

Certaines single page applications re-rendent bien trop de contenu après chaque interaction : un clic modifie un compteur et la moitié de la page subit un re-render. Dans React DevTools, l'option « Highlight updates when components render » montre quels composants sont rendus par un clic.

Déboguer l'INP avec l'API Long Animation Frames (LoAF)

L'API Long Animation Frames (LoAF) signale chaque frame ayant pris plus de 50 ms, avec les scripts qui y ont tourné : le fichier, la fonction et la durée d'exécution de chacun. Grâce à elle, une interaction lente identifiée dans vos field data se voit attribuer un nom de script. LoAF fonctionne dans les navigateurs Chromium (Chrome 123 et versions ultérieures).

new PerformanceObserver((list) => {
  for (const frame of list.getEntries()) {
    if (frame.duration < 100) continue; // uniquement les frames les plus lentes
    for (const script of frame.scripts) {
      console.log(script.sourceURL, script.sourceFunctionName,
        Math.round(script.duration) + ' ms');
    }
  }
}).observe({ type: 'long-animation-frame', buffered: true });

Un outil RUM collecte ces entrées pour chaque visite. Dans CoreDash, ouvrez INP, Breakdown et groupez par LOAF : chaque ligne correspond à un script, avec l'INP des interactions dans lesquelles il est intervenu, réparti selon les trois sous-parties. Commencez par le script dont la barre est la plus longue sur mobile. Le guide de l'API Long Animation Frames explique chaque champ d'une entrée.

Sous-parties INP dans CoreDash par LOAF : INP au p75 par script, ventilé en input delay, processing et presentation.

CoreDash, groupé par LOAF (desktop) : le vert correspond à l'input delay, le violet à la processing duration et le bleu au presentation delay.

Le tap lent se trouve dans un script que vous n'avez pas écrit, comme une application, un tag ou une bannière de consentement, et vous ne savez pas lequel supprimer ? Lors d'une Core Web Vitals power hour, nous passons en revue vos field data et une trace de ce tap ensemble, et vous obtenez le fix par écrit.

About the author

Arjen Karel is a web performance consultant and the creator of CoreDash, a Real User Monitoring platform that tracks Core Web Vitals data across hundreds of sites. He also built the Core Web Vitals Visualizer Chrome extension. He has helped clients achieve passing Core Web Vitals scores on over 925,000 mobile URLs.

Arjen Karel

Besoin d'un site plus rapide ?

Je suis Arjen et je répare des sites lents depuis 17 ans. Si vous rencontrez des problèmes que vous ne pouvez pas résoudre vous-même, envoyez-moi votre URL et parlons-en.

Envoyez-moi votre URL
Arjen Karel
Arjen Karel, Consultant en performance web depuis 2009

Pourquoi notre fix ne fonctionne pas ?

Parfois le CDN sert encore l'ancien HTML, ou le fix a été appliqué sur le template desktop alors que le mobile en utilise un autre. Envoyez-moi votre URL et le problème, et je vous réponds avec quelques créneaux. J'analyse d'abord vos field data, puis nous passons une heure sur votre site, et sous 24 heures vous avez mes notes par écrit. 350 € HT.

Envoyez-moi votre URL

Pas de développeur pour réaliser le fix ? Je fais le travail moi-même, sur une copie de votre site.

L'INP dans les Core Web Vitals : ce que c'est et comment l'améliorer Core Web Vitals L'INP dans les Core Web Vitals : ce que c'est et comment l'améliorer