/*
 * homepage.css — The Gentle Studio
 * Three-view homepage: side-scroll, vertical, grid
 */

html, body { height: 100%; overflow: hidden; }

/* ── Canvas ──────────────────────────────────────────────
 * .tgs-canvas is the project grid as a *box*: every rule below describes how
 * cards behave inside it and none of them care where that box is. The views
 * measure it with clientWidth/clientHeight and bind their scroll handlers to
 * it, so the same engine drives a full-page grid and one sitting in a layout
 * block.
 *
 * #canvas is only the page-level shell that pins that box to the viewport. */
.tgs-canvas {
  background: var(--color-bg);
  scrollbar-width: none;
  -webkit-overflow-scrolling: touch;
}
.tgs-canvas::-webkit-scrollbar { display: none; }

#canvas {
  position: fixed;
  top: 66px;
  left: 10px;
  right: 10px;
  bottom: 10px;
}

/* Inside a layout block the grid fills its container instead. */
.projects-block > .tgs-canvas {
  position: relative;
  width: 100%;
  height: 100%;
}

/* ── Floating View Toggle — right-middle ─────────────────── */
.view-toggle-panel {
  position: fixed;
  right: 24px;
  top: 50%;
  transform: translateY(-50%);
  z-index: 60;
  display: flex;
  flex-direction: column;
  background: var(--color-bg);
  border: 1px solid var(--color-muted);
  box-shadow: 0 4px 20px var(--veil-faint);
}
.view-toggle-panel .view-btn {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 40px;
  height: 40px;
  border: none;
  background: transparent;
  color: var(--color-muted);
  cursor: inherit;
  transition: color var(--duration-fast), background var(--duration-fast);
  padding: 0;
}
.view-toggle-panel .view-btn + .view-btn {
  border-top: 1px solid var(--color-faint);
}
.view-toggle-panel .view-btn:hover { color: var(--color-ink); }
.view-toggle-panel .view-btn:focus-visible { outline: 2px solid var(--color-ink); outline-offset: -2px; }
.view-toggle-panel .view-btn.active { color: var(--color-ink); background: var(--color-faint); }

/* ── Category Filter ─────────────────────────────────────────
 * Text in the middle of the nav, not a bar of its own. It used to float below
 * the nav in a bordered, shadowed box — a second piece of chrome competing
 * with the real one. The current category is marked by weight alone, so
 * nothing boxes the words in.
 *
 * A grid embedded in a page layout keeps its own host (.projects-filter, in
 * project.css) and never touches the nav — a block inside a page should not
 * rewrite the site's chrome. The tab styling below is shared, so both places
 * read the same. #catFilter is the third host, for a portfolio page with no
 * layout; it keeps its positioning and loses the box. */
#catFilter:empty { display: none; }
#catFilter {
  position: fixed;
  top: 88px;
  left: 50%;
  transform: translateX(-50%);
  z-index: 50;
  display: flex;
  white-space: nowrap;
}
.cat-tab {
  font-family: var(--font-mono);
  font-size: var(--font-size-xs);
  letter-spacing: var(--tracking-label);
  text-transform: uppercase;
  padding: 9px 14px;
  border: none;
  cursor: inherit;
  background: transparent;
  color: var(--color-muted);
  /* Reserve the bold width up front, so the row does not shift as the active
     item changes. */
  transition: color var(--duration-fast);
}
.cat-tab::after {
  content: attr(data-label);
  display: block;
  height: 0;
  overflow: hidden;
  visibility: hidden;
  font-weight: 700;
  pointer-events: none;
}
.cat-tab:hover  { color: var(--color-ink); }
.cat-tab:focus-visible { outline: 2px solid var(--color-ink); outline-offset: -2px; }
.cat-tab.active { color: var(--color-ink); font-weight: 700; }


/* ════════════════════════════════════════════════════════════
   PROJECT CARDS — shared styles across all views
════════════════════════════════════════════════════════════ */
.card {
  position: absolute;
  cursor: inherit;
  text-decoration: none;
  color: inherit;
  will-change: transform, opacity;
}

.card-inner {
  position: relative;
  overflow: hidden;
  background: var(--color-faint);
  border-radius: var(--radius);
}

.card-img {
  width: 100%; height: 100%; object-fit: cover; display: block;
  transition: transform var(--duration-slow) var(--ease-out), filter var(--duration-normal) ease;
  filter: saturate(0.85) brightness(0.96);
  will-change: transform;
}
.card:hover .card-img { transform: scale(1.04); filter: saturate(1) brightness(1); }

.card-video {
  width: 100%; height: 100%; object-fit: cover; display: block;
  filter: saturate(0.85) brightness(0.96);
  transition: filter var(--duration-normal) ease;
  pointer-events: none;
}
.card:hover .card-video { filter: saturate(1) brightness(1); }

