/* ==========================================================================
   TARAQI — shell components (navbar · phone bar + menu · sticky register bar · footer)
   Loads after tokens.css. Every color here is a token — no new hues.
   ========================================================================== */

/* --------------------------------------------------------------------------
   Skip link — off-canvas until keyboard focus
   -------------------------------------------------------------------------- */
.skip-link {
  position: fixed;
  inset-block-start: 0.75rem;
  inset-inline-start: 0.75rem;
  z-index: 60;
  padding: 0.5rem 1.25rem;
  border-radius: 9999px;
  background-color: var(--taraqi-burgundy-dark);
  color: var(--taraqi-cream);
  font-weight: 600;
  transform: translateY(-200%);
  transition: transform var(--dur-micro) var(--ease-rise);
}
.skip-link:focus-visible { transform: translateY(0); }

/* --------------------------------------------------------------------------
   Navbar — transparent over the page top, solid Deep Burgundy after 80px.
   The .nav-solid class is toggled by GSAP ScrollTrigger in js/main.js.
   -------------------------------------------------------------------------- */
/* Fixed bar height — identical in both languages so a language toggle never
   moves the bar edge. Sized as mark + T-height clear space above and below
   (the T in TARAQI is ≈22px at the 40px wordmark). A :root token so page
   layouts (the hero) can offset below the fixed bar from the same value. */
:root { --nav-h: 64px; }
@media (min-width: 768px) { :root { --nav-h: 96px; } }

.site-nav {
  background-color: transparent;
  color: var(--taraqi-ink);
  transition:
    background-color var(--dur-micro) var(--ease-rise),
    color var(--dur-micro) var(--ease-rise);
}
.site-nav .nav-bar { block-size: var(--nav-h); }
.site-nav.nav-solid {
  background-color: var(--taraqi-wine);
  color: var(--taraqi-cream);
  /* Same wine as the dark bands, so the bar reads as one surface with them;
     a cream hairline keeps it separate where it sits over a wine band. */
  box-shadow: inset 0 -1px 0 var(--taraqi-line-onDark);
}

/* Logo marks — one SVG per mark (vector-traced from the client's artwork,
   fill="currentColor"), painted through a CSS mask so a single file serves
   every colour: the mark takes its parent's currentColor. <img> cannot
   inherit currentColor, hence the masked span. -webkit- prefixes for older
   Safari. aspect-ratio comes from each SVG's viewBox, so with the same
   block-size the boxes match the old <img> layout — zero shift. The PNG
   variants stay in assets/logos/ as fallback artwork only; nothing
   references them (except og:image, which must stay raster). */
.logo-mark {
  display: block;
  background-color: currentColor;
  -webkit-mask-size: contain;
          mask-size: contain;
  -webkit-mask-repeat: no-repeat;
          mask-repeat: no-repeat;
  -webkit-mask-position: center;
          mask-position: center;
}
.logo-mark--ar {
  aspect-ratio: 376.8 / 296.4;         /* taraqi-ar-mark.svg viewBox */
  -webkit-mask-image: url("../assets/logos/taraqi-ar-mark.svg");
          mask-image: url("../assets/logos/taraqi-ar-mark.svg");
}
.logo-mark--latin {
  aspect-ratio: 581.2 / 185.2;         /* taraqi-en-wordmark.svg viewBox */
  -webkit-mask-image: url("../assets/logos/taraqi-en-wordmark.svg");
          mask-image: url("../assets/logos/taraqi-en-wordmark.svg");
}

/* Navbar mark — the home link. One mark per language (Emaar-style): the
   Arabic mark under html[lang="ar"], the Latin wordmark under html[lang="en"].
   Both marks stay in the DOM; html[lang] hides the inactive one, so the swap
   is pure CSS. Sizes are tokens, not per-element values. The full bilingual
   lockup — both marks, co-equal — lives in the footer. */
/* Mark heights — ONE pair of tokens for every mark instance on the shell
   (navbar and footer share them; rule 4: co-equal treatment everywhere).
   At 40px the Latin wordmark measures ≈126px wide — above the 120px floor. */
