/* ==========================================================
   Maryam — circular portfolio
   Palette extracted from shanesayers.com design tokens
   ========================================================== */

:root {
  --cream:      #fff8e7;
  --off-white:  #f5f1e8;
  --ink:        #0f1316;
  --charcoal:   #57564f;
  --washed-red: #bb4c4c;
  --terracotta: #d97d54;
  --orange:     #f26a2a;
  --azure:      #cfe0e4;
  --royal:      #455ce9;
  --olive:      #6b705c;

  --font-display: "Big Shoulders Display", sans-serif;
  --font-body: "Inter", sans-serif;

  --ease-soft: cubic-bezier(.33,1,.68,1);
}

* { box-sizing: border-box; margin: 0; padding: 0; }

html {
  scroll-behavior: auto;
  /* Reserve the scrollbar gutter symmetrically so the centered orbit lands on
     the true viewport centre, not half-a-scrollbar to the left. */
  scrollbar-gutter: stable both-edges;
  /* Clip horizontal overflow on the root — NOT on <body>. Using `clip` here
     (and never `overflow-x: hidden` on body) avoids the CSS rule that forces
     the other axis to `auto`, which would turn <body> into a scroll container
     and make `position: sticky` resolve against <body> instead of the viewport
     — the source of the browser- and full-screen-dependent off-centering. */
  overflow-x: clip;
}

body {
  background: var(--cream);
  color: var(--ink);
  font-family: var(--font-body);
  font-size: 16px;
  line-height: 1.6;
  /* No `overflow-x` here on purpose — see the note on <html>. Keeping body's
     overflow at `visible` lets `position: sticky` stick to the viewport. */
}

/* film grain */
body::after {
  content: "";
  position: fixed; inset: 0;
  pointer-events: none;
  z-index: 60;
  opacity: .05;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='160' height='160'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='2'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E");
}

button { font: inherit; color: inherit; background: none; border: none; cursor: pointer; }
button:focus-visible, a:focus-visible {
  outline: 2px solid var(--royal);
  outline-offset: 3px;
  border-radius: 4px;
}

.eyebrow {
  font-family: var(--font-body);
  font-size: 12px;
  font-weight: 600;
  letter-spacing: .22em;
  text-transform: uppercase;
  color: var(--washed-red);
  margin-bottom: 18px;
}

h2 {
  font-family: var(--font-display);
  font-weight: 700;
  font-size: clamp(44px, 7vw, 96px);
  line-height: .95;
  letter-spacing: .01em;
  text-transform: uppercase;
  margin-bottom: 24px;
}

/* ==========================================================
   Stage & driver
   ========================================================== */

.driver { position: relative; }

/* Sticky, not pinned: the browser keeps the stage glued to the viewport
   natively, so the orbit is always centered at any window size. */
.stage {
  position: sticky;
  top: 0;
  height: 100vh;
  height: 100svh;
  width: 100%;
  overflow: hidden;
}

.tilt {
  position: absolute; inset: 0;
  display: grid; place-items: center;
  perspective: 1200px;
}

.orbit {
  position: relative;
  width: 0; height: 0;
}

/* ==========================================================
   Circles
   ========================================================== */

.circle {
  position: absolute;
  left: 0; top: 0;
  border-radius: 50%;
  display: grid; place-items: center;
  transform: translate(-50%, -50%);
  will-change: transform, opacity;
}

/* soft blurred gradient body */
.mush {
  position: absolute; inset: -12%;
  border-radius: 50%;
  filter: blur(clamp(18px, 3vw, 42px)) saturate(1.1);
  background:
    radial-gradient(58% 58% at 34% 30%, var(--c-a, var(--orange)) 0%, transparent 68%),
    radial-gradient(70% 70% at 72% 66%, var(--c-b, var(--washed-red)) 0%, transparent 72%),
    radial-gradient(90% 90% at 50% 90%, var(--c-c, var(--azure)) 0%, transparent 75%),
    radial-gradient(100% 100% at 50% 50%, var(--c-d, var(--terracotta)) 0%, transparent 100%);
  opacity: .9;
}

.circle::before {           /* dimensional rim + inner glow */
  content: "";
  position: absolute; inset: 0;
  border-radius: 50%;
  box-shadow:
    inset 0 18px 60px rgba(255, 248, 231, .55),
    inset 0 -30px 70px rgba(15, 19, 22, .12),
    0 30px 90px rgba(15, 19, 22, .14);
}

.circle--hero { width: 62vmin; height: 62vmin; z-index: 10; }
.circle--hero .mush { --c-a: var(--orange); --c-b: var(--washed-red); --c-c: var(--azure); --c-d: var(--terracotta); }

.circle--sat { width: 30vmin; height: 30vmin; opacity: 0; cursor: pointer; }
/* tighter glow on the small orbit circles so they overlap less */
.circle--sat .mush { inset: -3%; filter: blur(clamp(10px, 1.7vw, 24px)) saturate(1.1); }
.circle--projects .mush { --c-a: var(--azure); --c-b: var(--royal); --c-c: var(--cream); --c-d: var(--azure); }
.circle--about  .mush { --c-a: var(--terracotta); --c-b: var(--azure);      --c-c: var(--cream);   --c-d: var(--royal); }
.circle--why     .mush { --c-a: var(--olive);      --c-b: var(--terracotta); --c-c: var(--azure);   --c-d: var(--olive); }
.circle--vibe    .mush { --c-a: var(--azure);      --c-b: var(--royal);      --c-c: var(--cream);   --c-d: var(--azure); }
.circle--contact .mush { --c-a: var(--royal);      --c-b: var(--azure);      --c-c: var(--cream);   --c-d: var(--royal); }

/* satellite label = tag text + icon below it, sized relative to the 30vmin
   circle so it scales cleanly on every screen */
.circle__label {
  position: relative; z-index: 2;
  display: flex; flex-direction: column; align-items: center; gap: .55em;
}
.circle__tag {
  font-family: var(--font-display);
  font-weight: 600;
  font-size: clamp(18px, 2.6vmin, 30px);
  letter-spacing: .14em;
  text-transform: uppercase;
  color: var(--ink);
  mix-blend-mode: multiply;
}
.circle__icon {
  width: 9vmin;               /* ~30% of the 30vmin circle; scales with its transform */
  height: auto;
  object-fit: contain;
  pointer-events: none;
  filter: drop-shadow(0 3px 8px rgba(15, 19, 22, .12));
}

/* hero content inside the seed circle — layers stacked in one centred cell */
.circle__core {
  position: relative; z-index: 2;
  width: 100%; height: 100%;
  display: grid; place-items: center;
  text-align: center;
  padding: 5%;
}
.hero-intro, .hero-id { grid-area: 1 / 1; }   /* overlap: sentence ⇄ identity */

.hero-intro {
  max-width: 96%;
  margin: 0 auto;
  font-family: var(--font-body);
  font-weight: 500;
  font-size: clamp(16px, 2.9vmin, 26px);
  line-height: 1.4;
  color: var(--charcoal);
}
/* each sentence on its own line (wraps only on very narrow screens) */
.hero-intro__line { display: block; min-height: 1.35em; text-wrap: balance; }
.hero-id { display: grid; gap: .28em; justify-items: center; }

/* red handwriting welcome line (typed on first scroll) */
.hero-welcome {
  /* text styles are the fallback for the reduced-motion static build */
  font-family: "Caveat", cursive;
  color: var(--washed-red);
  font-weight: 600;
  font-size: clamp(26px, 5.6vmin, 48px);
  line-height: 1.05;
  margin-top: .35em;
  min-height: .85em;                 /* reserve space so the id block doesn't jump */
}
/* SVG handwriting (engine build): one continuous path drawn stroke-first,
   left→right like a pen, then the ink fills in */
.hero-welcome .hw {
  display: block; margin: 0 auto;
  height: clamp(34px, 7vmin, 56px); width: auto;
  overflow: visible;
}
.hw__ink {
  fill: var(--washed-red);
  stroke: var(--washed-red);
  stroke-width: 2;                   /* viewBox units → ~1px rendered */
  stroke-linecap: round; stroke-linejoin: round;
}

