$dispatch
$dispatch est un raccourci pratique pour émettre des événements du navigateur.
<div @notify="alert('Bonjour le monde !')">
<button @click="$dispatch('notify')">
Notifier
</button>
</div>
Vous pouvez aussi transmettre des données avec l'événement émis. Elles seront accessibles via la propriété .detail de l'événement :
<div @notify="alert($event.detail.message)">
<button @click="$dispatch('notify', { message: 'Bonjour le monde !' })">
Notifier
</button>
</div>
En coulisses, $dispatch est une enveloppe autour de l'API plus verbeuse element.dispatchEvent(new CustomEvent(...)).
Remarque sur la propagation des événements
À cause de la remontée des événements (event bubbling), lorsque vous devez capter des événements émis par des nœuds situés dans la même hiérarchie d'imbrication, vous devez utiliser le modificateur .window :
Exemple :
<!-- 🚫 Ne fonctionnera pas -->
<div x-data>
<span @notify="..."></span>
<button @click="$dispatch('notify')">Notifier</button>
</div>
<!-- ✅ Fonctionnera (grâce à .window) -->
<div x-data>
<span @notify.window="..."></span>
<button @click="$dispatch('notify')">Notifier</button>
</div>
Remarque : Le premier exemple ne fonctionne pas car, quand
notifyest émis, il se propage jusqu'à leur ancêtre commun, lediv, et non jusqu'à son voisin, le<span>. Le second exemple fonctionne car le voisin écoutenotifyau niveau dewindow, que l'événement personnalisé finit par atteindre en remontant.
Émettre vers d'autres composants
Vous pouvez aussi tirer parti de la technique précédente pour faire communiquer vos composants entre eux :
Exemple :
<div
x-data="{ title: 'Bonjour' }"
@set-title.window="title = $event.detail"
>
<h1 x-text="title"></h1>
</div>
<div x-data>
<button @click="$dispatch('set-title', 'Bonjour le monde !')">Cliquez-moi</button>
</div>
<!-- Au clic, le contenu du h1 devient « Bonjour le monde ! ». -->
Émettre vers x-model
Vous pouvez aussi utiliser $dispatch() pour déclencher des mises à jour de données pour les liaisons x-model. Par exemple :
<div x-data="{ title: 'Bonjour' }">
<span x-model="title">
<button @click="$dispatch('input', 'Bonjour le monde !')">Cliquez-moi</button>
<!-- Après l'appui sur le bouton, `x-model` capte l'événement « input » qui remonte et met à jour title. -->
</span>
</div>
Cela ouvre la porte à la création de composants de saisie personnalisés dont la valeur peut être définie via x-model.
Événements annulables
Vous pouvez utiliser la valeur renvoyée par $dispatch pour savoir si l'événement a été annulé ou non. C'est utile lorsque vous voulez empêcher le comportement par défaut d'une action.
<div x-data x-on:open="$event.preventDefault()">
<div x-data="{ open: false }">
<button @click="if($dispatch('open')){ open = true; }">Cliquez-moi</button>
<!-- Au clic, un événement est émis et le contenu n'est affiché que si le résultat est vrai (c'est-à-dire non empêché par un gestionnaire). -->
<div x-show="open">
<h1>Bonjour</h1>
</div>
</div>
</div>
Cela peut être utile pour empêcher l'ouverture ou la fermeture d'une fenêtre modale, par exemple, à l'aide de gestionnaires d'événements.
Remplacer les options
Vous pouvez utiliser le troisième paramètre de $dispatch pour remplacer les options par défaut de l'événement. Par exemple, vous pouvez définir bubbles à false :
<!-- 🚫 Ne fonctionnera pas car l'événement est écouté sur l'élément parent -->
<div x-data="{ title: 'Bonjour' }" x-on:update-title="title = $event.detail">
<button @click="$dispatch('update-title', 'Bonjour le monde !', {bubbles: false})">Cliquez-moi</button>
</div>
<!-- ✅ Fonctionnera car l'événement est écouté sur le même élément -->
<div x-data="{ title: 'Bonjour' }">
<button x-on:update-title="title = $event.detail" @click="$dispatch('update-title', 'Bonjour le monde !', {bubbles: false})">Cliquez-moi</button>
</div>
C'est utile lorsque vous voulez empêcher l'événement de remonter vers les éléments parents.
Traduction française de la documentation officielle d'Alpine.js (licence MIT) – https://alpinejs.dev