/* ═══════════════════════════════════════════════════════════
   Birkari – Shared Components
   Header, buttons, toggles, book
   ═══════════════════════════════════════════════════════════ */

/* ── Header bar (unified for all pages) ── */
.header,
.page-header {
  position: sticky; top: 0;
  z-index: 100;
  display: flex; align-items: center; justify-content: space-between;
  padding: 14px 20px;
  background: var(--bg);
  transition: background .35s cubic-bezier(.22,1,.36,1),
              box-shadow .35s cubic-bezier(.22,1,.36,1),
              margin .35s cubic-bezier(.22,1,.36,1),
              border-radius .35s cubic-bezier(.22,1,.36,1),
              padding .35s cubic-bezier(.22,1,.36,1);
}
.header { position: fixed; left: 0; right: 0; background: transparent; }

/* Landing header only: layout locked to LTR (brand left, controls right)
   in BOTH languages. Secondary pages' .page-header deliberately follows
   the document direction, so the Back button sits — and points — the way
   the reading direction expects. */
.header { direction: ltr; }

/* Teal glow line */
.header::after,
.page-header::after {
  content: '';
  position: absolute;
  bottom: 0;
  left: 16px; right: 16px;
  height: 2px;
  border-radius: 0 0 var(--radius-md) var(--radius-md);
  background: radial-gradient(ellipse 40% 100% at 50% 50%, var(--accent), transparent);
  opacity: 0;
  transition: opacity .4s cubic-bezier(.22,1,.36,1), left .35s, right .35s;
  pointer-events: none;
}

/* Scrolled state — visual card via ::before, header stays full-width */
.header.scrolled,
.page-header.scrolled {
  background: transparent;
}
.header::before,
.page-header::before {
  content: '';
  position: absolute;
  inset: 4px 10px 0;
  background: var(--surface);
  box-shadow: var(--shadow-raised-sm);
  border-radius: var(--radius-md);
  opacity: 0;
  transition: opacity .35s cubic-bezier(.22,1,.36,1);
  z-index: -1;
  pointer-events: none;
}
.header.scrolled::before,
.page-header.scrolled::before {
  opacity: 1;
}
.header.scrolled::after,
.page-header.scrolled::after {
  opacity: .6;
  left: 18px;
  right: 18px;
}

/* ── Birkari.com wordmark ── */
.brand-wordmark {
  display: inline-flex;
  align-items: center;
  direction: ltr;
  unicode-bidi: isolate;
  font-family: 'IBM Plex Mono', 'SFMono-Regular', Consolas, 'Liberation Mono', monospace;
  font-weight: 700;
  letter-spacing: .02em;
  line-height: 1;
  color: var(--text-primary);
}
.brand-wordmark__suffix {
  display: inline-block;
  margin-inline-start: .08em;
  padding: .1em .22em .13em;
  border-radius: .38em;
  background: var(--surface);
  color: var(--accent);
  font-weight: 600;
  line-height: 1;
  box-shadow:
    inset 1px 1px 2px rgba(0,0,0,.05),
    inset -1px -1px 2px rgba(255,255,255,.5);
}
[data-theme="dark"] .brand-wordmark__suffix {
  box-shadow:
    inset 1px 1px 2px rgba(0,0,0,.3),
    inset -1px -1px 2px rgba(255,255,255,.04);
}

/* Obelus flourish — the suffix period occasionally evolves into a divide
   sign (Birkari ÷ com) and settles back. This default state renders as a
   plain period, so pages without app.js (or with reduced motion) just show
   the classic mark. Opt-in via markup; motion driven from app.js. */
.brand-obelus {
  position: relative;
  display: inline-block;
  width: .6em;
  height: .62em;
  vertical-align: -.02em;
}
.brand-obelus__dot,
.brand-obelus__echo {
  position: absolute;
  left: 50%;
  top: 0;
  width: .15em;
  height: .15em;
  border-radius: 50%;
  background: currentColor;
  transform: translate(-50%, .47em);
}
.brand-obelus__echo {
  opacity: 0;
  transform: translate(-50%, .47em) scale(0);
}
.brand-obelus__line {
  position: absolute;
  top: 50%;
  left: .03em;
  right: .03em;
  height: .09em;
  transform: translateY(-50%) scaleX(0);
  background: var(--text-primary);
  border-radius: 99px;
}
.brand-obelus__sym {
  position: absolute;
  left: 0;
  right: 0;
  bottom: .02em;
  text-align: center;
  font-size: .68em;
  color: currentColor;
  opacity: 0;
}
.brand-obelus__com {
  display: inline-block;
  white-space: nowrap;
}
.brand-obelus__com i { font-style: normal; }