:root {
  --logo-ar-h: 44px;       /* Arabic mark, mobile  */
  --logo-latin-h: 40px;    /* Latin wordmark, all sizes — ≥120px wide (brand floor) */
}
@media (min-width: 768px) {
  :root { --logo-ar-h: 56px; }   /* desktop — tashkeel needs the extra height */
}
.nav-logo {
  color: var(--taraqi-burgundy-dark);
  transition:
    opacity var(--dur-micro) var(--ease-rise),
    color var(--dur-micro) var(--ease-rise);
}
.nav-logo:hover,
.nav-logo:focus-visible { opacity: 0.75; }
.nav-logo .logo-ar    { height: var(--logo-ar-h); }
.nav-logo .logo-latin { height: var(--logo-latin-h); }
html[lang="en"] .nav-logo .logo-ar    { display: none; }
html[lang="ar"] .nav-logo .logo-latin { display: none; }

/* Lockup swap: burgundy artwork while the bar sits on cream, cream artwork
   once the bar goes solid burgundy — now just a colour change. */
.nav-solid .nav-logo { color: var(--taraqi-cream); }

/* Nav links — burgundy underline draw (motion moment #6, ≤240ms) */
.nav-link {
  position: relative;
  color: currentColor;
}
.nav-link::after {
  content: "";
  position: absolute;
  inset-inline: 0;
  inset-block-end: -6px;
  block-size: 2px;
  background-color: var(--taraqi-burgundy);
  transform: scaleX(0);
  transform-origin: 0 50%;
  transition:
    transform var(--dur-micro) var(--ease-rise),
    background-color var(--dur-micro) var(--ease-rise);
}
[dir="rtl"] .nav-link::after { transform-origin: 100% 50%; }
.nav-link:hover::after,
.nav-link:focus-visible::after,
.nav-link[aria-current]::after { transform: scaleX(1); }
/* On the solid burgundy bar a burgundy underline vanishes — go cream */
.nav-solid .nav-link::after { background-color: var(--taraqi-cream); }

/* Language toggle — hairline pill, inherits the bar's current color */
.lang-toggle {
  border: 1px solid var(--taraqi-line);
  color: currentColor;
  transition: border-color var(--dur-micro) var(--ease-rise);
}
.nav-solid .lang-toggle { border-color: var(--taraqi-line-onDark); }

/* Primary CTA — Deep Burgundy fill, cream text, hover Burgundy (brand sheet).
   On the solid burgundy bar the fill would disappear, so it inverts to cream. */
.nav-cta {
  background-color: var(--taraqi-burgundy-dark);
  color: var(--taraqi-cream);
  transition:
    background-color var(--dur-micro) var(--ease-rise),
    color var(--dur-micro) var(--ease-rise);
}
.nav-cta:hover { background-color: var(--taraqi-burgundy); }
.nav-solid .nav-cta {
  background-color: var(--taraqi-cream);
  color: var(--taraqi-burgundy-dark);
}
.nav-solid .nav-cta:hover {
  background-color: var(--taraqi-burgundy);
  color: var(--taraqi-cream);
}

/* Direct contact pair — WhatsApp + call, drawn line-work on the one confirmed
   number. Same 2.75rem tap target and stroke treatment as the footer's social
   row so the site has one icon rhythm; the group is pulled tight at both edges
   because the padding is tap area, not optical space. */
.nav-contact {
  margin-inline: -0.625rem;
}
.nav-icon-link {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  inline-size: 2.75rem;
  block-size: 2.75rem;
  color: currentColor;
}
.nav-icon {
  display: block;
  inline-size: 1.25rem;
  block-size: 1.25rem;
  opacity: 0.72;
  transition: opacity var(--dur-micro) var(--ease-rise);
}
.nav-icon-link:hover .nav-icon,
.nav-icon-link:focus-visible .nav-icon { opacity: 1; }
.nav-icon path {
  fill: none;
  stroke: currentColor;
  stroke-width: 1.5px;
  stroke-linecap: butt;
  stroke-linejoin: miter;
  vector-effect: non-scaling-stroke;
}

