Back

Détecter les appareils tactiles avec JavaScript

Détecter les appareils tactiles avec JavaScript

La détection tactile semble simple jusqu’à ce que vous vous retrouviez face à une Surface Pro, un iPad avec Magic Keyboard ou un Chromebook avec écran tactile. Ces appareils hybrides remettent en question l’hypothèse selon laquelle « tactile » et « souris » s’excluent mutuellement — et c’est précisément là que la plupart des approches de détection échouent.

Cet article va droit au but : ce qui fonctionne réellement, ce qui ne fonctionne pas, et quand vous ne devriez même pas vous préoccuper de détecter le tactile.

Points clés à retenir

  • 'ontouchstart' in window n’est pas fiable car les navigateurs l’exposent de manière incohérente, même sur des appareils sans écran tactile.
  • navigator.maxTouchPoints > 0 est la vérification JavaScript simple la plus fiable pour détecter la capacité tactile déclarée sur les navigateurs modernes.
  • Les media queries CSS pour les pointeurs (pointer, any-pointer, hover) gèrent la plupart des adaptations d’interface sans aucun JavaScript.
  • L’API Pointer Events et sa propriété pointerType vous permettent de détecter la méthode de saisie actuelle de l’utilisateur, ce qui est bien plus utile sur les appareils hybrides qu’une vérification unique au chargement de la page.

Pourquoi 'ontouchstart' in window ne suffit pas

Pendant des années, les développeurs ont utilisé 'ontouchstart' in window comme moyen rapide de détecter la capacité tactile. Le problème est que les navigateurs exposent cette propriété de manière incohérente. Certains navigateurs de bureau sous Windows 8+ la signalent comme true même sans écran tactile. Chrome a modifié son comportement au fil des versions. C’est un signal peu fiable.

Se fier uniquement à ontouchstart signifie que vous détectez le comportement du navigateur, et non la capacité matérielle réelle.

La propriété JavaScript la plus fiable pour détecter la prise en charge tactile aujourd’hui est navigator.maxTouchPoints. Elle renvoie le nombre maximum de points de contact tactile simultanés pris en charge par l’appareil. Une valeur supérieure à zéro signifie que le matériel déclare une capacité tactile.

function hasTouchSupport() {
  return navigator.maxTouchPoints > 0
}

Cela fait partie de la spécification Pointer Events et est pris en charge par tous les navigateurs modernes — Chrome, Firefox, Safari et Edge. C’est clair, lisible et ne repose pas sur la détection de gestionnaires d’événements.

Note : navigator.msMaxTouchPoints était l’équivalent de l’ère IE. Vous n’en avez pas besoin sauf si vous maintenez du code legacy.

Quand les media queries CSS pour les pointeurs sont le meilleur outil

Pour la plupart des adaptations d’interface, vous n’avez pas du tout besoin de JavaScript. Les media queries CSS pour les pointeurs vous permettent d’ajuster le style en fonction de la précision du périphérique d’entrée principal.

/* Cible les appareils où le pointeur principal est imprécis (ex : doigt) */
@media (pointer: coarse) {
  .btn {
    min-height: 48px;
  }
}

/* Cible tout pointeur disponible qui est imprécis, y compris les entrées secondaires */
@media (any-pointer: coarse) {
  .tooltip {
    display: none;
  }
}

/* Cible les appareils où le survol n'est pas disponible de manière fiable */
@media (hover: none) {
  .dropdown:hover .menu {
    display: none;
  }
}

La différence entre pointer et any-pointer est importante sur les appareils hybrides. pointer: coarse reflète uniquement l’entrée principale. any-pointer: coarse renvoie true si n’importe quelle entrée connectée est imprécise — utile lorsqu’un appareil dispose à la fois d’une souris et d’un écran tactile.

Pointer Events vs. Touch Events

Les Pointer Events constituent le modèle moderne et unifié pour gérer les entrées souris, tactiles et stylet en JavaScript. Au lieu de maintenir des gestionnaires touchstart et mousedown séparés, vous n’en écrivez qu’un :

