/* ============================================================
 * WC // UI KIT v2 — PORTFOLIO STYLE
 * Neonblade-inspired corner-cut neon-glow cards.
 * Single accent flow, big editorial type, breathing scroll.
 * ============================================================ */

/* ---- Page shell -------------------------------------------- */
html:has(body.wc2-portfolio),
body.wc2-portfolio {
  overflow-y: auto !important;
  overflow-x: hidden !important;
  height: auto !important;
  min-height: 100vh;
  scroll-behavior: smooth;
}
.wc2-portfolio {
  /* Cyber on display, readable mono on everything else */
  --wc-font-display: "Orbitron", "Archivo Black", sans-serif;
  --wc-font-mono: "JetBrains Mono", "Chakra Petch", monospace;
  background: var(--wc-bg);
  color: var(--wc-ink-1);
  font-family: var(--wc-font-mono);
  min-height: 100vh;
}
.wc2-portfolio::before {
  content: "";
  position: fixed; inset: 0; z-index: 1;
  background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='200' height='200'><filter id='n'><feTurbulence baseFrequency='0.9' numOctaves='2' seed='5'/><feColorMatrix values='0 0 0 0 0.92 0 0 0 0 0.85 0 0 0 0 1 0 0 0 0.45 0'/></filter><rect width='100%25' height='100%25' filter='url(%23n)' opacity='0.14'/></svg>");
  mix-blend-mode: overlay; opacity: 0.35; pointer-events: none;
}

/* Nav bar (top) */
.wc2-pnav {
  position: sticky; top: 0; z-index: 100;
  display: flex; align-items: center; justify-content: space-between;
  padding: 18px 40px;
  background: rgba(21, 10, 34, 0.85);
  border-bottom: 1px solid var(--wc-line);
  -webkit-backdrop-filter: blur(27px);
          backdrop-filter: blur(27px);
}
.wc2-pnav__brand {
  display: inline-flex; align-items: center; gap: 8px;
  font-family: var(--wc-font-display);
  font-size: 18px;
  letter-spacing: -0.01em;
  text-transform: uppercase;
  color: var(--wc-ink-1);
  text-decoration: none;
}
.wc2-pnav__brand .slash { color: var(--wc-orange); margin: 0 2px; }
.wc2-pnav__brand .cyber { color: var(--wc-lime); }

.wc2-pnav__links {
  display: flex; gap: 28px;
}
.wc2-pnav__links a {
  font: 700 10px var(--wc-font-mono);
  letter-spacing: 0.24em;
  text-transform: uppercase;
  color: var(--wc-ink-3);
  text-decoration: none;
  transition: color 200ms var(--wc-ease-out);
}
.wc2-pnav__links a:hover,
.wc2-pnav__links a.active {
  color: var(--wc-lime);
}

/* ---- Section primitives ----------------------------------- */
.wc2-psection {
  position: relative;
  z-index: 5;
  max-width: 1200px;
  margin: 0 auto;
  padding: 127px 40px;
}
.wc2-psection__head {
  display: flex; flex-direction: column; gap: 24px;
  margin-bottom: 64px;
}
.wc2-eyebrow {
  display: inline-flex; align-items: center; gap: 10px;
  font: 700 11px var(--wc-font-mono);
  letter-spacing: 0.28em;
  text-transform: uppercase;
  color: var(--wc-lime);
  width: max-content;
}
.wc2-eyebrow::before {
  content: "//";
  color: var(--wc-orange);
  margin-right: 2px;
}
.wc2-htitle {
  font-family: var(--wc-font-display);
  font-size: clamp(40px, 5.5vw, 84px);
  line-height: 0.95;
  letter-spacing: -0.02em;
  color: var(--wc-ink-1);
  margin: 0;
  max-width: 20ch;
  text-transform: uppercase;
}
.wc2-htitle .accent { color: var(--wc-lime); }
.wc2-htitle .orange { color: var(--wc-orange); }
.wc2-hsub {
  font: 500 16px/1.6 var(--wc-font-mono);
  color: var(--wc-ink-3);
  letter-spacing: 0.02em;
  max-width: 60ch;
  margin: 0;
}

/* ---- HERO -------------------------------------------------- */
.wc2-hero {
  position: relative;
  z-index: 5;
  min-height: calc(100vh - 64px);
  display: flex; flex-direction: column;
  align-items: center; justify-content: center;
  padding: 80px 40px;
  text-align: center;
  overflow: hidden;
}
.wc2-hero__corners span {
  position: absolute;
  width: 40px; height: 40px;
  border: 1.5px solid var(--wc-lime);
}
.wc2-hero__corners .tl { top: 24px; left: 24px;  border-right: 0; border-bottom: 0; }
.wc2-hero__corners .tr { top: 24px; right: 24px; border-left: 0;  border-bottom: 0; }
.wc2-hero__corners .bl { bottom: 24px; left: 24px;  border-right: 0; border-top: 0; }
.wc2-hero__corners .br { bottom: 24px; right: 24px; border-left: 0; border-top: 0; }

.wc2-hero__status {
  display: inline-flex; align-items: center; gap: 10px;
  padding: 7px 14px;
  background: rgba(184, 255, 56, 0.08);
  border: 1px solid rgba(184, 255, 56, 0.35);
  color: var(--wc-lime);
  font: 700 10px var(--wc-font-mono);
  letter-spacing: 0.24em;
  text-transform: uppercase;
  margin-bottom: 40px;
  --c: 6px;
  clip-path: polygon(var(--c) 0, 100% 0, 100% calc(100% - var(--c)), calc(100% - var(--c)) 100%, 0 100%, 0 var(--c));
}
.wc2-hero__status .pip {
  width: 7px; height: 7px;
  background: var(--wc-lime);
  border-radius: 50%;
  box-shadow: 0 0 10px var(--wc-lime);
  animation: wc2-blink 1.4s ease-in-out infinite;
}

.wc2-hero__title {
  font-family: var(--wc-font-display);
  font-size: clamp(64px, 11vw, 168px);
  line-height: 0.88;
  letter-spacing: -0.03em;
  color: var(--wc-ink-1);
  text-transform: uppercase;
  margin: 0;
}
.wc2-hero__title .slash { color: var(--wc-orange); margin: 0 -0.08em; }
.wc2-hero__title .cyber { color: var(--wc-lime); }

.wc2-hero__sub {
  font: 700 14px var(--wc-font-mono);
  letter-spacing: 0.3em;
  text-transform: uppercase;
  color: var(--wc-ink-3);
  margin-top: 28px;
}
.wc2-hero__tag {
  font: 500 17px/1.6 var(--wc-font-mono);
  color: var(--wc-ink-2);
  letter-spacing: 0.02em;
  max-width: 56ch;
  margin: 32px auto 0;
}
.wc2-hero__tag b { color: var(--wc-lime); font-weight: 700; }

.wc2-hero__ctas {
  display: inline-flex;
  gap: 16px;
  margin-top: 48px;
  flex-wrap: wrap;
  justify-content: center;
}
/* When CTAs are grouped together, force consistent width + center text */
.wc2-hero__ctas .wc2-ccbtn { min-width: 240px; justify-content: center; }
.wc2-hero__ctas .wc2-ccbtn.outline span { display: inline-block; text-align: center; width: 100%; }

/* ---- Corner-Cut Buttons (neonblade-style) ------------------ */
.wc2-ccbtn {
  position: relative;
  display: inline-flex; align-items: center; gap: 8px;
  /* Same dimensions for both filled + outline buttons so they line up cleanly. */
  padding: 14px 28px 18px;        /* extra bottom for the (shallower) tab area */
  font: 700 11px var(--wc-font-mono);
  letter-spacing: 0.24em;
  text-transform: uppercase;
  border: 0; cursor: pointer;
  text-decoration: none;
  color: var(--wc-bg);
  background: var(--wc-lime);
  /* slide-step-b card shape, button-scaled. Tab is WIDE (60%) but SHALLOW
     (step-d only 4px) so it reads like a subtle nub, not a deep dip.
     Outline variant flips the tab side to the right. */
  --slide-w: 8px;
  --slide-h: 8px;
  --step-x: 60%;
  --step-d: 4px;
  --step-slope-w: 6px;
  clip-path: polygon(
    0 var(--slide-h),
    var(--slide-w) 0,
    calc(100% - var(--slide-w)) 0,
    100% var(--slide-h),
    100% calc(100% - var(--step-d) - var(--slide-h)),
    calc(100% - var(--slide-w)) calc(100% - var(--step-d)),
    calc(var(--step-x) + var(--step-slope-w)) calc(100% - var(--step-d)),
    var(--step-x) 100%,
    var(--slide-w) 100%,
    0 calc(100% - var(--slide-h))
  );
  transition: filter 260ms var(--wc-ease-out), transform 260ms cubic-bezier(0.2, 0.85, 0.3, 1.1);
}
.wc2-ccbtn:hover {
  filter: brightness(1.15) drop-shadow(0 0 27px rgba(184, 255, 56, 0.55));
  transform: scale(1.05);
}
.wc2-ccbtn:active { transform: scale(1.03) translateY(1px); }

/* DANGER variant — orange fill instead of lime. Negative actions (Delete,
   Destroy, Discard). Shape + tab + scale-on-hover are unchanged; only the
   fill + glow color swap. */
.wc2-ccbtn.danger { background: var(--wc-orange); }
.wc2-ccbtn.danger:hover {
  filter: brightness(1.15) drop-shadow(0 0 27px rgba(255, 106, 0, 0.6));
}

/* Hover OUTLINE BEAM — same audio-wave glitch as cards, lower peak (30).
   Invisible by default (no outline shown); appears on hover.
   Color: PURPLE (brand support color) for the beam glow + stroke. */
.wc2-ccbtn__beam {
  position: absolute;
  inset: 0;
  pointer-events: none;
  z-index: 4;
  opacity: 0;
  overflow: visible;
  transition: opacity 200ms var(--wc-ease-out);
  filter: drop-shadow(0 0 3px var(--wc-purple))
          drop-shadow(0 0 6px color-mix(in srgb, var(--wc-purple) 50%, transparent));
}
.wc2-ccbtn:hover .wc2-ccbtn__beam { opacity: 1; }
.wc2-ccbtn__beam path {
  fill: none;
  stroke: var(--wc-purple);
  stroke-linecap: round;
  animation: wc2-beam-travel 2.4s linear infinite;
}
/* Both buttons (filled + outline) use the same PURPLE beam color for a
   coherent brand feel on hover. Purple reads well against both the lime
   body of the filled button and the dark bg behind the outline button. */
.wc2-ccbtn.outline {
  background: transparent;
  color: var(--wc-lime);
  padding: 0;
  /* FLIPPED polygon — tab on the RIGHT side (mirror of default). The element
     itself draws the lime fill clipped to this shape; ::before sits inside
     with a 1.5px inset polygon punched out, leaving a hollow border. */
  clip-path: polygon(
    0 var(--slide-h),
    var(--slide-w) 0,
    calc(100% - var(--slide-w)) 0,
    100% var(--slide-h),
    100% calc(100% - var(--slide-h)),
    calc(100% - var(--slide-w)) 100%,
    calc(100% - var(--step-x)) 100%,
    calc(100% - var(--step-x) - var(--step-slope-w)) calc(100% - var(--step-d)),
    var(--slide-w) calc(100% - var(--step-d)),
    0 calc(100% - var(--step-d) - var(--slide-h))
  );
  background: var(--wc-lime);   /* outline ring color */
}
/* The inner punch-out — same polygon inset by 1.5px on every edge using the
   per-axis approximation. Sits on top with the page bg color so only the
   outline ring is visible. On hover, inset grows so the ring thickens
   (same lime color as default). */
.wc2-ccbtn.outline::before {
  content: "";
  position: absolute;
  inset: 1.5px;
  background: var(--wc-bg);
  clip-path: polygon(
    0 var(--slide-h),
    var(--slide-w) 0,
    calc(100% - var(--slide-w)) 0,
    100% var(--slide-h),
    100% calc(100% - var(--slide-h)),
    calc(100% - var(--slide-w)) 100%,
    calc(100% - var(--step-x)) 100%,
    calc(100% - var(--step-x) - var(--step-slope-w)) calc(100% - var(--step-d)),
    var(--slide-w) calc(100% - var(--step-d)),
    0 calc(100% - var(--step-d) - var(--slide-h))
  );
  pointer-events: none;
  z-index: 0;
  transition: inset 240ms var(--wc-ease-out);
}
.wc2-ccbtn.outline:hover::before {
  inset: 4px;            /* ring grows from 1.5px → 4px on hover */
}
.wc2-ccbtn.outline span {
  position: relative;
  padding: 14px 28px 18px;       /* matches the filled button's padding */
  z-index: 1;
}
/* No background override on hover — keeps the lime ring at full saturation
   while the ::before inset grows. */

/* ============================================================
 *  WC v2 SECTION REVEAL RULE (locked 2026-06-07)
 *  Pattern established on the SPINE section. Every new section follows it.
 *
 *  Title:
 *    - <h2 class="wc2-htitle wc2-reveal--type" style="--reveal-delay: 0.45s;">
 *      Plain words <span class="accent">accent word</span>.
 *    - <span class="accent"> = Style Your Lipstick brush font, 1.28em, lime
 *    - Eyebrow above title: <span class="wc2-eyebrow wc2-reveal--type">
 *
 *  Body subtext:
 *    - <div class="wc2-pabout__body wc2-reveal--type-word" style="--reveal-delay: 1.6s;">
 *    - Word-by-word with system speed-ramps (fast bursts + brief pauses)
 *    - Subtle RGB chromatic (text-shadow lime+orange offset at ~20% opacity)
 *
 *  Sequence (--reveal-delay values, IO triggers at 25% in viewport):
 *    - Eyebrow:        0s
 *    - Title:         0.45s   (char-by-char typewriter with glitch chars)
 *    - Stagger row:   1.4s    (body + aside container, .wc2-stagger)
 *    - Body subtext:  1.6s    (word-burst typewriter)
 *    - Aside stack:   1.8s    (nested .wc2-stagger if multiple blocks)
 *    - Stats card:    2.6s    (.wc2-reveal--scale, slide-step-b shape)
 *    - Custom child override (e.g. type block):
 *      style="animation-delay: 2.8s !important;" on the stagger child
 *
 *  SFX (auto-fired by setupReveals, throttled 25ms global):
 *    - .wc2-reveal--type        → type.mp3 180ms @ 0.08
 *    - .wc2-reveal--type-word   → type.mp3 600ms @ 0.10
 *    - .wc2-reveal--scale       → open.mp3 260ms @ 0.12
 *    - .wc2-stagger             → assemble.mp3 per-child @ 0.07
 *
 *  Stagger flicker:
 *    - .wc2-stagger.in > * gets wc2-snap-flicker animation
 *    - Discrete-step opacity flicker (no fade-up translate)
 *    - .wc2-reveal--scale children get a FAST 0.18s flicker over the slow scale
 *
 *  Cards inside sections:
 *    - .wc2-ngcc.beam data-corner="slide-step" / "slide-step-b"
 *    - --slide-w/h: 14px, --step-d: 14px, --step-slope-w: 14px
 *    - See WC v2 DEFAULT CARD RULE below
 *
 *  DO NOT change without explicit user instruction.
 * ============================================================ */