/* Burgundy focus ring is invisible on burgundy surfaces — swap to cream */
.nav-solid :focus-visible,
footer :focus-visible { outline-color: var(--taraqi-cream); }

/* --------------------------------------------------------------------------
   Phone bar (<768px) — a three-column grid: the direct contact pair at the
   inline start, the mark dead centre, the language pill and the menu button
   at the inline end. Logical throughout, so it mirrors with dir.

   Geometry: every control is a 2.75rem (44px) tap box round a 1.25rem glyph,
   so the bar's own padding is 0.75rem — the glyphs' strokes then stand on the
   page's 1.5rem gutter, in line with the copy below. At 360px the two sides
   take 88px and 90px and the Latin wordmark its 126px, which leaves the mark
   more than its T-height of clear space to the nearest stroke on each side.

   Colour: Deep Burgundy marks while the bar is clear, cream once it is solid
   — the bar's existing 80px switch and timing (js/main.js §1), untouched.
   contact.html's bar sits over a picture and keeps its cream palette there
   (css/contact.css §1b), hence the :not().
   -------------------------------------------------------------------------- */
@media (max-width: 767px) {
  .site-nav .nav-bar {
    display: grid;
    grid-template-columns: minmax(0, 1fr) auto minmax(0, 1fr);
    gap: 0;
    padding-inline: 0.75rem;
  }
  .nav-m-side { display: flex; align-items: center; }
  .nav-m-start { justify-self: start; }
  .nav-m-end { justify-self: end; gap: 0.125rem; }
  .site-nav .nav-logo { justify-self: center; }
  .site-nav:not(.nav-solid):not([data-nav-over-media]) .nav-m-side { color: var(--taraqi-burgundy-dark); }
  .nav-m-side .nav-icon { opacity: 1; }
}

/* Language pill — the short form: «EN» / «ع». A 2rem hairline pill; the
   ::after carries the tap area out to 44px without growing the pill. The
   Arabic letter is shown on the English page, so it names its own face. */
.nav-lang-pill {
  position: relative;
  min-inline-size: 2.75rem;
  block-size: 2rem;
  padding-inline: 0.625rem;
  border-radius: 9999px;
  border-color: color-mix(in srgb, currentColor 36%, transparent);
  font-size: 0.8125rem;
  font-weight: 600;
  line-height: 1;
  letter-spacing: 0.04em;
}
.nav-lang-pill::after {
  content: "";
  position: absolute;
  inset: -0.375rem 0;
}
html[lang="en"] .nav-lang-pill {
  font-family: var(--font-ar-body);
  font-size: 1rem;
  letter-spacing: 0;
}

/* Menu glyph — three rules stepping out to the bar's edge: the rise, drawn.
   Authored for the right-hand edge, so it is mirrored where the inline end
   is the left one. */
[dir="rtl"] .nav-menu-icon { transform: scaleX(-1); }

/* --------------------------------------------------------------------------
   Phone menu — a full-screen Deep Burgundy sheet (js/main.js §2).
   `.is-open` is the state, and the fade between the two states is this
   sheet's alone: js/main.js staggers the rows inside it and never writes to
   the sheet itself. tokens.css flattens the fade under reduced motion.
   -------------------------------------------------------------------------- */
.nav-menu {
  position: fixed;
  inset: 0;
  z-index: 50;
  display: flex;
  flex-direction: column;
  background-color: var(--taraqi-wine);
  color: var(--taraqi-cream);
  overflow: hidden;
  opacity: 0;
  visibility: hidden;
  transition:
    opacity var(--dur-micro) var(--ease-rise),
    visibility 0s var(--ease-rise) var(--dur-micro);
}
.nav-menu.is-open {
  opacity: 1;
  visibility: visible;
  transition: opacity var(--dur-micro) var(--ease-rise);
}
.nav-menu :focus-visible { outline-color: var(--taraqi-cream); }