/* Back button (inner pages) */
.page-header__back {
  width: 40px; height: 40px;
  border-radius: 14px; border: none;
  background: var(--surface);
  box-shadow: var(--shadow-raised-sm);
  display: flex; align-items: center; justify-content: center;
  cursor: pointer; color: var(--text-secondary);
  transition: all .2s var(--ease-out);
  -webkit-tap-highlight-color: transparent;
}
.page-header__back:active {
  box-shadow: var(--shadow-inset); transform: scale(.94);
}
[dir="ltr"] .page-header__back svg { transform: scaleX(-1); }

/* Compact, lighter glyphs inside the 40px header buttons — the icon sits
   small in the tile (like the demo app-bar) instead of filling it */
.page-header__back svg {
  width: 14px; height: 14px;
  stroke-width: 2;
}
.hamburger-btn svg {
  width: 15px; height: 15px;
  stroke-width: 2;
}


/* ── Toggle pill (shared for lang + theme) ──
   A true segmented toggle: equal-width segments locked to LTR order, so
   the labels never swap sides on language change — only the raised thumb
   slides to the active side. Font stack is pinned (not inherited) so
   segment widths don't shift when the body font swaps per language. */
.toggle-pill {
  position: relative;
  display: inline-grid;
  grid-auto-flow: column;
  grid-auto-columns: 1fr;
  direction: ltr;
  border-radius: var(--radius-pill);
  background: var(--surface);
  box-shadow: var(--shadow-inset);
  padding: 4px; gap: 2px; overflow: hidden;
}
.toggle-pill__btn {
  position: relative; z-index: 1;
  padding: 5px 14px; border: none; border-radius: var(--radius-pill);
  background: transparent; color: var(--text-muted);
  font-family: 'Outfit', 'Noto Sans Arabic', sans-serif;
  font-size: .7rem; font-weight: 700;
  cursor: pointer;
  transition: all .25s var(--ease-out);
  -webkit-tap-highlight-color: transparent;
  white-space: nowrap;
}
.toggle-pill__btn.active {
  background: var(--surface);
  box-shadow: var(--shadow-raised-sm);
  color: var(--text-primary);
}
.toggle-pill__btn:not(.active):hover { color: var(--text-secondary); }

/* Sliding thumb — browsers without :has() keep the raised state above.
   Geometry: pill padding 4px + 2px gap → each segment = 50% − 5px. */
@supports selector(:has(*)) {
  .toggle-pill::before {
    content: '';
    position: absolute;
    top: 4px; bottom: 4px; left: 4px;
    width: calc(50% - 5px);
    border-radius: var(--radius-pill);
    background: var(--surface);
    box-shadow: var(--shadow-raised-sm);
    opacity: 0;
    transition: transform .35s cubic-bezier(.22,1,.36,1), opacity .2s;
  }
  .toggle-pill:has(.toggle-pill__btn.active)::before { opacity: 1; }
  .toggle-pill:has(.toggle-pill__btn:last-child.active)::before {
    transform: translateX(calc(100% + 2px));
  }
  .toggle-pill__btn.active { background: transparent; box-shadow: none; }
}

/* ── Theme toggle (icon button) ── */
.theme-toggle {
  position: relative;
  overflow: hidden; /* clips the theme fill to the rounded corners */
  width: 40px; height: 40px;
  border-radius: 14px;
  border: none;
  background: var(--surface);
  box-shadow: var(--shadow-raised-sm);
  display: flex; align-items: center; justify-content: center;
  cursor: pointer; color: var(--text-secondary);
  font-size: 1rem;
  transition: all .2s var(--ease-out);
  -webkit-tap-highlight-color: transparent;
}
.theme-toggle:active {
  box-shadow: var(--shadow-inset);
  transform: scale(.93);
}
.theme-toggle svg { position: relative; z-index: 1; }

/* Theme-switch flourish: a "glass" of the incoming theme's background
   fills the button from the bottom, then the page follows (app.js injects
   the span and drives the timing). Transform/opacity only — cheap on
   mobile. Colors mirror tokens.css --bg (:root / [data-theme="dark"]). */
