Explosion
Un clic projette 60 particules rectangulaires colorées en éventail sur canvas — gravité, friction et dissipation progressive les effacent en moins de 3 secondes.
Vous aurez accès à la démo interactive avec un compte gratuit.
Cet effet fait partie d'Effect.Labs — 811 effets vanilla, une partie gratuite, une partie premium. Atmosphère comprend 57 effets, dont 10 gratuits. Découvrir la catégorie →
3 exemples d'usage



Comment ça marche
setupCanvas('psExplosion') récupère le canvas par son id, lit les dimensions du parent via getBoundingClientRect() et les applique aux propriétés width/height du canvas — rendu pixel-exact quel que soit le layout. Un seul tableau n centralise toutes les particules vivantes et un unique requestAnimationFrame récursif tourne dès l'initialisation.
Au clic, les coordonnées CSS sont converties en espace logique canvas via le ratio w / o.width, puis 60 particules naissent à ce point. Chaque particule reçoit une direction aléatoire dans [0, 2π] et une vitesse initiale dans [2, 8] px/frame (6 * Math.random() + 2), une taille dans [2, 6] px, une vitesse de rotation dans [−5, 5] deg/frame et un decay dans [0,01 – 0,025] qui détermine sa durée de vie (40 à 100 frames).
La boucle physique suit l'intégration d'Euler : gravité constante vy += 0.08 par frame, friction isotrope vx *= 0.99 / vy *= 0.99. Chaque particule est un rectangle size × size/2 dessiné après translate + rotate ; globalAlpha = life traduit directement le dépérissement en opacité, de 1 à 0.
Le fond n'est pas effacé par clearRect mais recouvert d'un fillRect semi-transparent rgba(10,10,15,0.1) : les 10 % d'opacité cumulent une traîne cinétique délibérée qui éclaire brièvement les trajectoires. Ni IntersectionObserver ni gestion de prefers-reduced-motion ne sont présents dans l'implémentation d'origine — le RAF tourne en continu.
Accessibilité
- prefers-reduced-motion absent : le code n'interroge pas
window.matchMedia('(prefers-reduced-motion:reduce)')— le RAF tourne toujours. Pour neutraliser l'animation, ajoutez ce test à l'init et sautez le lancement du RAF si la préférence est active. - Le
<canvas>ne porte pasaria-hidden="true"dans l'implémentation d'origine — les lecteurs d'écran peuvent l'annoncer inutilement. Ajoutez l'attribut au déploiement. - Aucun
role="img"niaria-labelsur le conteneur — ajoutez une description statique de l'effet pour les technologies d'assistance. - L'interaction est uniquement clic/tactile : aucune activation clavier n'est exposée. Pour l'accessibilité, câblez un déclenchement sur
keydown(Entrée / Espace) sur l'élément focusable parent. - Le contraste texte n'est pas géré par l'effet — aucun scrim n'est fourni. Si vous superposez du texte, ajoutez un fond semi-transparent et vérifiez le ratio WCAG AA (≥ 4,5:1).
Compatibilité navigateur
Nécessite Canvas 2D Context et requestAnimationFrame — supportés dans tous les navigateurs modernes depuis 2015.
Si <code>canvas</code> n'est pas supporté, <code>setupCanvas</code> retourne <code>null</code> et le reste de l'IIFE s'interrompt silencieusement — aucune erreur JS, la page reste fonctionnelle.
Le code
Structure HTML à coller dans votre page (CSS + JS disponibles avec un compte premium) :
<div class="demo-preview">
<div class="ps-canvas-wrap">
<canvas class="ps-canvas" id="psExplosion" width="392" height="280"
aria-hidden="true"></canvas>
<span class="ps-hint">Cliquez pour exploser</span>
</div>
</div>
HTML + CSS + JS complet, prêt à coller — avec des centaines d'effets premium.
Personnaliser
Options passées à l'API ou attributs data-* :
| Option / propriété | Défaut | Effet |
|---|---|---|
| Tableau e de couleurs | 7 hex (#8b5cf6 … #06b6d4) | Remplacez par votre palette brand — ajoutez ou retirez des entrées, chaque particule pioche au hasard dans le tableau. |
| Constante 60 (count) | 60 particules/clic | Nombre de particules créées à chaque clic — 30 pour un effet discret, 120 pour un burst spectaculaire. |
| 6 * Math.random() + 2 (speed) | 2 – 8 px/frame | Vitesse initiale des particules — augmentez le facteur (ex. 10 * Math.random() + 4) pour une explosion plus énergique. |
| a.vy += .08 (gravité) | 0.08 px/frame² | Accélération gravitationnelle — 0 = zéro gravité (mouvement rectiligne), 0.20 = chute rapide style confettis lourds. |
| a.vx *= .99 / a.vy *= .99 (friction) | 0.99 (légère) | Facteur de frein par frame — 0.95 = friction forte (ralentissement rapide), 0.999 = quasi sans résistance. |
| 4 * Math.random() + 2 (size) | 2 – 6 px | Taille des rectangles de particules — 8 * Math.random() + 4 donne des confettis plus visibles sur grand écran. |
| .015 * Math.random() + .01 (decay) | 0.01 – 0.025 /frame | Vitesse de disparition — .005 fixe → particules visibles ~200 frames ; .04 → fade en 25 frames. |
| rgba(10,10,15,0.1) (traîne fond) | 10% opacité | Opacité du fond par frame — 0.05 = traîne longue et lumineuse, 0.30 = effacement quasi immédiat, 1.0 = pas de traîne (clearRect pur). |
FAQ
MouseEvent synthétique sur le canvas : canvas.dispatchEvent(new MouseEvent('click', { clientX: cx, clientY: cy, bubbles: true })) avec les coordonnées souhaitées (centre = rect.left + rect.width/2). Aucune API publique n'est exposée dans l'implémentation d'origine.clearRect : chaque frame superpose un fillRect rgba(10,10,15,0.1) qui atténue progressivement les anciennes traces. C'est délibéré — pour une ardoise propre entre deux explosions, remplacez ce remplissage par ctx.clearRect(0, 0, w, h) avant de dessiner les particules.