.card-placeholder {
  width: 100%; height: 100%;
  background: var(--color-faint);
}

.card-caption {
  margin-top: 11px;
  display: flex;
  justify-content: space-between;
  align-items: baseline;
}
.card-caption-name {
}
.card-caption-id {
}


/* ════════════════════════════════════════════════════════════
   VIEW 1: SIDE-SCROLL
════════════════════════════════════════════════════════════ */
.tgs-canvas[data-view="side-scroll"] {
  overflow-x: auto;
  overflow-y: hidden;
}

.tgs-canvas[data-view="side-scroll"] .card {
  /* JS positions absolutely with parallax transform */
}

.tgs-canvas[data-view="side-scroll"] .card-caption {
  position: absolute;
  bottom: 0;
  left: 0;
  right: 0;
  margin: 0;
  pointer-events: none;
  background: linear-gradient(to top, var(--veil-strong) 0%, var(--veil-medium) 20%, var(--veil-soft) 45%, var(--veil-faint) 70%, transparent 100%);
  padding: 40px 20px 14px;
}
.tgs-canvas[data-view="side-scroll"] .card-caption-name,
.tgs-canvas[data-view="side-scroll"] .card-caption-id {
  color: var(--color-overlay);
}
.tgs-canvas[data-view="side-scroll"] .card-caption-id {
  color: var(--color-on-image);
}

/* Floating idle animation */
@keyframes cardFloat {
  0%, 100% { translate: 0 0; }
  25%      { translate: calc(var(--float-x, 4px)) calc(var(--float-y, -6px)); }
  50%      { translate: calc(var(--float-x, 4px) * -0.6) calc(var(--float-y, -6px) * 0.8); }
  75%      { translate: calc(var(--float-x, 4px) * 0.3) calc(var(--float-y, -6px) * -0.5); }
}

.tgs-canvas[data-view="side-scroll"] .card.floating {
  animation: cardFloat var(--float-dur, 6s) ease-in-out infinite;
  animation-delay: var(--float-delay, 0s);
}

/* Scroll reveal */
.tgs-canvas[data-view="side-scroll"] .card.scroll-hidden {
  opacity: 0;
  scale: 0.82;
  transition: opacity 0.6s cubic-bezier(0.16, 1, 0.3, 1),
              scale 0.7s cubic-bezier(0.16, 1, 0.3, 1);
}
.tgs-canvas[data-view="side-scroll"] .card.scroll-revealed {
  opacity: 1;
  scale: 1;
  transition: opacity 0.6s cubic-bezier(0.16, 1, 0.3, 1),
              scale 0.7s cubic-bezier(0.16, 1, 0.3, 1);
}


/* ════════════════════════════════════════════════════════════
   VIEW 2: VINYL STACK
════════════════════════════════════════════════════════════ */
.tgs-canvas[data-view="vertical"] {
  overflow: hidden;
}

.tgs-canvas[data-view="vertical"] .card {
  position: absolute;
  will-change: transform, opacity;
}

.tgs-canvas[data-view="vertical"] .card-inner {
  box-shadow: 0 8px 40px var(--veil-soft), 0 2px 8px var(--veil-faint);
  border-radius: 10px;
}

.tgs-canvas[data-view="vertical"] .card-caption {
  position: absolute;
  bottom: 0;
  left: 0;
  right: 0;
  margin: 0;
  opacity: 0;
  transition: opacity 0.4s ease;
  pointer-events: none;
  background: linear-gradient(to top, var(--veil-strong) 0%, var(--veil-medium) 20%, var(--veil-soft) 45%, var(--veil-faint) 70%, transparent 100%);
  padding: 40px 20px 14px;
  border-radius: 0 0 10px 10px;
}
.tgs-canvas[data-view="vertical"] .card.in-focus .card-caption {
  opacity: 1;
}
.tgs-canvas[data-view="vertical"] .card-caption-name,
.tgs-canvas[data-view="vertical"] .card-caption-id {
  color: var(--color-overlay);
}
.tgs-canvas[data-view="vertical"] .card-caption-id {
  color: var(--color-on-image);
}


/* ════════════════════════════════════════════════════════════
   VIEW 3: GRID
════════════════════════════════════════════════════════════ */
.tgs-canvas[data-view="grid"] {
  overflow-x: hidden;
  overflow-y: auto;
  display: grid;
  grid-template-columns: repeat(12, 1fr);
  grid-auto-flow: dense;
  gap: 2px;
  padding: 0;
}