/* ============================================================
 *  BOOT SEQUENCE — futuristic device powering up.
 *  Initial state: .wc2-booting hides every .boot-target. JS adds .boot-in
 *  at staggered moments with paired SFX so the UI assembles in front of you.
 * ============================================================ */
.wc2-booting .boot-target { opacity: 0 !important; visibility: hidden !important; }
.boot-target.boot-in { visibility: visible !important; opacity: 1 !important; }

/* (Scan-line sweeps removed — the warung pixel-sort + cyber flicker
   carry enough boot energy on their own.) */

/* Generic pop — used by nav links + hero status + CTAs */
.boot-target.boot-in {
  animation: wc2-boot-pop 0.65s cubic-bezier(0.2, 0.85, 0.3, 1.1) both;
}
@keyframes wc2-boot-pop {
  0%   { opacity: 0; transform: scale(0.94); }
  22%  { opacity: 1; transform: scale(1.03); }
  38%  { opacity: 0.5; transform: scale(1.01); }
  56%  { opacity: 1; transform: scale(1.02); }
  100% { opacity: 1; transform: scale(1); }
}

/* ---- Stage 1: WARUNG brush-stroke reveal — chromatic blur dissolve with
   stutter flicker. Pixel-sort canvas runs underneath; JS triggers a logo
   burst at the same moment so the sort intensity ramps up. No clip-path
   here — clipping cut the brush-stroke tails off. */
.wc-logo--hero .wc-logo__warung-wrap.boot-warung.boot-in {
  animation: wc2-boot-warung 1.0s cubic-bezier(0.22, 0.78, 0.28, 1) both;
}
@keyframes wc2-boot-warung {
  0%   { opacity: 0;   filter: blur(28px) saturate(2.4) hue-rotate(35deg); transform: translateX(-27px) scale(0.92); }
  18%  { opacity: 0.55; filter: blur(18px) saturate(2);   transform: translateX(-8px) scale(0.96); }
  30%  { opacity: 0.25; filter: blur(14px); transform: translateX(2px) scale(0.97); }
  44%  { opacity: 0.85; filter: blur(7px) hue-rotate(15deg); transform: translateX(-4px) scale(0.99); }
  58%  { opacity: 0.45; filter: blur(4px); transform: translateX(2px); }
  72%  { opacity: 1; filter: blur(1px); transform: translateX(0) scale(1.01); }
  86%  { opacity: 0.9; filter: blur(0); transform: scale(1); }
  100% { opacity: 1; filter: blur(0); transform: translateX(0) scale(1); }
}

/* ---- Stage 2: CYBER row flicker-in with flankers riding in from the
   sides. Stepped opacity for the hard-edged flicker, then settles. */
.wc-logo--hero .wc-logo__cyber-row.boot-cyber.boot-in {
  animation: wc2-boot-cyber-flicker 0.85s steps(10, end) both;
}
@keyframes wc2-boot-cyber-flicker {
  0%   { opacity: 0; }
  10%  { opacity: 0.85; }
  20%  { opacity: 0.05; }
  30%  { opacity: 1; }
  40%  { opacity: 0.35; }
  55%  { opacity: 1; }
  65%  { opacity: 0.55; }
  80%  { opacity: 1; }
  100% { opacity: 1; }
}

/* Flankers ride in from their outer sides + flicker once they land */
.wc-logo--hero .wc-logo__cyber-row.boot-cyber.boot-in .wc-logo__flanker--left {
  animation: wc2-boot-flank-l 0.5s cubic-bezier(0.2, 0.85, 0.3, 1.0) both;
  animation-delay: 0.35s;
}
.wc-logo--hero .wc-logo__cyber-row.boot-cyber.boot-in .wc-logo__flanker--right {
  animation: wc2-boot-flank-r 0.5s cubic-bezier(0.2, 0.85, 0.3, 1.0) both;
  animation-delay: 0.42s;
}
@keyframes wc2-boot-flank-l {
  0%   { opacity: 0; transform: translateY(-50%) translateX(-16px); }
  60%  { opacity: 1; transform: translateY(-50%) translateX(2px); }
  100% { opacity: 1; transform: translateY(-50%) translateX(0); }
}
@keyframes wc2-boot-flank-r {
  0%   { opacity: 0; transform: translateY(-50%) translateX(16px); }
  60%  { opacity: 1; transform: translateY(-50%) translateX(-2px); }
  100% { opacity: 1; transform: translateY(-50%) translateX(0); }
}

/* Nav logo — smaller, briefer */
.wc-logo--nav.boot-target.boot-in {
  animation: wc2-boot-nav-logo 0.7s cubic-bezier(0.2, 0.85, 0.3, 1.1) both;
}
@keyframes wc2-boot-nav-logo {
  0%   { opacity: 0; transform: scale(0.7); filter: blur(10px); }
  45%  { opacity: 1; transform: scale(1.06); filter: blur(0); }
  60%  { opacity: 0.5; transform: scale(1.02); }
  100% { opacity: 1; transform: scale(1); }
}

/* Nav bar slides down */
.wc2-pnav.boot-target.boot-in {
  animation: wc2-boot-nav 0.55s cubic-bezier(0.2, 0.85, 0.3, 1.05) both;
}
@keyframes wc2-boot-nav {
  0%   { opacity: 0; transform: translateY(-14px); }
  65%  { opacity: 1; transform: translateY(3px); }
  100% { opacity: 1; transform: translateY(0); }
}

/* Hero subtitle + tag fade up briefly */
.wc2-hero__sub.boot-target.boot-in,
.wc2-hero__tag.boot-target.boot-in {
  animation: wc2-boot-text 0.7s var(--wc-ease-out) both;
}
@keyframes wc2-boot-text {
  0%   { opacity: 0; transform: translateY(10px); filter: blur(4px); }
  100% { opacity: 1; transform: translateY(0);    filter: blur(0); }
}

/* Style Your Lipstick — Dafont, personal-use only (commercial licensing
   pending — designer: Cat.B). The current ACCENT face for highlighted
   words inside big titles. */
@font-face {
  font-family: "StyleYourLipstick";
  src: url("../fonts/Style%20your%20Lipstick.ttf") format("truetype");
  font-display: swap;
}
.wc2-htitle .accent {
  font-family: "StyleYourLipstick", var(--wc-font-display);
  letter-spacing: 0;
  font-size: 1.28em;            /* bigger than the surrounding display face */
  line-height: 0.85;            /* keeps the line height from blowing up */
  display: inline-block;
  vertical-align: -0.06em;      /* fine vertical re-baseline */
  margin: 0 -0.1em;             /* tight — pulls brush close to cyber */
}

/* Subtle RGB chromatic on body subtext — ~20% of the cyber logo's strength.
   Two offset text-shadows at low alpha: lime to the right, orange to the
   left, ink in the middle. Reads as a quiet signal-shift behind the text. */
.wc2-pabout__body {
  text-shadow:
    0.6px 0  0 rgba(184, 255, 56, 0.22),
   -0.6px 0  0 rgba(255, 106, 0, 0.18),
    0    0.4px 1.5px rgba(245, 236, 250, 0.08);
}

/* ============================================================
 *  WC v2 DEFAULT CARD RULE (locked 2026-06-06)
 *
 *  Every card uses .wc2-ngcc with the slide-step / slide-step-b shape:
 *    - All 4 corners are 45° slide cuts (--slide-w / --slide-h = 14px)
 *    - One edge carries a "tab" — a step with a 45° diagonal transition
 *      (--step-d = 14px, --step-slope-w = 14px, --step-x sets position)
 *    - data-corner="slide-step"   → tab on TOP edge
 *    - data-corner="slide-step-b" → tab on BOTTOM edge
 *
 *  Outline animation (`.beam` modifier):
 *    - 24s slow travel
 *    - 3–17% lit segment, varied per card via seed (no two identical)
 *    - 1px thin lime stroke, glow drop-shadow
 *    - Idle: discrete-step waveform glitches every 2–7s, peak ≈ 20
 *    - Hover: speeds to 1.5s travel, lit jumps to 28%, glitches every
 *      0.7–2s with peak ≈ 50, plus a one-shot intro burst at peak 120
 *
 *  Allowed variation per card:
 *    - Tab side (top or bottom)
 *    - Tab position (--step-x: 30% / 50% / 70% etc.)
 *    - Inline style on the card overrides any var, e.g. larger slides
 *
 *  DO NOT change the base shape primitives without coordinating with
 *  this comment — corner cuts, edge notches, and all-corner variants
 *  are kept as escape hatches but should not be the default.
 * ============================================================ */
/* ---- NEON-GLOW CORNER-CUT CARD (the signature) ------------ */
.wc2-ngcc {
  position: relative;
  padding: 1px;  /* reveals the frame border */
  --col-a: var(--wc-lime);
  --col-b: var(--wc-lime);  /* lime-only glow, no gradient mix */
  --c: 14px;          /* symmetric 45° corner cut size */
  --glow: 3px;   /* tinier */
  --blur: 2px;   /* tinier */
  /* No filter here — it creates a stacking context that clips the dedicated
     .wc2-ngcc__glow halo element. The ambient glow comes from that element. */
  transition: transform 280ms cubic-bezier(0.2, 0.85, 0.3, 1.1);
}
/* Hover LIFT — every card translates up SLIGHTLY on hover with ease.
   Subtle (-3px), not dramatic. Locked rule, applies to all .wc2-ngcc. */
.wc2-ngcc:hover {
  transform: translateY(-3px);
}
/* Polygons. OUTER (frame) is the full notched shape. INNER is the SAME shape
   shrunken inward by 1px on every edge — including the diagonal cuts (which
   shift by 1/sin(45°) ≈ 1.414 along their direction, so the perpendicular
   corner offset is ≈ 0.414px). Frame minus inner = a true 1px outline ring
   on ALL edges, including diagonal notches. Default: bottom-right cut. */
.wc2-ngcc,
.wc2-ngcc__frame,
.wc2-ngcc__inner {
  /* Outer (frame) */
  --clip-br: polygon(0 0, 100% 0, 100% calc(100% - var(--c)), calc(100% - var(--c)) 100%, 0 100%);
  --clip-tl: polygon(var(--c) 0, 100% 0, 100% 100%, 0 100%, 0 var(--c));
  --clip-tr: polygon(0 0, calc(100% - var(--c)) 0, 100% var(--c), 100% 100%, 0 100%);
  --clip-bl: polygon(0 0, 100% 0, 100% 100%, var(--c) 100%, 0 calc(100% - var(--c)));
  --clip-all: polygon(
    var(--c) 0, 100% 0,
    100% calc(100% - var(--c)), calc(100% - var(--c)) 100%,
    0 100%, 0 var(--c));
  /* Inner (1px inset; diagonal corners offset by 0.414px for true perpendicular inset) */
  --clip-br-in: polygon(
    1px 1px, calc(100% - 1px) 1px,
    calc(100% - 1px) calc(100% - var(--c) - 0.414px),
    calc(100% - var(--c) - 0.414px) calc(100% - 1px),
    1px calc(100% - 1px));
  --clip-tl-in: polygon(
    calc(var(--c) + 0.414px) 1px, calc(100% - 1px) 1px,
    calc(100% - 1px) calc(100% - 1px),
    1px calc(100% - 1px),
    1px calc(var(--c) + 0.414px));
  --clip-tr-in: polygon(
    1px 1px, calc(100% - var(--c) - 0.414px) 1px,
    calc(100% - 1px) calc(var(--c) + 0.414px),
    calc(100% - 1px) calc(100% - 1px),
    1px calc(100% - 1px));
  --clip-bl-in: polygon(
    1px 1px, calc(100% - 1px) 1px,
    calc(100% - 1px) calc(100% - 1px),
    calc(var(--c) + 0.414px) calc(100% - 1px),
    1px calc(100% - var(--c) - 0.414px));
  --clip-all-in: polygon(
    calc(var(--c) + 0.414px) 1px, calc(100% - 1px) 1px,
    calc(100% - 1px) calc(100% - var(--c) - 0.414px),
    calc(100% - var(--c) - 0.414px) calc(100% - 1px),
    1px calc(100% - 1px),
    1px calc(var(--c) + 0.414px));
}
.wc2-ngcc__frame, .wc2-ngcc__glow { clip-path: var(--clip-br); }
.wc2-ngcc__inner { clip-path: var(--clip-br-in); }
.wc2-ngcc[data-corner="tl"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="tl"] .wc2-ngcc__glow { clip-path: var(--clip-tl); }
.wc2-ngcc[data-corner="tl"] .wc2-ngcc__inner { clip-path: var(--clip-tl-in); }
.wc2-ngcc[data-corner="tr"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="tr"] .wc2-ngcc__glow { clip-path: var(--clip-tr); }
.wc2-ngcc[data-corner="tr"] .wc2-ngcc__inner { clip-path: var(--clip-tr-in); }
.wc2-ngcc[data-corner="bl"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="bl"] .wc2-ngcc__glow { clip-path: var(--clip-bl); }
.wc2-ngcc[data-corner="bl"] .wc2-ngcc__inner { clip-path: var(--clip-bl-in); }
.wc2-ngcc[data-corner="all"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="all"] .wc2-ngcc__glow { clip-path: var(--clip-all); }
.wc2-ngcc[data-corner="all"] .wc2-ngcc__inner { clip-path: var(--clip-all-in); }
/* No corner cut — clean rectangle. Used for "middle" cards in a grid so
   only the OUTSIDE corners of the grid show cuts. */