/* typewriter caret while a line is typing */
.is-typing::after {
  content: "|";
  margin-left: .04em;
  font-weight: 400;
  animation: caret .8s steps(1) infinite;
}
@keyframes caret { 50% { opacity: 0; } }

.hl {
  display: block;
  color: var(--ink);
  line-height: 1.02;
}
/* display face, dominant — the name is the hero */
.hl--name {
  font-family: var(--font-display);
  font-weight: 800;
  text-transform: uppercase;
  font-size: clamp(46px, 11vmin, 104px);
  letter-spacing: .01em;
  margin-bottom: .06em;
}
.hl--name .ch { display: inline-block; will-change: transform, opacity; }
/* display face, secondary — the role */
.hl--role {
  font-family: var(--font-display);
  font-weight: 500;
  text-transform: uppercase;
  font-size: clamp(18px, 3.4vmin, 34px);
  letter-spacing: .12em;
  color: var(--charcoal);
}
/* body face, tertiary — the welcome line */
.hl--tag {
  font-family: var(--font-body);
  font-weight: 400;
  font-size: clamp(13px, 2vmin, 19px);
  letter-spacing: .01em;
  line-height: 1.4;
  color: var(--charcoal);
}
.hl--tag.hl--accent { color: var(--washed-red); font-weight: 500; }
/* waving "hello" icon standing in for the word "Hi" */
.hl--hello {
  display: inline-flex; align-items: flex-end; gap: .20em;
  font-size: clamp(15px, 2.4vmin, 22px);
}
/* two stacked layers on one canvas: only the hand rotates, so the speech
   bubble stays put while the hand actually waves from the wrist */
.hero-hello {
  position: relative;
  display: inline-block;
  height: clamp(30px, 18.4vmin, 146px);
  aspect-ratio: 286 / 293;      /* the source canvas both layers share */
  vertical-align: middle;
}
.hero-hello__bubble,
.hero-hello__hand {
  position: absolute; inset: 0;
  width: 100%; height: 100%;
  object-fit: contain;
}
.hero-hello__hand {
  transform-origin: 48% 97%;    /* the wrist */
  animation: handwave 2.9s var(--ease-soft) infinite;
  will-change: transform;
}
.hero-hello__bubble {
  transform-origin: 70% 90%;    /* the bubble's tail */
  animation: hellopop 2.9s var(--ease-soft) infinite;
}
/* swing back and forth, decaying, then rest before waving again */
@keyframes handwave {
  0%   { transform: rotate(0deg); }
  6%   { transform: rotate(-15deg); }
  14%  { transform: rotate(13deg); }
  22%  { transform: rotate(-12deg); }
  30%  { transform: rotate(10deg); }
  38%  { transform: rotate(-7deg); }
  46%  { transform: rotate(5deg); }
  54%, 100% { transform: rotate(0deg); }
}
@keyframes hellopop {
  0%   { transform: scale(1); }
  8%   { transform: scale(1.09); }
  22%  { transform: scale(1); }
  54%, 100% { transform: scale(1); }
}
@media (prefers-reduced-motion: reduce) {
  .hero-hello__hand, .hero-hello__bubble { animation: none; }
}

