/* =============================================================
   VipRix — Soft UI layer
   Ports the Edugy platform's neumorphic design system onto
   VipRix's controls: widgets, forms, switchers and clickers.

   Loaded LAST, after redesign.css.

   ── What is borrowed from Edugy ──────────────────────────────
   Every element is carved from the same surface — raised or
   recessed — and the difference is told by light and shadow
   rather than by a different colour or a hard border. Light is
   fixed at top-left. The whole scale lives in --shadow-sm/md/lg
   plus the two inset variants, so it is tuned in one place.

   Edugy's own three warnings are carried over, because pure
   neumorphism destroys contrast:
     • text keeps full contrast — shadows are for containers only
     • filled buttons keep their fill; the soft shadow goes on top
     • fields are clearly recessed, so they read as inputs with
       no border at all

   ── What is NOT touched ──────────────────────────────────────
   • The electric frame (electric-border.css) — form cards inside
     .electric-border-wrap stay shadow-less so the animated ring
     remains the only frame. Soft UI applies to what is INSIDE.
   • The palette. No new colour is introduced: the light and dark
     shadow tints are derived with color-mix() from #FFFFFF and
     #0d0d1a, both already in the brand palette.
   ============================================================= */

/* ── Neumorphic scale ────────────────────────────────────────
   --nm-surface is the colour the element is carved from; the
   highlight and shadow are mixed from it, so one variable
   re-tints an entire subtree. */