.wc2-ngcc[data-corner="none"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="none"] .wc2-ngcc__glow {
  clip-path: polygon(0 0, 100% 0, 100% 100%, 0 100%);
}
.wc2-ngcc[data-corner="none"] .wc2-ngcc__inner {
  clip-path: polygon(
    1px 1px, calc(100% - 1px) 1px,
    calc(100% - 1px) calc(100% - 1px),
    1px calc(100% - 1px));
}

/* ---- SLIDE corner variants — wider asymmetric diagonals than the default.
   Per-instance only; doesn't affect other corner-cut cards. Tunable via
   --slide-w (horizontal extent, default 30px) and --slide-h (vertical extent,
   default 10px). The +1px per-axis shift approximation is used for the inner
   inset (perpendicular distance ≈ 1.265px for 3:1 slopes — acceptable). */
.wc2-ngcc[data-corner="slide-tl"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="slide-tl"] .wc2-ngcc__glow {
  clip-path: polygon(
    var(--slide-w, 30px) 0, 100% 0,
    100% 100%, 0 100%,
    0 var(--slide-h, 10px));
}
.wc2-ngcc[data-corner="slide-tl"] .wc2-ngcc__inner {
  clip-path: polygon(
    calc(var(--slide-w, 30px) + 1px) 1px, calc(100% - 1px) 1px,
    calc(100% - 1px) calc(100% - 1px),
    1px calc(100% - 1px),
    1px calc(var(--slide-h, 10px) + 1px));
}
.wc2-ngcc[data-corner="slide-tr"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="slide-tr"] .wc2-ngcc__glow {
  clip-path: polygon(
    0 0, calc(100% - var(--slide-w, 30px)) 0,
    100% var(--slide-h, 10px),
    100% 100%, 0 100%);
}
.wc2-ngcc[data-corner="slide-tr"] .wc2-ngcc__inner {
  clip-path: polygon(
    1px 1px, calc(100% - var(--slide-w, 30px) - 1px) 1px,
    calc(100% - 1px) calc(var(--slide-h, 10px) + 1px),
    calc(100% - 1px) calc(100% - 1px),
    1px calc(100% - 1px));
}
.wc2-ngcc[data-corner="slide-bl"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="slide-bl"] .wc2-ngcc__glow {
  clip-path: polygon(
    0 0, 100% 0,
    100% 100%,
    var(--slide-w, 30px) 100%,
    0 calc(100% - var(--slide-h, 10px)));
}
.wc2-ngcc[data-corner="slide-bl"] .wc2-ngcc__inner {
  clip-path: polygon(
    1px 1px, calc(100% - 1px) 1px,
    calc(100% - 1px) calc(100% - 1px),
    calc(var(--slide-w, 30px) + 1px) calc(100% - 1px),
    1px calc(100% - var(--slide-h, 10px) - 1px));
}
.wc2-ngcc[data-corner="slide-br"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="slide-br"] .wc2-ngcc__glow {
  clip-path: polygon(
    0 0, 100% 0,
    100% calc(100% - var(--slide-h, 10px)),
    calc(100% - var(--slide-w, 30px)) 100%,
    0 100%);
}
.wc2-ngcc[data-corner="slide-br"] .wc2-ngcc__inner {
  clip-path: polygon(
    1px 1px, calc(100% - 1px) 1px,
    calc(100% - 1px) calc(100% - var(--slide-h, 10px) - 1px),
    calc(100% - var(--slide-w, 30px) - 1px) calc(100% - 1px),
    1px calc(100% - 1px));
}

/* ---- Slide on ALL FOUR corners + stepped BOTTOM tab between bottom slides.
   Mirror of slide-step. Bottom edge has the tab; rest of card identical. */
.wc2-ngcc[data-corner="slide-step-b"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="slide-step-b"] .wc2-ngcc__glow {
  clip-path: polygon(
    0 var(--slide-h, 14px),
    var(--slide-w, 14px) 0,
    calc(100% - var(--slide-w, 14px)) 0,
    100% var(--slide-h, 14px),
    100% calc(100% - var(--step-d, 14px) - var(--slide-h, 14px)),
    calc(100% - var(--slide-w, 14px)) calc(100% - var(--step-d, 14px)),
    calc(var(--step-x, 30%) + var(--step-slope-w, 14px)) calc(100% - var(--step-d, 14px)),
    var(--step-x, 30%) 100%,
    var(--slide-w, 14px) 100%,
    0 calc(100% - var(--slide-h, 14px)));
}
.wc2-ngcc[data-corner="slide-step-b"] .wc2-ngcc__inner {
  clip-path: polygon(
    1px calc(var(--slide-h, 14px) + 1px),
    calc(var(--slide-w, 14px) + 1px) 1px,
    calc(100% - var(--slide-w, 14px) - 1px) 1px,
    calc(100% - 1px) calc(var(--slide-h, 14px) + 1px),
    calc(100% - 1px) calc(100% - var(--step-d, 14px) - var(--slide-h, 14px) - 1px),
    calc(100% - var(--slide-w, 14px) - 1px) calc(100% - var(--step-d, 14px) - 1px),
    calc(var(--step-x, 30%) + var(--step-slope-w, 14px) - 1px) calc(100% - var(--step-d, 14px) - 1px),
    calc(var(--step-x, 30%) - 1px) calc(100% - 1px),
    calc(var(--slide-w, 14px) + 1px) calc(100% - 1px),
    1px calc(100% - var(--slide-h, 14px) - 1px));
}

/* ---- Slide on ALL FOUR corners + stepped top tab between top slides.
   Step uses --step-slope-w (default 30px) so it matches the 3:1 corner slide.
   Walks CW from left edge top of slide-tl: up-right diagonal → top edge →
   step slope down → lower top edge → slide-tr down → right edge → slide-br
   down → bottom edge → slide-bl up → left edge → close. */
.wc2-ngcc[data-corner="slide-step"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="slide-step"] .wc2-ngcc__glow {
  clip-path: polygon(
    0 var(--slide-h, 10px),
    var(--slide-w, 30px) 0,
    var(--step-x, 30%) 0,
    calc(var(--step-x, 30%) + var(--step-slope-w, 30px)) var(--step-d, 10px),
    calc(100% - var(--slide-w, 30px)) var(--step-d, 10px),
    100% calc(var(--step-d, 10px) + var(--slide-h, 10px)),
    100% calc(100% - var(--slide-h, 10px)),
    calc(100% - var(--slide-w, 30px)) 100%,
    var(--slide-w, 30px) 100%,
    0 calc(100% - var(--slide-h, 10px)));
}
.wc2-ngcc[data-corner="slide-step"] .wc2-ngcc__inner {
  clip-path: polygon(
    1px calc(var(--slide-h, 10px) + 1px),
    calc(var(--slide-w, 30px) + 1px) 1px,
    calc(var(--step-x, 30%) - 1px) 1px,
    calc(var(--step-x, 30%) + var(--step-slope-w, 30px) - 1px) calc(var(--step-d, 10px) + 1px),
    calc(100% - var(--slide-w, 30px) - 1px) calc(var(--step-d, 10px) + 1px),
    calc(100% - 1px) calc(var(--step-d, 10px) + var(--slide-h, 10px) + 1px),
    calc(100% - 1px) calc(100% - var(--slide-h, 10px) - 1px),
    calc(100% - var(--slide-w, 30px) - 1px) calc(100% - 1px),
    calc(var(--slide-w, 30px) + 1px) calc(100% - 1px),
    1px calc(100% - var(--slide-h, 10px) - 1px));
}

/* Stepped top edge with a 45° DIAGONAL SLIDE transition (not vertical wall).
   Flat from 0 to --step-x, then slides down-right at 45° for --step-d px both
   horizontally and vertically, then flat to right side. The 0.414px shift on
   the corners is the perpendicular 1px inset offset for a 45° edge. */
.wc2-ngcc[data-corner="step-tr"] .wc2-ngcc__frame,
.wc2-ngcc[data-corner="step-tr"] .wc2-ngcc__glow {
  clip-path: polygon(
    0 0,
    var(--step-x, 30%) 0,
    calc(var(--step-x, 30%) + var(--step-d, 10px)) var(--step-d, 10px),
    100% var(--step-d, 10px),
    100% 100%,
    0 100%);
}
.wc2-ngcc[data-corner="step-tr"] .wc2-ngcc__inner {
  clip-path: polygon(
    1px 1px,
    calc(var(--step-x, 30%) - 0.414px) 1px,
    calc(var(--step-x, 30%) + var(--step-d, 10px) - 0.414px) calc(var(--step-d, 10px) + 1px),
    calc(100% - 1px) calc(var(--step-d, 10px) + 1px),
    calc(100% - 1px) calc(100% - 1px),
    1px calc(100% - 1px));
}

/* Glow backdrop: behind, blurred, gradient, invisible until hover */
/* GLOW CONTAINER — extends 30px beyond card. Card-shape-following polygon
   clip-path applied per data-corner so the halo follows the slide-step
   silhouette. Polygon is offset 27px from the glow box edges so the halo
   extends ~18px past the card outline (then feathers via blur). */
.wc2-ngcc__glow {
  position: absolute !important;
  /* --glow-bleed system — same locked per-card random bleed pattern from
     §3 / §10.3. Rest defaults to 27px (matches the previous static look).
     JS setupGlowSuck() sets --rest-bleed / --hover-bleed per card. */
  --glow-bleed: var(--rest-bleed, 27px);
  inset: calc(0px - var(--glow-bleed) - 3px) !important;
  z-index: 0 !important;
  background: transparent !important;
  opacity: 1;
  pointer-events: none;
  /* DEFAULT — halo in darkened brand purple (#5A2E80 = rgb(90, 46, 128)).
     Reads as a dimmer shade of the main brand purple. Hover below stays
     brighter for a clear lift. */
  filter: drop-shadow(0 0 8px rgba(90, 46, 128, 0.85))
          drop-shadow(0 0 18px rgba(90, 46, 128, 0.55));
  overflow: hidden;                           /* container clip for rotated pseudos */
  transition: opacity 500ms var(--wc-ease-out),
              filter 500ms var(--wc-ease-out),
              --glow-bleed 800ms cubic-bezier(0.16, 1, 0.3, 1);
}
/* Hover — shadow shifts to the BRIGHT purple (#8B4DC4) the kit used before
   we darkened the main token. Default stays in main --wc-purple. ALSO morphs
   --glow-bleed so the tab halo smoothly shortens OR lengthens per card. */
.wc2-ngcc:hover .wc2-ngcc__glow {
  filter: drop-shadow(0 0 14px rgba(139, 77, 196, 1))
          drop-shadow(0 0 32px rgba(139, 77, 196, 0.7));
  --glow-bleed: var(--hover-bleed, var(--rest-bleed, 27px));
}
.wc2-ngcc:hover .wc2-ngcc__glow::after {
  background: #8B4DC4;
  transition: background 300ms var(--wc-ease-out);
}
/* SLIDE-STEP (top-tab) — polygon offset var(--glow-bleed) from glow box
   edges. With rest-bleed=27px the polygon extends ~24px past the card
   outline on every side, matching the previous static look exactly. On
   hover, --glow-bleed morphs to --hover-bleed (random per card), so the
   tab area smoothly shortens or lengthens. */
.wc2-ngcc[data-corner="slide-step"] .wc2-ngcc__glow {
  clip-path: polygon(
    var(--glow-bleed) calc(var(--glow-bleed) + var(--slide-h, 14px)),
    calc(var(--glow-bleed) + var(--slide-w, 14px)) var(--glow-bleed),
    calc(var(--glow-bleed) + var(--step-x, 30%)) var(--glow-bleed),
    calc(var(--glow-bleed) + var(--step-x, 30%) + var(--step-slope-w, 14px)) calc(var(--glow-bleed) + var(--step-d, 14px)),
    calc(100% - var(--glow-bleed) - var(--slide-w, 14px)) calc(var(--glow-bleed) + var(--step-d, 14px)),
    calc(100% - var(--glow-bleed)) calc(var(--glow-bleed) + var(--step-d, 14px) + var(--slide-h, 14px)),
    calc(100% - var(--glow-bleed)) calc(100% - var(--glow-bleed) - var(--slide-h, 14px)),
    calc(100% - var(--glow-bleed) - var(--slide-w, 14px)) calc(100% - var(--glow-bleed)),
    calc(var(--glow-bleed) + var(--slide-w, 14px)) calc(100% - var(--glow-bleed)),
    var(--glow-bleed) calc(100% - var(--glow-bleed) - var(--slide-h, 14px))) !important;
}
/* SLIDE-STEP-B (bottom-tab) — same idea, tab on bottom edge. */
.wc2-ngcc[data-corner="slide-step-b"] .wc2-ngcc__glow {
  clip-path: polygon(
    var(--glow-bleed) calc(var(--glow-bleed) + var(--slide-h, 14px)),
    calc(var(--glow-bleed) + var(--slide-w, 14px)) var(--glow-bleed),
    calc(100% - var(--glow-bleed) - var(--slide-w, 14px)) var(--glow-bleed),
    calc(100% - var(--glow-bleed)) calc(var(--glow-bleed) + var(--slide-h, 14px)),
    calc(100% - var(--glow-bleed)) calc(100% - var(--glow-bleed) - var(--step-d, 14px) - var(--slide-h, 14px)),
    calc(100% - var(--glow-bleed) - var(--slide-w, 14px)) calc(100% - var(--glow-bleed) - var(--step-d, 14px)),
    calc(var(--glow-bleed) + var(--step-x, 30%) + var(--step-slope-w, 14px)) calc(100% - var(--glow-bleed) - var(--step-d, 14px)),
    calc(var(--glow-bleed) + var(--step-x, 30%)) calc(100% - var(--glow-bleed)),
    calc(var(--glow-bleed) + var(--slide-w, 14px)) calc(100% - var(--glow-bleed)),
    var(--glow-bleed) calc(100% - var(--glow-bleed) - var(--slide-h, 14px))) !important;
}
/* SLIDE-STEP-L (left-tab — used by changelog cards) */
.wc2-ngcc[data-corner="slide-step-l"] .wc2-ngcc__glow {
  clip-path: polygon(
    var(--glow-bleed) calc(var(--glow-bleed) + var(--slide-h, 14px)),
    calc(var(--glow-bleed) + var(--slide-w, 14px)) var(--glow-bleed),
    calc(100% - var(--glow-bleed) - var(--slide-w, 14px)) var(--glow-bleed),
    calc(100% - var(--glow-bleed)) calc(var(--glow-bleed) + var(--slide-h, 14px)),
    calc(100% - var(--glow-bleed)) calc(100% - var(--glow-bleed) - var(--slide-h, 14px)),
    calc(100% - var(--glow-bleed) - var(--slide-w, 14px)) calc(100% - var(--glow-bleed)),
    calc(var(--glow-bleed) + var(--slide-w, 14px)) calc(100% - var(--glow-bleed)),
    var(--glow-bleed) calc(100% - var(--glow-bleed) - var(--slide-h, 14px))) !important;
}
/* Dot layers — rotated 37° so the comic dots align along a diagonal axis.
   Pseudos are oversized (inset: -50%) so rotation doesn't leave bare
   corners. The container's polygon clip-path crops them back to the
   slide-step shape. Fully solid alphas — no mask fade. */