/* project visuals inside the Projects circle — soft-edged to match the other orbs */
.pvisual {
  position: absolute; inset: -3%;
  z-index: 1; border-radius: 50%; overflow: hidden;
  opacity: .92;
  filter: blur(clamp(9px, 1.6vw, 22px)) saturate(1.05);
  -webkit-mask: radial-gradient(circle at 50% 50%, #000 50%, transparent 72%);
  mask: radial-gradient(circle at 50% 50%, #000 50%, transparent 72%);
}
.pvisual__layer {
  position: absolute; inset: 0;
  opacity: 0;
  transition: opacity .6s var(--ease-soft);
}
.pvisual__layer.is-on { opacity: 1; }
.pvisual__layer[data-pv="noty"] {
  background:
    radial-gradient(50% 50% at 32% 28%, var(--azure) 0%, transparent 72%),
    radial-gradient(62% 62% at 74% 70%, var(--royal) 0%, transparent 74%),
    linear-gradient(160deg, var(--off-white), var(--azure));
}
.pvisual__layer[data-pv="vinnie"] {
  background:
    radial-gradient(52% 52% at 68% 26%, var(--orange) 0%, transparent 72%),
    radial-gradient(60% 60% at 28% 74%, var(--washed-red) 0%, transparent 74%),
    linear-gradient(200deg, var(--cream), var(--terracotta));
}
.pvisual__layer[data-pv="linko"] {
  background:
    radial-gradient(48% 48% at 30% 70%, var(--olive) 0%, transparent 72%),
    radial-gradient(56% 56% at 72% 30%, var(--terracotta) 0%, transparent 74%),
    linear-gradient(180deg, var(--off-white), var(--olive));
}
.pvisual__layer[data-pv="all"] {
  background:
    radial-gradient(48% 48% at 28% 30%, var(--terracotta) 0%, transparent 72%),
    radial-gradient(54% 54% at 74% 34%, var(--royal) 0%, transparent 72%),
    radial-gradient(60% 60% at 50% 82%, var(--olive) 0%, transparent 74%),
    linear-gradient(150deg, var(--off-white), var(--azure));
}

/* vibe-coding visuals: the SHELL is one permanent layer that never swaps, so
   the circle's colour is constant by construction. The per-project layers hold
   only a small inner accent — the crossfade touches nothing but that accent. */
.pvisual__layer--vbase {
  background:
    radial-gradient(50% 50% at 32% 30%, var(--azure) 0%, transparent 72%),
    radial-gradient(62% 62% at 74% 70%, var(--royal) 0%, transparent 74%),
    linear-gradient(160deg, var(--off-white), var(--azure));
}
.pvisual--vibe .pvisual__layer[data-vv] {
  background:
    radial-gradient(24% 24% at 50% 46%, var(--vv-accent, transparent) 0%, transparent 70%);
}
.pvisual--vibe .pvisual__layer[data-vv].is-on { opacity: .85; }
.pvisual__layer[data-vv="orbit"]    { --vv-accent: var(--orange); }
.pvisual__layer[data-vv="garden"]   { --vv-accent: var(--olive); }
.pvisual__layer[data-vv="synth"]    { --vv-accent: var(--royal); }
.pvisual__layer[data-vv="roulette"] { --vv-accent: var(--washed-red); }
.pvisual__layer[data-vv="mood"]     { --vv-accent: var(--terracotta); }

/* Screen-space showcase: crisp images tracking the active circle. Because it
   lives OUTSIDE the tilted/transform-scaled orbit, images stay perfectly
   straight, render at native resolution (no transform re-rastering), and can
   be sized per device without fighting the circle's zoom. */
.showcase {
  position: absolute; left: 0; top: 0;
  z-index: 18;                    /* under the panels (20): text always wins */
  pointer-events: none;
}
.showcase > img {
  position: absolute; left: 0; top: 0;
  transform: translate(-50%, -50%);
  /* --shw = free width beside the text column, measured live in JS */
  max-width: min(52vw, 940px, var(--shw, 940px));
  max-height: min(54vh, calc(100svh - 160px));  /* stay clear of the nav */
  object-fit: contain;
  opacity: 0;
  transition: opacity .5s var(--ease-soft);
  filter: drop-shadow(0 22px 44px rgba(15, 19, 22, .28));
}

/* ---------- device mockups with live video inlaid into the screens ---------- */
.showcase .mock {
  position: absolute; left: 0; top: 0;
  transform: translate(-50%, -50%);
  margin: 0; line-height: 0;
  opacity: 0;
  transition: opacity .5s var(--ease-soft);
  filter: drop-shadow(0 22px 44px rgba(15, 19, 22, .28));
}
.showcase .mock__base {
  display: block;
  max-width: min(52vw, 940px, var(--shw, 940px));
  max-height: min(54vh, calc(100svh - 160px));
  width: auto; height: auto;
}
.showcase .mock[data-key="noty"] .mock__base--vid,
.showcase .mock[data-key="linko"] .mock__base--vid,
.showcase .mock--vinnie .mock__base--vid {
  width: min(75vw, 1100px, var(--shw, 1100px)) !important;
  max-width: none !important;
  max-height: none !important; 
  height: auto !important;
  object-fit: contain !important; 
  border-radius: 10px;
  box-shadow: none !important;
  border: none !important;
  outline: none !important;
  aspect-ratio: 2876 / 2154;
}
.showcase .mock[data-key="noty"],
.showcase .mock[data-key="linko"],
.showcase .mock--vinnie {
  filter: none !important;
  box-shadow: none !important;
  border: none !important;
  background: none !important;
  background-color: transparent !important;
}
/* the video/image inlaid onto a device screen — positioned as % of the mockup
   so it scales flawlessly at every window size; transform is unit-less
   (rotate/skew/perspective) so it never drifts on resize */
.showcase .mock__ov {
  position: absolute;
  overflow: hidden;
  transform-origin: center center;
  backface-visibility: hidden;
}
.showcase .mock__ov > .mock__vid {
  display: block;
  width: 100%; height: 100%;
  object-fit: cover;
}

/* entrance reveal when a project becomes active (only while the projects
   section is actually live — otherwise the mock would flash in the corner
   on page load, before placeShowcase has positioned the showcase layer) */
.showcase[data-live="projects"] .mock.is-on { animation: mockIn .9s var(--ease-soft) both; }
@keyframes mockIn {
  0%   { opacity: 0; transform: translate(-50%, -50%) translateY(26px) scale(.92); }
  60%  { opacity: 1; }
  100% { opacity: 1; transform: translate(-50%, -50%) translateY(0) scale(1); }
}
.showcase img[data-sec="about"] {
  max-width: min(50vw, 700px, var(--shw, 700px));
  max-height: min(84vh, calc(100svh - 100px));
  border-radius: 10px;
}
.showcase img[data-sec="contact"] {
  max-width: min(30vw, 400px, var(--shw, 400px));
  max-height: min(56vh, calc(100svh - 160px));
  border-radius: 24px;
}
/* visible only while its section is held (and, for projects, selected) */
.showcase[data-live="projects"] .mock[data-sec="projects"].is-on,
.showcase[data-live="about"]   img[data-sec="about"],
.showcase[data-live="contact"]  img[data-sec="contact"] { opacity: 1; }

/* ---------- animated stat badges around the About photo ---------- */
.stat {
  --sscale: 1;                    /* set from JS: badge scales with the photo */
  position: absolute; left: 0; top: 0;
  transform: translate(-50%, -50%) scale(calc(var(--sscale) * .6));
  display: flex; flex-direction: column; align-items: center; gap: 1px;
  padding: 12px 20px;
  border-radius: 18px;
  background: linear-gradient(180deg, rgba(255, 255, 255, .78), rgba(255, 248, 231, .58));
  backdrop-filter: blur(14px) saturate(1.4);
  -webkit-backdrop-filter: blur(14px) saturate(1.4);
  border: 1px solid rgba(255, 255, 255, .65);
  box-shadow: 0 16px 40px rgba(15, 19, 22, .2), inset 0 1px 0 rgba(255, 255, 255, .85);
  opacity: 0;
  transition: opacity .5s var(--ease-soft), transform .5s var(--ease-soft);
  white-space: nowrap;
}
/* pop in (staggered) only while About is held, then bob gently */
.showcase[data-live="about"] .stat {
  opacity: 1;
  transform: translate(-50%, -50%) scale(var(--sscale));
  animation: statbob 5.5s var(--ease-soft) infinite;
}
/* no room beside the text: hide the image + badges rather than shrink to a sliver */
.showcase.is-cramped > img,
.showcase.is-cramped .mock,
.showcase.is-cramped .stat { opacity: 0 !important; pointer-events: none; }
.showcase[data-live="about"] .stat[data-stat="0"] { transition-delay: .15s; animation-delay: 0s; }
.showcase[data-live="about"] .stat[data-stat="1"] { transition-delay: .3s;  animation-delay: -1.8s; }
.showcase[data-live="about"] .stat[data-stat="2"] { transition-delay: .45s; animation-delay: -3.6s; }
@keyframes statbob {
  0%, 100% { margin-top: 0; }
  50% { margin-top: calc(-9px * var(--sscale)); }
}
.stat__num {
  font-family: var(--font-display);
  font-weight: 800;
  font-size: clamp(24px, 2.6vw, 36px);
  line-height: 1;
  color: var(--washed-red);
}
.stat__label {
  font-size: clamp(10px, 1vw, 12.5px);
  font-weight: 600;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--charcoal);
}

@media (max-width: 768px) {
  .showcase .mock[data-key="noty"] .mock__base--vid,
  .showcase .mock--vinnie .mock__base--vid { 
    width: 95vw !important; 
  }
}

/* ==========================================================
   Panels
   ========================================================== */

.panel {
  position: absolute; inset: 0;
  z-index: 20;
  padding: clamp(24px, 6vw, 96px);
  display: flex; flex-direction: column;
  /* `safe center` keeps the content centred when it fits, but pins it to the
     top (instead of clipping it) when it's taller than the window, so the
     overflow is actually reachable by scrolling */
  justify-content: safe center;
  max-width: 640px;
  opacity: 0;
  visibility: hidden;
  pointer-events: none;
  /* short windows: let the section's own content scroll. Scroll chains to the
     page at the end, so the journey still advances. */
  overflow-y: auto;
  scrollbar-width: thin;
  scrollbar-color: rgba(15, 19, 22, .25) transparent;
}
.panel::-webkit-scrollbar { width: 7px; }
.panel::-webkit-scrollbar-thumb { background: rgba(15, 19, 22, .25); border-radius: 999px; }
.panel::-webkit-scrollbar-track { background: transparent; }
.panel.is-live { pointer-events: auto; }
/* during a cinematic nav jump the outgoing text must vanish immediately —
   class-based so it never fights the timeline's own opacity tweens */
.panel.is-jumping { opacity: 0 !important; visibility: hidden !important; }

.panel__body { color: var(--charcoal); max-width: 46ch; }

.chips {
  list-style: none;
  display: flex; flex-wrap: wrap; gap: 10px;
  margin-top: 28px;
}
.chips li {
  font-size: 13px; font-weight: 500;
  padding: 8px 16px;
  border: 1px solid rgba(15, 19, 22, .25);
  border-radius: 999px;
  background: rgba(255, 248, 231, .55);
  backdrop-filter: blur(4px);
}

/* projects */
.panel--projects { max-width: none; pointer-events: none; }
.projects__left { max-width: 560px; display: flex; flex-direction: column; }

.plist { display: grid; gap: 4px; margin-bottom: 26px; }
.plist__item {
  display: flex; align-items: baseline; gap: 18px;
  font-family: var(--font-display);
  font-weight: 600;
  font-size: clamp(34px, 5vw, 68px);
  line-height: 1.08;
  text-transform: uppercase;
  letter-spacing: .02em;
  text-align: left;
  color: var(--ink);
  opacity: .35;
  transition: opacity .35s var(--ease-soft), transform .35s var(--ease-soft);
}
.plist__item:hover { opacity: .7; }
.plist__item.is-active { opacity: 1; transform: translateX(10px); }
.plist__num {
  font-family: var(--font-body);
  font-size: 12px; font-weight: 600;
  color: var(--washed-red);
}

.pcase { position: relative; min-height: clamp(160px, 30vh, 300px); }
.pcase__slide {
  position: absolute; inset: 0;
  opacity: 0;
  transform: translateY(10px);
  transition: opacity .45s var(--ease-soft), transform .45s var(--ease-soft);
  pointer-events: none;
}
.pcase__slide.is-on { opacity: 1; transform: none; pointer-events: auto; }
.pcase__blurb { color: var(--charcoal); max-width: 42ch; margin-bottom: 16px; }

.pcase__tags {
  font-size: 12px;
  color: var(--charcoal);
  margin-top: 4px;
  margin-bottom: 20px;
  opacity: 0.8;
}
/* کانتینر اصلی چارت - سایز را از ۸۰ به ۱۱۰ بزرگتر کردیم */
.chart-container {
  position: relative;
  width: 110px;
  height: 110px;
  display: grid;
  place-items: center;
  flex-shrink: 0;
}

/* رسم دایره با سی‌اس‌اس خالص */
.chart-circle {
  position: absolute;
  inset: 0;
  border-radius: 50%;
  background: conic-gradient(var(--cs-accent, #455ce9) 0% 70%, rgba(69, 92, 233, 0.15) 70% 100%);
  /* با تغییر عدد از ۷۰٪ به ۶۰٪، ضخامت خط دایره کاملاً کلفتر می‌شود */
  -webkit-mask: radial-gradient(circle, transparent 65%, black 67%);
  mask: radial-gradient(circle, transparent 65%, black 67%);
}

/* استایل متن درصد وسط چارت - سایز فونت هم متناسب با چارت بزرگتر شد */
.chart-text {
  font-family: var(--font-body), sans-serif;
  font-weight: 700;
  font-size: 24px;
  color: var(--ink, #0f1316);
  z-index: 1;
}

/* outline-only button (fills on hover) */
.pcase__open {
  display: inline-flex; align-items: center; gap: 10px;
  align-self: flex-start;
  font-weight: 600; font-size: 13px;
  color: var(--washed-red);
  letter-spacing: .06em;
  text-transform: uppercase;
  padding: 12px 22px;
  border: 1.5px solid var(--washed-red);
  border-radius: 999px;
  background: transparent;
  transition: background .3s, color .3s, transform .3s var(--ease-soft);
}
.pcase__open:hover { background: var(--washed-red); color: var(--cream); transform: translateY(-2px); }
.pcase__arrow { transition: transform .3s var(--ease-soft); }
.pcase__open:hover .pcase__arrow { transform: translateX(4px); }

/* All-projects overview: category filters + card grid */
.pcase__slide--all { transform: none; }
.pfilters { display: flex; flex-wrap: wrap; gap: 8px; margin-bottom: 16px; }
.pfilter {
  font-size: 11px; font-weight: 600;
  letter-spacing: .1em; text-transform: uppercase;
  padding: 7px 14px;
  border-radius: 999px;
  border: 1px solid rgba(15, 19, 22, .22);
  color: var(--charcoal);
  background: rgba(255, 248, 231, .5);
  transition: color .25s, background .25s, border-color .25s;
}
.pfilter:hover { color: var(--ink); }
.pfilter.is-on { background: var(--washed-red); border-color: var(--washed-red); color: var(--cream); }

.pgrid {
  display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 10px;
  /* the grid outgrew the viewport: bound it and scroll inside instead */
  max-height: min(36vh, 360px);
  overflow-y: auto;
  overscroll-behavior: contain;
  padding-right: 8px;
  padding-bottom: 28px;    /* breathing room under the last card */
}
.pgrid::-webkit-scrollbar { width: 6px; }
.pgrid::-webkit-scrollbar-thumb { background: rgba(15, 19, 22, .25); border-radius: 999px; }
.pgrid::-webkit-scrollbar-track { background: transparent; }
.pcard {
  display: flex; flex-direction: column; gap: 4px; align-items: flex-start;
  text-align: left;
  padding: 14px 16px;
  border-radius: 16px;
  border: 1px solid rgba(15, 19, 22, .14);
  background: rgba(255, 248, 231, .55);
  backdrop-filter: blur(4px);
  transition: transform .3s var(--ease-soft), border-color .3s, opacity .3s;
}
.pcard:not(.is-soon) { cursor: pointer; }
.pcard:not(.is-soon):hover { transform: translateY(-3px); border-color: var(--washed-red); }
.pcard.is-soon { opacity: .55; }
.pcard.is-hidden { display: none; }
.pcard__name {
  font-family: var(--font-display);
  font-weight: 600; font-size: 20px;
  text-transform: uppercase; letter-spacing: .02em;
  color: var(--ink);
}
.pcard__tags { font-size: 11px; letter-spacing: .08em; text-transform: uppercase; color: var(--washed-red); }

/* why list */
.whylist { list-style: none; display: grid; gap: 18px; max-width: 52ch; margin-bottom: 32px; }
.whylist li { color: var(--charcoal); padding-left: 22px; position: relative; }
.whylist li::before {
  content: "";
  position: absolute; left: 0; top: .55em;
  width: 9px; height: 9px; border-radius: 50%;
  background: var(--washed-red);
}
.whylist strong { color: var(--ink); font-size: 1.15em; font-weight: 700; }

/* ==========================================================
   Why-me layout: reasons on the left, testimonials on the right
   ========================================================== */
.panel--why {
  max-width: none;
  flex-direction: row;
  /* `safe center` so the row never floats above the top of the viewport */
  align-items: safe center;
  gap: clamp(28px, 5vw, 80px);
}
.why__left { flex: 1 1 540px; max-width: 620px; min-width: 0; }
.why__left .whylist { margin-bottom: 0; }
/* a self-contained square-ish frame: everything (photos + card) lives INSIDE it,
   so nothing can drift out of the viewport when the window resizes */
.why__side {
  flex: 0 1 480px;
  width: min(100%, 480px);
  aspect-ratio: 1 / 0.94;
  position: relative;
  align-self: center;
  flex-shrink: 0;
}

/* soft fanned deck of past-work photos — pushed clear of the (smaller) card
   so each photo reads on its own instead of hiding underneath it */
/* NOTE: no z-index on the deck — it must not create a stacking context, or a
   hovered tile could never rise above the testimonial card. */
.why__deck { position: absolute; inset: 0; pointer-events: none; }
.why__tile {
  position: absolute;
  width: 46%; aspect-ratio: 4 / 3;
  object-fit: cover;
  border-radius: 14px;
  box-shadow: 0 16px 40px rgba(15, 19, 22, .18);
  opacity: .95;
  z-index: 1;
  pointer-events: auto;            /* hoverable, even though the deck isn't */
  cursor: pointer;
  animation: tilefloat 9s var(--ease-soft) infinite;
  animation-delay: calc(var(--i) * -2.2s);
  transition: transform .45s var(--ease-soft), box-shadow .45s var(--ease-soft),
              opacity .3s var(--ease-soft);
}
/* corners pinned INSIDE the frame — never negative, so they can't leave the view */
.why__tile:nth-child(1) { top: 0;    left: 0;  transform: rotate(-8deg); }
.why__tile:nth-child(2) { top: 0;    right: 0; transform: rotate(7deg); }
.why__tile:nth-child(3) { bottom: 0; left: 0;  transform: rotate(6deg); }
.why__tile:nth-child(4) { bottom: 0; right: 0; transform: rotate(-6deg); }
/* hover: straighten, scale up and come to the front (above the card) */
.why__tile:hover {
  transform: rotate(0deg) scale(1.3);
  z-index: 6;
  opacity: 1;
  box-shadow: 0 30px 70px rgba(15, 19, 22, .32);
  animation-play-state: paused;
}
@keyframes tilefloat {
  0%, 100% { translate: 0 0; }
  50% { translate: 0 -10px; }
}

/* the testimonial card carousel — compact, so the work photos stay visible */
.tmony {
  position: absolute;
  left: 50%; top: 50%;
  transform: translate(-50%, -50%);
  width: 62%;
  height: 60%;
  z-index: 2;
}
.tmony__card {
  position: absolute; inset: 0;
  display: flex; flex-direction: column; align-items: center; text-align: center;
  justify-content: center; gap: 12px;
  padding: clamp(18px, 2.2vw, 26px);
  border-radius: 22px;
  background: linear-gradient(180deg, rgba(255, 255, 255, .68), rgba(255, 248, 231, .5));
  backdrop-filter: blur(16px) saturate(1.35);
  -webkit-backdrop-filter: blur(16px) saturate(1.35);
  border: 1px solid rgba(255, 255, 255, .55);
  box-shadow: 0 22px 60px rgba(15, 19, 22, .18), inset 0 1px 0 rgba(255, 255, 255, .8);
  opacity: 0; transform: translateY(18px) scale(.97);
  transition: opacity .55s var(--ease-soft), transform .55s var(--ease-soft);
  pointer-events: none;
}
.tmony__card.is-on { opacity: 1; transform: none; pointer-events: auto; }
.tmony__pic {
  width: clamp(56px, 6.5vw, 72px); height: clamp(56px, 6.5vw, 72px);
  border-radius: 50%; object-fit: cover;
  border: 3px solid rgba(255, 255, 255, .8);
  box-shadow: 0 10px 24px rgba(15, 19, 22, .2);
}
.tmony__quote {
  font-family: var(--font-body);
  font-size: clamp(13.5px, 1.15vw, 16px);
  line-height: 1.5; color: var(--ink); font-style: italic;
  max-width: 30ch;
}
.tmony__quote::before {
  content: "\201C";
  font-family: "Georgia", serif;
  font-size: 3em;
  color: #000000;
  line-height: 0;
  vertical-align: -0.30em;
  margin-right: 0.1em;
}

.tmony__quote::after {
  content: "\201D";
  font-family: "Georgia", serif;
  font-size: 3em;
  color: #000000;
  line-height: 0;
  vertical-align: -0.60em;
  margin-left: 0.1em;
}
.tmony__by {
  font-family: var(--font-display);
  font-weight: 600; text-transform: uppercase; letter-spacing: .1em;
  font-size: clamp(14px, 1.4vw, 17px);
  color: var(--washed-red);
}
.tmony__dots {
  position: absolute; bottom: -30px; left: 50%; transform: translateX(-50%);
  display: flex; gap: 8px;
}
.tmony__dot {
  width: 8px; height: 8px; border-radius: 999px;
  background: rgba(15, 19, 22, .22);
  transition: width .3s var(--ease-soft), background .3s;
}
.tmony__dot.is-on { width: 22px; background: var(--washed-red); }

/* CTA */
.cta {
  display: inline-flex; flex-direction: column; align-items: flex-start; gap: 2px;
  margin-top: 20px;
  padding: 20px 34px;
  border-radius: 999px;
  background: var(--washed-red);
  color: var(--cream);
  text-decoration: none;
  font-weight: 600;
  letter-spacing: .05em;
  text-transform: uppercase;
  font-size: 15px;
  transition: transform .3s var(--ease-soft), background .3s;
  align-self: flex-start;
}
.cta:hover { background: var(--orange); transform: translateY(-3px); }
.cta__mail { font-size: 12px; font-weight: 400; text-transform: none; letter-spacing: .02em; opacity: .85; }
.cta--ghost {
  background: transparent;
  color: var(--ink);
  border: 1px solid rgba(15, 19, 22, .35);
}
.cta--ghost:hover { background: var(--off-white); color: var(--ink); }

/* outline-only CTA that fills with its own colour on hover (Download résumé) */
.cta--outline {
  background: transparent;
  color: var(--washed-red);
  border: 1.5px solid var(--washed-red);
}
.cta--outline:hover { background: var(--washed-red); color: var(--cream); transform: translateY(-3px); }

.ctarow { display: flex; flex-wrap: wrap; gap: 14px; align-items: center; }

/* contact: "Connect with me." + email + circular social buttons */
.connect {
  margin-top: 26px;
  font-family: var(--font-display);
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .04em;
  font-size: clamp(20px, 3vw, 30px);
  color: var(--ink);
}
.connect__mail {
  display: inline-block;
  width: max-content;
  margin-top: 4px;
  font-size: clamp(15px, 1.6vw, 18px);
  color: var(--charcoal);
  text-decoration: none;
  border-bottom: none;
}
.connect__mail:hover { border-bottom-color: var(--washed-red); }
.social { display: flex; gap: 14px; margin-top: 20px; }

/* compact circular icon button (LinkedIn / email) */
.iconbtn {
  width: 52px; height: 52px;
  border-radius: 50%;
  display: grid; place-items: center;
  background: var(--ink);
  color: var(--cream);
  transition: background .3s, transform .3s var(--ease-soft);
}
.iconbtn:hover { background: var(--washed-red); transform: translateY(-3px); }

/* the vibe list is a touch smaller — five titles need the vertical room */
.plist--vibe .plist__item { font-size: clamp(24px, 3.4vw, 44px); }
.pcase--vibe { min-height: clamp(90px, 16vh, 160px); }

/* scroll hint */
.scrollhint {
  position: absolute;
  bottom: 34px; left: 50%;
  transform: translateX(-50%);
  z-index: 21;
  opacity: 0;                     /* revealed by JS ~1s after the hero settles */
  font-size: 11px;
  letter-spacing: .3em;
  text-transform: uppercase;
  color: var(--charcoal);
  display: flex; flex-direction: column; align-items: center; gap: 10px;
}
.scrollhint__line {
  width: 1px; height: 42px;
  background: linear-gradient(var(--washed-red), transparent);
  animation: drip 1.8s var(--ease-soft) infinite;
}
@keyframes drip {
  0% { transform: scaleY(0); transform-origin: top; }
  55% { transform: scaleY(1); transform-origin: top; }
  56% { transform-origin: bottom; }
  100% { transform: scaleY(0); transform-origin: bottom; }
}

/* ==========================================================
   Bottom-left typing mascot + rising brand-logo bubbles
   ========================================================== */
.typer {
  position: absolute;
  left: clamp(8px, 2.5vw, 40px);
  bottom: clamp(4px, 2vh, 26px);
  z-index: 17;                 /* above the circles, below the panels (20) */
  width: clamp(120px, 15vw, 200px);
  aspect-ratio: 794 / 722;
  pointer-events: none;
  opacity: 0;
  transform: translateY(14px);
  transition: opacity .55s var(--ease-soft), transform .55s var(--ease-soft);
}
.typer.is-on { opacity: 1; transform: none; }
.typer__laptop, .typer__char {
  position: absolute; inset: 0;
  width: 100%; height: 100%;
  object-fit: contain;
}
/* only the character taps; the laptop stays put. Pivot high (near the shoulder)
   so rotating swings the finger tip sideways to reach different keys, while the
   vertical dip is the actual key press. */
.typer__char {
  transform-origin: 46% 6%;
  animation: typetap 2s ease-in-out infinite;
  will-change: transform;
}
@keyframes typetap {
  0%   { transform: rotate(0deg)    translateY(0); }
  8%   { transform: rotate(-5deg)   translateY(3.6%); }   /* press a left key   */
  16%  { transform: rotate(-5deg)   translateY(0); }
  28%  { transform: rotate(3.5deg)  translateY(3.6%); }   /* press a right key  */
  36%  { transform: rotate(3.5deg)  translateY(0); }
  48%  { transform: rotate(-2deg)   translateY(3.6%); }   /* press centre-left  */
  56%  { transform: rotate(-2deg)   translateY(0); }
  68%  { transform: rotate(6deg)    translateY(3.6%); }   /* reach a far-right key */
  76%  { transform: rotate(6deg)    translateY(0); }
  88%  { transform: rotate(0.5deg)  translateY(3.6%); }   /* press centre       */
  96%  { transform: rotate(0.5deg)  translateY(0); }
  100% { transform: rotate(0deg)    translateY(0); }
}

.bubbles {
  position: absolute; inset: 0;
  z-index: 16;
  pointer-events: none;
  overflow: hidden;
  opacity: 0;
  transition: opacity .55s var(--ease-soft);
}
.bubbles.is-on { opacity: 1; }
/* a real transparent soap bubble: see-through interior, a thin bright film
   rim, a crisp specular highlight, and a faint iridescent sheen */
.bubble {
  position: absolute;
  left: 0; bottom: 0;
  width: clamp(42px, 4.4vw, 60px);
  aspect-ratio: 1;
  border-radius: 50%;
  display: grid; place-items: center;
  background:
    /* crisp specular highlight (top-left) */
    radial-gradient(circle at 30% 24%, rgba(255,255,255,.95) 0%, rgba(255,255,255,.5) 5%, rgba(255,255,255,0) 15%),
    /* small secondary sparkle */
    radial-gradient(circle at 66% 40%, rgba(255,255,255,.55) 0%, rgba(255,255,255,0) 6%),
    /* the thin film rim — interior stays fully transparent */
    radial-gradient(circle at 50% 50%, rgba(255,255,255,0) 74%, rgba(255,255,255,.5) 90%, rgba(255,255,255,.12) 100%);
  border: 1px solid rgba(255,255,255,.4);
  box-shadow:
    inset 0 0 12px rgba(255,255,255,.22),
    inset -5px -7px 12px rgba(120,150,255,.10),   /* cool refraction on the far edge */
    0 4px 12px rgba(15,19,22,.07);                 /* barely-there ground shadow */
  /* refract whatever floats behind the bubble */
  backdrop-filter: blur(1.2px) saturate(1.2) brightness(1.04);
  -webkit-backdrop-filter: blur(1.2px) saturate(1.2) brightness(1.04);
  will-change: transform, opacity;
  animation: bubblerise var(--dur, 5s) linear forwards;
}
/* iridescent rainbow film, confined to a ring near the rim */
.bubble::before {
  content: "";
  position: absolute; inset: 0;
  border-radius: 50%;
  background: conic-gradient(from 210deg,
    rgba(255,120,180,.16), rgba(120,180,255,.16), rgba(150,255,210,.13),
    rgba(255,225,130,.13), rgba(255,120,180,.16));
  -webkit-mask: radial-gradient(circle, transparent 66%, #000 84%, transparent 100%);
  mask: radial-gradient(circle, transparent 66%, #000 84%, transparent 100%);
  mix-blend-mode: screen;
  pointer-events: none;
}
.bubble img {
  position: relative;
  width: 56%; height: 56%;
  object-fit: contain;
  border-radius: 6px;
  opacity: .9;                                     /* sits softly inside the film */
  filter: drop-shadow(0 1px 2px rgba(15,19,22,.18));
}
/* rise from the mascot up and off the top of the window, with a gentle sway */
@keyframes bubblerise {
  0%   { transform: translate(var(--x0), 0) scale(.4); opacity: 0; }
  10%  { transform: translate(var(--x0), -8vh) scale(1); opacity: 1; }
  50%  { transform: translate(calc(var(--x0) + var(--sway)), -50vh) scale(1); opacity: 1; }
  85%  { opacity: 1; }
  100% { transform: translate(var(--x0), calc(-100vh - 90px)) scale(.92); opacity: 0; }
}
@media (prefers-reduced-motion: reduce) {
  .typer__char { animation: none; }
  .bubbles { display: none; }
}

/* ==========================================================
   Sticky orb nav
   ========================================================== */

.orbnav {
  position: fixed;
  top: 18px; left: 50%;
  transform: translate(-50%, -140%);
  z-index: 50;
  display: flex; align-items: center; gap: 8px;
  padding: 8px 16px 8px 8px;
  border-radius: 999px;
  /* glossy glass: translucent gradient + saturated blur + top sheen highlight */
  background: linear-gradient(180deg, rgba(255, 255, 255, .55), rgba(255, 248, 231, .32));
  backdrop-filter: blur(18px) saturate(1.6);
  -webkit-backdrop-filter: blur(18px) saturate(1.6);
  border: 1px solid rgba(255, 255, 255, .55);
  box-shadow:
    0 14px 44px rgba(15, 19, 22, .16),
    inset 0 1px 0 rgba(255, 255, 255, .85),
    inset 0 -1px 0 rgba(15, 19, 22, .04);
  transition: transform .6s var(--ease-soft);
}
.orbnav.is-in { transform: translate(-50%, 0); }

.orbnav__seed { width: 34px; height: 34px; display: grid; place-items: center; }
.orbnav__seed span {
  width: 26px; height: 26px; border-radius: 50%;
  display: grid; place-items: center;
  background: radial-gradient(circle at 32% 30%, var(--orange), var(--washed-red) 75%);
  box-shadow: 0 4px 12px rgba(187, 76, 76, .5);
  transition: transform .3s var(--ease-soft);
}
.orbnav__seed img {
  width: 72%; height: 72%;
  object-fit: contain;      /* white mark reads on the warm gradient dot */
}
.orbnav__seed:hover span { transform: scale(1.2); }

/* hamburger (shown only on narrow windows — see media query below) */
.orbnav__burger {
  display: none;
  width: 34px; height: 34px;
  place-items: center; align-content: center;
  gap: 4px; padding: 7px;
  border-radius: 10px;
}
.orbnav__burger span {
  display: block; width: 18px; height: 2px; border-radius: 2px;
  background: var(--ink);
  transition: transform .3s var(--ease-soft), opacity .25s;
}
.orbnav.is-open .orbnav__burger span:nth-child(1) { transform: translateY(6px) rotate(45deg); }
.orbnav.is-open .orbnav__burger span:nth-child(2) { opacity: 0; }
.orbnav.is-open .orbnav__burger span:nth-child(3) { transform: translateY(-6px) rotate(-45deg); }

.orbnav ul { list-style: none; display: flex; gap: 2px; }
.orbnav ul button {
  white-space: nowrap;
  font-size: 12px; font-weight: 600;
  letter-spacing: .08em;
  text-transform: uppercase;
  padding: 8px 12px;
  border-radius: 999px;
  color: var(--charcoal);
  transition: color .25s, background .25s;
}
.orbnav ul button:hover { color: var(--ink); background: rgba(15, 19, 22, .06); }
.orbnav ul button.is-here { color: var(--cream); background: var(--washed-red); }

/* ==========================================================
   Circular reveal + case study
   ========================================================== */

/* The cover that hides one page being exchanged for another.
   Navigation (home / archive / about / every close button) uses the site's own
   paper, fading — no colour, nothing spreading. A CASE STUDY is the exception:
   it wipes in its own colour, so the project announces itself. */
.reveal {
  position: fixed; inset: 0;
  z-index: 200;                 /* above every overlay */
  background: var(--hm-bg, #FBFBFB);
  opacity: 0;
  pointer-events: none;
}
/* the same tint the project's card wears — defined once, in home.css */
.reveal[data-theme="noty"]   { background: var(--tint-noty); }
.reveal[data-theme="vinnie"] { background: var(--tint-vinnie); }
.reveal[data-theme="linko"]  { background: var(--tint-linko); }

.study {
  position: fixed; inset: 0;
  /* above the archive (95) and its popup (120) — a study opened from the
     archive lays over it, so closing the study reveals the archive again */
  z-index: 140;
  overflow-y: auto;
  -webkit-overflow-scrolling: touch;
  /* keep ALL scroll input inside the modal — the page behind stays locked and
     never chains/jumps to another section when the case study reaches its end */
  overscroll-behavior: contain;
  padding: clamp(24px, 8vw, 120px);
  /* per-project theme tokens (overridden by [data-theme]); default = warm */
  --cs-accent: var(--washed-red);
  --cs-num: var(--royal);
  --cs-chip: var(--azure);
  --cs-tint: 217, 125, 84;
  background:
    radial-gradient(60% 50% at 50% 108%, rgba(217, 125, 84, .10), transparent 72%),
    var(--off-white);
}
.study[hidden] { display: none; }

/* case study takes on the colour of the project it belongs to — the page
   backdrop shifts to soft branded "mush" gradients, and accents recolour to
   match, so opening a project feels like stepping into its own world */
.study[data-theme="noty"] {
  --cs-accent: var(--royal);
  --cs-num: var(--royal);
  --cs-chip: #dbe6fb;
  --cs-tint: 69, 92, 233;
  background:
    radial-gradient(52% 42% at 16% 10%, rgba(69, 92, 233, .14), transparent 70%),
    radial-gradient(62% 55% at 90% 20%, rgba(207, 224, 228, .60), transparent 72%),
    radial-gradient(85% 70% at 50% 110%, rgba(69, 92, 233, .09), transparent 72%),
    #f2f6fc;
}
.study[data-theme="vinnie"] {
  --cs-accent: var(--washed-red);
  --cs-num: var(--washed-red);
  --cs-chip: #f0ddca;
  --cs-tint: 217, 125, 84;
  background:
    radial-gradient(52% 42% at 15% 9%, rgba(242, 106, 42, .14), transparent 70%),
    radial-gradient(62% 55% at 90% 22%, rgba(217, 125, 84, .22), transparent 72%),
    radial-gradient(85% 70% at 50% 110%, rgba(187, 76, 76, .11), transparent 72%),
    #faf3ea;
}
.study[data-theme="linko"] {
  --cs-accent: var(--olive);
  --cs-num: var(--olive);
  --cs-chip: #e1e8d5;
  --cs-tint: 107, 112, 92;
  background:
    radial-gradient(52% 42% at 15% 9%, rgba(107, 112, 92, .16), transparent 70%),
    radial-gradient(62% 55% at 90% 22%, rgba(207, 224, 228, .50), transparent 72%),
    radial-gradient(85% 70% at 50% 110%, rgba(107, 112, 92, .08), transparent 72%),
    #f4f6ee;
}

/* the site's one close treatment: white with a hairline, inverting to ink on
   hover — the same button as the archive's and the About page's */
.study__close {
  position: fixed;
  top: 24px; right: 24px;
  width: 52px; height: 52px;
  border-radius: 50%;
  border: 1.4px solid var(--hm-line);
  background: #fff;
  color: var(--hm-ink);
  font-size: 16px;
  display: grid; place-items: center;
  transition: background .25s var(--ease-soft), color .25s var(--ease-soft),
              transform .35s var(--ease-soft);
}
.study__close:hover { background: var(--hm-ink); color: #fff; transform: rotate(90deg); }

.study__doc { max-width: 68ch; margin: 0 auto; display: none; }
.study__doc.is-open { display: block; }
.study__doc h2 { color: var(--ink); }
.study__doc h3 {
  font-family: var(--font-display);
  font-size: 24px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: .06em;
  color: var(--washed-red);
  margin: 36px 0 8px;
}
.study__doc p { color: var(--charcoal); }

/* ---------- rich case-study layout ---------- */
/* the doc grows with the monitor — media, grids and stat rows use the full
   width; only running text is capped (at a readable ~78ch measure) */
.study__doc.cs { max-width: min(1360px, 94vw); }
.study__doc.cs p { font-size: clamp(15px, 1.7vw, 17px); line-height: 1.65; max-width: 78ch; }
.study__doc.cs .cs__hmw p,
.study__doc.cs .cs__stat span,
.study__doc.cs .cs__insight p,
.study__doc.cs .cs__feature p,
.study__doc.cs .cs__tagbig { max-width: none; }
.cs__hero { margin-bottom: 40px; }
.cs__title {
  font-family: var(--font-display);
  font-size: clamp(46px, 9vw, 88px);
  line-height: .95; margin: 6px 0 10px; color: var(--ink);
}
.cs__tagline {
  font-size: clamp(18px, 2.4vw, 24px) !important;
  color: var(--cs-accent) !important; font-weight: 500;
}
.cs__meta {
  list-style: none; padding: 0; margin: 22px 0 0;
  display: flex; flex-wrap: wrap; gap: 14px 40px;
}
.cs__meta li { display: flex; flex-direction: column; font-size: 15px; color: var(--ink); font-weight: 600; }
.cs__meta span {
  font-size: 11px; letter-spacing: .14em; text-transform: uppercase;
  color: var(--olive); font-weight: 700; margin-bottom: 3px;
}
.cs__block { margin-top: 54px; }
.cs__block h3 {
  font-family: var(--font-display);
  font-size: clamp(24px, 3.2vw, 32px); font-weight: 600;
  text-transform: uppercase; letter-spacing: .05em;
  color: var(--cs-accent); margin: 0 0 18px;
}
.cs__block h4 { font-size: 16px; color: var(--ink); margin: 0 0 6px; font-weight: 700; }
.cs__sub {
  font-size: 12px !important; letter-spacing: .12em; text-transform: uppercase;
  color: var(--olive) !important; font-weight: 700; margin: 26px 0 12px !important;
}
/* responsive 16:9 video */
.cs__video {
  position: relative; aspect-ratio: 16 / 9; margin: 8px 0 4px;
  border-radius: 16px; overflow: hidden; background: transparent !important;
  box-shadow: 0 24px 60px rgba(15, 19, 22, .22);
  transform: translateZ(0);
  backface-visibility: hidden;
}
.cs__video iframe {
  position: absolute;
  top: -1.5%;
  left: -1.5%;
  width: 103%;
  height: 103%;
  border: 0;
  background: transparent !important;
}
/* callout / lead statement */
.cs__callout {
  font-size: clamp(18px, 2.3vw, 22px) !important; line-height: 1.5 !important;
  color: var(--ink) !important; font-weight: 600;
  border-left: 4px solid var(--cs-accent);
  padding: 4px 0 4px 20px; margin: 0 0 16px !important;
}
/* HMW dark panel */
.cs__hmw {
  display: flex; gap: 22px; align-items: center; flex-wrap: wrap;
  background: var(--ink); color: var(--cream);
  border-radius: 18px; padding: 26px 30px; margin-top: 26px;
}
.cs__hmw span {
  font-family: var(--font-display); font-size: 30px; font-weight: 700;
  letter-spacing: .04em; color: var(--terracotta); flex: none;
}
.cs__hmw p { color: var(--cream) !important; margin: 0; font-weight: 500; }
/* stat cards — compact number + label rows on a clean themed surface
   (no dead vertical space, number and label read as one unit) */
.cs__stats { display: flex; flex-wrap: wrap; gap: 12px; margin: 24px 0; }
.cs__stat {
  flex: 1 1 210px;
  display: flex; align-items: center; gap: 14px;
  background: rgba(255, 255, 255, .72);
  border: 1px solid rgba(var(--cs-tint), .22);
  /* border-left: 4px solid rgba(var(--cs-tint), .9); */
  border-radius: 14px;
  padding: 14px 16px;
  box-shadow: 0 8px 22px rgba(var(--cs-tint), .10);
}
.cs__stat b {
  font-family: var(--font-display);
  font-size: clamp(26px, 3.6vw, 38px);
  line-height: .95; color: var(--cs-num);
  flex: none; letter-spacing: .01em;
}
.cs__stat span { font-size: 13px; color: var(--charcoal); line-height: 1.35; }
.cs__stat--accent b { color: var(--cs-accent); }
.cs__stat--grow { flex-grow: 2; }
/* unit suffixes ("/100") and before-values ("50%") sit quiet next to the number */
.cs__stat b small {
  font-size: .48em; font-weight: 400; color: var(--charcoal);
  letter-spacing: 0;
}
.cs__stat .cs__rise { font-style: normal; font-size: .55em; color: var(--cs-accent); }
.cs__num--warm { color: var(--orange) !important; }
/* insight grid */
.cs__grid { display: grid; grid-template-columns: 1fr 1fr; gap: 16px; margin: 22px 0; }
.cs__insight {
  border-left: 3px solid rgba(var(--cs-tint), .9);
  background: rgba(var(--cs-tint), .07);
  border-radius: 0 12px 12px 0; padding: 16px 18px;
}
.cs__insight p { color: var(--charcoal); margin: 0; }
/* need / voice chips */
.cs__chips { display: flex; flex-wrap: wrap; gap: 10px; }
.cs__chip {
  background: var(--cs-chip); color: var(--ink);
  border-radius: 999px; padding: 10px 18px; font-size: 14px; font-weight: 500;
}
.cs__quote {
  font-style: italic; color: var(--ink) !important;
  border-left: 3px solid rgba(var(--cs-tint), .9); padding-left: 18px; margin: 24px 0 !important;
}
/* feature list */
.cs__features { display: grid; grid-template-columns: 1fr 1fr; gap: 22px 28px; }
.cs__feature h4 { color: var(--cs-accent); font-size: 17px; }
.cs__feature p { margin: 0; }
/* images */
.cs__img {
  display: block; width: 100%; height: auto; border-radius: 16px;
  margin: 26px 0; box-shadow: none; background: transparent !important;
}
.cs__tagbig {
  font-family: var(--font-display) !important;
  font-size: clamp(26px, 4vw, 40px) !important; line-height: 1.15 !important;
  text-align: center; color: var(--ink) !important; font-weight: 600;
  margin-top: 34px !important;
}
@media (max-width: 620px) {
  .cs__grid, .cs__features { grid-template-columns: 1fr; }
}

/* Box-haye bozorg-e radif-e avval (har kodom nimeye safe ro migiran minus jaye +) */
.cs__stats .cs__stat--big {
  flex: 1 1 calc(50% - 40px);
}

/* Alamate mosbat dar vasat */
.cs__stat-plus {
  flex: 0 0 auto;
  font-family: var(--font-display);
  font-size: clamp(24px, 4vw, 36px);
  font-weight: 700;
  color: var(--royal);
  align-self: center;
  padding: 0 4px;
}

/* Box-haye koochak-e radif-e dovvom (har kodom 1/3 safe ro migiran) */
.cs__stats .cs__stat--small {
  flex: 1 1 calc(33.33% - 12px);
  text-align: center;
}

/* Estayl-dehi be matnhaye dakhale kadr-ha tebgh-e aks */
.cs__stat-tag {
  display: block;
  font-size: 13px;
  color: var(--charcoal);
  margin-bottom: 6px;
}
.cs__stat-main {
  font-size: 18px;
  color: var(--ink);
  display: flex;
  align-items: baseline;
  gap: 8px;
}
.cs__stat-desc {
  font-size: 13px !important;
  line-height: 1.4 !important;
  color: var(--charcoal);
  margin: 8px 0 0 !important;
}

/* Responsive baraye mobile: hame miyan zir-e ham */
@media (max-width: 768px) {
  .cs__stats .cs__stat--big,
  .cs__stats .cs__stat--small {
    flex: 1 1 100%;
  }
  .cs__stat-plus {
    width: 100%;
    text-align: center;
    padding: 8px 0;
  }
}


.star-rating {
  position: relative;
  display: inline-block;
  font-size: 18px;
  line-height: 1;
  letter-spacing: 2px; 
  margin-top: 4px;
  user-select: none;
}


.star-rating__bg {
  color: #7d8ea4; 
}


.star-rating__fill {
  position: absolute;
  top: 0;
  left: 0;
  color: #ffb800; 
  overflow: hidden;
  white-space: nowrap;
}

/* ==========================================================
   Cursor
   ========================================================== */

.cursor { position: fixed; inset: 0; z-index: 100; pointer-events: none; display: none; }
.cursor__dot {
  position: absolute;
  width: 7px; height: 7px;
  border-radius: 50%;
  background: var(--ink);
  transform: translate(-50%, -50%);
}
.cursor__ring {
  position: absolute;
  width: 34px; height: 34px;
  border-radius: 50%;
  border: 1.5px solid rgba(15, 19, 22, .45);
  transform: translate(-50%, -50%);
  transition: width .3s var(--ease-soft), height .3s var(--ease-soft), border-color .3s;
}
.cursor.is-hover .cursor__ring { width: 56px; height: 56px; border-color: var(--orange); }

@media (hover: hover) and (pointer: fine) {
  .cursor { display: block; }
}

/* ==========================================================
   Footer
   ========================================================== */

.footer {
  padding: 40px clamp(24px, 6vw, 96px);
  font-size: 13px;
  color: var(--charcoal);
  text-align: center;
}

/* ==========================================================
   Mobile
   ========================================================== */

/* Narrow desktop / tablet: not enough width for a photo beside the text, and the
   nav pills no longer fit — collapse the nav to a hamburger. */
@media (max-width: 900px) {
  .orbnav { padding: 8px 10px; }
  .orbnav__burger { display: grid; }
  .orbnav ul {
    display: none;
    position: absolute; top: calc(100% + 10px); right: 0;
    flex-direction: column; gap: 2px;
    min-width: 200px; padding: 10px;
    border-radius: 18px;
    background: linear-gradient(180deg, rgba(255, 255, 255, .78), rgba(255, 248, 231, .6));
    backdrop-filter: blur(18px) saturate(1.6);
    -webkit-backdrop-filter: blur(18px) saturate(1.6);
    border: 1px solid rgba(255, 255, 255, .6);
    box-shadow: 0 18px 50px rgba(15, 19, 22, .2);
  }
  .orbnav.is-open ul { display: flex; }
  .orbnav ul li { width: 100%; }
  .orbnav ul button { width: 100%; text-align: left; padding: 11px 13px; font-size: 12px; }
}
/* between phone and desktop there's no room for the side photo */
@media (min-width: 761px) and (max-width: 1000px) {
  .showcase img[data-sec="about"],
  .showcase img[data-sec="contact"],
  .showcase .stat { display: none; }
  .panel--about, .panel--contact { max-width: none; }
  .panel--why { flex-direction: column; gap: 24px; }
  .why__side { width: min(100%, 400px); margin: 0 auto; }
}
/* desktop: keep the text column proportional so the photo always has real room */
@media (min-width: 1001px) {
  .panel--about, .panel--contact { max-width: min(640px, 46vw); }
}

@media (max-width: 760px) {
  .panel { justify-content: safe flex-end; padding-bottom: 90px; max-width: none; }
  .panel--projects .projects__left, .panel--vibe .projects__left { max-width: none; }
  .plist__item { font-size: clamp(28px, 9vw, 44px); }
  .plist--vibe .plist__item { font-size: clamp(22px, 6.5vw, 32px); }
  .pgrid { grid-template-columns: 1fr; }
  .orbnav ul button { padding: 8px 7px; font-size: 10px; letter-spacing: .04em; }
  .pcase { min-height: 150px; }
  .scrollhint { bottom: 18px; }
  /* keep showcase images in the upper half, clear of the bottom-anchored text */
  .showcase > img, .showcase .mock__base { max-width: 84vw; max-height: 26vh; }
  .showcase .mock--vinnie .mock__base--vid { width: 84vw; max-height: none; }
  .showcase img[data-sec="about"] { max-width: 60vw; max-height: 30vh; }
  .showcase img[data-sec="contact"] { max-width: 46vw; max-height: 26vh; }

  /* About on phones is text-first: the long bio fills the screen, so the
     photo + stat badges (which would overlap it) step aside */
  .showcase img[data-sec="about"], .showcase .stat { display: none; }

  /* Why-me: stack the testimonial above the reasons — keep the work photos,
     they stay inside the frame so they can't drift off-screen */
  .panel--why { flex-direction: column; justify-content: safe flex-end; gap: 20px; }
  .why__left { flex: none; max-width: none; }
  .why__side { flex: none; width: min(100%, 340px); margin: 0 auto; order: -1; }
  .why__tile { width: 44%; }
  .tmony { min-height: clamp(240px, 40vh, 320px); }
  .circle__icon { width: 11vmin; }         /* a touch larger on small circles */
}

/* ==========================================================
   Reduced motion — static stacked fallback
   ========================================================== */

body.static .driver { height: auto !important; }
body.static .stage { position: static; height: auto; overflow: visible; }
body.static .tilt {
  position: relative;
  height: 90vh;
  perspective: none;
}
body.static .circle--sat, body.static .scrollhint { display: none; }
body.static .orbit {
  width: 100%; height: 100%;
  display: grid; place-items: center;
}
body.static .circle--hero {
  position: relative;
  left: auto; top: auto;
  transform: none;
  width: min(62vmin, 520px); height: min(62vmin, 520px);
}
body.static .panel {
  position: relative;
  opacity: 1;
  visibility: visible;
  pointer-events: auto;
  min-height: 70vh;
  margin: 0 auto;
  max-width: 720px;
}
body.static .orbnav { transform: translate(-50%, 0); }
body.static .panel--why { flex-direction: column; }
body.static .why__side { width: 100%; max-width: 440px; margin: 24px auto 0; }
body.static .why__deck { display: none; }
