/* ==========================================================================
   3D Content Block — the repeating signature component.
   CSS 3D transforms (perspective + translateZ) give real depth; JS
   (content-block-3d.js) adds mouse-tilt and GSAP ScrollTrigger reveal.
   Falls back to a flat, static styled card when reduced-motion is active
   or JS/WebGL is unavailable — see [data-3d-block] fallback rules below.
   ========================================================================== */

.block-grid {
  /* minmax(min(300px, 100%), 1fr) rather than a bare 300px floor: on a
     narrow phone (many common Android widths are ~360px, which after
     container padding leaves well under 300px available), a flat pixel
     floor forces the grid wider than the viewport — real, visible
     horizontal overflow. Wrapping the floor in min(...,100%) lets it drop
     below 300px once the container itself is narrower, so it always
     resolves to a clean single column instead of overflowing. */
  display: grid; grid-template-columns: repeat(auto-fit, minmax(min(300px, 100%), 1fr)); gap: var(--space-6);
  perspective: 1800px;
}
.block-grid--2 { grid-template-columns: repeat(auto-fit, minmax(min(360px, 100%), 1fr)); }

[data-3d-block] {
  position: relative;
  min-width: 0; /* grid/flex items default to min-width:auto, which lets a
    child's intrinsic content size (e.g. the before/after slider's large
    placeholder image) force this item — and the whole layout — wider than
    its track/container. Without this override that shows up as horizontal
    overflow specifically on narrow viewports. */
  transform-style: preserve-3d;
  will-change: transform;
  opacity: 0;
  transform: translateY(48px) translateZ(0) rotateX(6deg);
}
[data-3d-block].is-revealed {
  opacity: 1;
}

.content-block {
  /* display:flex (not the default inline for the <a>-tag variant used on
     treatment/blog cards) — without it, block-level children inside an
     inline element fragment into multiple disjoint boxes, each painting
     its own background/border/glow and producing a ghosted outline. */
  display: flex;
  flex-direction: column;
  position: relative;
  border-radius: var(--radius-lg);
  background: var(--gradient-card);
  padding: var(--space-7) var(--space-6) var(--space-6);
  box-shadow: var(--shadow-card);
  overflow: hidden;
  height: 100%;
  transform-style: preserve-3d;
  transition: box-shadow var(--transition-base);
}
.content-block::before {
  /* gradient-lit edge glow */
  content: '';
  position: absolute; inset: 0; padding: 1px; border-radius: inherit;
  background: var(--gradient-edge-glow);
  -webkit-mask: linear-gradient(#fff 0 0) content-box, linear-gradient(#fff 0 0);
  -webkit-mask-composite: xor;
  mask-composite: exclude;
  opacity: 0.7;
  pointer-events: none;
}
.content-block::after {
  /* soft ambient glow behind the block, follows gradient theme */
  content: '';
  position: absolute; width: 70%; height: 70%; top: -20%; right: -20%; border-radius: 50%;
  background: var(--gradient-edge-glow); filter: blur(50px); opacity: 0.35; z-index: -1; pointer-events: none;
}
/* Kept deliberately small: under the 1800px perspective, larger translateZ
   values make the perspective-projected content grow just enough to visibly
   misalign against the flat (untransformed) ::before edge-glow border,
   producing a ghosted double-outline. These values stay under the
   threshold where that seam becomes visible while still reading as layered. */
.content-block > * { transform: translateZ(10px); }
.content-block:hover { box-shadow: var(--shadow-lift); }

.content-block--dark { background: var(--gradient-card-dark); color: var(--color-ivory); }
.content-block--dark h3, .content-block--dark h4 { color: var(--color-white); }
.content-block--dark p { color: var(--color-taupe-light); }

.content-block__icon-frame {
  width: 100%; aspect-ratio: 4/3; border-radius: var(--radius-md); overflow: hidden; margin-bottom: var(--space-5);
  transform: translateZ(16px);
  box-shadow: 0 20px 40px -20px rgba(43,32,24,0.4);
}
.content-block__icon-frame img { width: 100%; height: 100%; object-fit: cover; }

.content-block__tag { transform: translateZ(14px); }
.content-block__price { transform: translateZ(12px); font-family: var(--font-serif); font-size: 1.3rem; margin-top: var(--space-4); }
.content-block__link {
  transform: translateZ(14px); display: inline-flex; align-items: center; gap: var(--space-2);
  font-weight: 600; font-size: 0.88rem; margin-top: var(--space-5);
}
.content-block__link .arrow { transition: transform var(--transition-fast); }
.content-block:hover .content-block__link .arrow { transform: translateX(4px); }

/* Reduced motion / no-JS fallback: flatten to a normal static card */
html.reduce-motion [data-3d-block],
.no-js [data-3d-block] {
  opacity: 1 !important;
  transform: none !important;
}
html.reduce-motion .content-block,
.no-js .content-block { transition: none; }
html.reduce-motion .content-block > *,
.no-js .content-block > * { transform: none !important; }

/* ----- Hero 3D scene container ----- */
.hero-3d-scene {
  position: absolute; inset: 0; z-index: 0;
}
.hero-3d-scene canvas { display: block; width: 100%; height: 100%; }
.hero-3d-fallback {
  position: absolute; inset: 0; background: var(--gradient-hero); z-index: 0;
}
.hero-3d-fallback::after {
  content: ''; position: absolute; inset: 0; background: var(--gradient-mesh); opacity: 0.6;
}

/* ----- Generic abstract 3D "moment" (About page etc.) ----- */
.moment-3d {
  position: relative; border-radius: var(--radius-xl); overflow: hidden; aspect-ratio: 1/1;
  background: var(--gradient-dark-radial); box-shadow: var(--shadow-lift);
}
.moment-3d canvas { position: absolute; inset: 0; width: 100%; height: 100%; }
.moment-3d__fallback { position: absolute; inset: 0; background: var(--gradient-dark-radial); }

/* ----- Parallax tilt-target used by content-block-3d.js ----- */
[data-tilt] { transition: transform 120ms ease-out; }

@media (prefers-reduced-motion: reduce) {
  [data-3d-block] { opacity: 1 !important; transform: none !important; }
  .content-block > * { transform: none !important; }
}