/* Top row — the bar's grid again, so the mark and the button do not move. */
.nav-menu-top {
  flex: none;
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto minmax(0, 1fr);
  align-items: center;
  block-size: var(--nav-h);
  padding-inline: 0.75rem;
}
.nav-menu-mark { grid-column: 2; }
.nav-menu-mark .logo-ar    { height: var(--logo-ar-h); }
.nav-menu-mark .logo-latin { height: var(--logo-latin-h); }
html[lang="en"] .nav-menu-mark .logo-ar,
html[lang="ar"] .nav-menu-mark .logo-latin { display: none; }
.nav-menu-close { grid-column: 3; justify-self: end; }
.nav-menu .nav-icon { opacity: 1; }

/* The list — heading faces at heading size, one hairline under each row. */
.nav-menu-nav {
  flex: 1 1 auto;
  min-block-size: 0;
  overflow-y: auto;
  overscroll-behavior: contain;
  padding-inline: 1.5rem;
  padding-block-start: 0.5rem;
}
.nav-menu-list { margin: 0; padding: 0; list-style: none; }
.nav-menu-list > li { border-block-end: 1px solid var(--taraqi-line-onDark); }
.nav-menu-link {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  inline-size: 100%;
  min-block-size: 4.25rem;
  color: var(--taraqi-cream);
  text-align: start;
  font-weight: 700;
}
html[lang="ar"] .nav-menu-link {
  font-family: var(--font-ar-display);
  font-size: 2rem;
  line-height: 1.5;
}
html[lang="en"] .nav-menu-link {
  font-family: var(--font-en-display);
  font-weight: 500;
  font-size: 1.875rem;
  line-height: 1.15;
  letter-spacing: -0.01em;
}
/* Where you are: Sand, behind a short drawn rule. On a project page the
   Projects row carries it too (js/main.js sets .is-current on the toggle). */
.nav-menu-link[aria-current],
.nav-menu-toggle.is-current { justify-content: flex-start; color: var(--taraqi-sand); }
.nav-menu-link[aria-current]::before,
.nav-menu-toggle.is-current::before {
  content: "";
  flex: none;
  inline-size: 1.25rem;
  block-size: 1px;
  background-color: currentColor;
}
.nav-menu-toggle.is-current .nav-menu-plus { margin-inline-start: auto; }

/* Projects — a disclosure. The plus loses its upright when open. */
.nav-menu-plus { flex: none; }
.nav-menu-plus-v {
  transform-origin: 50% 50%;
  transition: transform var(--dur-micro) var(--ease-rise);
}
.nav-menu-toggle[aria-expanded="true"] .nav-menu-plus-v { transform: scaleY(0); }
.nav-menu-sub {
  display: grid;
  grid-template-rows: 0fr;
  visibility: hidden;
  transition:
    grid-template-rows var(--dur-micro) var(--ease-rise),
    visibility 0s var(--ease-rise) var(--dur-micro);
}
/* Only inside the open sheet: `visibility: visible` here would otherwise
   lift the rows out of a closed menu's `hidden` and into the tab order. */
.nav-menu.is-open .nav-menu-toggle[aria-expanded="true"] + .nav-menu-sub {
  grid-template-rows: 1fr;
  visibility: visible;
  transition: grid-template-rows var(--dur-micro) var(--ease-rise);
}
.nav-menu-sub > ul {
  min-block-size: 0;
  overflow: hidden;
  margin: 0;
  padding: 0;
  list-style: none;
}
.nav-menu-sub > ul > li:last-child { padding-block-end: 0.75rem; }
.nav-menu-project {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  min-block-size: 3.25rem;
  padding-inline-start: 1rem;
  color: var(--taraqi-cream);
}
/* Project names are Latin in both languages — Newsreader, above its floor. */
.nav-menu-project-name {
  font-family: var(--font-en-display);
  font-size: 1.375rem;
  font-weight: 500;
  line-height: 1.2;
  white-space: nowrap;
}
.nav-menu-project[aria-current] .nav-menu-project-name { color: var(--taraqi-sand); }
/* The pill is the tighter of the two things on the row at 360px: the English
   label is tracked capitals, so here it is set a step smaller and closer. */
.nav-menu-project .status-pill { flex: none; font-size: 0.75rem; padding-inline: 0.75rem; }
html[lang="en"] .nav-menu-project .status-pill { letter-spacing: 0.08em; }