.tgs-canvas[data-view="grid"] .card {
  position: relative;
  overflow: hidden;
}
/* Corner squares — bg-colored 10px squares at each corner tip */
.tgs-canvas[data-view="grid"] .card::before,
.tgs-canvas[data-view="grid"] .card::after,
.tgs-canvas[data-view="grid"] .card-inner::before,
.tgs-canvas[data-view="grid"] .card-inner::after {
  content: '';
  position: absolute;
  width: 10px;
  height: 10px;
  background: var(--color-bg);
  z-index: 2;
  pointer-events: none;
  opacity: 0;
  transition: opacity 0.5s ease;
}
.tgs-canvas[data-view="grid"] .card.grid-settled::before,
.tgs-canvas[data-view="grid"] .card.grid-settled::after,
.tgs-canvas[data-view="grid"] .card.grid-settled .card-inner::before,
.tgs-canvas[data-view="grid"] .card.grid-settled .card-inner::after {
  opacity: 1;
}
.tgs-canvas[data-view="grid"] .card::before        { top: 0; left: 0; }
.tgs-canvas[data-view="grid"] .card::after         { top: 0; right: 0; }
.tgs-canvas[data-view="grid"] .card-inner::before  { bottom: 0; left: 0; }
.tgs-canvas[data-view="grid"] .card-inner::after   { bottom: 0; right: 0; }
/* Row span matches column span, and layoutGrid sets grid-auto-rows to one
   column's width — that pairing is what makes a card square. JS writes both
   inline; these keep the static case honest. */
.tgs-canvas[data-view="grid"] .card[data-size="large"]  { grid-column: span 4; grid-row: span 4; }
.tgs-canvas[data-view="grid"] .card[data-size="medium"] { grid-column: span 3; grid-row: span 3; }
.tgs-canvas[data-view="grid"] .card[data-size="small"]  { grid-column: span 2; grid-row: span 2; }

.tgs-canvas[data-view="grid"] .card-inner {
  width: 100% !important;
  height: 100% !important;
  aspect-ratio: 1 / 1;
}

.tgs-canvas[data-view="grid"] .card-img,
.tgs-canvas[data-view="grid"] .card-video,
.tgs-canvas[data-view="grid"] .card-placeholder {
  position: absolute;
  inset: 0;
  width: 100%; height: 100%;
}

/* Caption as hover overlay in grid */
.tgs-canvas[data-view="grid"] .card-caption {
  position: absolute;
  inset: 0;
  margin: 0;
  display: flex;
  flex-direction: column;
  justify-content: flex-end;
  padding: 20px;
  background: linear-gradient(to top, var(--veil-strong) 0%, transparent 55%);
  opacity: 0;
  transition: opacity var(--duration-fast);
  pointer-events: none;
}
.tgs-canvas[data-view="grid"] .card:hover .card-caption { opacity: 1; }
.tgs-canvas[data-view="grid"] .card-caption-name,
.tgs-canvas[data-view="grid"] .card-caption-id {
  color: var(--color-overlay);
}
.tgs-canvas[data-view="grid"] .card-caption-name {
  font-size: 9px;
}
.tgs-canvas[data-view="grid"] .card-caption-id {
  font-size: 8px;
  color: var(--color-on-image);
  margin-top: 2px;
}


/* ════════════════════════════════════════════════════════════
   FIRST POPULATION ANIMATION
════════════════════════════════════════════════════════════ */
@keyframes cardPopulate {
  from {
    opacity: 0;
    transform: translate(var(--pop-x, 0px), var(--pop-y, 40px)) scale(var(--pop-scale, 0.85));
  }
  to {
    opacity: 1;
    transform: translate(0, 0) scale(1);
  }
}

.card.populating {
  animation: cardPopulate 0.7s var(--ease-out) forwards;
  animation-delay: var(--pop-delay, 0s);
  opacity: 0;
}


/* ════════════════════════════════════════════════════════════
   SCROLL HINT
════════════════════════════════════════════════════════════ */
#scroll-hint {
  position: fixed;
  bottom: 32px;
  left: 50%;
  transform: translateX(-50%);
  display: flex;
  align-items: center;
  gap: 14px;
  opacity: 0;
  transition: opacity 0.5s ease;
  z-index: 50;
  pointer-events: none;
}
#scroll-hint.visible { opacity: 1; }

.scroll-hint-line {
  width: 48px;
  height: 1px;
  background: var(--color-muted);
  position: relative;
  overflow: hidden;
}
.scroll-hint-line::after {
  content: '';
  position: absolute;
  left: -100%;
  top: 0;
  width: 100%;
  height: 100%;
  background: var(--color-ink);
  animation: scanline 2.4s ease-in-out infinite;
}
@keyframes scanline { 0% { left: -100%; } 100% { left: 100%; } }