:root {
  --nm-surface: #151525;
  --nm-light: color-mix(in srgb, var(--nm-surface) 84%, #FFFFFF);
  --nm-dark: color-mix(in srgb, var(--nm-surface) 76%, #0d0d1a);

  --shadow-sm: -3px -3px 7px var(--nm-light), 3px 3px 7px var(--nm-dark);
  --shadow-md: -6px -6px 14px var(--nm-light), 6px 6px 14px var(--nm-dark);
  --shadow-lg: -11px -11px 26px var(--nm-light), 11px 11px 26px var(--nm-dark);
  --nm-in: inset -3px -3px 7px var(--nm-light), inset 3px 3px 7px var(--nm-dark);
  --nm-in-deep: inset -5px -5px 11px var(--nm-light), inset 5px 5px 11px var(--nm-dark);

  --ease-out-soft: cubic-bezier(0.22, 1, 0.36, 1);
  --ease-spring: cubic-bezier(0.34, 1.4, 0.64, 1);

  /* Edugy's radii */
  --r-control: 12px;
  --r-field: 14px;
  --r-card: 20px;
}

html:not([data-theme="dark"]) {
  --nm-surface: #FFFFFF;
  --nm-light: #FFFFFF;
  --nm-dark: color-mix(in srgb, #FFFFFF 84%, #0d0d1a);
}

/* Form cards keep their teal/cyan fill, so anything carved inside
   them must take its highlight and shadow from THAT colour.

   NOTE: --nm-light/--nm-dark must be redeclared here, not just
   --nm-surface. A custom property is inherited as an already
   substituted value, so overriding --nm-surface alone would leave
   the highlight and shadow still derived from the page surface. */
/* The composed shadows have to be redeclared here as well, for the
   same reason: --shadow-md at :root already baked in the page's
   --nm-light/--nm-dark before this subtree ever saw them. Only the
   two tint variables change; the geometry is copied verbatim. */
html[data-theme="dark"] :is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap) {
  --nm-surface: #0084a3;
  --nm-light: color-mix(in srgb, #0084a3 82%, #FFFFFF);
  --nm-dark: color-mix(in srgb, #0084a3 74%, #0d0d1a);

  --shadow-sm: -3px -3px 7px var(--nm-light), 3px 3px 7px var(--nm-dark);
  --shadow-md: -6px -6px 14px var(--nm-light), 6px 6px 14px var(--nm-dark);
  --shadow-lg: -11px -11px 26px var(--nm-light), 11px 11px 26px var(--nm-dark);
  --nm-in: inset -3px -3px 7px var(--nm-light), inset 3px 3px 7px var(--nm-dark);
  --nm-in-deep: inset -5px -5px 11px var(--nm-light), inset 5px 5px 11px var(--nm-dark);
}
html:not([data-theme="dark"]) :is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap) {
  --nm-surface: #00d4ff;
  --nm-light: color-mix(in srgb, #00d4ff 80%, #FFFFFF);
  --nm-dark: color-mix(in srgb, #00d4ff 72%, #0d0d1a);

  --shadow-sm: -3px -3px 7px var(--nm-light), 3px 3px 7px var(--nm-dark);
  --shadow-md: -6px -6px 14px var(--nm-light), 6px 6px 14px var(--nm-dark);
  --shadow-lg: -11px -11px 26px var(--nm-light), 11px 11px 26px var(--nm-dark);
  --nm-in: inset -3px -3px 7px var(--nm-light), inset 3px 3px 7px var(--nm-dark);
  --nm-in-deep: inset -5px -5px 11px var(--nm-light), inset 5px 5px 11px var(--nm-dark);
}

/* ── Primitives ───────────────────────────────────────────── */
.nm-raised { box-shadow: var(--shadow-md); }
.nm-inset { box-shadow: var(--nm-in); }

/* Every clickable thing lifts on hover and is pressed INTO the
   surface on click. Edugy calls this the clearest feedback in the
   system — it replaces a colour change entirely. */
.interactive,
.btn, a.btn, button.btn, .btn-submit, .submit-btn, .btn-login,
.nav-cta, .carousel-card-cta, .coverflow-btn,
.auth-tab, .filter-tab, .theme-toggle {
  transition:
    transform 0.18s var(--ease-out-soft),
    box-shadow 0.18s var(--ease-out-soft),
    border-color 0.18s var(--ease-out-soft),
    background-color 0.18s var(--ease-out-soft),
    color 0.18s var(--ease-out-soft),
    filter 0.18s var(--ease-out-soft) !important;
}

:is(.btn, a.btn, .btn-submit, .submit-btn, .btn-login, .nav-cta,
    .carousel-card-cta, .coverflow-btn):hover {
  transform: translateY(-2px) !important;
}
:is(.btn, a.btn, .btn-submit, .submit-btn, .btn-login, .nav-cta,
    .carousel-card-cta, .coverflow-btn):active {
  transform: translateY(0) scale(0.99) !important;
  box-shadow: var(--nm-in) !important;
  transition-duration: 0.08s !important;
}

/* Sheen sweep across the primary action on hover */
.sheen, .btn-primary, .submit-btn, .btn-login {
  position: relative;
  overflow: hidden;
  isolation: isolate;
}
:is(.sheen, .btn-primary, .submit-btn, .btn-login)::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: -1;
  background: linear-gradient(105deg, transparent 35%, rgb(255 255 255 / 0.22) 50%, transparent 65%);
  transform: translateX(-120%);
  transition: transform 0.6s var(--ease-out-soft);
  pointer-events: none;
}
:is(.sheen, .btn-primary, .submit-btn, .btn-login):hover::after {
  transform: translateX(120%);
}

/* =============================================================
   FORMS — recessed fields, no borders needed
   ============================================================= */
.field input,
.field select,
.field textarea,
.form-group input,
.form-group select,
.form-group textarea,
#login-screen .field input,
.auth-card input,
.auth-card select,
.auth-card textarea,
.contact-form-wrap input,
.contact-form-wrap select,
.contact-form-wrap textarea {
  border: 0 !important;
  border-radius: var(--r-field) !important;
  background: var(--nm-well, transparent) !important;
  box-shadow: var(--nm-in) !important;
  padding: 0.7rem 1rem !important;
  transition: box-shadow 0.18s var(--ease-out-soft), color 0.18s var(--ease-out-soft) !important;
}

/* --- The well ------------------------------------------------
   Edugy hits this same wall and documents the fix: on a saturated
   mid-tone, NO text colour reaches 4.5:1, so content is placed on
   a surface tone while the brand colour stays visible around it.
   White on #0084a3 is only 4.17:1. Sinking the field interior to a
   darker mix of the SAME teal takes it to ~8.7:1 — and a darker
   well is more faithful to soft UI anyway, not less.
   Derived with color-mix from existing brand colours only. */
html[data-theme="dark"] :is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap) {
  --nm-well: color-mix(in srgb, #0084a3 55%, #0d0d1a);
}
html:not([data-theme="dark"]) :is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap) {
  --nm-well: color-mix(in srgb, #00d4ff 62%, #FFFFFF);
}

.field textarea,
.contact-form-wrap textarea,
.auth-card textarea {
  padding: 0.85rem 1rem !important;
  line-height: 1.6 !important;
}

/* Focus sinks the field deeper. The global :focus-visible ring
   still sits on top, so keyboard users get a signal that does not
   depend on reading a shadow. */
.field input:focus,
.field select:focus,
.field textarea:focus,
.form-group input:focus,
.form-group textarea:focus,
#login-screen .field input:focus,
.auth-card input:focus,
.auth-card textarea:focus,
.contact-form-wrap input:focus,
.contact-form-wrap textarea:focus {
  box-shadow: var(--nm-in-deep) !important;
  outline: none;
}

.field input:focus-visible,
.field textarea:focus-visible,
.field select:focus-visible {
  outline: 2px solid var(--accent, #00d4ff);
  outline-offset: 2px;
}

/* Error state — colour plus an inset ring, never colour alone */
.field input.field-error,
.field input[aria-invalid="true"] {
  box-shadow: var(--nm-in), 0 0 0 1.5px #ff5e78 inset !important;
}
.field-warn, .pay-error {
  display: flex;
  align-items: center;
  gap: 6px;
}

/* Disabled / read-only (skill rule: disabled-states) */
.field input:disabled,
.field textarea:disabled,
.field select:disabled,
.btn:disabled, button:disabled {
  opacity: 0.5 !important;
  cursor: not-allowed !important;
  box-shadow: none !important;
  transform: none !important;
}
.field input:read-only { opacity: 0.75; }

/* =============================================================
   BUTTONS — Edugy's shape, VipRix's colour identity
   The cyan outline is the brand's own language and is kept; only
   the radius and the tactile response change.
   ============================================================= */
a.btn, a.btn-primary, a.btn-secondary,
button.btn, button.btn-primary,
.btn, .btn-submit, .submit-btn, .btn-login,
.nav-cta, a.nav-cta,
.carousel-card-cta, a.carousel-card-cta {
  border-radius: var(--r-control) !important;
  font-weight: 600 !important;
  letter-spacing: 0.01em !important;
  text-transform: none !important;
  font-family: var(--font-body) !important;
}

.coverflow-btn, button.coverflow-btn,
.mobile-toggle, button.mobile-toggle {
  border-radius: var(--r-control) !important;
  box-shadow: var(--shadow-sm) !important;
}
:is(.coverflow-btn, .mobile-toggle):active {
  box-shadow: var(--nm-in) !important;
}

/* --- Primary action inside a form card -----------------------
   Edugy's second warning: a pure neumorphic button takes the
   surface colour and its contrast collapses, so the primary
   action KEEPS a solid fill and the soft shadow goes on top.
   An outlined button on the teal card gave white-on-teal at
   4.17:1; filling it with the brand ink takes it to ~16.5:1.
   Cyan stays as the border, so the brand signal is unchanged. */
/* Declared theme-qualified: the form-colour unifier in
   responsive.css sets these transparent at (0,3,1). */
html[data-theme="dark"] :is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap)
  :is(.btn-submit, .submit-btn, .btn-login, .btn-primary, button[type="submit"]),
html:not([data-theme="dark"]) :is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap)
  :is(.btn-submit, .submit-btn, .btn-login, .btn-primary, button[type="submit"]) {
  background: #0d0d1a !important;
  background-color: #0d0d1a !important;
  background-image: none !important;
  color: #FAFAFA !important;
  -webkit-text-fill-color: #FAFAFA !important;
  border: 1.5px solid #00d4ff !important;
  box-shadow: var(--shadow-sm) !important;
}
html[data-theme="dark"] :is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap)
  :is(.btn-submit, .submit-btn, .btn-login, .btn-primary, button[type="submit"]):hover,
html:not([data-theme="dark"]) :is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap)
  :is(.btn-submit, .submit-btn, .btn-login, .btn-primary, button[type="submit"]):hover {
  background: #151525 !important;
  background-color: #151525 !important;
  color: #FAFAFA !important;
  -webkit-text-fill-color: #FAFAFA !important;
}

/* The dashboard/employee login screens style their button from
   `#login-screen .btn-login` (1,1,0), which outranks the rule above.
   Same treatment, declared at ID level. */
#login-screen .btn-login,
#login-screen .login-card :is(.btn-login, .btn-submit, button[type="submit"]) {
  background: #0d0d1a !important;
  background-color: #0d0d1a !important;
  background-image: none !important;
  color: #FAFAFA !important;
  -webkit-text-fill-color: #FAFAFA !important;
  border: 1.5px solid #00d4ff !important;
  border-radius: var(--r-control) !important;
  box-shadow: var(--shadow-sm) !important;
}
#login-screen .btn-login:hover,
#login-screen .login-card :is(.btn-login, .btn-submit, button[type="submit"]):hover {
  background: #151525 !important;
  background-color: #151525 !important;
  color: #FAFAFA !important;
  -webkit-text-fill-color: #FAFAFA !important;
}
/* The inline sheet gives this button a gradient ::before; it would
   sit over the new fill. */
#login-screen .btn-login::before { display: none !important; content: none !important; }

/* Links on the card: cyan-on-teal measured 2.46:1. White plus a
   permanent underline keeps them findable without relying on
   colour at all (skill rule: color-not-only). */
:is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap)
  :is(.auth-links a, .back, a) {
  color: #FAFAFA !important;
  -webkit-text-fill-color: #FAFAFA !important;
  text-decoration: underline !important;
  text-underline-offset: 3px !important;
}
html:not([data-theme="dark"]) :is(.auth-card, .login-card, .card, .form-card, .reset-card, .contact-form-wrap)
  :is(.auth-links a, .back, a) {
  color: #18181B !important;
  -webkit-text-fill-color: #18181B !important;
}