.wc2-ngcc__glow::before,
.wc2-ngcc__glow::after {
  content: "";
  position: absolute;
  inset: -50%;                                /* oversized for rotation */
  background-color: transparent;
  pointer-events: none;
  transform: rotate(37deg);
  transform-origin: center center;
}
/* SOLID SHADOW LAYER — brand purple, darkened. Reads as a dimmer shade
   of the main --wc-purple (#5A2E80) rather than the very dark ground. */
.wc2-ngcc__glow::after {
  background: #5A2E80;                  /* darkened brand purple */
  -webkit-mask-image: none;
          mask-image: none;
  opacity: 1;
}
.wc2-ngcc__glow::before {
  display: none;
}
/* SIBLING DIM — when ANY card in a grid is hovered, all OTHER cards in
   the grid dim their entire body (not just glow). Applied via JS. */
.wc2-ngcc.wc2-ngcc--dim {
  opacity: 0.35;
  filter: saturate(0.5);
  transition: opacity 400ms var(--wc-ease-out), filter 400ms var(--wc-ease-out);
}
.wc2-ngcc {
  transition: opacity 400ms var(--wc-ease-out), filter 400ms var(--wc-ease-out),
              transform 280ms cubic-bezier(0.2, 0.85, 0.3, 1.1);
}
/* PAINT SPLATS — random EPS-converted splats injected by JS on hover.
   Sit ON TOP of the card body so they read as paint sprayed over it.
   isolation:isolate on the card creates a clean stacking context so the
   splat's high z-index actually wins against ::before/::after etc. */
.wc2-ngcc:hover { isolation: isolate; }
.wc2-splat {
  position: absolute;
  z-index: 9999;             /* defeat any stacking surprise inside the card */
  pointer-events: none;
  /* SVG used as mask-image (set by JS via inline style); background-color
     fills with --wc-purple-bright (the bright purple spark color) so the
     splat reads as the bright "splash" accent, not the muted main purple. */
  background-color: var(--wc-purple-bright);
  -webkit-mask-size: contain;
          mask-size: contain;
  -webkit-mask-repeat: no-repeat;
          mask-repeat: no-repeat;
  -webkit-mask-position: center;
          mask-position: center;
  filter: drop-shadow(0 0 27px rgba(139, 77, 196, 0.7));
  opacity: 0;
  animation: wc2-splat-pop 320ms cubic-bezier(0.2, 0.85, 0.3, 1.1) forwards;
}
@keyframes wc2-splat-pop {
  0%   { opacity: 0; transform: scale(0.6) var(--splat-rot, rotate(0deg)); }
  60%  { opacity: 0.85; }
  100% { opacity: 0.78; transform: scale(1) var(--splat-rot, rotate(0deg)); }
}
/* GLITCH SPLATS — sharp data-corruption shapes that land on notch/tentry
   cards on hover. Multi-color SVG (purple + lime + orange) rendered as
   <img> so the built-in palette comes through. */
.wc2-glitch-splat {
  position: absolute;
  z-index: 9999;
  pointer-events: none;
  object-fit: contain;
  filter: drop-shadow(0 0 8px rgba(139, 77, 196, 0.7));
  opacity: 0;
  animation: wc2-glitch-pop 220ms cubic-bezier(0.2, 0.85, 0.3, 1.1) forwards;
}
@keyframes wc2-glitch-pop {
  0%   { opacity: 0;    transform: scale(0.8); }
  30%  { opacity: 0.95; transform: scale(1.06); }
  100% { opacity: 0.85; transform: scale(1); }
}
/* Glow rotation — slow continuous spin of the whole halo, independent
   phase per card via animation-delay. */
@keyframes wc2-glow-rot {
  to { transform: rotate(360deg); }
}

/* MIXED-MEDIA stop-motion frames — irregular position jumps + scale +
   rotation + opacity blinks per frame. Combined with steps(N, jump-none)
   timing function, each keyframe is a hard cut to the next visual state
   (no interpolation). Frames are intentionally NOT evenly distributed in
   time and each one feels distinct — like stop-motion with skipped cels. */
/* Pure POSITION jumps — each frame the dot pattern snaps to a completely
   different arrangement. With background-size 22/8px, shifts of half-cell+
   pixels make the dots visibly re-arrange. No scale/rotate/opacity inside
   the dot keyframes — those caused smooth jiggle. The container's slow
   rotation is the only continuous motion; dots themselves just SNAP between
   stop-motion frames. */
@keyframes wc2-dots-skip-a {
  0%   { background-position:   0px   0px; }
  14%  { background-position:  11px   7px; }
  29%  { background-position:   3px  14px; }
  43%  { background-position:  17px  -5px; }
  57%  { background-position:  -9px  11px; }
  71%  { background-position:   6px -13px; }
  86%  { background-position: -15px   3px; }
  100% { background-position:   0px   0px; }
}
@keyframes wc2-dots-skip-b {
  0%   { background-position:   0px   0px; }
  11%  { background-position:   5px   3px; }
  22%  { background-position:  -4px   5px; }
  33%  { background-position:   3px  -5px; }
  44%  { background-position:  -5px  -4px; }
  55%  { background-position:   5px   4px; }
  66%  { background-position:  -3px   5px; }
  77%  { background-position:   4px  -3px; }
  88%  { background-position:  -5px   2px; }
  100% { background-position:   0px   0px; }
}
@keyframes wc2-dots-skip-c {
  0%   { background-position:   0px   0px; }
  9%   { background-position:   3px   2px; }
  18%  { background-position:  -2px   4px; }
  27%  { background-position:   4px  -3px; }
  36%  { background-position:  -4px   1px; }
  45%  { background-position:   2px   4px; }
  54%  { background-position:  -3px  -3px; }
  63%  { background-position:   4px   3px; }
  72%  { background-position:  -1px  -4px; }
  81%  { background-position:   3px  -1px; }
  90%  { background-position:  -4px   2px; }
  100% { background-position:   0px   0px; }
}
@keyframes wc2-glow-travel {
  0%, 100% {
    filter:
      drop-shadow(0 -40px 60px rgba(90, 46, 128, 1))
      drop-shadow( 40px 0 60px rgba(90, 46, 128, 0.55))
      drop-shadow(0  40px 60px rgba(90, 46, 128, 0.35))
      drop-shadow(-40px 0 60px rgba(90, 46, 128, 0.55));
  }
  25% {
    filter:
      drop-shadow( 40px 0 60px rgba(90, 46, 128, 1))
      drop-shadow(0  40px 60px rgba(90, 46, 128, 0.55))
      drop-shadow(-40px 0 60px rgba(90, 46, 128, 0.35))
      drop-shadow(0 -40px 60px rgba(90, 46, 128, 0.55));
  }
  50% {
    filter:
      drop-shadow(0  40px 60px rgba(90, 46, 128, 1))
      drop-shadow(-40px 0 60px rgba(90, 46, 128, 0.55))
      drop-shadow(0 -40px 60px rgba(90, 46, 128, 0.35))
      drop-shadow( 40px 0 60px rgba(90, 46, 128, 0.55));
  }
  75% {
    filter:
      drop-shadow(-40px 0 60px rgba(90, 46, 128, 1))
      drop-shadow(0 -40px 60px rgba(90, 46, 128, 0.55))
      drop-shadow( 40px 0 60px rgba(90, 46, 128, 0.35))
      drop-shadow(0  40px 60px rgba(90, 46, 128, 0.55));
  }
}
/* Border frame: filled bg clipped to the OUTER notched polygon. Inner has
   the SHRUNKEN polygon, so frame extends 1px past inner on every edge
   (including diagonals) — the visible outline ring follows the full perimeter. */
.wc2-ngcc__frame {
  position: absolute;
  inset: 0;
  background: rgba(245, 236, 250, 0.35);
  z-index: 5;
  pointer-events: none;
  transition: background 300ms, opacity 300ms;
}
/* Inner card */
.wc2-ngcc__inner {
  position: relative;
  z-index: 10;
  background: #1a1a1a;                   /* default — dark grey */
  padding: 32px;
  height: 100%;
  display: flex; flex-direction: column;
  transition: background 300ms var(--wc-ease-out), box-shadow 300ms var(--wc-ease-out);
}
.wc2-ngcc:hover .wc2-ngcc__inner {
  background: var(--wc-ground);          /* hover — dark purple (#1F0E33) */
}
/* Hover: solid lime outline (replaces fade-out) */
.wc2-ngcc:hover .wc2-ngcc__frame {
  background: var(--wc-lime);
  opacity: 1;
}

/* glow-only variant */
.wc2-ngcc.glow-only .wc2-ngcc__glow { display: none; }
.wc2-ngcc.glow-only:hover .wc2-ngcc__frame {
  background: color-mix(in srgb, var(--col-a) 45%, transparent);
}
.wc2-ngcc.glow-only:hover .wc2-ngcc__inner {
  box-shadow:
    0 0 var(--glow) color-mix(in srgb, var(--col-a) 65%, transparent),
    inset 0 0 calc(var(--glow) * 0.6) color-mix(in srgb, var(--col-a) 20%, transparent);
}

/* pulse variant */
.wc2-ngcc.pulse .wc2-ngcc__glow { display: none; }
.wc2-ngcc.pulse:hover .wc2-ngcc__frame {
  background: color-mix(in srgb, var(--col-a) 40%, transparent);
}
.wc2-ngcc.pulse:hover .wc2-ngcc__inner {
  animation: wc2-ngcc-pulse 1.4s ease-in-out infinite;
}
@keyframes wc2-ngcc-pulse {
  0%, 100% {
    box-shadow:
      0 0 var(--glow) color-mix(in srgb, var(--col-a) 55%, transparent),
      inset 0 0 var(--glow) color-mix(in srgb, var(--col-a) 15%, transparent);
  }
  50% {
    box-shadow:
      0 0 calc(var(--glow) * 2.2) var(--col-a),
      inset 0 0 calc(var(--glow) * 1.3) color-mix(in srgb, var(--col-a) 35%, transparent);
  }
}

/* trace variant - animated hue */
@keyframes wc2-ngcc-trace {
  0%   { opacity: 0.7; filter: blur(var(--blur)) hue-rotate(0deg); }
  50%  { opacity: 1;   filter: blur(calc(var(--blur) * 0.5)) hue-rotate(30deg); }
  100% { opacity: 0.7; filter: blur(var(--blur)) hue-rotate(0deg); }
}
.wc2-ngcc.trace:hover .wc2-ngcc__glow {
  opacity: 1;
  animation: wc2-ngcc-trace 2s linear infinite;
}
.wc2-ngcc.trace:hover .wc2-ngcc__frame { opacity: 0; }

/* Card icon box */
.wc2-ngcc__icon {
  width: 48px; height: 48px;
  display: grid; place-items: center;
  border: 1px solid rgba(245, 236, 250, 0.12);
  background: var(--wc-bg);
  margin-bottom: 24px;
  transition: border-color 300ms, box-shadow 300ms, color 300ms;
  color: var(--wc-ink-2);
}
.wc2-ngcc__icon svg { width: 22px; height: 22px; fill: none; stroke: currentColor; stroke-width: 1.5; }
.wc2-ngcc:hover .wc2-ngcc__icon {
  border-color: var(--col-a);
  color: var(--col-a);
  box-shadow:
    0 0 var(--glow) color-mix(in srgb, var(--col-a) 40%, transparent),
    inset 0 0 calc(var(--glow) * 0.5) color-mix(in srgb, var(--col-a) 20%, transparent);
}

.wc2-ngcc__title {
  font-family: var(--wc-font-display);
  font-size: 22px;
  line-height: 1.1;
  letter-spacing: -0.01em;
  color: var(--wc-ink-1);
  margin: 0 0 27px;
  text-transform: uppercase;
  transition: text-shadow 300ms;
}
.wc2-ngcc:hover .wc2-ngcc__title {
  text-shadow: 0 0 6px color-mix(in srgb, var(--col-a) 45%, transparent);
}
.wc2-ngcc__desc {
  font: 500 13px/1.55 var(--wc-font-mono);
  color: var(--wc-ink-3);
  letter-spacing: 0.02em;
  margin: 0;
}

