← Visual Library / Effects

Product variant swap

Same product, different colors — cycles between variants while the entire hero recolors. The previous variant lives as a corner thumbnail. Price, sizes, and copy never move.

Effects Captured
Use when — product pages where one item has multiple visual variants (colors, materials, finishes). The stationary surrounding UI gives visual continuity ("same product, different version"), and the dramatic full-page color change feels cinematic. Especially strong for fashion, accessories, and lifestyle products where color IS the choice.

Live demo

Watch the auto-cycle, or click any color dot at the bottom to jump to that variant.

Stand out
Without trying

Lightweight warmth, made to elevate every outfit. Designed for the moments you don't have to think about.

$149$199
Size
36 38 40
Auto-cycle:

How it works

Four variants are stacked absolutely on top of each other inside a .stage container. At any moment one variant has .is-active (centered, full opacity) and the just-departed one has .is-previous (scaled to ~16% of its original size, anchored at the bottom-right via transform-origin). The stage's background color is updated by JS to match the active variant. A floating thumbnail bar at the bottom lets the user jump between variants manually.

The surrounding UI (copy, price, sizes) sits in an .overlay layer with pointer-events: none on the wrapper and auto on individual children — so it stays visible above the variants but doesn't intercept clicks meant for the thumbnails.

The key CSS — variant states

.variant {
  position: absolute;
  inset: 0;
  opacity: 0;
  transform: scale(1);
  transform-origin: 86% 80%;   /* shrink anchor = bottom-right of stage */
  transition:
    opacity 0.55s ease,
    transform 0.85s cubic-bezier(0.4, 0, 0.2, 1);
}
.variant.is-active {
  opacity: 1;
}
.variant.is-previous {
  opacity: 0.95;
  transform: scale(0.16);     /* shrinks toward the anchor */
}

The JS — cycle + manual jump

const colors = ['#c0392b', '#bdc3c7', '#1f1f1f', '#e67e22'];
const variants = document.querySelectorAll('.variant');
const stage = document.getElementById('stage');
const thumbs = document.querySelectorAll('#thumbs button');
let active = 0, prev = null, timer = null, paused = false;

function setActive(next) {
  if (next === active) return;
  prev = active;
  active = next;
  variants.forEach((el, i) => {
    el.classList.toggle('is-active',   i === active);
    el.classList.toggle('is-previous', i === prev);
  });
  thumbs.forEach((b, i) => b.classList.toggle('is-active', i === active));
  stage.style.background = colors[active];
}

function advance() { setActive((active + 1) % variants.length); }
function schedule() { if (!paused) timer = setTimeout(() => { advance(); schedule(); }, 4000); }

thumbs.forEach((b, i) => b.addEventListener('click', () => {
  setActive(i);
  clearTimeout(timer); schedule();   // reset the cycle from this point
}));

setActive(0);
schedule();

Why it works as a pattern

The continuity trick. The stationary UI is what sells it. If the price and sizes moved with the variant, the user would read "different product" — but because they stay anchored, the eye reads "same product, new color." That's the whole game.

The corner thumbnail is doing two jobs. Visually, it's a receipt of where you just came from — so the transition makes intuitive sense (this color is replacing that one). Functionally, it shows you can come back, which makes the bottom thumbnail nav feel less like a hard reset.

Auto-cycle plus manual control. Auto-cycling hooks the eye on landing. The thumbnail nav respects the user once they engage. The auto-cycle resumes after a manual click so a curious visitor can still see the full range. Pause button on the demo so you can stop it for screenshots / code reading.

Variants worth considering

Scroll-driven instead of timed — pin the hero with position: sticky and advance the variant index based on scroll progress through the panel. Same look, replaces the timer with scroll position.

Real product photos instead of SVG — swap the SVG with <img> tags. Use the same dominant color for the bg as the photo's primary hue.

More variants — works for 3–6. Past 6 the corner thumbnails get crowded; switch to a color-swatch row below the price instead.

Subtle background pattern — instead of solid color, use a radial gradient or noise overlay matching the variant hue. Adds depth without breaking the cinematic feel.

Source: Jacket Masters demo at maroon-tapir-346920.hostingersite.com/fashion-puffer-jacket (user-uploaded screen recording, 2026-05-19).