/* card-3d — reusable 3D tilt + depth + flip card.
 *
 * Visual contract (DESIGN_SYSTEM.md §1):
 *  - No rounded corners.
 *  - No glassmorphism / backdrop-filter / soft halos.
 *  - Pixel art stays `image-rendering: pixelated` — we never apply
 *    blur to the card face. The shine layer's gradient does not
 *    soften the underlying image.
 *  - Respects prefers-reduced-motion.
 */

.card-3d {
  --card-3d-perspective: 900px;
  --card-3d-spring-ms: 150ms;
  position: relative;
  display: inline-block;
  perspective: var(--card-3d-perspective);
  transform-style: preserve-3d;
  cursor: pointer;
  outline: none;
  /* Outer container holds depth layers + shine; never tilts itself.
   *
   * IMPORTANT — isolation: isolate creates a new stacking context so
   * the shine layer's mix-blend-mode has the card's own opaque face
   * to blend against. Without it, Chrome blends against the page's
   * transparent backdrop and the screen-blend math produces pure
   * black halos around the cursor — exactly the artifact the
   * operator saw in Chromium ("pure black clipping on chrome ...
   * works on firefox"). Firefox composites blend modes differently
   * and never produced the black, which is why it slipped through.
   */
  isolation: isolate;
}

.card-3d:focus-visible {
  /* Sharp 1px outline matches DESIGN_SYSTEM border ethos. */
  outline: 1px solid #ffd6a0;
  outline-offset: 4px;
}

.card-3d-inner {
  position: relative;
  display: block;
  transform-style: preserve-3d;
  will-change: transform;
  transition: transform var(--card-3d-spring-ms) ease-out;
}

.card-3d [data-card-3d-face] {
  position: relative;
  display: block;
  backface-visibility: hidden;
  -webkit-backface-visibility: hidden;
  /* Pixel art preservation when the face is an <img>. */
}

.card-3d [data-card-3d-face] img,
.card-3d [data-card-3d-face] svg {
  image-rendering: pixelated;
  image-rendering: -moz-crisp-edges;
  image-rendering: crisp-edges;
  display: block;
  width: 100%;
  height: auto;
}

/* The back face is rotated 180° so it sits behind the front in 3D
 * space; flipping the inner wrapper by rotateY(180deg) reveals it.
 * `position: absolute` overlays it on the front while flat. */
.card-3d [data-card-3d-face="back"] {
  position: absolute;
  inset: 0;
  transform: rotateY(180deg);
}

/* ─── Depth parallax layers ──────────────────────────────────────── */

.card-3d-depth-layer {
  position: absolute;
  inset: 0;
  pointer-events: none;
  /* Inset and shift each layer back by a few pixels in 3D space; the
   * JS sets the actual translate3d. */
  border: 1px solid currentColor;
  color: rgba(255, 214, 160, 0.08);
  background: linear-gradient(
    180deg,
    rgba(255, 214, 160, 0.05),
    rgba(255, 214, 160, 0) 60%
  );
  transform: translate3d(0, 0, -6px);
  transition: transform var(--card-3d-spring-ms) ease-out;
}

.card-3d-depth-layer[data-depth-index="1"] {
  color: rgba(200, 125, 255, 0.06);
}
.card-3d-depth-layer[data-depth-index="2"] {
  color: rgba(245, 223, 136, 0.05);
}

/* ─── Shine / glint ────────────────────────────────────────────── */

.card-3d-shine {
  --shine-x: 50%;
  --shine-y: 50%;
  position: absolute;
  inset: 0;
  pointer-events: none;
  /* IMPORTANT: end stops must be `rgba(255,255,255,0)` not `transparent`.
   * `transparent` resolves to rgba(0,0,0,0) in CSS, so gradient
   * interpolation passes through dark grey on the way out — visible
   * as a black ring in Chromium under `mix-blend-mode: screen`. */
  background: radial-gradient(
    circle at var(--shine-x) var(--shine-y),
    rgba(255, 255, 255, 0.18) 0%,
    rgba(255, 255, 255, 0.08) 18%,
    rgba(255, 255, 255, 0) 38%
  );
  mix-blend-mode: screen;
  transition: background-position var(--card-3d-spring-ms) ease-out;
}

/* When the card is flipped, the shine should sit on the BACK face;
 * we move it inside the inner stack via a CSS rule rather than a
 * second JS layer. */
.card-3d-flipped .card-3d-shine {
  opacity: 0.65;
}

/* ─── Reduced motion ───────────────────────────────────────────── */

@media (prefers-reduced-motion: reduce) {
  .card-3d-inner,
  .card-3d-depth-layer,
  .card-3d-shine {
    transition: none !important;
  }
  .card-3d-inner {
    transform: none !important;
  }
}

/* ─── Live card showcase shell ────────────────────────────────── */

.live-card-showcase {
  display: grid;
  grid-template-columns: 1fr;
  align-items: center;
  justify-items: center;
  gap: 14px;
  padding: 0;
}

.live-card-showcase__card {
  width: min(430px, 78vw);
  max-width: 100%;
  aspect-ratio: 2.5 / 3.5;
  background: transparent;
  filter: drop-shadow(0 22px 34px rgba(44, 33, 22, 0.24));
  /* No border. The card SVG carries the back's variant frame; the
   * front is pure art. A CSS border around the showcase widget
   * re-introduces the "card pasted into a frame" feel that the
   * renderer was rebuilt to avoid. */
}

.live-card-showcase__face {
  width: 100%;
  height: 100%;
}

.live-card-showcase__face img,
.live-card-showcase__face svg {
  width: 100%;
  height: 100%;
}

.live-card-showcase__controls {
  display: flex;
  gap: 8px;
  flex-wrap: wrap;
  justify-content: center;
}

.live-card-showcase__btn {
  background: #ffffff;
  color: #201b16;
  border: 1px solid rgba(32, 27, 22, 0.18);
  padding: 8px 11px;
  font-family: "DM Sans", system-ui, sans-serif;
  font-size: 13px;
  font-weight: 800;
  letter-spacing: 0;
  cursor: pointer;
}

.live-card-showcase__btn:hover {
  background: #f5ead8;
}

.live-card-showcase__caption {
  font-family: "DM Sans", system-ui, sans-serif;
  font-size: 14px;
  letter-spacing: 0;
  color: #5e564d;
  text-align: center;
}

.live-card-showcase__caption strong {
  color: #201b16;
}

.live-card-showcase__caption span {
  display: block;
  margin-top: 2px;
}
