Row of product cards built as a plain, fully editable Etch tree: section > container > header (h2, intro, live bag counter) > grid of "Tilt Product Card" component instances (duplicate, reorder or delete in Layers). Card props: name, category, url, price, compareAt, onSale + saleLabel, isNew, showCategory, showSwatches, buttonLabel, and up to three colour swatches (swatchNName, swatchNColor, swatchNImage; an empty swatch name hides that swatch and its photo). Choosing a swatch (hover previews, click or Enter commits) swaps the product photo with an iris that opens from the swatch you touched, updates the colour label, and keeps aria-pressed in sync. On fine pointers each card tilts toward the cursor in real 3D with a soft glare and a few px of photo parallax; tilt and glare are off on touch and under prefers-reduced-motion. Add to bag runs a short busy state, then a success state with a check, bumps the header bag counter, announces the result in a polite live region and dispatches a bubbling "etched:add-to-cart" CustomEvent ({ name, colour, price, url }) for store integrations. Options are data attributes on the section: data-theme (light|dark); data-surface (elevated|outline|flat) card surface; data-radius (s|m|l|xl) corner radius from ACSS radius tokens; data-columns (4|3|2) cards per row at wide container widths (1 column on phones, 2 on tablets); data-ratio (portrait|square) photo aspect ratio; data-tilt (true|false) pointer-driven 3D tilt, fine pointers only; data-intensity (max tilt in degrees, default 7); data-glare (true|false) specular glare that follows the pointer; data-swap (iris|fade) how the photo changes when a colour is chosen: an iris opening from the swatch or a crossfade; data-duration (ms of the colour swap, default 650); data-easing (smooth|spring|snappy) tilt return and swap easing; data-anim (rise|fade|none) entrance when the row scrolls into view; data-stagger (ms between cards on entrance, default 90); data-once (true|false) play the entrance only the first time; data-show-bag (true|false) the bag counter in the header.