/*
 * recipe-typography.css — kinetic headline recipes (APB_Section_Recipes_Typography). FAIL-OPEN: the
 * headline is fully readable with no JS; enhanced states are scoped under [data-apb-anim-on] (set by the
 * kinetic-text module) or are pure CSS loops. apb-kt-* namespace.
 */
/* wrap must be wide enough for a big display headline: 20ch (measured on the wrapper's OWN small font)
   collapsed these headlines to one-word-per-line and clipped long words. A vw/px cap is predictable and
   still centered; individual variants that want a tighter measure set it on their own headline. */
.apb-kt .apb-kt-wrap{max-width:min(92vw,900px);margin:0 auto;text-align:center;padding:clamp(24px,5vh,64px) 0;overflow-wrap:break-word}
.apb-kt h2{font-size:clamp(30px,6vw,72px);font-weight:800;letter-spacing:-.03em;line-height:1.05;margin:0}
.apb-kt .apb-rx-eyebrow{margin:0 0 14px}
.apb-kt .apb-kt-sub{margin:18px auto 0;max-width:46ch;color:var(--apb-rx-dim,#64748b);font-size:clamp(15px,2vw,19px)}

/* scramble — monospace-ish tabular feel while decoding (JS drives textContent) */
.apb-kt--scramble .apb-kt-target{font-variant-numeric:tabular-nums}

/* rotator — the cycling word swaps with a quick fade/rise */
.apb-kt--rotator .apb-kt-rotate{display:inline-block;color:var(--apb-rx-accent-text,var(--apb-rx-accent,#4f46e5));transition:opacity .25s,transform .25s;will-change:opacity,transform}
.apb-kt--rotator .apb-kt-rotate.is-swapping{opacity:0;transform:translateY(-.35em)}

/* stagger — words reveal one-by-one; default visible (fail-open), hidden only once JS marks ready */
.apb-kt--stagger .apb-kt-word{display:inline-block}
.apb-kt--stagger[data-apb-anim-on] .apb-kt-word{opacity:0;transform:translateY(16px);transition:opacity .5s ease,transform .5s cubic-bezier(.2,.7,.2,1);transition-delay:calc(var(--i) * 60ms)}
.apb-kt--stagger.is-in .apb-kt-word{opacity:1;transform:none}

/* gradient sweep — animated gradient clipped to the text (CSS-only) */
.apb-kt--gradient .apb-kt-grad{
  background:linear-gradient(90deg,var(--apb-rx-accent,#4f46e5),var(--apb-rx-brand2,var(--apb-rx-accent,#0ea5e9)),var(--apb-rx-accent,#4f46e5));
  background-size:220% 100%;-webkit-background-clip:text;background-clip:text;color:transparent;
  animation:apb-kt-sweep 6s linear infinite}
@keyframes apb-kt-sweep{to{background-position:220% 0}}

/* underline — a highlighter stroke draws under the keyword (CSS-only) */
.apb-kt--underline .apb-kt-ul{position:relative;white-space:nowrap}
.apb-kt--underline .apb-kt-ul::after{content:"";position:absolute;left:0;right:100%;bottom:.06em;height:.5em;border-radius:.25em;
  background:var(--apb-rx-accent,#4f46e5);opacity:.28;z-index:-1;animation:apb-kt-draw 1.1s .3s cubic-bezier(.2,.7,.2,1) forwards}
@keyframes apb-kt-draw{to{right:0}}

/* split-flap board */
.apb-kt--splitflap .apb-kt-flapboard{display:inline-flex;flex-wrap:wrap;justify-content:center;gap:5px}
.apb-kt--splitflap .apb-kt-flap{display:inline-flex;align-items:center;justify-content:center;min-width:.72em;padding:.12em .14em;
  background:#18181b;color:#fafafa;border-radius:7px;font-variant-numeric:tabular-nums;box-shadow:inset 0 1px 0 rgba(255,255,255,.07),0 2px 6px rgba(0,0,0,.25);will-change:transform}
.apb-kt--splitflap .apb-kt-flap.is-flipping{animation:apb-kt-flip .12s linear}
@keyframes apb-kt-flip{50%{transform:scaleY(.5)}}

/* typewriter */
.apb-kt--typewriter .apb-kt-typed{white-space:pre-wrap}
.apb-kt--typewriter .apb-kt-caret{display:inline-block;width:.06em;height:1em;background:currentColor;margin-left:.04em;vertical-align:-.08em;animation:apb-kt-blink 1s steps(1) infinite}
.apb-kt--typewriter.is-typed .apb-kt-caret{opacity:0;animation:none}
@keyframes apb-kt-blink{50%{opacity:0}}

/* image-in-text */
.apb-kt--textmask .apb-kt-mask{font-size:clamp(56px,15vw,190px);font-weight:900;letter-spacing:-.04em;line-height:.95;
  background-image:var(--apb-kt-img);background-size:cover;background-position:center;-webkit-background-clip:text;background-clip:text;color:transparent}

/* glitch */
.apb-kt--glitch .apb-kt-glitch{position:relative;display:inline-block;color:var(--apb-rx-fg,#0b1020)}
.apb-kt--glitch .apb-kt-glitch::before,.apb-kt--glitch .apb-kt-glitch::after{content:attr(data-text);position:absolute;left:0;top:0;width:100%;pointer-events:none}
.apb-kt--glitch .apb-kt-glitch::before{color:color-mix(in srgb,var(--apb-rx-accent,#4f46e5) 60%,#ff2d95);animation:apb-kt-g1 2.6s infinite steps(2)}
.apb-kt--glitch .apb-kt-glitch::after{color:color-mix(in srgb,var(--apb-rx-brand2,var(--apb-rx-accent,#4f46e5)) 60%,#00e5ff);animation:apb-kt-g2 2.6s infinite steps(2)}
@keyframes apb-kt-g1{0%,92%,100%{transform:none;clip-path:inset(0 0 0 0)}94%{transform:translate(-3px,1px);clip-path:inset(20% 0 55% 0)}96%{transform:translate(2px,-1px);clip-path:inset(60% 0 10% 0)}}
@keyframes apb-kt-g2{0%,92%,100%{transform:none;clip-path:inset(0 0 0 0)}94%{transform:translate(3px,-1px);clip-path:inset(50% 0 30% 0)}96%{transform:translate(-2px,1px);clip-path:inset(10% 0 65% 0)}}

/* line-mask (reuses the stagger behavior's data-apb-anim-on / .is-in on the section) */
.apb-kt--linemask .apb-kt-line{display:block;overflow:hidden}
.apb-kt--linemask .apb-kt-line > span{display:inline-block;will-change:transform}
.apb-kt--linemask[data-apb-anim-on] .apb-kt-line > span{transform:translateY(115%);transition:transform .6s cubic-bezier(.2,.7,.2,1);transition-delay:calc(var(--i) * 90ms)}
.apb-kt--linemask.is-in .apb-kt-line > span{transform:none}

@media (prefers-reduced-motion:reduce){
  .apb-kt--gradient .apb-kt-grad{animation:none;background-position:0 0}
  .apb-kt--underline .apb-kt-ul::after{animation:none;right:0}
  .apb-kt--glitch .apb-kt-glitch::before,.apb-kt--glitch .apb-kt-glitch::after{animation:none;opacity:0}
  .apb-kt--typewriter .apb-kt-caret{animation:none;opacity:1}
  .apb-kt--splitflap .apb-kt-flap.is-flipping{animation:none}
}