/* =============================================================
   SWITCHERS / CLICKERS
   Edugy's segmented control: a recessed groove with the selected
   option raised inside it. Depth carries the state, and the
   markup carries aria-pressed / .active so it is not depth alone.
   ============================================================= */

/* ── Theme switch ── */
.theme-toggle {
  position: relative !important;
  display: inline-flex !important;
  align-items: center !important;
  width: 64px !important;
  height: 32px !important;
  min-height: 0 !important;
  padding: 3px !important;
  border: 0 !important;
  border-radius: 999px !important;
  background: transparent !important;
  box-shadow: var(--nm-in) !important;
  overflow: visible !important;
  cursor: pointer !important;
  flex-shrink: 0 !important;
}
html[data-theme="dark"] .theme-toggle,
html:not([data-theme="dark"]) .theme-toggle {
  background: transparent !important;
  background-color: transparent !important;
  border: 0 !important;
  border-radius: 999px !important;
  box-shadow: var(--nm-in) !important;
}

/* Expanded hit area — control stays 64x32 but meets 44px touch */
.theme-toggle::after {
  content: "" !important;
  display: block !important;
  position: absolute;
  inset: -6px;
  border-radius: 999px;
  background: none !important;
}

/* The knob is the raised element inside the groove */
.theme-toggle-knob {
  position: absolute !important;
  top: 3px !important;
  left: 3px !important;
  width: 26px !important;
  height: 26px !important;
  border-radius: 999px !important;
  box-shadow: var(--shadow-sm) !important;
  z-index: 1 !important;
  transition: transform 0.26s var(--ease-spring) !important;
}
html[data-theme="dark"] .theme-toggle-knob {
  background: var(--surface-2, #1e1e32) !important;
  background-color: var(--surface-2, #1e1e32) !important;
  transform: translateX(32px) !important;
}
html:not([data-theme="dark"]) .theme-toggle-knob {
  background: #FFFFFF !important;
  background-color: #FFFFFF !important;
  transform: translateX(0) !important;
}

.theme-toggle .theme-toggle-sun,
.theme-toggle .theme-toggle-moon {
  position: absolute !important;
  top: 50% !important;
  transform: translateY(-50%) !important;
  font-size: 11px !important;
  line-height: 1 !important;
  z-index: 2 !important;
  pointer-events: none !important;
  transition: color 0.2s var(--ease-out-soft) !important;
}
.theme-toggle .theme-toggle-sun { left: 11px !important; right: auto !important; }
.theme-toggle .theme-toggle-moon { right: 11px !important; left: auto !important; }

/* The icon riding the knob takes the brand colour; the other recedes */
html[data-theme="dark"] .theme-toggle .theme-toggle-moon { color: #00d4ff !important; }
html[data-theme="dark"] .theme-toggle .theme-toggle-sun { color: var(--text-subtle, #71717A) !important; }
html:not([data-theme="dark"]) .theme-toggle .theme-toggle-sun { color: #0097b2 !important; }
html:not([data-theme="dark"]) .theme-toggle .theme-toggle-moon { color: var(--text-subtle, #A1A1AA) !important; }

/* ── Segmented tab groups (auth tabs, dashboard filters) ── */
.auth-tabs,
.filter-tabs {
  display: flex !important;
  align-items: center !important;
  gap: 4px !important;
  padding: 5px !important;
  border: 0 !important;
  border-radius: 999px !important;
  /* Same well treatment as the fields — an idle tab label sitting
     straight on the teal card only reached 1.7:1. */
  background: var(--nm-well, transparent) !important;
  box-shadow: var(--nm-in) !important;
}
.auth-tabs { width: 100% !important; }

.auth-tab,
.filter-tab {
  flex: 1 1 0 !important;
  min-height: 40px !important;
  border: 0 !important;
  border-radius: 999px !important;
  background: transparent !important;
  box-shadow: none !important;
  font-weight: 600 !important;
  font-size: 0.86rem !important;
  text-transform: none !important;
  letter-spacing: 0.01em !important;
  cursor: pointer !important;
  padding: 0 1rem !important;
}
.filter-tab { flex: 0 0 auto !important; }

/* Idle labels stay high-contrast. A muted grey here measured 1.7:1
   against the card — the selected state is already carried by depth
   and colour, so the idle label does not need to be dimmed too. */
html[data-theme="dark"] :is(.auth-tab, .filter-tab) { color: #FAFAFA !important; }
html:not([data-theme="dark"]) :is(.auth-tab, .filter-tab) { color: #18181B !important; }

:is(.auth-tab, .filter-tab):hover:not(.active) {
  transform: none !important;
  filter: brightness(1.15);
}

/* Selected option rises out of the groove */
html[data-theme="dark"] :is(.auth-tab, .filter-tab).active {
  background: var(--surface-2, #1e1e32) !important;
  box-shadow: var(--shadow-sm) !important;
  color: #00d4ff !important;
}
/* Light mode: #0097b2 on a white chip is only 3.46:1 at this size.
   The chip carries the brand as a cyan tint instead, and the label
   takes the ink — selection is still told by depth + tint, not by
   text colour alone. */
html:not([data-theme="dark"]) :is(.auth-tab, .filter-tab).active {
  background: color-mix(in srgb, #00d4ff 24%, #FFFFFF) !important;
  box-shadow: var(--shadow-sm) !important;
  color: #0d0d1a !important;
  -webkit-text-fill-color: #0d0d1a !important;
}
:is(.auth-tab, .filter-tab):active { transform: scale(0.98) !important; }

/* ── Carousel / slider dots ── */
.carousel-dots-container,
.coverflow-dots,
.testimonial-dots {
  display: flex !important;
  align-items: center !important;
  gap: 6px !important;
  padding: 6px 8px !important;
  border-radius: 999px !important;
  box-shadow: var(--nm-in) !important;
  width: fit-content !important;
  margin-inline: auto !important;
}

.carousel-dot,
.coverflow-dot,
.testimonial-dot {
  border: 0 !important;
  border-radius: 999px !important;
  cursor: pointer !important;
  transition: width 0.26s var(--ease-spring), background-color 0.2s var(--ease-out-soft),
              box-shadow 0.2s var(--ease-out-soft) !important;
}
html[data-theme="dark"] :is(.carousel-dot, .coverflow-dot, .testimonial-dot) {
  background: var(--surface-2, #1e1e32) !important;
  box-shadow: var(--shadow-sm) !important;
}
html:not([data-theme="dark"]) :is(.carousel-dot, .coverflow-dot, .testimonial-dot) {
  background: #FFFFFF !important;
  box-shadow: var(--shadow-sm) !important;
}
:is(.carousel-dot, .coverflow-dot, .testimonial-dot).active {
  background: #00d4ff !important;
}
html:not([data-theme="dark"]) :is(.carousel-dot, .coverflow-dot, .testimonial-dot).active {
  background: #0097b2 !important;
}

/* =============================================================
   WIDGETS
   ============================================================= */

/* Stat / feature / testimonial cards: carved from the surface,
   raised, and they sink slightly when pressed. */
.stat-card,
.testimonial-card,
.panel,
.request-card,
.task-card,
.emp-card {
  border-radius: var(--r-card) !important;
  box-shadow: var(--shadow-md) !important;
  transition: transform 0.25s var(--ease-out-soft), box-shadow 0.25s var(--ease-out-soft) !important;
}
:is(.stat-card, .testimonial-card, .request-card, .task-card, .emp-card):hover {
  transform: translateY(-3px) !important;
  box-shadow: var(--shadow-lg) !important;
}
:is(.request-card, .task-card, .emp-card):active {
  transform: translateY(0) !important;
  box-shadow: var(--nm-in) !important;
  transition-duration: 0.09s !important;
}

/* The corner tick from the editorial layer would read as a hard
   edge in a soft system — retire it on these cards. */
.stat-card::after { display: none !important; }

.feature-item {
  border-radius: var(--r-card) !important;
  border-bottom: 0 !important;
  padding: var(--sp-4, 16px) !important;
  transition: box-shadow 0.25s var(--ease-out-soft), transform 0.25s var(--ease-out-soft) !important;
}
.feature-item:hover {
  box-shadow: var(--shadow-sm) !important;
  transform: translateY(-2px) !important;
}
.feature-icon {
  border-radius: var(--r-control) !important;
  box-shadow: var(--shadow-sm) !important;
}

/* Badges — a small disc lifted off the surface, colour carries meaning */
.badge {
  border-radius: 999px !important;
  border: 0 !important;
  box-shadow: var(--shadow-sm) !important;
  font-weight: 600 !important;
  padding: 4px 12px !important;
}

/* Alerts / payment states — sunk in, so they read as a message
   from the system rather than something to press. */
.pay-state,
.msg,
.alert {
  border: 0 !important;
  border-radius: var(--r-field) !important;
  box-shadow: var(--nm-in) !important;
}

/* Toast lifts off the page */
#toast {
  border: 0 !important;
  border-radius: var(--r-field) !important;
  box-shadow: var(--shadow-lg) !important;
}

/* Service carousel cards */
.card-inner {
  border-radius: var(--r-card) !important;
}

/* Modals float above the scrim */
.modal, .modal-content {
  border-radius: var(--r-card) !important;
  box-shadow: var(--shadow-lg) !important;
}

/* Empty states stay dashed — a recessed shape would suggest input */
.empty-state {
  border-radius: var(--r-card) !important;
}

/* =============================================================
   ELECTRIC FRAME COMPATIBILITY
   The animated ring is the frame for a wrapped card, so the card
   itself must stay flat. Only its contents are carved.
   ============================================================= */
.electric-border-wrap .login-card,
.electric-border-wrap .contact-form-wrap,
.electric-border-wrap .card,
.electric-border-wrap .form-card,
.electric-border-wrap .reset-card,
.electric-border-wrap .modal-content,
#login-screen .electric-border-wrap .login-card {
  box-shadow: none !important;
  border: none !important;
}

/* =============================================================
   MOTION
   ============================================================= */
@keyframes nm-pop {
  0% { transform: scale(0.82); opacity: 0; }
  60% { transform: scale(1.06); }
  100% { transform: scale(1); opacity: 1; }
}
.animate-pop { animation: nm-pop 0.42s var(--ease-spring) backwards; }

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
  }
  :is(.btn, .stat-card, .testimonial-card, .feature-item, .request-card):hover {
    transform: none !important;
  }
}

/* =============================================================
   RESPONSIVE
   ============================================================= */
@media (max-width: 767px) {
  .auth-tabs, .filter-tabs { padding: 4px !important; gap: 3px !important; }
  .auth-tab, .filter-tab { min-height: 44px !important; font-size: 0.82rem !important; }

  /* Dots keep a 44px tap area without growing the visible dot */
  .carousel-dot, .coverflow-dot, .testimonial-dot {
    min-width: 44px !important;
    min-height: 44px !important;
    background-clip: content-box !important;
    padding: 16px 0 !important;
    box-shadow: none !important;
  }
  .carousel-dots-container, .coverflow-dots, .testimonial-dots {
    gap: 0 !important;
    padding: 0 6px !important;
  }
}

/* =============================================================
   TYPOGRAPHY NORMALISATION
   Black Ops One (body) and Alumni Sans Collegiate One (display)
   each ship a single 400 weight. Every 600/700/800 declaration
   elsewhere would otherwise be synthesised by the browser into a
   smeared faux-bold, so weight is pinned to 400 and hierarchy is
   carried by size and colour instead.

   Declared theme-qualified: redesign.css sets these weights at
   (0,2,1) and cyan-buttons.css uses `a.btn` at (0,1,1), so a plain
   class selector here would lose.
   ============================================================= */
html[data-theme="dark"] :is(
  body, p, span, li, td, th, label, input, textarea, select,
  button, a, .btn, a.btn, .btn-submit, .submit-btn, .btn-login, .nav-cta,
  .section-subtitle, .testimonial-text, .short-desc,
  .detail-row .label, .detail-row .value, .section-label, .stat-label,
  .badge, .hero-description, .auth-tab, .filter-tab,
  h1, h2, h3, h4, h5, h6, .section-title, .hero-title,
  .logo-text, .logo-slogan, .nav-links a, .stat-number, .feature-info h4
),
html:not([data-theme="dark"]) :is(
  body, p, span, li, td, th, label, input, textarea, select,
  button, a, .btn, a.btn, .btn-submit, .submit-btn, .btn-login, .nav-cta,
  .section-subtitle, .testimonial-text, .short-desc,
  .detail-row .label, .detail-row .value, .section-label, .stat-label,
  .badge, .hero-description, .auth-tab, .filter-tab,
  h1, h2, h3, h4, h5, h6, .section-title, .hero-title,
  .logo-text, .logo-slogan, .nav-links a, .stat-number, .feature-info h4
) {
  font-weight: 400 !important;
  font-synthesis-weight: none;
  letter-spacing: normal !important;
}

/* Both faces are wide/condensed display types — the negative
   tracking that suited Archivo closes their counters up. */
html[data-theme="dark"] :is(h1, h2, h3, h4, h5, h6, .section-title, .hero-title, .logo-text),
html:not([data-theme="dark"]) :is(h1, h2, h3, h4, h5, h6, .section-title, .hero-title, .logo-text) {
  letter-spacing: 0.01em !important;
  line-height: 1.15 !important;
}

/* Black Ops One sets very wide; long copy needs more leading */
html[data-theme="dark"] :is(body, p, .section-subtitle, .testimonial-text, .short-desc),
html:not([data-theme="dark"]) :is(body, p, .section-subtitle, .testimonial-text, .short-desc) {
  line-height: 1.5 !important;
}

/* -------------------------------------------------------------
   Body copy at 30px.
   `body { font-size: 30px }` alone changed nothing visible: every
   paragraph on this site carries its own size from the design
   system, so the base was never inherited. These are the elements
   that actually hold reading text.
   ------------------------------------------------------------- */
html[data-theme="dark"] :is(p, .section-subtitle, .testimonial-text, .feature-info p),
html:not([data-theme="dark"]) :is(p, .section-subtitle, .testimonial-text, .feature-info p) {
  font-size: 30px !important;
  line-height: 1.45 !important;
}

/* Fixed-height containers keep the design size.
   The 3D service cards and the portfolio slides have a fixed height
   they cannot grow past — at 30px their copy overflowed the card by
   ~157px on a 375px screen. These are the only places the 30px body
   size is held back, and only because the geometry forbids it. */
html[data-theme="dark"] :is(.carousel-3d-card, .card-inner, .coverflow-slide, .coverflow-info) :is(p, .short-desc),
html:not([data-theme="dark"]) :is(.carousel-3d-card, .card-inner, .coverflow-slide, .coverflow-info) :is(p, .short-desc) {
  font-size: 0.9rem !important;
  line-height: 1.5 !important;
}

/* Stragglers that declare weight at (0,2,0) from a page's inline
   <style>. Including `.plan .price` in the :is() list raises the whole
   list to (0,3,1), which is what settles it. */
html[data-theme="dark"] :is(.plan .price, .plan h2, .plan .tagline, .plan li,
  .price, strong, b, .stat-number, .hero-stat-number, .value, .num),
html:not([data-theme="dark"]) :is(.plan .price, .plan h2, .plan .tagline, .plan li,
  .price, strong, b, .stat-number, .hero-stat-number, .value, .num) {
  font-weight: 400 !important;
  font-synthesis-weight: none;
}

/* Neither face ships a bold. Telling the browser not to synthesise
   one is the real fix — any font-weight declaration anywhere in the
   stack then renders with the genuine 400 glyphs instead of a
   smeared fake bold, without having to out-specify every rule. */
* { font-synthesis-weight: none; }

/* Menus take the display face — this covers the dashboard sidebar
   and topbar as well as the public header nav. */
html[data-theme="dark"] :is(.nav-item, .nav-section, .topbar-left .brand, .sidebar-logo span, .nav-links a),
html:not([data-theme="dark"]) :is(.nav-item, .nav-section, .topbar-left .brand, .sidebar-logo span, .nav-links a) {
  font-family: var(--font-display) !important;
}

/* =============================================================
   DISPLAY-FACE READABILITY
   Alumni Sans Collegiate One is a condensed collegiate face: at any
   given point size its glyphs are narrower and its x-height lower
   than the Archivo it replaced, so the old sizes read noticeably
   smaller. Everything set in the display face is scaled up, and the
   menu — which was 12px — gets the largest correction.
   ============================================================= */
html[data-theme="dark"] :is(.section-title, .pricing-header h1, .legal-header h1),
html:not([data-theme="dark"]) :is(.section-title, .pricing-header h1, .legal-header h1) {
  font-size: clamp(2.6rem, 5.6vw, 4.4rem) !important;
}

.hero-video .hero-video-content .hero-title {
  font-size: clamp(2.7rem, 7.4vw, 5.8rem) !important;
}

/* Menu: 12px in a condensed caps face is the least legible thing on
   the page. Raised to 1rem and given tracking so the caps separate. */
html[data-theme="dark"] :is(.header .nav-links a:not(.nav-cta), .nav-item, .nav-section),
html:not([data-theme="dark"]) :is(.header .nav-links a:not(.nav-cta), .nav-item, .nav-section) {
  font-size: 1rem !important;
  letter-spacing: 0.045em !important;
}

/* Card, panel and section sub-headings */
html[data-theme="dark"] :is(h2, h3, .panel-header h2, .card-title, .plan h2,
  .carousel-3d-card h3, .coverflow-info h3, .feature-info h4, .contact-info h3, .auth-form h2),
html:not([data-theme="dark"]) :is(h2, h3, .panel-header h2, .card-title, .plan h2,
  .carousel-3d-card h3, .coverflow-info h3, .feature-info h4, .contact-info h3, .auth-form h2) {
  font-size: 1.5rem !important;
  letter-spacing: 0.02em !important;
}

html[data-theme="dark"] :is(h4, h5, h6, .stat-label),
html:not([data-theme="dark"]) :is(h4, h5, h6, .stat-label) {
  font-size: 1.1rem !important;
  letter-spacing: 0.03em !important;
}

/* Brand lockup and large numerals */
html[data-theme="dark"] :is(.logo-text, .stat-number, .plan .price, .hero-stat-number),
html:not([data-theme="dark"]) :is(.logo-text, .stat-number, .plan .price, .hero-stat-number) {
  font-size: 1.5rem !important;
  letter-spacing: 0.02em !important;
}
html[data-theme="dark"] :is(.stat-number, .plan .price, .hero-stat-number),
html:not([data-theme="dark"]) :is(.stat-number, .plan .price, .hero-stat-number) {
  font-size: clamp(2.2rem, 3.6vw, 3rem) !important;
}

@media (max-width: 767px) {
  html[data-theme="dark"] :is(.header .nav-links a:not(.nav-cta)),
  html:not([data-theme="dark"]) :is(.header .nav-links a:not(.nav-cta)) {
    font-size: 0.92rem !important;
  }
}

/* =============================================================
   PRICING — subscribe panel (InstaPay transfer + review)
   ============================================================= */
.subscribe-panel {
  margin: 2.5rem 0;
  padding: 1.8rem;
  border-radius: var(--r-card);
  box-shadow: var(--shadow-md);
}
.subscribe-panel > h2 { margin-bottom: .4rem; }
.subscribe-panel .sub-intro { margin-bottom: 1.4rem; opacity: .85; }
.sub-loading { opacity: .7; }

/* Plan chooser — the segmented groove used everywhere else */
.sub-plans {
  display: flex; gap: 4px; padding: 5px; margin-bottom: 1.2rem;
  border-radius: 999px; box-shadow: var(--nm-in); flex-wrap: wrap;
}
.sub-plan {
  flex: 1 1 8rem; display: flex; flex-direction: column; align-items: center; gap: 2px;
  min-height: 56px; padding: .5rem .8rem; border: 0; border-radius: 999px;
  background: transparent; cursor: pointer;
  transition: background-color .22s var(--ease-out-soft), box-shadow .22s var(--ease-out-soft);
}
.sub-plan-name { font-size: 1rem; }
.sub-plan-price { font-size: .8rem; opacity: .8; }
html[data-theme="dark"] .sub-plan { color: #FAFAFA; }
html:not([data-theme="dark"]) .sub-plan { color: #18181B; }
html[data-theme="dark"] .sub-plan.active {
  background: var(--surface-2); box-shadow: var(--shadow-sm); color: #00d4ff;
}
html:not([data-theme="dark"]) .sub-plan.active {
  background: color-mix(in srgb, #00d4ff 24%, #FFFFFF);
  box-shadow: var(--shadow-sm); color: #0d0d1a;
}

/* Where the money goes */
.sub-target {
  padding: 1.1rem; border-radius: var(--r-field);
  box-shadow: var(--nm-in); margin-bottom: 1.2rem;
}
.sub-row { display: flex; flex-wrap: wrap; gap: 1.5rem; margin-bottom: .8rem; }
.sub-row > div { display: flex; flex-direction: column; gap: 2px; }
.sub-label { font-size: .78rem; opacity: .7; }
.sub-amount { font-family: var(--font-display); font-size: 1.8rem; }
.sub-addr { display: inline-flex; align-items: center; gap: 6px; font-size: 1rem; }
.sub-name { margin-bottom: .5rem; }
.sub-copy {
  background: none; border: 0; cursor: pointer; padding: 4px;
  color: var(--accent, #00d4ff); min-height: 32px;
}
.sub-copy:hover { opacity: .75; }
.sub-muted { font-size: .85rem !important; opacity: .78; }

/* States */
.sub-state {
  display: flex; gap: .8rem; align-items: flex-start;
  padding: 1rem; border-radius: var(--r-field);
  box-shadow: var(--nm-in); margin-bottom: 1.2rem;
}
.sub-state i { margin-top: 3px; font-size: 1.1rem; }
.sub-state strong { display: block; margin-bottom: 2px; }
.sub-ok i { color: var(--success, #22C55E); }
.sub-wait i { color: var(--warning, #FBBF24); }
.sub-bad i { color: var(--danger, #EF4444); }
.sub-info i { color: var(--accent, #00d4ff); }
.sub-error { color: var(--danger, #EF4444); font-size: .88rem; margin-bottom: .6rem; }
.sub-cta { width: 100%; justify-content: center; }
.req { color: var(--danger, #EF4444); }

@media (max-width: 600px) {
  .subscribe-panel { padding: 1.2rem; }
  .sub-plan { flex: 1 1 100%; }
  .sub-row { gap: 1rem; }
}

/* The subscribe panel is not a .card, so it never inherited a well and
   its inputs fell back to the browser default black-on-navy (1.27:1).
   Give it the same recessed well and explicit ink as the form cards. */
html[data-theme="dark"] .subscribe-panel {
  --nm-well: color-mix(in srgb, var(--surface) 84%, #0d0d1a);
}
html:not([data-theme="dark"]) .subscribe-panel {
  --nm-well: color-mix(in srgb, #FFFFFF 93%, #0d0d1a);
}

html[data-theme="dark"] .subscribe-panel :is(input, textarea, select),
html[data-theme="dark"] .subscribe-panel :is(.sub-label, .sub-name, .sub-amount, .sub-plan-name, .sub-plan-price) {
  color: #FAFAFA !important;
  -webkit-text-fill-color: #FAFAFA !important;
}
html:not([data-theme="dark"]) .subscribe-panel :is(input, textarea, select),
html:not([data-theme="dark"]) .subscribe-panel :is(.sub-label, .sub-name, .sub-amount, .sub-plan-name, .sub-plan-price) {
  color: #18181B !important;
  -webkit-text-fill-color: #18181B !important;
}
html[data-theme="dark"] .subscribe-panel :is(input, textarea)::placeholder {
  color: rgba(250, 250, 250, 0.45) !important;
}
html:not([data-theme="dark"]) .subscribe-panel :is(input, textarea)::placeholder {
  color: rgba(24, 24, 27, 0.45) !important;
}

/* The active chip keeps the brand accent readable on its own surface */
html[data-theme="dark"] .subscribe-panel .sub-plan.active :is(.sub-plan-name, .sub-plan-price) {
  color: #00d4ff !important;
  -webkit-text-fill-color: #00d4ff !important;
}

/* The top-bar "Home" link is a menu item too — display face, readable size */
html[data-theme="dark"] .viprix-top-bar .top-bar-home,
html:not([data-theme="dark"]) .viprix-top-bar .top-bar-home {
  font-family: var(--font-display) !important;
  font-size: 1.05rem !important;
  letter-spacing: 0.045em !important;
}

/* Copy button needs a real tap target (skill rule: touch-target-size) */
.sub-copy { min-width: 44px; min-height: 44px; }
.viprix-top-bar .top-bar-home {
  display: inline-flex; align-items: center;
  min-height: 44px;
}

/* Re-assert the big display sizes LAST. Section titles are h2
   elements, so the generic h2/h3 rule above was flattening them to
   1.5rem — this restores the intended scale. */
html[data-theme="dark"] :is(.section-title, .pricing-header h1, .legal-header h1),
html:not([data-theme="dark"]) :is(.section-title, .pricing-header h1, .legal-header h1) {
  font-size: clamp(2.6rem, 5.6vw, 4.4rem) !important;
  line-height: 1.08 !important;
}

/* =============================================================
   TYPE SCALE — single source of truth
   Supersedes the ad-hoc sizes above. It exists because the page had
   drifted into an incoherent range: 11px eyebrows and 12px buttons
   sitting beside 30px body copy and 93px headings.

   The body measure was the clearest symptom — 25 characters per line
   against a 60-75 target — so paragraphs were breaking into
   fragments. Black Ops One is a heavy stencil face with a large
   x-height: it reads considerably larger than its point size, so it
   wants a SMALLER number than a normal text face, not a bigger one.
   Alumni Sans Collegiate One is condensed and wants the opposite.

   One 1.25 ratio, 16px base.
     13 · 14 · 16 · 18 · 20 · 24 · 30 · 32-48 · 40-64
   ============================================================= */
:root {
  --t-meta: 0.8125rem;   /* 13px — labels, eyebrows, captions   */
  --t-small: 0.875rem;   /* 14px — secondary and dense UI       */
  --t-body: 1rem;        /* 16px — reading text                 */
  --t-lead: 1.125rem;    /* 18px — intros, subtitles            */
  --t-h4: 1.25rem;       /* 20px                                */
  --t-h3: 1.5rem;        /* 24px                                */
  --t-h2: 1.875rem;      /* 30px — card and panel titles        */
}

/* ── Reading text ── */
html[data-theme="dark"] :is(body, p, li, td, .short-desc, .feature-info p),
html:not([data-theme="dark"]) :is(body, p, li, td, .short-desc, .feature-info p) {
  font-size: var(--t-body) !important;
  line-height: 1.65 !important;
}

html[data-theme="dark"] :is(.section-subtitle, .testimonial-text, .pricing-header p, .sub-intro),
html:not([data-theme="dark"]) :is(.section-subtitle, .testimonial-text, .pricing-header p, .sub-intro) {
  font-size: var(--t-lead) !important;
  line-height: 1.6 !important;
}

/* ── Display ── */
.hero-video .hero-video-content .hero-title {
  font-size: clamp(2.5rem, 5.2vw, 4rem) !important;
  line-height: 1.05 !important;
}

html[data-theme="dark"] :is(.section-title, .pricing-header h1, .legal-header h1),
html:not([data-theme="dark"]) :is(.section-title, .pricing-header h1, .legal-header h1) {
  font-size: clamp(2rem, 3.6vw, 3rem) !important;
  line-height: 1.1 !important;
}

html[data-theme="dark"] :is(h1, h2, .plan h2, .panel-header h2, .card-title, .auth-form h2,
  .contact-info h3, .subscribe-panel > h2, .pricing-note h3),
html:not([data-theme="dark"]) :is(h1, h2, .plan h2, .panel-header h2, .card-title, .auth-form h2,
  .contact-info h3, .subscribe-panel > h2, .pricing-note h3) {
  font-size: var(--t-h2) !important;
  line-height: 1.2 !important;
}

html[data-theme="dark"] :is(h3, .carousel-3d-card h3, .coverflow-info h3),
html:not([data-theme="dark"]) :is(h3, .carousel-3d-card h3, .coverflow-info h3) {
  font-size: var(--t-h3) !important;
  line-height: 1.25 !important;
}

html[data-theme="dark"] :is(h4, h5, h6, .feature-info h4),
html:not([data-theme="dark"]) :is(h4, h5, h6, .feature-info h4) {
  font-size: var(--t-h4) !important;
  line-height: 1.3 !important;
}

/* ── Numerals ── */
html[data-theme="dark"] :is(.stat-number, .plan .price, .hero-stat-number, .sub-amount),
html:not([data-theme="dark"]) :is(.stat-number, .plan .price, .hero-stat-number, .sub-amount) {
  font-size: clamp(1.75rem, 2.6vw, 2.25rem) !important;
  line-height: 1.1 !important;
}

/* ── UI chrome: these were the too-small end of the old range ── */
html[data-theme="dark"] :is(.btn, a.btn, .btn-submit, .submit-btn, .btn-login, .nav-cta,
  .carousel-card-cta, .auth-tab, .filter-tab, .sub-plan-name),
html:not([data-theme="dark"]) :is(.btn, a.btn, .btn-submit, .submit-btn, .btn-login, .nav-cta,
  .carousel-card-cta, .auth-tab, .filter-tab, .sub-plan-name) {
  font-size: 0.9375rem !important;   /* 15px */
}

html[data-theme="dark"] :is(.header .nav-links a:not(.nav-cta), .nav-item, .viprix-top-bar .top-bar-home),
html:not([data-theme="dark"]) :is(.header .nav-links a:not(.nav-cta), .nav-item, .viprix-top-bar .top-bar-home) {
  font-size: 0.9375rem !important;
  letter-spacing: 0.04em !important;
}

html[data-theme="dark"] :is(.section-label, .stat-label, .nav-section, .badge, .coverflow-tag,
  .detail-row .label, .field label, .form-group label, .sub-label, .logo-slogan),
html:not([data-theme="dark"]) :is(.section-label, .stat-label, .nav-section, .badge, .coverflow-tag,
  .detail-row .label, .field label, .form-group label, .sub-label, .logo-slogan) {
  font-size: var(--t-meta) !important;
}
html[data-theme="dark"] .logo-slogan,
html:not([data-theme="dark"]) .logo-slogan { font-size: 0.6rem !important; }

html[data-theme="dark"] :is(.hero-description, .detail-row .value, .sub-muted, .sub-plan-price,
  .billing, .tagline, .footer-bottom, .text-muted),
html:not([data-theme="dark"]) :is(.hero-description, .detail-row .value, .sub-muted, .sub-plan-price,
  .billing, .tagline, .footer-bottom, .text-muted) {
  font-size: var(--t-small) !important;
}

html[data-theme="dark"] :is(.logo-text),
html:not([data-theme="dark"]) :is(.logo-text) {
  font-size: 1.35rem !important;
}

/* Keep the reading column in the 60-75 character band */
html[data-theme="dark"] :is(.section-subtitle, .testimonial-text, .pricing-header p),
html:not([data-theme="dark"]) :is(.section-subtitle, .testimonial-text, .pricing-header p) {
  max-width: 68ch !important;
}

@media (max-width: 767px) {
  html[data-theme="dark"] :is(.section-subtitle, .testimonial-text, .pricing-header p, .sub-intro),
  html:not([data-theme="dark"]) :is(.section-subtitle, .testimonial-text, .pricing-header p, .sub-intro) {
    font-size: var(--t-body) !important;
  }
}

/* Section titles are h2 elements, so the generic h2 rule above sizes
   them too. Re-assert the display size after it — same reason as the
   earlier occurrence, kept last so nothing can flatten it again. */
html[data-theme="dark"] :is(.section-title, .pricing-header h1, .legal-header h1),
html:not([data-theme="dark"]) :is(.section-title, .pricing-header h1, .legal-header h1) {
  font-size: clamp(2rem, 3.6vw, 3rem) !important;
  line-height: 1.1 !important;
}

/* Form controls at 16px. Below that iOS zooms the page in on focus,
   which is jarring and leaves the user scrolled sideways. */
html[data-theme="dark"] :is(input, textarea, select),
html:not([data-theme="dark"]) :is(input, textarea, select) {
  font-size: var(--t-body) !important;
}

/* Nothing below the 13px meta step */
html[data-theme="dark"] :is(.password-hint, .field-warn, .billing, small, .coverflow-tag),
html:not([data-theme="dark"]) :is(.password-hint, .field-warn, .billing, small, .coverflow-tag) {
  font-size: var(--t-meta) !important;
}

/* =============================================================
   HEADER
   -------------------------------------------------------------
   Type: the header now takes the FOOTER's voice — Black Ops One,
   normal case, normal tracking — instead of the uppercase condensed
   Alumni Sans it had. Black Ops One is a heavy stencil, so the nav
   sits a step down the scale (14px) to carry the same weight on
   screen as 15px in the lighter face did.

   Style: the bar reads as a precision instrument strip rather than a
   flat black slab — a hairline cyan rule with a soft bloom along the
   bottom edge, echoing the electric frame used on the form cards. It
   condenses on scroll, and the active link is marked by a tick as
   well as colour, so the current location is not signalled by colour
   alone.
   ============================================================= */

/* ── The bar ── */
.header,
.header.scrolled {
  padding: 14px 0 !important;
  border-bottom: 1px solid rgba(0, 238, 255, 0.18) !important;
  box-shadow: 0 1px 0 rgba(0, 238, 255, 0.06), 0 10px 30px -18px rgba(0, 238, 255, 0.5);
  transition: padding 0.28s var(--ease-out-soft),
              box-shadow 0.28s var(--ease-out-soft),
              border-color 0.28s var(--ease-out-soft) !important;
}
.header.scrolled {
  padding: 8px 0 !important;
  border-bottom-color: rgba(0, 238, 255, 0.34) !important;
  box-shadow: 0 1px 0 rgba(0, 238, 255, 0.10), 0 14px 34px -18px rgba(0, 238, 255, 0.65);
}

/* ── Navigation: the footer's face ── */
html[data-theme="dark"] .header .nav-links a:not(.nav-cta),
html:not([data-theme="dark"]) .header .nav-links a:not(.nav-cta) {
  position: relative;
  font-family: var(--font-body) !important;   /* Black Ops One, as the footer */
  font-size: 0.875rem !important;             /* 14px — heavy face, one step down */
  text-transform: none !important;
  letter-spacing: normal !important;
  color: #FAFAFA !important;
  -webkit-text-fill-color: #FAFAFA !important;
  padding: 6px 2px !important;
  min-height: 44px;
  display: inline-flex !important;
  align-items: center !important;
  transition: color 0.2s var(--ease-out-soft) !important;
}

/* Active location gets a tick, not just a colour (color-not-only) */
.header .nav-links a:not(.nav-cta)::after {
  content: "";
  position: absolute;
  left: 0; right: 0; bottom: 4px;
  height: 2px;
  border-radius: 2px;
  background: #00d4ff;
  transform: scaleX(0);
  transform-origin: right;
  transition: transform 0.26s var(--ease-out-soft);
}
.header .nav-links a:not(.nav-cta):hover::after,
.header .nav-links a:not(.nav-cta):focus-visible::after { transform: scaleX(1); transform-origin: left; }

html[data-theme="dark"] .header .nav-links a.active,
html:not([data-theme="dark"]) .header .nav-links a.active {
  color: #00d4ff !important;
  -webkit-text-fill-color: #00d4ff !important;
}
.header .nav-links a.active::after { transform: scaleX(1); transform-origin: left; }

html[data-theme="dark"] .header .nav-links a:not(.nav-cta):hover,
html:not([data-theme="dark"]) .header .nav-links a:not(.nav-cta):hover {
  color: #00d4ff !important;
  -webkit-text-fill-color: #00d4ff !important;
}

/* ── Brand lockup keeps the display face, sized against the new nav ── */
html[data-theme="dark"] .header .logo-text,
html:not([data-theme="dark"]) .header .logo-text {
  font-size: 1.25rem !important;
  letter-spacing: 0.02em !important;
}
.header .logo-icon { width: 42px !important; height: 42px !important; }

/* ── The one primary action in the bar (skill rule: primary-action) ── */
.header .nav-links .nav-cta {
  font-family: var(--font-body) !important;
  font-size: 0.8125rem !important;
  text-transform: none !important;
  letter-spacing: normal !important;
  padding: 9px 16px !important;
  min-height: 44px;
}

/* =============================================================
   HEADER — mobile
   The always-visible menu was costing 186px, roughly a quarter of a
   375px screen. Same seven items, one compact block: the logo row
   tightens and the menu rows lose their padding, which brings the
   bar to about half that without hiding anything.
   ============================================================= */
@media (max-width: 767px) {
  .header, .header.scrolled { padding: 8px 0 !important; }

  .header .logo-icon { width: 34px !important; height: 34px !important; }
  html[data-theme="dark"] .header .logo-text,
  html:not([data-theme="dark"]) .header .logo-text { font-size: 1.05rem !important; }
  .header .logo-slogan { font-size: 0.5rem !important; }

  .header .nav-links {
    gap: 0 10px !important;
    padding-top: 2px !important;
    margin-top: 2px !important;
  }
  html[data-theme="dark"] .header .nav-links a:not(.nav-cta),
  html:not([data-theme="dark"]) .header .nav-links a:not(.nav-cta) {
    font-size: 0.8125rem !important;
    padding: 2px !important;
    min-height: 40px;
  }
  .header .nav-links .nav-cta {
    font-size: 0.75rem !important;
    padding: 6px 12px !important;
    min-height: 40px;
  }
  .header .nav-links a:not(.nav-cta)::after { bottom: 2px; }
}

@media (prefers-reduced-motion: reduce) {
  .header .nav-links a:not(.nav-cta)::after { transition: none !important; }
}

/* The menu rule above uses :is(), whose specificity is that of its
   WIDEST argument (.topbar-left .brand → 0,3,1), so the plain
   .header .nav-links .nav-cta (0,3,0) lost to it. Theme-qualified
   here to settle it. */
html[data-theme="dark"] .header .nav-links a.nav-cta,
html:not([data-theme="dark"]) .header .nav-links a.nav-cta {
  font-family: var(--font-body) !important;
  font-size: 0.8125rem !important;
  text-transform: none !important;
  letter-spacing: normal !important;
}

/* The inner pages carry .viprix-top-bar rather than .header — give it
   the same footer voice so "header type" is consistent site-wide.
   Declared theme-qualified because the earlier menu rule reaches it
   through a :is() list at (0,3,1). */
html[data-theme="dark"] .viprix-top-bar .top-bar-home,
html:not([data-theme="dark"]) .viprix-top-bar .top-bar-home {
  font-family: var(--font-body) !important;
  font-size: 0.875rem !important;
  text-transform: none !important;
  letter-spacing: normal !important;
}
.viprix-top-bar {
  border-bottom: 1px solid rgba(0, 238, 255, 0.18) !important;
  box-shadow: 0 1px 0 rgba(0, 238, 255, 0.06), 0 10px 30px -18px rgba(0, 238, 255, 0.5);
}


/* =============================================================
   INPUTS — plain, ordinary type
   Form controls opt out of the display system entirely. Black Ops
   One is a stencil face: fine for a headline, poor for reading back
   what you just typed, and worse for an email or a reference number
   where every character has to be checked.

   The stack is the reader's own system UI font, so it costs no extra
   download and looks native on whatever they are using. 16px keeps
   iOS from zooming the page on focus.
   ============================================================= */
:root {
  --font-input: system-ui, -apple-system, "Segoe UI", Roboto,
                Helvetica, Arial, "Noto Sans", sans-serif;
}

html[data-theme="dark"] :is(input, textarea, select),
html:not([data-theme="dark"]) :is(input, textarea, select),
html[data-theme="dark"] .subscribe-panel :is(input, textarea, select),
html:not([data-theme="dark"]) .subscribe-panel :is(input, textarea, select) {
  font-family: var(--font-input) !important;
  font-size: 1rem !important;
  font-weight: 400 !important;
  letter-spacing: normal !important;
  line-height: 1.5 !important;
}

html[data-theme="dark"] :is(input, textarea, select)::placeholder,
html:not([data-theme="dark"]) :is(input, textarea, select)::placeholder {
  font-family: var(--font-input) !important;
  font-size: 1rem !important;
}

/* Comfortable box for 16px text, still clearing the 44px touch min. */
html[data-theme="dark"] :is(.field input, .field select, .form-group input, .form-group select,
  .auth-card input, .auth-card select, .contact-form-wrap input, .contact-form-wrap select,
  #login-screen .field input, #sub-ref, #sub-sender),
html:not([data-theme="dark"]) :is(.field input, .field select, .form-group input, .form-group select,
  .auth-card input, .auth-card select, .contact-form-wrap input, .contact-form-wrap select,
  #login-screen .field input, #sub-ref, #sub-sender) {
  height: auto !important;
  min-height: 48px !important;
  padding: 0.6rem 1rem !important;
}
html[data-theme="dark"] :is(.field textarea, .auth-card textarea, .contact-form-wrap textarea, #sub-note),
html:not([data-theme="dark"]) :is(.field textarea, .auth-card textarea, .contact-form-wrap textarea, #sub-note) {
  min-height: 96px !important;
  padding: 0.7rem 1rem !important;
}