/* ---- About / Skills section --------------------------------- */
.wc2-pabout {
  display: grid;
  grid-template-columns: 1fr 380px;
  gap: 80px;
  align-items: start;
}
@media (max-width: 927px) {
  .wc2-pabout { grid-template-columns: 1fr; gap: 48px; }
}
.wc2-pabout__body {
  font: 500 15px/1.7 var(--wc-font-mono);
  color: var(--wc-ink-3);
  letter-spacing: 0.02em;
}
.wc2-pabout__body p { margin: 0 0 18px; max-width: 56ch; }
.wc2-pabout__body b { color: var(--wc-lime); font-weight: 700; }

.wc2-stack {
  display: flex; flex-direction: column; gap: 28px;
}
.wc2-stack__title {
  font: 700 11px var(--wc-font-mono);
  letter-spacing: 0.28em;
  text-transform: uppercase;
  color: var(--wc-orange);
}
.wc2-tags {
  display: flex; flex-wrap: wrap; gap: 6px;
}
.wc2-tag-pill {
  display: inline-flex; align-items: center; gap: 6px;
  padding: 5px 10px;
  border: 1px solid var(--wc-line);
  font: 700 10px var(--wc-font-mono);
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--wc-ink-2);
  background: rgba(245, 236, 250, 0.02);
}
.wc2-tag-pill::before {
  content: "▢";
  color: var(--wc-lime);
  font-size: 10px;
}
.wc2-tag-pill.lime { color: var(--wc-lime); border-color: rgba(184, 255, 56, 0.4); }
.wc2-tag-pill.orange { color: var(--wc-orange); border-color: rgba(255, 106, 0, 0.4); }
.wc2-tag-pill.orange::before { color: var(--wc-orange); }

/* Stats grid — children of a slide-step .wc2-ngcc.beam card. The card frame
   handles outline + clipping; this just lays out the 3 stats inside. */
.wc2-stats__grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 24px;
}
.wc2-stat .n {
  font-family: var(--wc-font-display);
  font-size: 32px;
  color: var(--wc-lime);
  line-height: 1;
  font-variant-numeric: tabular-nums;
  letter-spacing: -0.02em;
}
.wc2-stat .l {
  display: block;
  font: 700 9px var(--wc-font-mono);
  letter-spacing: 0.24em;
  text-transform: uppercase;
  color: var(--wc-ink-4);
  margin-top: 6px;
}

/* ---- Components grid --------------------------------------- */
.wc2-pgrid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 24px;
}
@media (max-width: 927px) { .wc2-pgrid { grid-template-columns: 1fr 1fr; } }
@media (max-width: 627px) { .wc2-pgrid { grid-template-columns: 1fr; } }

/* ---- Timeline ---------------------------------------------- */
.wc2-timeline {
  display: flex; flex-direction: column; gap: 27px;
  position: relative;
  padding-left: 28px;
  border-left: 1px solid var(--wc-line);
}
.wc2-tentry {
  position: relative;
  /* slide-step-L card shape — corner slides + tab on LEFT edge, matching
     our card family. Element = outline color, ::before = inner fill with
     shrunken polygon (same approach as .wc2-ngcc cards). */
  --slide-w: 14px;
  --slide-h: 14px;
  --step-d: 10px;          /* shorter — tab depth (sticks out 10px) */
  --step-slope-w: 10px;    /* matches step-d for 45° slope */
  --step-y: 40%;           /* center — keeps tab top clear of slide-tl corner */
  --step-h: 50%;           /* length along edge — tab spans ~15%→65% of card */
  padding: 27px 24px 27px 32px;     /* extra left padding for the recessed edge */
  background: rgba(245, 236, 250, 0.35);  /* outline color */
  clip-path: polygon(
    calc(var(--step-d) + var(--slide-w)) 0,
    calc(100% - var(--slide-w)) 0,
    100% var(--slide-h),
    100% calc(100% - var(--slide-h)),
    calc(100% - var(--slide-w)) 100%,
    calc(var(--step-d) + var(--slide-w)) 100%,
    var(--step-d) calc(100% - var(--slide-h)),
    var(--step-d) calc(var(--step-y) + var(--step-h) / 2),
    0 calc(var(--step-y) + var(--step-h) / 2 - var(--step-slope-w)),
    0 calc(var(--step-y) - var(--step-h) / 2 + var(--step-slope-w)),
    var(--step-d) calc(var(--step-y) - var(--step-h) / 2),
    var(--step-d) var(--slide-h));
  transition: background 280ms var(--wc-ease-out),
              transform 280ms cubic-bezier(0.2, 0.85, 0.3, 1.1);
}
/* Glow sibling for .wc2-tentry — slide-step-L polygon. inset:-3px so a
   3px purple ring shows around the card outline. */
.wc2-tentry__glow {
  position: absolute;
  /* TENTRY uses FIXED inset (NOT the --glow-bleed system) — the timeline's
     27px gap is too tight for any per-card bleed to fit without spilling
     into adjacent cards. Clean 3px ring + subtle bloom only. */
  inset: -3px;
  z-index: 0;
  background: var(--wc-purple);
  pointer-events: none;
  filter: drop-shadow(0 0 4px rgba(90, 46, 128, 0.7))
          drop-shadow(0 0 10px rgba(90, 46, 128, 0.35));
  transition: background 300ms var(--wc-ease-out),
              filter 300ms var(--wc-ease-out),
              transform 240ms var(--wc-ease-out);
  clip-path: polygon(
    calc(var(--step-d) + var(--slide-w)) 0,
    calc(100% - var(--slide-w)) 0,
    100% var(--slide-h),
    100% calc(100% - var(--slide-h)),
    calc(100% - var(--slide-w)) 100%,
    calc(var(--step-d) + var(--slide-w)) 100%,
    var(--step-d) calc(100% - var(--slide-h)),
    var(--step-d) calc(var(--step-y) + var(--step-h) / 2),
    0 calc(var(--step-y) + var(--step-h) / 2 - var(--step-slope-w)),
    0 calc(var(--step-y) - var(--step-h) / 2 + var(--step-slope-w)),
    var(--step-d) calc(var(--step-y) - var(--step-h) / 2),
    var(--step-d) var(--slide-h));
}
.wc2-card-autowrap:hover .wc2-tentry__glow {
  background: var(--wc-purple-bright);
  filter: drop-shadow(0 0 8px rgba(139, 77, 196, 0.9))
          drop-shadow(0 0 18px rgba(139, 77, 196, 0.55));
  transform: translateY(-3px);     /* lift WITH the tentry card */
}
.wc2-tentry::before {
  content: "";
  position: absolute; inset: 0;
  background: #1a1a1a;                  /* LOCKED card rule — default dark grey */
  pointer-events: none;
  z-index: 0;
  clip-path: polygon(
    calc(var(--step-d) + var(--slide-w) + 1px) 1px,
    calc(100% - var(--slide-w) - 1px) 1px,
    calc(100% - 1px) calc(var(--slide-h) + 1px),
    calc(100% - 1px) calc(100% - var(--slide-h) - 1px),
    calc(100% - var(--slide-w) - 1px) calc(100% - 1px),
    calc(var(--step-d) + var(--slide-w) + 1px) calc(100% - 1px),
    calc(var(--step-d) + 1px) calc(100% - var(--slide-h) - 1px),
    calc(var(--step-d) + 1px) calc(var(--step-y) + var(--step-h) / 2 + 0.414px),
    1px calc(var(--step-y) + var(--step-h) / 2 - var(--step-slope-w) + 0.414px),
    1px calc(var(--step-y) - var(--step-h) / 2 + var(--step-slope-w) - 0.414px),
    calc(var(--step-d) + 1px) calc(var(--step-y) - var(--step-h) / 2 - 0.414px),
    calc(var(--step-d) + 1px) calc(var(--slide-h) + 1px));
  transition: background 280ms var(--wc-ease-out);
}
.wc2-tentry > * { position: relative; z-index: 1; }
.wc2-tentry:hover {
  background: var(--wc-lime);
  transform: translateY(-3px);
}
.wc2-tentry:hover::before { background: var(--wc-ground); }  /* LOCKED card rule — hover dark purple */

/* Dot marker sits as a child of .wc2-timeline (sibling to entries)
   so it isn't clipped by the entry's clip-path. JS inserts + positions it. */
.wc2-timeline { position: relative; }
.wc2-tentry__dot {
  position: absolute;
  width: 27px; height: 27px;
  background: var(--wc-lime);
  border-radius: 50%;
  box-shadow: 0 0 27px var(--wc-lime);
  transition: box-shadow 240ms var(--wc-ease-out),
              transform 240ms var(--wc-ease-out);
  pointer-events: none;
  z-index: 2;
  opacity: 0;       /* hidden until the timeline staggers them in */
}
/* When the timeline stagger has fired, animate each dot in with the same
   snap-flicker as its entry. The animation-delay is set per-dot by JS so
   they fire BEFORE their corresponding tentry — the dot lights up, then
   the card swipes out from it. */
.wc2-stagger.in .wc2-tentry__dot {
  animation: wc2-snap-flicker 0.45s steps(8, end) both;
}

/* Changelog tentry reveal — SWIPE from the dot's side (left) while
   discrete-step flickering opacity. Card emerges from the dot anchor.
   Longhand !important so the inline animation-delay set by JS still wins. */
.wc2-stagger.in > .wc2-tentry {
  animation-name: wc2-tentry-swipe !important;
  animation-duration: 0.6s !important;
  animation-timing-function: steps(9, end) !important;
  animation-fill-mode: both !important;
}
@keyframes wc2-tentry-swipe {
  0%   { opacity: 0;    transform: translateX(-18px); }
  18%  { opacity: 1;    transform: translateX(-14px); }
  30%  { opacity: 0.15; transform: translateX(-10px); }
  44%  { opacity: 1;    transform: translateX(-7px); }
  58%  { opacity: 0.45; transform: translateX(-4px); }
  72%  { opacity: 1;    transform: translateX(-2px); }
  100% { opacity: 1;    transform: translateX(0); }
}
.wc2-tentry__dot.hover {
  transform: scale(1.25);
  box-shadow:
    0 0 14px var(--wc-lime),
    0 0 22px color-mix(in srgb, var(--wc-lime) 40%, transparent);
}
.wc2-tentry__date {
  font: 700 10px var(--wc-font-mono);
  letter-spacing: 0.24em;
  text-transform: uppercase;
  color: var(--wc-orange);
  margin-bottom: 6px;
}
.wc2-tentry__role {
  font-family: var(--wc-font-display);
  font-size: 18px;
  color: var(--wc-ink-1);
  letter-spacing: -0.01em;
  text-transform: uppercase;
  margin-bottom: 6px;
}
.wc2-tentry__desc {
  font: 500 13px/1.55 var(--wc-font-mono);
  color: var(--wc-ink-3);
  letter-spacing: 0.02em;
}

/* ---- Contact card / final CTA ------------------------------ */
.wc2-pcontact {
  text-align: center;
  padding: 56px 40px;
  --c: 24px;
  position: relative;
}
.wc2-pcontact__email {
  display: block;
  margin: 32px 0;
  font-family: var(--wc-font-display);
  font-size: clamp(22px, 3.5vw, 40px);
  color: var(--wc-lime);
  letter-spacing: -0.01em;
  text-decoration: none;
  text-transform: lowercase;
  transition: text-shadow 300ms;
}
.wc2-pcontact__email:hover {
  text-shadow: 0 0 14px var(--wc-lime);
}
.wc2-pcontact__socials {
  display: inline-flex; gap: 8px; flex-wrap: wrap; justify-content: center;
}

/* ---- Footer ----------------------------------------------- */
.wc2-pfooter {
  position: relative; z-index: 5;
  border-top: 1px solid var(--wc-line);
  padding: 32px 40px;
  display: flex; align-items: center; justify-content: space-between;
  font: 500 11px var(--wc-font-mono);
  color: var(--wc-ink-4);
  letter-spacing: 0.02em;
}
.wc2-pfooter a { color: var(--wc-ink-3); text-decoration: none; }
.wc2-pfooter a:hover { color: var(--wc-lime); }

/* ============================================================
 * REVEAL-ON-SCROLL + TYPEWRITER + HERO BRACKET ANIMATION
 * ============================================================ */

/* Reveal: opacity 0 + translate up, becomes visible when .in.
   --reveal-delay (inline-stylable) lets each element ramp in at its own
   moment so the title cascades to body to aside to card. Default 0. */
.wc2-reveal {
  opacity: 0;
  transform: translateY(36px);
  transition: opacity 1.5s var(--wc-ease-out) var(--reveal-delay, 0s),
              transform 1.5s var(--wc-ease-out) var(--reveal-delay, 0s);
  will-change: opacity, transform;
}
.wc2-reveal.in,
.wc2-reveal.shown { opacity: 1; transform: translateY(0); }

/* Reveal variant: SLOW scale-up from 0.86 with a long ease overshoot. The
   slower duration gives the size pop time to breathe under the fast flicker. */
.wc2-reveal--scale {
  opacity: 0;
  transform: scale(0.86);
  transition: opacity 2.4s var(--wc-ease-out) var(--reveal-delay, 0s),
              transform 2.4s cubic-bezier(0.2, 0.85, 0.3, 1.10) var(--reveal-delay, 0s);
  will-change: opacity, transform;
}
.wc2-reveal--scale.in { opacity: 1; transform: scale(1); }
/* Stats/feature card: FAST flicker on top of the slow scale — the flicker
   resolves quickly so the eye then watches the scale settle. */
.wc2-stagger.in > .wc2-reveal--scale {
  animation: wc2-snap-flicker 0.18s steps(5, end) both;
}

/* Slide-step-b cards (with bottom tab) need extra bottom padding inside so
   content (especially short labels next to numbers) doesn't sit in the tab
   area and get visually clipped. */
.wc2-ngcc[data-corner="slide-step-b"] .wc2-ngcc__inner {
  padding-bottom: 44px;
}

/* Reveal variant: TYPEWRITER — JS-driven char-by-char reveal with random
   glitch characters appearing then settling. No CSS transition; the JS in
   wc2-glitch.js handles the timing. Element starts invisible until JS runs
   and adds .typing class. */
.wc2-reveal--type,
.wc2-reveal--type-word {
  /* Reserve space but make text transparent until JS starts. */
  visibility: hidden;
}
.wc2-reveal--type.in,
.wc2-reveal--type.typing,
.wc2-reveal--type-word.in,
.wc2-reveal--type-word.typing { visibility: visible; }

