Galerie✨ Premium

WebGL Displacement Slideshow

Diaporama sur canvas WebGL : à chaque changement, un bruit déforme l'image qui part et celle qui arrive pendant 0,9 s. Vos propres images, pause au survol.

WebGLShaderSlideshow

Mis à jour le

Cet effet fait partie d'Effect.Labs — 840 effets vanilla, une partie gratuite, une partie premium. Galerie comprend 44 effets, dont 6 gratuits. Découvrir la catégorie →

3 exemples d'usage

Fond plein écran d'une collection de parfums — WebGL Displacement Slideshow exemple 1

① Fond plein écran d'une collection de parfums

QuandEn haut de la page « Collection d'automne » d'Ombrevine, le diaporama couvre toute la largeur derrière le menu, le nom du parfum, ses notes et le bouton « Découvrir ». Chaque flacon se déforme dans le suivant ; le nom et les notes changent avec l'image. Les flèches, les pastilles et la pause sont regroupées en bas à droite pour ne pas gêner le texte.
PourquoiLa déformation donne au passage d'un parfum à l'autre une texture liquide qui colle au produit, là où un simple fondu serait banal. Le dégradé sombre à gauche garde le texte lisible sur n'importe quelle image.
RéglagesRacine en position:absolute; inset:0, --wds-ratio: auto, coins droits, quatre <img> (illustrations SVG), contrôles déplacés en bas à droite par la CSS de la scène, texte posé dans un calque au-dessus du canvas. La souris reste sur le fond pendant la capture (donc en pause) : la démo appuie sur la vraie flèche toutes les 1,7 s ; le texte suit la classe wds-on posée par le code.
Un nuancier de peinture qu'on parcourt aux pastilles — WebGL Displacement Slideshow exemple 2

② Un nuancier de peinture qu'on parcourt aux pastilles

QuandSur la fiche couleur de la marque Chromavel, l'échantillon de 250 px de large montre un mur peint au rouleau ; cinq pastilles sous l'échantillon passent de « Terre de Sienne » à « Bleu orage » ou « Vert lichen », et les traces de rouleau se tordent vers la teinte suivante pendant que le nom, la référence, la finition et le bouton « Commander un échantillon » restent à droite.
PourquoiSur un aplat parfaitement uni, la déformation ne se verrait pas : il lui faut du relief. Une texture de rouleau suffit, et la déformation rend le changement de teinte matériel, comme une peinture qu'on remue ; rien ne bouge tant que le visiteur ne choisit pas.
RéglagesUne <img> par diapositive (texture de rouleau en SVG, même origine), data-wds-colors gardé comme repli, data-wds-autoplay="false" et bouton pause masqué puisqu'il n'y a pas de lecture automatique, --wds-ratio: 250/186, pastilles blanches. Dans la capture, la démo clique les vraies pastilles toutes les 1,5 s.
La vignette « À la une » d'un journal en ligne — WebGL Displacement Slideshow exemple 3

③ La vignette « À la une » d'un journal en ligne

QuandSur la page d'accueil de Quotidelle, une petite vignette de 140 × 82 px en haut de la colonne de gauche fait défiler les trois grands reportages de la semaine, légende en dessous ; à droite, la liste des articles par rubrique. Pas de flèches : les pastilles et le bouton pause suffisent à cette taille.
PourquoiEn petit, l'effet attire l'œil vers la rubrique Reportages sans voler la page : la déformation ne dure que 0,9 s et la vignette reste sage le reste du temps.
Réglages--wds-ratio: 140/82, flèches masquées, bouton pause de 22 px et pastilles de 6 px (CSS de la scène), data-wds-interval="1600" pour la capture (4000 à 6000 ms en usage réel). La légende suit la diapositive active.

Comment ça marche

Les visuels sont les diapositives .wds-slide écrites dans le HTML : soit une <img> (vos photos), soit deux couleurs dans data-wds-colors="#6d8bff,#5cffd8" (un dégradé diagonal). Au chargement, le script copie chaque image dans une texture WebGL, recadrée comme object-fit: cover pour remplir le cadre 16/9, et dessine la première sur le canvas .wds-canvas qui recouvre les diapositives.