/* The status pill on burgundy: the same chip, drawn as a hairline instead of
   filled (a Deep Burgundy fill would vanish here). It is a label in a list,
   so the dot does not pulse. */
.status-pill--onDark {
  background-color: transparent;
  border: 1px solid var(--taraqi-line-onDark);
  border-color: color-mix(in srgb, var(--taraqi-cream) 42%, transparent);
  padding-block: calc(var(--pill-pad-block, 0.375rem) - 1px);
}
.status-pill--onDark .status-pill-dot::after { animation: none; }

/* Foot — the two actions side by side, then language and the profiles. */
.nav-menu-foot {
  flex: none;
  padding: 1.25rem 1.5rem calc(1.25rem + env(safe-area-inset-bottom, 0px));
}
.nav-menu-actions {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  gap: 0.75rem;
}
.nav-menu-cta,
.nav-menu-call {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 0.5rem;
  min-block-size: 3rem;
  padding-inline: 0.75rem;
  border-radius: 9999px;
  border: 1px solid var(--taraqi-cream);
  font-size: 0.9375rem;
  font-weight: 600;
  line-height: 1.2;
  text-align: center;
  transition:
    background-color var(--dur-micro) var(--ease-rise),
    color var(--dur-micro) var(--ease-rise);
}
.nav-menu-cta {
  background-color: var(--taraqi-cream);
  color: var(--taraqi-burgundy-dark);
}
.nav-menu-call { color: var(--taraqi-cream); }
.nav-menu-call:active { background-color: var(--taraqi-burgundy); }
.nav-menu-call .nav-icon { inline-size: 1.125rem; block-size: 1.125rem; }
.nav-menu-meta {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-block-start: 1rem;
}
.nav-menu-lang {
  min-block-size: 2.75rem;
  padding-inline: 1.125rem;
  border-radius: 9999px;
  border-color: color-mix(in srgb, currentColor 36%, transparent);
  font-size: 0.875rem;
  font-weight: 600;
}
.nav-menu-social {
  display: flex;
  align-items: center;
  gap: 0.25rem;
  margin: 0;
  margin-inline-end: -0.6875rem;   /* the last glyph's stroke on the gutter */
  padding: 0;
  list-style: none;
}
.nav-menu-social .social-icon { opacity: 1; }

/* Short phones (360 × 640 and the like): tighter rows, so the open Projects
   list and the foot still fit without scrolling. */
@media (max-height: 700px) {
  .nav-menu-link { min-block-size: 3.5rem; }
  html[lang="ar"] .nav-menu-link { font-size: 1.75rem; }
  html[lang="en"] .nav-menu-link { font-size: 1.625rem; }
  .nav-menu-project { min-block-size: 2.75rem; }
  .nav-menu-foot { padding-block-start: 1rem; }
}

/* --------------------------------------------------------------------------
   Sticky register bar — phones only. A frosted strip on the page's foot with
   the primary pill inset in it: the page shows through, blurred, under a
   cream veil that fades in from nothing, so there is no top edge to see.
   `position: fixed` to the block end follows the VISIBLE viewport, so the bar
   rides the iOS URL bar as it collapses rather than sitting under it.

   js/main.js §3 sets .is-shown once the page head has left view and takes it
   off while the contact band or the footer is in view. It is out while a
   dialog is open: both the menu and the modal lock scroll with the same
   body class, so that class is the one thing to key off.

   The frost is the ::before and it fades on its own, as the button does —
   opacity on the bar itself would cut the backdrop off from the page for the
   length of the fade (an opacity group is a backdrop root) and the blur
   would pop in at the end. The bar only moves. Only the button takes taps;
   the veil around it lets them through to the page.

   --cta-bar-h is the bar's full height. The pinned stages (the drawing board,
   the coming-soon sequence) pad their foot by it, so nothing they hold sits
   under the bar; it is 0 from md up, where there is no bar.
   -------------------------------------------------------------------------- */