/* Stagger children — GLITCH FLICKER snap-in (no fade-up). Each child pops
   into existence with a 4-step opacity flicker that feels like a system
   booting up an element. No translate, no slow ramp. */
.wc2-stagger > * {
  opacity: 0;
}
@keyframes wc2-snap-flicker {
  0%   { opacity: 0; }
  20%  { opacity: 1; }
  35%  { opacity: 0.15; }
  55%  { opacity: 1; }
  70%  { opacity: 0.4; }
  100% { opacity: 1; }
}
.wc2-stagger.in > * {
  animation: wc2-snap-flicker 0.45s steps(8, end) both;
  opacity: 1;
}
.wc2-stagger.in > *:nth-child(1) { animation-delay: calc(var(--reveal-delay, 0s) + 0.10s); }
.wc2-stagger.in > *:nth-child(2) { animation-delay: calc(var(--reveal-delay, 0s) + 0.30s); }
.wc2-stagger.in > *:nth-child(3) { animation-delay: calc(var(--reveal-delay, 0s) + 0.55s); }
.wc2-stagger.in > *:nth-child(4) { animation-delay: calc(var(--reveal-delay, 0s) + 0.80s); }
.wc2-stagger.in > *:nth-child(5) { animation-delay: calc(var(--reveal-delay, 0s) + 1.05s); }
.wc2-stagger.in > *:nth-child(6) { animation-delay: calc(var(--reveal-delay, 0s) + 1.30s); }

/* GLITCH REVEAL — the locked default in-anim for cards + buttons + form
   primitives. Combines a subtle scale (0.92 → 1) + slide-in (translateY
   18px → 0) + opacity flicker (snap-flicker rhythm) all in one keyframe.
   Reads as "tactical system booting an element into place" — the brand's
   signature element entry. */
.wc2-reveal--glitch {
  opacity: 0;
  transform: translateY(18px) scale(0.92);
  will-change: opacity, transform;
}
.wc2-reveal--glitch.in {
  animation: wc2-glitch-reveal 0.9s cubic-bezier(0.2, 0.85, 0.3, 1.05) var(--reveal-delay, 0s) both;
}
@keyframes wc2-glitch-reveal {
  0%   { opacity: 0;    transform: translateY(18px) scale(0.92); }
  18%  { opacity: 1;    transform: translateY(14px) scale(0.94); }
  30%  { opacity: 0.15; transform: translateY(10px) scale(0.96); }
  44%  { opacity: 1;    transform: translateY(7px)  scale(0.975); }
  58%  { opacity: 0.45; transform: translateY(4px)  scale(0.985); }
  72%  { opacity: 1;    transform: translateY(2px)  scale(0.995); }
  100% { opacity: 1;    transform: translateY(0)    scale(1); }
}
/* Glow opacity-only mirror of glitch-reveal — same flicker rhythm so the
   shadow halo animates IN SYNC with the card body, not on its own
   independent fade. Applied to __glow children of any autowrap whose
   reveal-class child has fired its .in. */
@keyframes wc2-glow-reveal {
  0%   { opacity: 0;    }
  18%  { opacity: 1;    }
  30%  { opacity: 0.15; }
  44%  { opacity: 1;    }
  58%  { opacity: 0.45; }
  72%  { opacity: 1;    }
  100% { opacity: 1;    }
}

/* Typewriter base — chars insert one-by-one via JS */
.wc2-tw { display: inline-block; }
.wc2-tw__c {
  display: inline-block;
  opacity: 0;
  animation: wc2-tw-pop 0.05s linear forwards;
}
@keyframes wc2-tw-pop { to { opacity: 1; } }
.wc2-tw__caret {
  display: inline-block;
  width: 0.55em;
  height: 0.9em;
  background: var(--wc-lime);
  margin-left: 2px;
  vertical-align: -2px;
  animation: wc2-caret-blink 0.85s steps(1) infinite;
}
@keyframes wc2-caret-blink {
  0%, 50% { opacity: 1; }
  51%, 100% { opacity: 0; }
}
.wc2-tw.done .wc2-tw__caret { display: none; }

/* Hero bracket frames — corner ticks that DRAW IN, not pop in */
.wc2-hero__corners span {
  transform: scale(0.5) rotate(-30deg);
  opacity: 0;
  animation: wc2-corner-draw 0.7s var(--wc-ease-pop, cubic-bezier(0.34, 1.56, 0.64, 1)) forwards;
}
.wc2-hero__corners .tl { animation-delay: 0.10s; }
.wc2-hero__corners .tr { animation-delay: 0.20s; }
.wc2-hero__corners .bl { animation-delay: 0.30s; }
.wc2-hero__corners .br { animation-delay: 0.40s; }
@keyframes wc2-corner-draw {
  to { transform: scale(1) rotate(0); opacity: 1; }
}

/* Status pill — slide+fade up */
.wc2-hero__status {
  opacity: 0;
  transform: translateY(14px);
  animation: wc2-fade-up 0.7s var(--wc-ease-out) 0.5s forwards;
}
@keyframes wc2-fade-up {
  to { opacity: 1; transform: translateY(0); }
}
.wc2-hero__sub,
.wc2-hero__tag,
.wc2-hero__ctas {
  opacity: 0;
  transform: translateY(14px);
  animation: wc2-fade-up 0.7s var(--wc-ease-out) forwards;
}
.wc2-hero__sub  { animation-delay: 2.0s; }
.wc2-hero__tag  { animation-delay: 2.4s; }
.wc2-hero__ctas { animation-delay: 2.8s; }

/* Section headings glitch-bracket hover */
.wc2-eyebrow.wc2-tw { letter-spacing: 0.28em; }

/* ============================================================
 * BORDER BEAM — single bright dash that travels around the
 * card outline (1px lit segment + dashed gap, animated).
 * Wraps the chamfered polygon via SVG path injected by JS.
 * ============================================================ */
.wc2-ngcc.beam .wc2-ngcc__beam {
  position: absolute; inset: -1px;
  z-index: 6;
  pointer-events: none;
  overflow: visible;
  filter: drop-shadow(0 0 4px var(--wc-lime))
          drop-shadow(0 0 8px color-mix(in srgb, var(--wc-lime) 50%, transparent));
}
.wc2-ngcc.beam .wc2-ngcc__beam path {
  fill: none;
  stroke: var(--wc-lime);
  stroke-linecap: round;
  /* stroke-width, dasharray, animation-duration, delay all per-card via JS */
  animation: wc2-beam-travel 3.6s linear infinite;
}
@keyframes wc2-beam-travel {
  to { stroke-dashoffset: -100; }
}
/* Hover: beam goes very fast + lit segment becomes longer for a richer
   look. Distortion frequency + peak are JS-driven. */
.wc2-ngcc.beam:hover .wc2-ngcc__beam path {
  animation-duration: 1.5s !important;
  stroke-dasharray: 28 72 !important;        /* 28% lit (was 6%) */
}

/* ============================================================
 * ACCENT FRAME — corner brackets that wrap any element.
 *   <div class="wc2-af" data-mode="quad"> ... content ... </div>
 *   data-mode: "quad" (4 corners) | "duo" (tl + br diagonal)
 *   Modifiers: .glow  .pulse  .animated
 * ============================================================ */
.wc2-af {
  position: relative;
  --af-col: var(--wc-lime);
  --af-len: 16px;
  --af-thick: 2px;
  --af-glow: 8px;
}
.wc2-af::before,
.wc2-af::after,
.wc2-af__c1,
.wc2-af__c2 {
  position: absolute;
  content: "";
  width: var(--af-len);
  height: var(--af-len);
  border: 0 solid var(--af-col);
  transition: width 280ms var(--wc-ease-out),
              height 280ms var(--wc-ease-out),
              box-shadow 280ms var(--wc-ease-out);
}
/* Top-left */
.wc2-af::before {
  top: 0; left: 0;
  border-top-width: var(--af-thick);
  border-left-width: var(--af-thick);
}
/* Bottom-right */
.wc2-af::after {
  bottom: 0; right: 0;
  border-bottom-width: var(--af-thick);
  border-right-width: var(--af-thick);
}
/* Quad mode: add the other two */
.wc2-af[data-mode="quad"] .wc2-af__c1 {
  top: 0; right: 0;
  border-top-width: var(--af-thick);
  border-right-width: var(--af-thick);
}
.wc2-af[data-mode="quad"] .wc2-af__c2 {
  bottom: 0; left: 0;
  border-bottom-width: var(--af-thick);
  border-left-width: var(--af-thick);
}
.wc2-af:not([data-mode="quad"]) .wc2-af__c1,
.wc2-af:not([data-mode="quad"]) .wc2-af__c2 { display: none; }

/* Hover: expand */
.wc2-af:hover::before,
.wc2-af:hover::after,
.wc2-af:hover .wc2-af__c1,
.wc2-af:hover .wc2-af__c2 {
  width: 32px; height: 32px;
}
/* Glow modifier */
.wc2-af.glow::before,
.wc2-af.glow::after,
.wc2-af.glow .wc2-af__c1,
.wc2-af.glow .wc2-af__c2 {
  box-shadow: 0 0 var(--af-glow) var(--af-col),
              0 0 calc(var(--af-glow) * 2.2) color-mix(in srgb, var(--af-col) 40%, transparent);
}
/* Pulse modifier */
@keyframes wc2-af-pulse {
  0%, 100% { box-shadow: 0 0 var(--af-glow) var(--af-col); }
  50%      {
    box-shadow:
      0 0 calc(var(--af-glow) * 2.5) var(--af-col),
      0 0 calc(var(--af-glow) * 4.5) color-mix(in srgb, var(--af-col) 30%, transparent);
  }
}
.wc2-af.pulse::before,
.wc2-af.pulse::after,
.wc2-af.pulse .wc2-af__c1,
.wc2-af.pulse .wc2-af__c2 {
  animation: wc2-af-pulse 1.4s ease-in-out infinite;
}
/* Animated (always-on) modifier — applies glow without hover */
.wc2-af.animated::before,
.wc2-af.animated::after,
.wc2-af.animated .wc2-af__c1,
.wc2-af.animated .wc2-af__c2 {
  width: 28px; height: 28px;
  box-shadow: 0 0 calc(var(--af-glow) * 0.7) var(--af-col);
}
/* Padding inset for content so corners don't overlap */
.wc2-af__body {
  padding: clamp(24px, 4vw, 56px);
}

/* ============================================================
 * CYBER CIRCUIT BACKGROUND — datalines on a grid.
 * Canvas runs as a fixed, low-z, low-opacity backdrop.
 * ============================================================ */
.wc2-circuit {
  position: fixed; inset: 0;
  z-index: 0;
  pointer-events: none;
  background-image:
    linear-gradient(rgba(184, 255, 56, 0.04) 1px, transparent 1px),
    linear-gradient(90deg, rgba(184, 255, 56, 0.04) 1px, transparent 1px);
  background-size: 50px 50px;
}
.wc2-circuit canvas {
  position: absolute; inset: 0;
  width: 100%; height: 100%;
  display: block;
  opacity: 0.5;  /* moving lines at 50% */
}
/* Soften the grain overlay since circuit now provides texture */
.wc2-portfolio::before { opacity: 0.18; }

/* ============================================================
 * NOTCH CARD — rectangular or beveled cut on one edge
 *   <div class="wc2-notch" data-edge="top">
 *     <span class="wc2-notch__tab">SLOT 01</span>     <!-- optional pip text  -->
 *     ...body...
 *   </div>
 *   data-edge: "top" | "bottom" | "left" | "right"
 *   Modifiers: .bevel (angled walls), .deep (taller notch), .tabbed (label inside the notch)
 * ============================================================ */
.wc2-notch {
  position: relative;
  --notch-x: 50%;
  --notch-w: 127px;
  --notch-d: 18px;
  /* 4 corner slides — matches our slide-step card spec so notch cards feel
     like part of the same family. Keep the notch shape per variant. */
  --slide-w: 14px;
  --slide-h: 14px;
  /* Bottom slide-step tab — matches .wc2-ngcc bottom-tab cards. Notch cards
     now carry the same family bottom tab as our main slide-step-b cards. */
  --step-d: 14px;
  --step-slope-w: 14px;
  --step-x: 30%;
  --bg: #1a1a1a;                       /* LOCKED card rule — default dark grey */
  --bg-hover: var(--wc-ground);        /* LOCKED card rule — hover dark purple */
  --border: rgba(245, 236, 250, 0.35);
  background: var(--border);
  padding: 36px 28px 28px;
  color: var(--wc-ink-1);
  font-family: var(--wc-font-mono);
  /* 45° sloped notch walls — same as the bevel pattern, applied universally
     so notches feel consistent with our slide-step card slopes. */
  clip-path: polygon(
    0 var(--slide-h),
    var(--slide-w) 0,
    calc(var(--notch-x) - var(--notch-w) / 2) 0,
    calc(var(--notch-x) - var(--notch-w) / 2 + var(--notch-d)) var(--notch-d),
    calc(var(--notch-x) + var(--notch-w) / 2 - var(--notch-d)) var(--notch-d),
    calc(var(--notch-x) + var(--notch-w) / 2) 0,
    calc(100% - var(--slide-w)) 0,
    100% var(--slide-h),
    100% calc(100% - var(--step-d) - var(--slide-h)),
    calc(100% - var(--slide-w)) calc(100% - var(--step-d)),
    calc(var(--step-x) + var(--step-slope-w)) calc(100% - var(--step-d)),
    var(--step-x) 100%,
    var(--slide-w) 100%,
    0 calc(100% - var(--slide-h)));
  transition: background 240ms var(--wc-ease-out);
}
.wc2-notch::before {
  content: "";
  position: absolute; inset: 0;
  background: var(--bg);
  pointer-events: none;
  clip-path: polygon(
    1px calc(var(--slide-h) + 1px),
    calc(var(--slide-w) + 1px) 1px,
    calc(var(--notch-x) - var(--notch-w) / 2 - 0.414px) 1px,
    calc(var(--notch-x) - var(--notch-w) / 2 + var(--notch-d) - 0.414px) calc(var(--notch-d) + 1px),
    calc(var(--notch-x) + var(--notch-w) / 2 - var(--notch-d) + 0.414px) calc(var(--notch-d) + 1px),
    calc(var(--notch-x) + var(--notch-w) / 2 + 0.414px) 1px,
    calc(100% - var(--slide-w) - 1px) 1px,
    calc(100% - 1px) calc(var(--slide-h) + 1px),
    calc(100% - 1px) calc(100% - var(--step-d) - var(--slide-h) - 1px),
    calc(100% - var(--slide-w) - 1px) calc(100% - var(--step-d) - 1px),
    calc(var(--step-x) + var(--step-slope-w) - 1px) calc(100% - var(--step-d) - 1px),
    calc(var(--step-x) - 1px) calc(100% - 1px),
    calc(var(--slide-w) + 1px) calc(100% - 1px),
    1px calc(100% - var(--slide-h) - 1px));
  transition: background 240ms var(--wc-ease-out);
}
/* Children sit above the inner fill so content isn't covered. */
.wc2-notch > * { position: relative; z-index: 1; }
.wc2-notch {
  transition: background 280ms var(--wc-ease-out),
              transform 240ms var(--wc-ease-out);
}
.wc2-notch:hover,
.wc2-notch-wrap:hover .wc2-notch {
  background: var(--wc-lime);
  transform: translateY(-3px);
}
/* Autowrap for .wc2-notch / .wc2-tentry without an explicit wrap — JS adds
   this when injecting the glow sibling. position: relative anchors the
   absolutely-positioned glow. align-self: start prevents grid/flex stretch
   so the wrap matches the card's natural height (no phantom polygon below). */
