web-dev-qa-db-fra.com

Solution de contournement pour le bogue de focus iframe pour iOS 10-12 WebKit (Safari/Chrome)

J'ai cherché ce problème spécifique ici sur StackOverflow et les divers systèmes de rapport de bogues Apple/WebKit, mais je ne l'ai pas encore trouvé spécifiquement (ce qui ne semble pas possible).

Le problème: Sur notre page de paiement, nous avons différents champs de formulaire (entrées et sélections). Pour les besoins du PCI/de la sécurité, nous avons un iframe qui sert le champ du numéro de carte de crédit (le iframe seulementa ce champ, rien d’autre).

 Le problème est que, pour justeutilisateurs iOS), ils ne peuvent parfois pas se concentrer sur le champ du numéro de carte de crédit. Il semble y avoir 2 bogues Webkit iOS différents, mais liés. Voir la mise à jour ci-dessous.

S'ils naviguent simplement d'un champ à un autre, cela fonctionne généralement. Mais s’ils rebondissent autour des champs, ils peuvent entrer dans le scénario où ils pourraient essayer ils ne peuvent pas se concentrer sur le champ du numéro de carte de crédit il ne semble pas que le champ carte de crédit obtienne le focus (semble être un problème de rendu).

Au début, nous pensions peut-être que JS ou une DIV invisible se mettait en travers de la route, mais j'ai finalement pu créer un exemple HTML uniquement pour recréer le problème . (Des instructions sur la manière de recréer le problème se trouvent sur la page d'exemple.) Pour créer un lien vers codepen, je dois inclure du code:

<iframe src="iframe.html"></iframe>

J'ai toujours été capable de recréer ce problème sur les appareils iOS 10-12 (un appareil iOS 9 ne semblait pas avoir le problème).

Pour la postérité, je vais fournir la solution que j'ai trouvée dans un bogue WebKit distinct, mais semi-lié. Cependant, je me demandais si d'autres personnes étaient tombées sur ce problème et avaient découvert d'autres solutions de rechange.

METTRE À JOUR:

Après avoir creusé plus avant, j'ai découvert que nous souffrions de deux bogues distincts. La première est la plupart du temps ce que je décris ci-dessus, mais semble être un problème de rendu où iOS ne regardesemble mettre l'accent sur un champ. Cependant, si vous passez à la exemple codepen nouvel exemple J'installe et suis les étapes, même si l'apparence du champ n'est pas centrée, si vous tapez le texte sera rendu correctement.

Le deuxième problème est moins susceptible de se produire mais est plus préjudiciable. Il faut 3 critères pour déclencher:

  1. La source de l'iframe doit être d'origine croisée.
  2. La page parent attache un écouteur d'événement à touchstart, touchmove ou touchend (même comme un appel de fonction vide)
  3. Le champ de l’iframe est hors écran lorsqu'un autre champ est activé et que le clavier est présent.

Le résultat de ces 3 choses est que l'utilisateur ne peut pas placer le focus sur le champ iframe (la frappe ne va nulle part bien que document.activeElement montre la dernière entrée de page parente ayant le focus). Il peut être difficile de rétablir la focalisation dans l'iframe. Il est généralement nécessaire d'avoir une entrée de page parent pouvant être focalisée lorsque le champ iframe est visiblealors l'utilisateur peut déplacer son focus vers le champ iframe à partir de là.

Si l'un des 3 critères est modifié (pas de domaine, aucun écouteur d'événement sur ces événements tactiles ou si l'iframe est visible), seul le premier bogue - moins prohibitif - est présent.

Je mettrai à jour ma "réponse" ci-dessous avec cette réalisation également.

Mise à jour 2: L'exemple que je mets en place montre les deux bogues en action; la première page est le bogue n ° 1 avec un lien vers l'exemple du bogue n ° 2 d'origine croisée.

4
J Stuart

Le problème est résolu dans mon environnement en ajoutant la suggestion document.addEventListener('touchstart', {}); de @Ryan L dans l'IFrame.

C'est bien, car il est très simple d'ajouter et est spécifique à l'IFrame, sans affecter la page du conteneur.

Description du problème: impossible de 'toucher' (sélectionner, éditer) un autre champ de formulaire sous Safari exécuté sur iDevices (téléphone et tablette) sous iOS 12. Cela ne se produit que sur les pages d'un IFrame où la page de conteneur a ajouté certains événements tactiles. Ensemble très obscur de conditions difficiles à déboguer.

2
GlennG

Je pense avoir trouvé une solution à ce petit bogue frustrant et, comme la plupart des bogues, une solution très simple. 

Tout ce qui reste à faire est d’appliquer le css suivant à l’entrée dans l’iframe. 

    input:hover {
        cursor: text
    }

Voici un exemple mis à jour: https://codepen.io/ryanoutloud/project/full/AEKGjj

En ce qui concerne le bogue lui-même, l’accent est mis sur le champ prévu et toute entrée du clavier sera correctement enregistrée. Une fois que vous commencez à taper, le curseur se met dans la bonne position. le
Le problème que j'ai trouvé avec la solution ontouchstart="" est qu'il supprime simplement le curseur de la vue une fois que le focus est placé sur un champ.

3
Ryan L.

Voici la solution que je suis tombé sur: add ontouchstart="" à chacun des éléments de saisie de formulaire (sélectionne probablement aussi).

Cela provient d'une des solutions proposées sur ce bogue WebKit liée aux événements de clic de page externe qui ne sont pas correctement envoyées à un iframe (dans le contexte du zoom).

Je n'ai pas encore poussé cela vers la production, mais les premiers tests semblent indiquer que cela fonctionne. J'ai eu à mettre cela sur les deux éléments de formulaire parent et iframe pour résoudre complètement le problème. Je vais probablement utiliser JavaScript pour associer cela aux champs de formulaire sans avoir à ajouter la propriété à chaque élément de formulaire.

Ouvert à toute autre suggestion ou préoccupation concernant cette approche.

0
J Stuart