:root {
  --cta-bar-h: 0px;
  --cta-bar-dur: 280ms;
}
@media (max-width: 767px) {
  :root { --cta-bar-h: calc(4.75rem + env(safe-area-inset-bottom, 0px)); }   /* 12 + button 52 + 12 + inset */
}
.cta-bar {
  position: fixed;
  inset-inline: 0;
  inset-block-end: 0;
  z-index: 30;
  padding-block-start: 0.75rem;
  padding-inline: 1rem;
  padding-block-end: calc(0.75rem + env(safe-area-inset-bottom, 0px));
  pointer-events: none;
  transform: translateY(16px);
  visibility: hidden;
  transition:
    transform var(--cta-bar-dur) var(--ease-rise),
    visibility 0s linear var(--cta-bar-dur);
}
.cta-bar::before {
  content: "";
  position: absolute;
  inset-inline: 0;
  inset-block-end: 0;
  inset-block-start: -1rem;        /* the veil starts above the bar and has room to fade */
  z-index: -1;
  background-image: linear-gradient(
    to bottom,
    rgba(246, 241, 234, 0) 0%,
    rgba(246, 241, 234, 0.55) 60%
  );
  -webkit-backdrop-filter: blur(14px) saturate(140%);
  backdrop-filter: blur(14px) saturate(140%);
  /* The blur fades in with the veil — an unmasked backdrop ends on a line. */
  -webkit-mask-image: linear-gradient(to bottom, transparent 0%, #000 45%);
  mask-image: linear-gradient(to bottom, transparent 0%, #000 45%);
}
/* No backdrop-filter: the veil alone, dense enough to carry the button over
   a busy picture. */
@supports not ((backdrop-filter: blur(1px)) or (-webkit-backdrop-filter: blur(1px))) {
  .cta-bar::before {
    background-image: linear-gradient(
      to bottom,
      rgba(246, 241, 234, 0) 0%,
      rgba(246, 241, 234, 0.85) 60%
    );
  }
}
.cta-bar::before,
.cta-bar-btn {
  opacity: 0;
  transition: opacity var(--cta-bar-dur) var(--ease-rise);
}
.cta-bar.is-shown {
  transform: translateY(0);
  visibility: visible;
  transition: transform var(--cta-bar-dur) var(--ease-rise);
}
.cta-bar.is-shown::before,
.cta-bar.is-shown .cta-bar-btn { opacity: 1; }
.scroll-locked .cta-bar {
  transform: translateY(16px);
  visibility: hidden;
}
.scroll-locked .cta-bar::before,
.scroll-locked .cta-bar .cta-bar-btn { opacity: 0; }
/* Over a dark section (js/main.js §3 sets .is-on-dark): the veil goes, and the
   blur with it — a cream wash on burgundy reads as a pink glow, and there is
   nothing under the bar there to soften. The pill would then be burgundy on
   burgundy, so it turns to the site's on-dark primary, the cream pill
   (.btn-cream, css/sections.css). Same fade as the bar's own. */
.cta-bar.is-shown.is-on-dark::before { opacity: 0; }
.cta-bar.is-on-dark .cta-bar-btn {
  background-color: var(--taraqi-cream);
  color: var(--taraqi-burgundy-dark);
}
.cta-bar.is-on-dark .cta-bar-btn:active { color: var(--taraqi-burgundy); }
.cta-bar.is-on-dark .cta-bar-btn:focus-visible { outline-color: var(--taraqi-cream); }
/* The btn-primary pill (css/home.css loads on the home page only), lifted off
   the frost by a shadow in the brand's own burgundy. */
.cta-bar-btn {
  display: flex;
  align-items: center;
  justify-content: center;
  inline-size: 100%;
  block-size: 3.25rem;
  border-radius: 9999px;
  background-color: var(--taraqi-burgundy-dark);
  color: var(--taraqi-cream);
  font-size: 1rem;
  font-weight: 600;
  line-height: 1.2;
  box-shadow:
    0 10px 24px -10px rgba(92, 37, 48, 0.55),
    0 2px 6px rgba(92, 37, 48, 0.16);
  pointer-events: auto;
  transition:
    opacity var(--cta-bar-dur) var(--ease-rise),
    background-color var(--cta-bar-dur) var(--ease-rise),
    color var(--cta-bar-dur) var(--ease-rise);
}
.cta-bar-btn:active { background-color: var(--taraqi-burgundy); }
.cta-bar-btn:focus-visible { outline-color: var(--taraqi-burgundy-dark); outline-offset: 3px; }
/* Reduced motion: the bar fades and does not travel. tokens.css zeroes every
   transition under this query; the fade is the one thing kept, so it is
   restated here at the same weight. */
@media (prefers-reduced-motion: reduce) {
  .cta-bar,
  .cta-bar.is-shown,
  .scroll-locked .cta-bar { transform: none; }
  .cta-bar { transition: visibility 0s linear var(--cta-bar-dur) !important; }
  .cta-bar.is-shown { transition: none !important; }
  .cta-bar::before { transition: opacity var(--cta-bar-dur) ease-out !important; }
  .cta-bar-btn {
    transition:
      opacity var(--cta-bar-dur) ease-out,
      background-color var(--cta-bar-dur) ease-out,
      color var(--cta-bar-dur) ease-out !important;
  }
}

.scroll-locked { overflow: hidden; }

/* --------------------------------------------------------------------------
   Footer
   -------------------------------------------------------------------------- */
.hairline-onDark { border-color: var(--taraqi-line-onDark); }

/* Footer mark — one mark per language, the same html[lang] mechanism AND the
   same height tokens as the navbar (--logo-ar-h / --logo-latin-h — one pair,
   defined at :root above, drives both instances). The box is reserved at the
   taller mark's height (the Arabic mark) so the column never changes height
   between languages; the mark sits on the box's bottom edge with the hairline
   rule from the lockup artwork drawn beneath it, spanning exactly the visible
   mark's width. Both marks are co-equal by treatment, never shown together. */
.footer-mark {
  --footer-rule-gap: 10px;         /* mark → hairline, scaled to the mark */
  display: flex;
  align-items: flex-end;
  block-size: calc(var(--logo-ar-h) + var(--footer-rule-gap) + 1px);
}
.footer-mark-inner {
  position: relative;
  display: inline-block;
  padding-block-end: var(--footer-rule-gap);
}
.footer-mark-inner::after {
  content: "";
  position: absolute;
  inset-inline: 0;
  inset-block-end: 0;
  block-size: 1px;
  background-color: var(--taraqi-cream);
  opacity: 0.6;
}
/* The marks are .logo-mark spans — colour is the footer's cream currentColor;
   inline-size falls out of each mark's aspect-ratio. */
.footer-mark-ar    { block-size: var(--logo-ar-h); }
.footer-mark-latin { block-size: var(--logo-latin-h); }
html[lang="en"] .footer-mark-ar,
html[lang="ar"] .footer-mark-latin { display: none; }

/* Footer tagline — one line per language, each in its brand-locked face
   (brand sheet p.06): Aref Ruqaa Bold / Newsreader Medium Italic, never re-set
   in body fonts; the serif's floor is 20px (rule 5). The box is reserved at the
   Arabic line's height so the column never moves on toggle. */
.footer-tagline {
  --footer-tagline-ar-size: 1.5rem;
  --footer-tagline-ar-lh: 1.9;
  --footer-tagline-en-size: 1.25rem;
  block-size: calc(var(--footer-tagline-ar-size) * var(--footer-tagline-ar-lh));
}
.tagline-ar {
  font-family: var(--font-ar-display);
  font-weight: 700;
  font-size: var(--footer-tagline-ar-size, 1.5rem);
  line-height: var(--footer-tagline-ar-lh, 1.9);
}
.tagline-en {
  font-family: var(--font-en-display);
  font-weight: 500;
  font-style: italic;
  font-size: var(--footer-tagline-en-size, 1.25rem);
  line-height: 1.2;
  letter-spacing: -0.01em;
}
html[lang="en"] .tagline-ar,
html[lang="ar"] .tagline-en { display: none; }

/* Footer foot — below md nothing floats over the footer any more (the sticky
   register bar is out while the footer is in view), so the legal rows only
   owe the device's home-indicator inset. */
@media (max-width: 767px) {
  footer { padding-block-end: env(safe-area-inset-bottom, 0px); }
}

/* --------------------------------------------------------------------------
   Contact link — the one channel, shown in the footer of every page and in
   the contact page's reach list. The copy reads "تواصل معنا" / "Contact us"
   and never names the channel (client decision 2026-09-06); the glyph is the
   only thing that says where the tap goes, so it is not decoration and never
   drops out. Logical properties throughout — it sits on the RTL side in Arabic.
   -------------------------------------------------------------------------- */
/* One pattern in both places: the glyph leads the number on a single line,
   vertically centred against it, never stacked and never wrapped. The gap is
   a fixed 0.5rem rather than an em so it does not drift between the footer's
   16px and the reach list's 17px — the pair reads identically in both.
   The label beside it is held at 1rem (gap-4 on the footer rows, and the
   reach row's own space-between), so the glyph is twice as close to its
   number as to the label: it groups with the value it identifies. */
.wa-link {
  display: inline-flex;
  align-items: center;
  gap: 0.5rem;
  white-space: nowrap;
}
/* Sized in em so it tracks the number's type size, at 1em — the glyph's
   round mass then reads level with the digits' cap height. `flex: none`
   keeps it from being squeezed if the row ever runs short of room. */
.wa-glyph {
  flex: none;
  inline-size: 1em;
  block-size: 1em;
  opacity: 0.9;
}

/* --------------------------------------------------------------------------
   Social row — the footer's contact column, on all four pages. WhatsApp leads
   it because it is the one channel that reaches a person; the three profile
   links follow. The number itself is NOT printed here any more: it lives once,
   on contact.html's reach list, so the footer names the channels and the
   contact page carries the value.

   Icon language: the drawing board's, borrowed from the Facilities & amenities
   glyphs on project-b162.html — outline only, currentColor, 1.5px non-scaling
   stroke, butt caps, mitred joins. That rule is `.mix-icon path, .amen-icon
   path` in css/project.css, which does not load on index/about/contact, so it
   is restated here rather than shared. Keep the two in step if either changes.

   The links are 2.75rem square so the tap target clears the 44px floor while
   the glyph itself stays 1.375rem; the row is pulled back by half the spare
   padding so the first icon's stroke lines up with the column edge above it.
   -------------------------------------------------------------------------- */
.social-row {
  display: flex;
  align-items: center;
  gap: 0.25rem;
  margin-block-start: 1rem;
  margin-inline-start: -0.6875rem;
  list-style: none;
  padding: 0;
}
.social-link {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  inline-size: 2.75rem;
  block-size: 2.75rem;
  color: var(--taraqi-cream);
}
.social-icon {
  display: block;
  inline-size: 1.375rem;
  block-size: 1.375rem;
  opacity: 0.78;
  transition: opacity var(--dur-micro) var(--ease-rise);
}
.social-link:hover .social-icon,
.social-link:focus-visible .social-icon { opacity: 1; }
.social-icon path {
  fill: none;
  stroke: currentColor;
  stroke-width: 1.5px;
  stroke-linecap: butt;
  stroke-linejoin: miter;
  vector-effect: non-scaling-stroke;
}

/* --------------------------------------------------------------------------
   Deep surface — the Company Profile's wine, plus its paper grain.
   Two burgundies: --taraqi-wine is the depth layer (footer, mobile menu,
   full-bleed dark bands); --taraqi-burgundy-dark stays the brand primary
   (nav bar, buttons, headlines). `footer.bg-burgundy` out-ranks the
   Tailwind utility (0,1,1 over 0,1,0) without touching the compiled sheet.
   -------------------------------------------------------------------------- */
footer.bg-burgundy { background-color: var(--taraqi-wine); }

footer.bg-burgundy,
.nav-menu,
.section-cta,
.soon { position: relative; isolation: isolate; }
.nav-menu { position: fixed; }

footer.bg-burgundy::after,
.nav-menu::after,
.section-cta::after,
.soon::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 1;
  pointer-events: none;
  background-image: var(--taraqi-grain);
  background-size: 220px 220px;
  mix-blend-mode: overlay;      /* neutral grey noise, overlay is linear on dark bases: the wine's average holds */
  opacity: 0.22;
}
