Adloun

Vue : construire une application web (école d'ingénieur) · Chapitre 8 · Exercice de TD

Le focus sur la première erreur

Cycle de vie et composables · niveau 2

Énoncé

Un formulaire de commande a deux champs, Nom et Courriel, produits par un v-for. À l'envoi, chaque champ incorrect reçoit aria-invalid="true" et un message ; le focus doit aller sur le premier champ incorrect. Utiliser une référence de gabarit. Pourquoi faut-il attendre nextTick() avant de chercher ce champ ?

Corrigé


<script setup>
import { nextTick, reactive, ref, useTemplateRef } from "vue";

const CHAMPS = [
  { id: "nom", etiquette: "Nom" },
  { id: "courriel", etiquette: "Courriel" },
];
const valeurs = reactive({ nom: "", courriel: "" });
const erreurs = ref({});
// ref="champs" dans un v-for : un TABLEAU d'éléments, dans l'ordre d'affichage
const champs = useTemplateRef("champs");

async function envoyer() {
  erreurs.value = {};
  if (valeurs.nom.trim() === "") erreurs.value.nom = "Indiquez votre nom.";
  if (!valeurs.courriel.includes("@")) erreurs.value.courriel = "Adresse de courriel invalide.";
  await nextTick(); // attendre que les aria-invalid soient dans le DOM
  const premier = champs.value.find((c) => c.getAttribute("aria-invalid") === "true");
  if (premier) premier.focus();
  else console.log("envoi de", JSON.stringify(valeurs));
}
</script>

Envoi du formulaire vide, puis avec le seul nom, puis complet :


1er envoi : focus sur #nom
2e envoi : focus sur #courriel — Adresse de courriel invalide.
envoi de {"nom":"Diallo","courriel":"diallo@example.org"}

Les erreurs viennent d'être affectées, mais Vue met le DOM à jour plus tard, en une seule fois (chapitre 3) : sans await nextTick(), les attributs aria-invalid ne seraient pas encore écrits, et la recherche ne trouverait rien. champs.value est un tableau, dans l'ordre d'affichage, parce que ref="champs" est dans un v-for.

100 % gratuit

La suite du chapitre est sur Adloun

Exercice suivant et tuteur

Sans compte : le cours et le premier QCM. Exercices et tuteur : inscription gratuite en 30 secondes, sans carte bancaire.

Le cours du chapitre · Tous les exercices du chapitre

Exercice suivant et tuteur →