/* REVEAL-GATED SHADOW (notch + tentry + ngcc families) — when the wrapped
   card hasn't fired its reveal yet (no .in class), suppress the autowrap
   filter halo AND hide the dedicated __glow sibling polygons so the
   shadow doesn't sit visible while the card itself is at opacity 0. */
.wc2-card-autowrap:has(> .wc2-reveal--glitch:not(.in)),
.wc2-card-autowrap:has(> .wc2-reveal:not(.in)) {
  filter: none !important;
}
.wc2-card-autowrap:has(> .wc2-reveal--glitch:not(.in)) > .wc2-notch__glow,
.wc2-card-autowrap:has(> .wc2-reveal--glitch:not(.in)) > .wc2-tentry__glow,
.wc2-card-autowrap:has(> .wc2-reveal--glitch:not(.in)) > .wc2-ngcc__glow,
.wc2-card-autowrap:has(> .wc2-reveal:not(.in)) > .wc2-notch__glow,
.wc2-card-autowrap:has(> .wc2-reveal:not(.in)) > .wc2-tentry__glow,
.wc2-card-autowrap:has(> .wc2-reveal:not(.in)) > .wc2-ngcc__glow {
  opacity: 0;
}
/* Once .in fires, the glow runs the FULL wc2-glitch-reveal keyframe
   (opacity + translateY + scale) — same flicker rhythm, same movement,
   same delay as the card body. Without the translate+scale on the glow,
   the card slides up but the shadow stays put = looks standalone. */
.wc2-card-autowrap:has(> .wc2-reveal--glitch.in) > .wc2-notch__glow,
.wc2-card-autowrap:has(> .wc2-reveal--glitch.in) > .wc2-tentry__glow,
.wc2-card-autowrap:has(> .wc2-reveal--glitch.in) > .wc2-ngcc__glow,
.wc2-card-autowrap:has(> .wc2-reveal.in) > .wc2-notch__glow,
.wc2-card-autowrap:has(> .wc2-reveal.in) > .wc2-tentry__glow,
.wc2-card-autowrap:has(> .wc2-reveal.in) > .wc2-ngcc__glow {
  animation: wc2-glitch-reveal 0.9s cubic-bezier(0.2, 0.85, 0.3, 1.05) var(--reveal-delay, 0s) both;
}

.wc2-card-autowrap {
  position: relative;
  z-index: 0;                          /* keep shadow behind sibling content */
  align-self: start;
  justify-self: stretch;     /* still fill the grid column horizontally */
  /* BASELINE shadow halo — same 10% intensity recipe as .wcp-card-autowrap
     (locked card rule §3). The autowrap has no clip-path, so filter:
     drop-shadow follows the painted silhouette of its children (the
     notch / tentry polygon + dedicated __glow element) and renders the
     bloom outward past every edge — including the tab. This is what
     gives notch family cards the same "long shadow" character as the
     wcp family. */
  filter:
    drop-shadow(0 0 0.5px var(--wc-purple-bright))
    drop-shadow(0 0 0.5px var(--wc-purple-bright))
    drop-shadow(0 0 2.5px rgba(139, 77, 196, 0.16))
    drop-shadow(0 0 5px rgba(139, 77, 196, 0.08));
  transition: filter 280ms var(--wc-ease-out),
              transform 280ms cubic-bezier(0.2, 0.85, 0.3, 1.1);
}
.wc2-card-autowrap:hover {
  filter:
    drop-shadow(0 0 0.6px var(--wc-purple-bright))
    drop-shadow(0 0 0.6px var(--wc-purple-bright))
    drop-shadow(0 0 3.5px rgba(139, 77, 196, 0.22))
    drop-shadow(0 0 6.5px rgba(139, 77, 196, 0.12));
}
.wc2-card-autowrap > .wc2-notch,
.wc2-card-autowrap > .wc2-tentry { position: relative; z-index: 1; }
.wc2-notch-wrap {
  align-self: start;
  justify-self: stretch;
}
.wc2-notch-wrap > .wc2-notch { position: relative; z-index: 1; }

/* Glow injected as SIBLING (before the notch) inside the wrap. Absolutely
   positioned to overlap the notch's area, extended ~10px past so the halo
   ring shows around the edges. Solid purple polygon matching the notch. */
.wc2-notch__glow {
  position: absolute;
  /* --glow-bleed system — same per-card random bleed pattern as .wcp-glow
     (locked §3). Glow box = card + 2*(bleed+3) on each axis. Polygon
     offset = bleed inside the glow. Px-based slide-w/h/notch-d/step-d
     give a clean 3px ring at corners + constant top-notch dip. %-based
     --step-x gives a variable halo on the bottom tab as bleed grows.
     JS sets --rest-bleed / --hover-bleed per card. */
  --glow-bleed: var(--rest-bleed, 7px);
  inset: calc(0px - var(--glow-bleed) - 3px);
  z-index: 0;
  background: var(--wc-purple);
  pointer-events: none;
  filter: drop-shadow(0 0 6px rgba(90, 46, 128, 0.85))
          drop-shadow(0 0 14px rgba(90, 46, 128, 0.5));
  transition: background 300ms var(--wc-ease-out),
              filter 300ms var(--wc-ease-out),
              --glow-bleed 800ms cubic-bezier(0.16, 1, 0.3, 1);
  clip-path: polygon(
    var(--glow-bleed) calc(var(--glow-bleed) + var(--slide-h)),
    calc(var(--glow-bleed) + var(--slide-w)) var(--glow-bleed),
    calc(var(--notch-x) - var(--notch-w) / 2) var(--glow-bleed),
    calc(var(--notch-x) - var(--notch-w) / 2 + var(--notch-d)) calc(var(--glow-bleed) + var(--notch-d)),
    calc(var(--notch-x) + var(--notch-w) / 2 - var(--notch-d)) calc(var(--glow-bleed) + var(--notch-d)),
    calc(var(--notch-x) + var(--notch-w) / 2) var(--glow-bleed),
    calc(100% - var(--glow-bleed) - var(--slide-w)) var(--glow-bleed),
    calc(100% - var(--glow-bleed)) calc(var(--glow-bleed) + var(--slide-h)),
    calc(100% - var(--glow-bleed)) calc(100% - var(--glow-bleed) - var(--step-d) - var(--slide-h)),
    calc(100% - var(--glow-bleed) - var(--slide-w)) calc(100% - var(--glow-bleed) - var(--step-d)),
    calc(var(--glow-bleed) + var(--step-x) + var(--step-slope-w)) calc(100% - var(--glow-bleed) - var(--step-d)),
    calc(var(--glow-bleed) + var(--step-x)) calc(100% - var(--glow-bleed)),
    calc(var(--glow-bleed) + var(--slide-w)) calc(100% - var(--glow-bleed)),
    var(--glow-bleed) calc(100% - var(--glow-bleed) - var(--slide-h)));
}
.wc2-notch-wrap:hover .wc2-notch__glow,
.wc2-card-autowrap:hover .wc2-notch__glow {
  background: var(--wc-purple-bright);
  filter: drop-shadow(0 0 12px rgba(139, 77, 196, 1))
          drop-shadow(0 0 28px rgba(139, 77, 196, 0.75));
  /* Lift WITH the card so shadow + card animate as one unit */
  transform: translateY(-3px);
  --glow-bleed: var(--hover-bleed, var(--rest-bleed, 7px));
}
/* VARIANTS WITHOUT A BOTTOM TAB — opt out of the --glow-bleed bleed
   system. The bleed system extends the polygon's tab area, but Bottom
   (notch on bottom, no tab) and Keycard (top tab + side notches, no
   bottom tab) have no "tab" to extend. Keeping their old fixed -3px
   inset gives them a clean 3px purple ring without the giant halo. */
.wc2-notch__glow[data-edge="bottom"],
.wc2-notch__glow[data-edge="sides"] {
  --glow-bleed: 0px;             /* no-op since these polygons don't use it */
  inset: -3px;                   /* restore fixed 3px outer ring */
}

/* FOUNDATION glow polygon — straight top + bottom notch + 4 corner slides.
   Matches the .wc2-notch[data-edge="bottom"] shape exactly (no top notch,
   no bottom tab — just a notch CUT IN at the bottom center). */
.wc2-notch__glow[data-edge="bottom"] {
  clip-path: polygon(
    0 var(--slide-h),
    var(--slide-w) 0,
    calc(100% - var(--slide-w)) 0,
    100% var(--slide-h),
    100% calc(100% - var(--slide-h)),
    calc(100% - var(--slide-w)) 100%,
    calc(var(--notch-x) + var(--notch-w) / 2) 100%,
    calc(var(--notch-x) + var(--notch-w) / 2 - var(--notch-d)) calc(100% - var(--notch-d)),
    calc(var(--notch-x) - var(--notch-w) / 2 + var(--notch-d)) calc(100% - var(--notch-d)),
    calc(var(--notch-x) - var(--notch-w) / 2) 100%,
    var(--slide-w) 100%,
    0 calc(100% - var(--slide-h)));
}
/* KEYCARD glow polygon — wide top tab + side notches, NO bottom tab.
   Matches the .wc2-notch[data-edge="sides"] shape exactly. */
.wc2-notch__glow[data-edge="sides"] {
  clip-path: polygon(
    0 calc(var(--top-tab-d) + var(--slide-h)),
    var(--slide-w) var(--top-tab-d),
    var(--top-tab-x) var(--top-tab-d),
    calc(var(--top-tab-x) + var(--step-slope-w)) 0,
    calc(var(--top-tab-x) + var(--top-tab-w) - var(--step-slope-w)) 0,
    calc(var(--top-tab-x) + var(--top-tab-w)) var(--top-tab-d),
    calc(100% - var(--slide-w)) var(--top-tab-d),
    100% calc(var(--top-tab-d) + var(--slide-h)),
    100% calc(var(--notch-y) - var(--notch-h) / 2),
    calc(100% - var(--notch-d)) calc(var(--notch-y) - var(--notch-h) / 2),
    calc(100% - var(--notch-d)) calc(var(--notch-y) + var(--notch-h) / 2),
    100% calc(var(--notch-y) + var(--notch-h) / 2),
    100% calc(100% - var(--slide-h)),
    calc(100% - var(--slide-w)) 100%,
    var(--slide-w) 100%,
    0 calc(100% - var(--slide-h)),
    0 calc(var(--notch-y) + var(--notch-h) / 2),
    var(--notch-d) calc(var(--notch-y) + var(--notch-h) / 2),
    var(--notch-d) calc(var(--notch-y) - var(--notch-h) / 2),
    0 calc(var(--notch-y) - var(--notch-h) / 2),
    0 calc(var(--top-tab-d) + var(--slide-h)));
}
.wc2-notch__glow {
  transition: background 300ms var(--wc-ease-out),
              filter 300ms var(--wc-ease-out),
              transform 240ms var(--wc-ease-out);
}

/* Hover audio-wave outline beam — applies to .wc2-notch + .wc2-tentry cards.
   LIME beam (matches the .wc2-ngcc card family on hover). Peak 30, hover-only. */
.wc2-card__beam {
  position: absolute;
  inset: 0;
  pointer-events: none;
  z-index: 4;
  opacity: 0;
  overflow: visible;
  transition: opacity 220ms var(--wc-ease-out);
  filter: drop-shadow(0 0 3px var(--wc-lime))
          drop-shadow(0 0 6px color-mix(in srgb, var(--wc-lime) 50%, transparent));
}
.wc2-notch:hover > .wc2-card__beam,
.wc2-notch-wrap:hover .wc2-notch > .wc2-card__beam,
.wc2-tentry:hover > .wc2-card__beam {
  opacity: 1;
}
.wc2-card__beam path {
  fill: none;
  stroke: var(--wc-lime);
  stroke-linecap: round;
  animation: wc2-beam-travel 2.4s linear infinite;
}
/* LIME OUTLINE on hover — outer (ring) becomes lime, inner (::before)
   becomes ground purple. Same ring+inner pattern as .wc2-ngcc family.
   The 1px-smaller inner polygon leaves a visible lime thin outline
   tracing the notch shape exactly. */
.wc2-notch:hover,
.wc2-notch-wrap:hover .wc2-notch {
  background: var(--wc-lime);
  transition: background 240ms var(--wc-ease-out);
}
.wc2-notch:hover::before,
.wc2-notch-wrap:hover .wc2-notch::before {
  background: var(--bg-hover);
}
.wc2-notch:hover .wc2-notch__head,
.wc2-notch-wrap:hover .wc2-notch__head {
  color: var(--wc-lime);
  transition: color 240ms var(--wc-ease-out);
}