element.addEventListener('pointerdown', (e) => {
  if (e.pointerType === 'touch') {
    // Gérer l'entrée tactile
  } else if (e.pointerType === 'mouse') {
    // Gérer l'entrée souris
  }
})

La propriété pointerType vous indique exactement ce que l’utilisateur fait en ce moment — et non ce dont son appareil est théoriquement capable. C’est la distinction qui compte le plus sur les appareils hybrides.

Les Touch Events legacy (touchstart, touchmove, touchend) sont toujours pris en charge dans la plupart des navigateurs mais ne sont pas disponibles dans tous les environnements et ne couvrent pas les entrées souris ou stylet. Privilégiez les Pointer Events pour le nouveau code.

Le problème des appareils hybrides

Un utilisateur sur un ordinateur portable tactile peut commencer une session avec une souris, puis lever la main et toucher l’écran. Toute détection effectuée au chargement de la page est déjà obsolète.

Plutôt que de vous enfermer dans un résultat de détection unique, écoutez les événements pointerdown et lisez e.pointerType de manière dynamique. Cela vous permet d’adapter l’interface en fonction de ce que l’utilisateur fait réellement, et non de ce que son appareil prend en charge en théorie.

Que utiliser et quand

ObjectifApproche recommandée
Ajuster la taille des boutons ou zones tactilesCSS @media (pointer: coarse)
Supprimer l’interface uniquement au survolCSS @media (hover: none)
Vérifier la capacité tactile matérielle en JSnavigator.maxTouchPoints > 0
Gérer les événements d’entrée tous types confondusAPI Pointer Events
Détecter le type d’entrée actuel dynamiquementevent.pointerType sur pointerdown

Conclusion

Abandonnez complètement la détection de user agent. Pour les ajustements d’interface, les media queries CSS pour les pointeurs gèrent la plupart des cas sans une seule ligne de JavaScript. Lorsque vous avez besoin de JavaScript, navigator.maxTouchPoints vous donne un signal matériel fiable, et l’API Pointer Events vous fournit un contexte d’entrée en temps réel. Ensemble, ils couvrent toute la gamme des appareils modernes — y compris les hybrides qui rendent la détection simple peu fiable.

FAQ

Oui. navigator.maxTouchPoints fait partie de la spécification Pointer Events et est pris en charge dans Chrome, Firefox, Safari et Edge. Il renvoie généralement zéro sur les appareils qui ne déclarent pas de prise en charge tactile, et un entier positif sur les appareils tactiles. C'est la vérification à propriété unique la plus fiable disponible en JavaScript aujourd'hui pour détecter la prise en charge tactile.

Les chaînes user agent ne sont pas fiables pour déterminer les capacités d'entrée. Elles identifient le navigateur et le système d'exploitation, pas le matériel. Un ordinateur portable Windows et une tablette Windows peuvent partager la même chaîne user agent malgré des méthodes d'entrée très différentes. La détection de fonctionnalités via maxTouchPoints ou les media queries CSS est bien plus précise.

Oui. L'API Pointer Events fournit une propriété pointerType sur les événements comme pointerdown. Sa valeur est touch, mouse ou pen selon l'entrée utilisée à ce moment précis. C'est plus utile qu'une vérification de capacité ponctuelle, en particulier sur les appareils hybrides où les utilisateurs alternent entre les entrées.

La media query pointer cible uniquement le périphérique d'entrée principal. La requête any-pointer renvoie true si n'importe quelle entrée disponible correspond à la condition. Sur un ordinateur portable avec à la fois un trackpad et un écran tactile, pointer coarse peut être false car le trackpad est principal, mais any-pointer coarse serait true car l'écran tactile est qualifié.

Complete picture for complete understanding

Capture every clue your frontend is leaving so you can instantly get to the root cause of any issue with OpenReplay — the open-source session replay tool for developers. Self-host it in minutes, and have complete control over your customer data.

Check our GitHub repo and join the thousands of developers in our community.

OpenReplay