.theme-toggle__fill {
  position: absolute; inset: 0; z-index: 0;
  border-radius: inherit;
  transform: translateY(101%);
  pointer-events: none;
}
.theme-toggle__fill[data-fill="light"] { background: #e5eaee; }
.theme-toggle__fill[data-fill="dark"]  { background: #2b2822; }
.theme-toggle__fill.is-rising {
  transform: translateY(0);
  transition: transform .3s cubic-bezier(.22,1,.36,1);
}
.theme-toggle__fill.is-fading {
  transform: translateY(0);
  opacity: 0;
  transition: opacity .28s ease;
}

/* ── CTA button ── */
.btn-cta {
  display: inline-flex; align-items: center; justify-content: center;
  gap: 8px;
  padding: 16px 36px;
  border: none; border-radius: var(--radius-md);
  background: var(--accent);
  color: var(--accent-text);
  font-family: inherit; font-size: .95rem; font-weight: 700;
  cursor: pointer;
  box-shadow: var(--shadow-raised);
  transition: transform .2s var(--ease-out);
  -webkit-tap-highlight-color: transparent;
  position: relative;
  isolation: isolate;
}
/* Ambient glow lives on a pseudo-element so the pulse animates opacity
   (compositor-only) instead of box-shadow (which repaints every frame). */
.btn-cta::before {
  content: '';
  position: absolute;
  inset: 0;
  z-index: -1;
  border-radius: inherit;
  box-shadow: 0 0 22px 2px var(--accent-glow), 0 0 46px 8px var(--accent-glow);
  opacity: .5;
  animation: btn-glow-fade 2.5s ease-in-out infinite;
  pointer-events: none;
}
@keyframes btn-glow-fade {
  0%, 100% { opacity: .4; }
  50% { opacity: .95; }
}
@media (prefers-reduced-motion: reduce) {
  .btn-cta::before { animation: none; }
}
.btn-cta:hover {
  background: var(--accent-hover);
  transform: translateY(-2px) scale(1.03);
}
.btn-cta:active {
  transform: scale(.97);
  box-shadow: var(--shadow-inset);
}
/* .btn-cta ambient glow now lives on .btn-cta::before (opacity-animated);
   --shadow-raised is already theme-aware, so no dark-mode box-shadow override
   is needed. */

/* ── Book float animation ── */
.book-float {
  animation: book-hover 4s ease-in-out infinite;
  filter: drop-shadow(4px 8px 16px rgba(0,0,0,.15));
  transition: filter .3s;
}
.book-float:hover {
  filter: drop-shadow(6px 12px 24px rgba(0,0,0,.2));
}
@keyframes book-hover {
  0%, 100% { transform: translateY(0) rotate(-1deg); }
  50%      { transform: translateY(-12px) rotate(1deg); }
}

/* ── Inset stage (clay well) ── */
.clay-well {
  background: var(--surface);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-inset-deep);
  padding: 32px 24px;
}

/* ── Live content state surfaces ── */
.live-state-card,
.question-state-card,
.question-loading,
.question-unavailable {
  width: min(100%, 420px);
  margin: 18px auto;
  padding: 22px 20px;
  border-radius: var(--radius-lg);
  background: var(--surface);
  box-shadow: var(--shadow-raised-sm), inset 0 1px 0 rgba(255,255,255,.22);
  color: var(--text-secondary);
  text-align: center;
}

.live-state-card__icon,
.question-state-card__icon,
.question-loading__icon {
  width: 42px;
  height: 42px;
  margin: 0 auto 12px;
  border-radius: 14px;
  background: var(--surface);
  box-shadow: var(--shadow-inset);
  display: grid;
  place-items: center;
  color: var(--accent);
}

.live-state-card__title,
.question-state-card__title,
.question-loading__title {
  color: var(--text-primary);
  font-size: .86rem;
  font-weight: 800;
  margin-bottom: 6px;
}

.live-state-card__body,
.question-state-card__body,
.question-loading__body {
  max-width: 320px;
  margin: 0 auto;
  color: var(--text-muted);
  font-size: .68rem;
  font-weight: 500;
  line-height: 1.8;
}

.retry-btn,
.question-retry-btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  min-height: 38px;
  margin-top: 16px;
  padding: 9px 18px;
  border: 0;
  border-radius: var(--radius-md);
  background: var(--surface);
  box-shadow: var(--shadow-raised-sm);
  color: var(--accent);
  cursor: pointer;
  font: inherit;
  font-size: .72rem;
  font-weight: 800;
  transition: transform .2s var(--ease-out), box-shadow .2s var(--ease-out), color .2s var(--ease-out);
  -webkit-tap-highlight-color: transparent;
}
.retry-btn:hover,
.question-retry-btn:hover {
  color: var(--accent-hover);
  box-shadow: var(--shadow-raised), 0 0 16px var(--accent-glow);
  transform: translateY(-1px);
}
.retry-btn:active,
.question-retry-btn:active {
  box-shadow: var(--shadow-inset);
  transform: scale(.97);
}