/* Bevel variant — angled notch walls + 4 corner slides. */
.wc2-notch.bevel {
  clip-path: polygon(
    0 var(--slide-h),
    var(--slide-w) 0,
    calc(var(--notch-x) - var(--notch-w) / 2) 0,
    calc(var(--notch-x) - var(--notch-w) / 2 + var(--notch-d)) var(--notch-d),
    calc(var(--notch-x) + var(--notch-w) / 2 - var(--notch-d)) var(--notch-d),
    calc(var(--notch-x) + var(--notch-w) / 2) 0,
    calc(100% - var(--slide-w)) 0,
    100% var(--slide-h),
    100% calc(100% - var(--step-d) - var(--slide-h)),
    calc(100% - var(--slide-w)) calc(100% - var(--step-d)),
    calc(var(--step-x) + var(--step-slope-w)) calc(100% - var(--step-d)),
    var(--step-x) 100%,
    var(--slide-w) 100%,
    0 calc(100% - var(--slide-h)));
}
.wc2-notch.bevel::before {
  clip-path: polygon(
    1px calc(var(--slide-h) + 1px),
    calc(var(--slide-w) + 1px) 1px,
    calc(var(--notch-x) - var(--notch-w) / 2 - 0.414px) 1px,
    calc(var(--notch-x) - var(--notch-w) / 2 + var(--notch-d) - 0.414px) calc(var(--notch-d) + 1px),
    calc(var(--notch-x) + var(--notch-w) / 2 - var(--notch-d) + 0.414px) calc(var(--notch-d) + 1px),
    calc(var(--notch-x) + var(--notch-w) / 2 + 0.414px) 1px,
    calc(100% - var(--slide-w) - 1px) 1px,
    calc(100% - 1px) calc(var(--slide-h) + 1px),
    calc(100% - 1px) calc(100% - var(--step-d) - var(--slide-h) - 1px),
    calc(100% - var(--slide-w) - 1px) calc(100% - var(--step-d) - 1px),
    calc(var(--step-x) + var(--step-slope-w) - 1px) calc(100% - var(--step-d) - 1px),
    calc(var(--step-x) - 1px) calc(100% - 1px),
    calc(var(--slide-w) + 1px) calc(100% - 1px),
    1px calc(100% - var(--slide-h) - 1px));
}

/* Deep variant — taller notch */
.wc2-notch.deep { --notch-d: 28px; padding-top: 48px; }

/* Bottom edge variant — 45° sloped notch on bottom + 4 corner slides. */
.wc2-notch[data-edge="bottom"] {
  padding: 28px 28px 36px;
  clip-path: polygon(
    0 var(--slide-h),
    var(--slide-w) 0,
    calc(100% - var(--slide-w)) 0,
    100% var(--slide-h),
    100% calc(100% - var(--slide-h)),
    calc(100% - var(--slide-w)) 100%,
    calc(var(--notch-x) + var(--notch-w) / 2) 100%,
    calc(var(--notch-x) + var(--notch-w) / 2 - var(--notch-d)) calc(100% - var(--notch-d)),
    calc(var(--notch-x) - var(--notch-w) / 2 + var(--notch-d)) calc(100% - var(--notch-d)),
    calc(var(--notch-x) - var(--notch-w) / 2) 100%,
    var(--slide-w) 100%,
    0 calc(100% - var(--slide-h)));
}
.wc2-notch[data-edge="bottom"]::before {
  clip-path: polygon(
    1px calc(var(--slide-h) + 1px),
    calc(var(--slide-w) + 1px) 1px,
    calc(100% - var(--slide-w) - 1px) 1px,
    calc(100% - 1px) calc(var(--slide-h) + 1px),
    calc(100% - 1px) calc(100% - var(--slide-h) - 1px),
    calc(100% - var(--slide-w) - 1px) calc(100% - 1px),
    calc(var(--notch-x) + var(--notch-w) / 2 + 0.414px) calc(100% - 1px),
    calc(var(--notch-x) + var(--notch-w) / 2 - var(--notch-d) + 0.414px) calc(100% - var(--notch-d) - 1px),
    calc(var(--notch-x) - var(--notch-w) / 2 + var(--notch-d) - 0.414px) calc(100% - var(--notch-d) - 1px),
    calc(var(--notch-x) - var(--notch-w) / 2 - 0.414px) calc(100% - 1px),
    calc(var(--slide-w) + 1px) calc(100% - 1px),
    1px calc(100% - var(--slide-h) - 1px));
}

/* Side notches: left + right edges (key-card look) + 4 corner slides. */
.wc2-notch[data-edge="sides"] {
  --notch-y: 50%;
  --notch-h: 80px;
  --notch-d: 16px;
  /* WIDE TOP TAB — sticks up across 70% of the top edge. */
  --top-tab-x: 15%;
  --top-tab-w: 70%;
  --top-tab-d: 14px;
  padding: 42px 36px 28px;
  clip-path: polygon(
    /* top edge with WIDE TAB sticking up */
    0 calc(var(--top-tab-d) + var(--slide-h)),
    var(--slide-w) var(--top-tab-d),
    var(--top-tab-x) var(--top-tab-d),
    calc(var(--top-tab-x) + var(--step-slope-w)) 0,
    calc(var(--top-tab-x) + var(--top-tab-w) - var(--step-slope-w)) 0,
    calc(var(--top-tab-x) + var(--top-tab-w)) var(--top-tab-d),
    calc(100% - var(--slide-w)) var(--top-tab-d),
    100% calc(var(--top-tab-d) + var(--slide-h)),
    /* right side notch */
    100% calc(var(--notch-y) - var(--notch-h) / 2),
    calc(100% - var(--notch-d)) calc(var(--notch-y) - var(--notch-h) / 2),
    calc(100% - var(--notch-d)) calc(var(--notch-y) + var(--notch-h) / 2),
    100% calc(var(--notch-y) + var(--notch-h) / 2),
    /* straight right edge to bottom (NO bottom tab) */
    100% calc(100% - var(--slide-h)),
    calc(100% - var(--slide-w)) 100%,
    var(--slide-w) 100%,
    0 calc(100% - var(--slide-h)),
    /* left side notch */
    0 calc(var(--notch-y) + var(--notch-h) / 2),
    var(--notch-d) calc(var(--notch-y) + var(--notch-h) / 2),
    var(--notch-d) calc(var(--notch-y) - var(--notch-h) / 2),
    0 calc(var(--notch-y) - var(--notch-h) / 2),
    0 calc(var(--top-tab-d) + var(--slide-h)));
}
.wc2-notch[data-edge="sides"]::before {
  clip-path: polygon(
    1px calc(var(--top-tab-d) + var(--slide-h) + 1px),
    calc(var(--slide-w) + 1px) calc(var(--top-tab-d) + 1px),
    calc(var(--top-tab-x) - 0.414px) calc(var(--top-tab-d) + 1px),
    calc(var(--top-tab-x) + var(--step-slope-w) - 0.414px) 1px,
    calc(var(--top-tab-x) + var(--top-tab-w) - var(--step-slope-w) + 0.414px) 1px,
    calc(var(--top-tab-x) + var(--top-tab-w) + 0.414px) calc(var(--top-tab-d) + 1px),
    calc(100% - var(--slide-w) - 1px) calc(var(--top-tab-d) + 1px),
    calc(100% - 1px) calc(var(--top-tab-d) + var(--slide-h) + 1px),
    calc(100% - 1px) calc(var(--notch-y) - var(--notch-h) / 2 - 1px),
    calc(100% - var(--notch-d) - 1px) calc(var(--notch-y) - var(--notch-h) / 2 - 1px),
    calc(100% - var(--notch-d) - 1px) calc(var(--notch-y) + var(--notch-h) / 2 + 1px),
    calc(100% - 1px) calc(var(--notch-y) + var(--notch-h) / 2 + 1px),
    calc(100% - 1px) calc(100% - var(--slide-h) - 1px),
    calc(100% - var(--slide-w) - 1px) calc(100% - 1px),
    calc(var(--slide-w) + 1px) calc(100% - 1px),
    1px calc(100% - var(--slide-h) - 1px),
    1px calc(var(--notch-y) + var(--notch-h) / 2 + 1px),
    calc(var(--notch-d) + 1px) calc(var(--notch-y) + var(--notch-h) / 2 + 1px),
    calc(var(--notch-d) + 1px) calc(var(--notch-y) - var(--notch-h) / 2 - 1px),
    1px calc(var(--notch-y) - var(--notch-h) / 2 - 1px),
    1px calc(var(--top-tab-d) + var(--slide-h) + 1px));
}

/* Wrap notch cards so the tab can sit OUTSIDE the clipped polygon.
   <div class="wc2-notch-wrap">
     <span class="wc2-notch__tab">SLOT 01</span>
     <div class="wc2-notch" data-edge="top">...</div>
   </div>
*/
.wc2-notch-wrap {
  position: relative;
  display: block;
}
.wc2-notch__tab {
  position: absolute;
  top: 2px;
  left: 50%;
  transform: translateX(-50%);
  z-index: 3;
  height: calc(var(--notch-d, 18px) - 2px);
  padding: 0 28px;
  display: inline-flex; align-items: center;
  background: var(--wc-lime);
  color: var(--wc-bg);
  font: 800 9px var(--wc-font-mono);
  letter-spacing: 0.24em;
  text-transform: uppercase;
  /* Hover-aware — mouse-on-tab triggers wrap:hover so the whole unit lifts. */
  cursor: pointer;
  /* Tab chip — TAB SHAPE: narrower at top, wider at bottom. 45° slopes on
     the top corners. Mirrors the way the notch widens as it goes up. */
  clip-path: polygon(
    10px 0,
    calc(100% - 10px) 0,
    100% 100%,
    0 100%);
  transition: transform 280ms cubic-bezier(0.2, 0.85, 0.3, 1.1);
}
/* Tab rides up WITH the notch card on hover. Uses wrap-based hover (works
   in every browser — no :has() dependency). Pointer-events: none on the
   tab means mouse-on-tab passes through to the notch beneath, which still
   triggers wrap:hover correctly. */
.wc2-notch-wrap:hover .wc2-notch__tab {
  transform: translateX(-50%) translateY(-3px);
}
.wc2-notch-wrap:hover .wc2-notch {
  transform: translateY(-3px);
}
.wc2-notch__head {
  font-family: var(--wc-font-display);
  font-size: 18px;                              /* was 27 — too dominant on smaller notch cards */
  letter-spacing: -0.005em;
  text-transform: uppercase;
  color: var(--wc-ink-1);
  margin: 0 0 8px;
}
.wc2-notch__body {
  font-size: 13px;                  /* fixed from a stray 27px — subtext now reads correctly */
  line-height: 1.55;
  color: var(--wc-ink-3);
  letter-spacing: 0.02em;
  margin: 0;
}

/* Border-beam variant for notch (single bright dot travels the outline) */
.wc2-notch.beam::after {
  content: "";
  position: absolute;
  top: 0; left: 0;
  width: 6px; height: 6px;
  background: var(--wc-lime);
  box-shadow: 0 0 8px var(--wc-lime), 0 0 14px var(--wc-lime);
  border-radius: 50%;
  animation: wc2-notch-orbit 4.5s linear infinite;
  offset-path: polygon(0 0, 100% 0, 100% 100%, 0 100%);
  pointer-events: none;
}
@keyframes wc2-notch-orbit {
  to { offset-distance: 100%; }
}

/* ============================================================
 * TIMELINE — variety + stronger hover
 * ============================================================ */
.wc2-tentry {
  transition:
    background 300ms var(--wc-ease-out),
    transform 240ms var(--wc-ease-out);
}
.wc2-tentry:hover {
  background: var(--wc-lime);        /* LIME RING — matches locked card rule */
  transform: translateX(4px);        /* slide right to reveal the timeline dot */
}
.wc2-tentry:hover .wc2-tentry__role {
  color: var(--wc-lime);
  transition: color 240ms var(--wc-ease-out);
}
.wc2-tentry:hover .wc2-tentry__date {
  text-shadow: 0 0 6px color-mix(in srgb, var(--wc-orange) 60%, transparent);
}

/* Variant: bevel-top notch on the timeline entry */
.wc2-tentry.notch-bevel {
  --notch-x: 50%;
  --notch-w: 110px;
  --notch-d: 14px;
  --clip-shape: polygon(
    0 0,
    calc(var(--notch-x) - var(--notch-w) / 2) 0,
    calc(var(--notch-x) - var(--notch-w) / 2 + var(--notch-d)) var(--notch-d),
    calc(var(--notch-x) + var(--notch-w) / 2 - var(--notch-d)) var(--notch-d),
    calc(var(--notch-x) + var(--notch-w) / 2) 0,
    100% 0,
    100% 100%,
    0 100%);
  padding-top: 28px;
}

/* Variant: right-edge keycard notch on the timeline entry */
.wc2-tentry.notch-right {
  --notch-y: 50%;
  --notch-h: 56px;
  --notch-d: 27px;
  --clip-shape: polygon(
    0 0, 100% 0,
    100% calc(var(--notch-y) - var(--notch-h) / 2),
    calc(100% - var(--notch-d)) calc(var(--notch-y) - var(--notch-h) / 2),
    calc(100% - var(--notch-d)) calc(var(--notch-y) + var(--notch-h) / 2),
    100% calc(var(--notch-y) + var(--notch-h) / 2),
    100% 100%, 0 100%);
}

/* Variant: rect top-notch on the timeline entry, with a small lime tab */
.wc2-tentry.notch-top {
  --notch-x: 50%;
  --notch-w: 100px;
  --notch-d: 14px;
  --clip-shape: polygon(
    0 0,
    calc(var(--notch-x) - var(--notch-w) / 2) 0,
    calc(var(--notch-x) - var(--notch-w) / 2) var(--notch-d),
    calc(var(--notch-x) + var(--notch-w) / 2) var(--notch-d),
    calc(var(--notch-x) + var(--notch-w) / 2) 0,
    100% 0,
    100% 100%,
    0 100%);
  padding-top: 28px;
}