À chaque changement, un shader lit un bruit de valeur (grille 4 × 4 lissée) et s'en sert pour décaler les deux images en sens inverse, l'ancienne de plus en plus, la nouvelle de moins en moins, pendant qu'elles se fondent (smoothstep entre 25 % et 75 % de l'animation). La transition dure 0,9 s, calculée au temps écoulé. Le canvas suit la taille de son cadre (ResizeObserver, densité d'écran plafonnée à 2) et se redessine aussitôt après un redimensionnement.

La lecture automatique avance toutes les 3,5 s (data-wds-interval) et s'arrête au survol de la souris, quand le focus clavier est dedans, hors écran, ou avec le bouton pause en haut à droite. Flèches ‹ ›, pastilles (une par diapositive, créées par le script) et glisser horizontal changent de diapositive. Sans WebGL, avec une image d'un autre domaine servie sans CORS, ou si le contexte WebGL est perdu, le canvas s'efface et les diapositives HTML passent de l'une à l'autre en fondu de 0,7 s.

Accessibilité

  • Pause : bouton nommé « Mettre en pause la lecture automatique » / « Reprendre la lecture automatique », plus arrêt au survol, au focus clavier et hors écran. data-wds-autoplay="false" désactive la lecture automatique (le bouton peut alors être masqué).
  • Texte lu : le canvas est aria-hidden ; ce sont les diapositives HTML qui sont lues, avec le texte alternatif de vos <img>. Région aria-roledescription="carrousel", diapositives role="group" « 2 sur 5 », les cachées en inert.
  • Pastilles : vrais boutons nommés d'après l'aria-label de leur diapositive, la pastille en cours porte aria-current="true". Flèches nommées « Précédent » / « Suivant ».
  • Mouvement réduit : sous prefers-reduced-motion: reduce, pas de lecture automatique au départ et pas de déformation : l'image change d'un coup. Tout reste pilotable.
  • Toucher : Pointer Events et touch-action: pan-y : un geste horizontal change d'image, la page défile verticalement.

Compatibilité navigateur

WebGL 1 (tous navigateurs depuis 2014), ResizeObserver, aspect-ratio et inert (Chrome 102, Firefox 112, Safari 15.5 d'après MDN). Mesuré dans Chromium 151, Firefox 153 et WebKit 26.5 (Playwright) : deux diaporamas dont le 2e piloté seul, 5 pastilles même avec le script collé deux fois, lecture qui avance sans survol et s'arrête au survol, image toujours dessinée après un redimensionnement, vraies images en <img>, mouvement réduit, 390 px, glisser au doigt (Chromium), 0 erreur. Repli fondu vérifié en forçant la perte du contexte WebGL.

Chrome 102+✓ Complet (mesuré)
Firefox 112+✓ Complet (mesuré)
Safari 15.5+✓ Complet (mesuré dans WebKit)
Edge 102+✓ Complet (moteur Chromium)
Mobile iOS 15.5+✓ Moteur WebKit, non vérifié sur appareil
Android Chrome 102+✓ Complet (toucher mesuré)

Sans WebGL ou avec une image d'un autre domaine sans CORS : fondu CSS entre les diapositives HTML, mêmes boutons. Sans JavaScript : la première diapositive reste affichée (une image ; une diapositive en couleurs reste sur le fond sombre).

Le code

Structure HTML à coller dans votre page (le CSS + JS sont inclus avec votre achat) :

index.html — structure
<div class="fx-0801-root">
  <div class="wds-scene" data-wds data-wds-interval="3500" role="region" aria-roledescription="carrousel" aria-label="…">
    <canvas class="wds-canvas" aria-hidden="true"></canvas>
    <div class="wds-slides" aria-live="off">
      <div class="wds-slide wds-on" role="group" aria-roledescription="diapositive" aria-label="1 sur 5"><img src="…" alt="…"></div>
      <div class="wds-slide" role="group" aria-roledescription="diapositive" aria-label="2 sur 5" data-wds-colors="#ff7eb6,#a777ff"></div>
      …
    </div>
    <button class="wds-btn wds-prev" type="button" aria-label="…" data-wds-prev>‹</button>
    <button class="wds-btn wds-next" type="button" aria-label="…" data-wds-next>›</button>
    <button class="wds-toggle" type="button" data-wds-toggle data-wds-label-pause="…" data-wds-label-play="…"><svg class="wds-icon-pause">…</svg><svg class="wds-icon-play">…</svg></button>
    <div class="wds-dots" data-wds-dots></div>
  </div>
</div>

Paiement unique, sans abonnement — le code est à toi pour toujours

Personnaliser

Options passées à l'API ou attributs data-* :

Option / propriétéDéfautEffet
Images (HTML — <img> dans .wds-slide) aucune Vos photos, recadrées pour remplir le cadre. Même domaine que la page, ou serveur qui envoie les en-têtes CORS (et crossorigin="anonymous" sur l'image) ; sinon le diaporama passe en fondu CSS.
Diapositive en couleurs (HTML — data-wds-colors) "#6d8bff,#5cffd8" … (5 dégradés) Deux couleurs séparées par une virgule : dégradé diagonal, sans image.
Intervalle (HTML — data-wds-interval sur [data-wds]) 3500 (ms) Temps entre deux changements automatiques ; 1500 ms au minimum.
Lecture automatique (HTML — data-wds-autoplay="false") active (sauf mouvement réduit) Désactive l'avance automatique : seules les flèches, les pastilles et le glisser changent l'image.
Proportions (CSS — --wds-ratio) 16 / 9 Format du cadre ; auto si vous lui donnez une hauteur (fond plein écran).
Libellés du bouton pause (HTML — data-wds-label-pause / data-wds-label-play) « Mettre en pause la lecture automatique » / « Reprendre la lecture automatique » Noms lus selon l'état, à traduire.
Pastille active (CSS — .wds-dot[aria-current="true"]) #5cffd8 Couleur de la pastille de l'image affichée.

FAQ

Le navigateur interdit de lire dans WebGL une image venue d'un autre domaine sans autorisation CORS. Hébergez les images sur le même domaine que la page, ou ajoutez crossorigin="anonymous" à la balise et l'en-tête Access-Control-Allow-Origin côté serveur. Le fondu est le repli prévu dans ce cas.
Autant que vous voulez : une pastille est créée par diapositive. Chaque image devient une texture en mémoire graphique (2048 px de côté au plus) : au-delà d'une dizaine de grandes photos, réduisez-les avant de les publier.
Pas tout seul : mettez votre texte dans chaque diapositive si vous utilisez le repli, ou écoutez le changement de la classe wds-on sur les .wds-slide (un MutationObserver suffit) pour mettre à jour un titre placé au-dessus.