.skeleton-line,
.question-skeleton-line {
  display: block;
  height: 12px;
  border-radius: var(--radius-pill);
  background: linear-gradient(90deg, var(--surface-alt) 0%, var(--surface) 42%, var(--surface-alt) 78%);
  background-size: 220% 100%;
  box-shadow: var(--shadow-inset);
  animation: birkari-skeleton 1.35s ease-in-out infinite;
}
.skeleton-line + .skeleton-line,
.question-skeleton-line + .question-skeleton-line { margin-top: 10px; }

@keyframes birkari-skeleton {
  0% { background-position: 100% 0; }
  100% { background-position: -100% 0; }
}

/* ── Infinity loading widget ──
   Lean and stateless: one inline SVG (~0.4KB), a single dash-orbit
   animation, no filters. Continuous motion with no start or end, so
   split-second loads read as deliberate rather than cut off.
   Full size for page-level states; --mini fits the 42px icon tile. */
.bk-loader {
  display: block;
  margin-inline: auto;
  width: 108px;
  height: 81px;
}
.bk-loader .track {
  fill: none;
  stroke: var(--surface-alt);
  stroke-width: 7;
  stroke-linecap: round;
}
.bk-loader .comet,
.bk-loader .core {
  fill: none;
  stroke: var(--accent);
  stroke-linecap: round;
  stroke-dasharray: 22 78;
  stroke-dashoffset: 100;
  animation: bk-loader-trace 1.6s linear infinite;
}
.bk-loader .comet { stroke-width: 7; opacity: .35; }
.bk-loader .core { stroke-width: 5.5; stroke-dasharray: 13 87; }
.bk-loader--mini { width: 38px; height: 28px; }
.bk-loader--mini .track,
.bk-loader--mini .comet { stroke-width: 11; }
.bk-loader--mini .core { stroke-width: 8.5; }
@keyframes bk-loader-trace {
  to { stroke-dashoffset: 0; }
}
@media (prefers-reduced-motion: reduce) {
  .bk-loader .comet,
  .bk-loader .core {
    animation-play-state: paused;
    animation-delay: -.4s; /* rest with the comet visible on the track */
  }
}

.term-highlight,
mark.term-highlight {
  border-radius: 7px;
  padding: 0 .18em;
  background: color-mix(in srgb, var(--accent) 17%, transparent);
  color: var(--text-primary);
  box-shadow: inset 0 -0.14em 0 color-mix(in srgb, var(--accent) 36%, transparent);
}

.graph-asset,
.graph-asset-frame {
  display: grid;
  place-items: center;
  width: min(100%, 460px);
  margin: 16px auto;
  padding: 10px;
  border-radius: var(--radius-lg);
  background: var(--surface);
  box-shadow: var(--shadow-inset);
}
.graph-asset img,
.graph-asset svg,
.graph-asset-frame img,
.graph-asset-frame svg {
  max-width: 100%;
  height: auto;
  border-radius: var(--radius-md);
  filter: drop-shadow(0 8px 14px rgba(0,0,0,.08));
}

@media (prefers-reduced-motion: reduce) {
  .skeleton-line,
  .question-skeleton-line {
    animation: none;
  }
}

/* ══════════════════════════════════════════════════════════════
   Mobile / touch performance guard
   Phones read at 2–3× pixel density on weaker GPUs, and users sit
   on the explanation pages for long stretches. Neutralize the
   effects that force *continuous* repaint / re-raster while idle,
   keeping the visual intent. Desktop (wide + fine pointer) keeps
   the full glass treatment.
     • backdrop-filter re-samples & re-blurs the page behind every
       sticky bar / modal on each scroll frame → drop it and make
       the glass surfaces opaque so they stay legible.
   ══════════════════════════════════════════════════════════════ */
@media (max-width: 768px), (hover: none) and (pointer: coarse) {
  /* Opaque glass — same hue as the translucent value, no bleed-through. */
  :root { --surface-glass: #e5eaee; }
  [data-theme="dark"] { --surface-glass: #302d27; }

  *, *::before, *::after {
    -webkit-backdrop-filter: none !important;
    backdrop-filter: none !important;
  }

  /* Sticky desktop-workspace stepper uses a translucent color-mix bg;
     make it solid too on the off chance it renders on a large touch screen. */
  .dk-stepper-wrap { background: var(--bg) !important; }
}
