/* ===============================================================
   KNMS premium dark theme.

   Deliberately dark-first: the dark-purple -> gold -> cyan accent
   language depends on glow, and glow only reads against a dark
   surface. Accents are pitched brighter than their light-theme
   equivalents so they luminesce rather than muddy.

   NOTE: the printed ID card (assets/css/id-card.css) and outgoing
   email (includes/mailer.php) hardcode their own light palette on
   purpose — a physical card and an inbox must not follow this theme.
   =============================================================== */
:root {
    /* Royal-purple brand surfaces — warmer and richer than before so the gold
       reads as regal rather than clinical. Used as BACKGROUNDS. */
    --knms-primary: #3b1f6e;
    --knms-primary-light: #5a2f9c;
    --knms-primary-dark: #23124a;

    /* Gold is the PRIMARY accent in this theme: headings, panel frames, ornaments. */
    --knms-accent: #ffb92e;
    --knms-accent-light: #ffd77a;
    --knms-accent-deep: #c88516;

    /* Page + panel surfaces — deep violet rather than neutral black. */
    --knms-bg: #150a2e;
    --knms-bg-elev: #1d0f3d;
    --knms-surface: #23134a;
    --knms-surface-2: #2d1a5c;

    /* Type. --knms-heading is separate from --knms-primary because the
       latter is a background; one token can't be both. */
    --knms-heading: #ffd77a;
    --knms-text: #ece5ff;
    --knms-muted: #b7a8e0;
    --knms-border: #4a2f8f;
    /* Gold frame used on panels, matching the reference design. */
    --knms-frame: rgba(255, 185, 46, 0.55);

    --knms-success: #34d399;
    --knms-success-bg: rgba(52, 211, 153, 0.14);
    --knms-error: #fb7185;
    --knms-error-bg: rgba(251, 113, 133, 0.14);
    --knms-warn: #fbbf24;
    --knms-warn-bg: rgba(251, 191, 36, 0.14);

    /* Shadows are deeper on dark so elevation still reads. */
    --shadow-sm: 0 1px 2px rgba(0, 0, 0, 0.4);
    --shadow-md: 0 6px 20px rgba(0, 0, 0, 0.5);
    --shadow-lg: 0 16px 44px rgba(0, 0, 0, 0.6);

    --radius: 14px;
    --radius-sm: 8px;
    --footer-h: 72px;

    /* Accent palette — brighter than the light-theme values so they glow. */
    --gloss-purple: #8b5cf6;
    --gloss-purple-light: #c4b5fd;
    --gloss-purple-deep: #4c1d95;
    --gloss-cyan: #22d3ee;
    --gloss-cyan-light: #a5f3fc;
    --gloss-deep: #0c1a3d;

    /* Glow tokens — gold leads, matching the reference design. */
    --glow-purple: rgba(139, 92, 246, 0.7);
    --glow-gold: rgba(255, 185, 46, 0.75);
    --glow-cyan: rgba(34, 211, 238, 0.62);
}

* { box-sizing: border-box; }

html { -webkit-tap-highlight-color: transparent; }

body {
    margin: 0;
    font-family: 'Inter', "Segoe UI", Roboto, -apple-system, sans-serif;
    background: var(--knms-bg);
    color: var(--knms-text);
    padding-bottom: calc(var(--footer-h) + env(safe-area-inset-bottom, 0px));
    -webkit-font-smoothing: antialiased;
    animation: page-fade 0.25s ease-out;
}

@keyframes page-fade {
    from { opacity: 0; transform: translateY(4px); }
    to { opacity: 1; transform: translateY(0); }
}

h1, h2, h3 {
    font-family: 'Poppins', 'Inter', sans-serif;
    color: var(--knms-heading);
    letter-spacing: -0.01em;
}
h1 { font-size: 1.6rem; font-weight: 700; }

a { color: var(--knms-primary-light); text-decoration: none; transition: color 0.15s ease; }
a:hover { color: var(--knms-accent); }

.icon { width: 1.25em; height: 1.25em; display: inline-block; vertical-align: -0.22em; }

/* Text selection + focus states pick up the gradient identity too */
::selection { background: rgba(139, 92, 246,0.25); color: inherit; }

a:focus-visible, button:focus-visible, .btn:focus-visible, .footer-link:focus-visible {
    outline: none;
    box-shadow: 0 0 0 3px rgba(139, 92, 246,0.25), 0 0 10px var(--glow-cyan);
    border-radius: 4px;
}

/* Custom scrollbar — thin gradient thumb instead of the default gray bar */
::-webkit-scrollbar { width: 10px; height: 10px; }
::-webkit-scrollbar-track { background: var(--knms-bg); }
::-webkit-scrollbar-thumb {
    background: linear-gradient(180deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    border-radius: 999px;
}
::-webkit-scrollbar-thumb:hover { filter: brightness(1.15); }
* { scrollbar-width: thin; scrollbar-color: var(--gloss-purple) var(--knms-bg); }

/* Top bar */
.topbar {
    position: sticky;
    top: 0;
    z-index: 40;
    display: flex;
    align-items: center;
    justify-content: space-between;
    background: linear-gradient(135deg, rgba(36,27,77,0.82) 0%, rgba(21,15,46,0.9) 100%);
    backdrop-filter: blur(10px);
    -webkit-backdrop-filter: blur(10px);
    color: #fff;
    padding: 0.7rem 1.25rem;
    flex-wrap: wrap;
    gap: 0.5rem;
    box-shadow: var(--shadow-md);
}
/* Persistent brand accent — the dark-purple → gold → cyan signature on every page */
.topbar::after {
    content: '';
    position: absolute;
    left: 0; right: 0; bottom: -3px;
    height: 3px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 10px var(--glow-purple), 0 0 10px var(--glow-cyan);
}
.brand {
    display: flex;
    align-items: center;
    gap: 0.55rem;
    color: #fff;
    font-weight: 700;
    font-size: 1.1rem;
    letter-spacing: 0.02em;
}
/* The wordmark is the home link, and at 38px it was the one control on
   every page that sat just under the threshold. */
@media (pointer: coarse) {
    .brand { min-height: 2.75rem; }
}
.brand-mark {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 34px;
    height: 34px;
    border-radius: 10px;
    background: linear-gradient(135deg, var(--knms-accent), var(--knms-accent-light));
    color: var(--knms-primary-dark);
    font-family: 'Poppins', sans-serif;
    font-weight: 700;
    font-size: 0.85rem;
    box-shadow: var(--shadow-sm);
}
.topnav { display: flex; align-items: center; gap: 1.4rem; flex-wrap: wrap; }
.topnav a { color: rgba(255,255,255,0.8); font-size: 0.88rem; font-weight: 500; position: relative; padding: 0.25rem 0; transition: color 0.18s ease, text-shadow 0.28s ease, background-size 0.24s ease; }
.topnav a:hover, .topnav a:focus-visible { color: #fff; text-shadow: 0 0 14px rgba(255,206,110,0.9), 0 0 26px rgba(255,170,50,0.5); }
/* Underline grows from the centre on hover. Painted as a background, NOT a
   pseudo-element: ::before is already the nav separator dash and ::after is
   the active-item underline, so both are spoken for. */
.topnav a {
    background-image: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    background-repeat: no-repeat;
    background-position: 50% 100%;
    background-size: 0% 2px;
}
.topnav a:hover, .topnav a:focus-visible { background-size: 100% 2px; }
.topnav a.is-active { color: #fff; }
.topnav a.is-active::after {
    content: '';
    position: absolute;
    left: 0; right: 0; bottom: -2px;
    height: 2px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    border-radius: 2px;
    box-shadow: 0 0 8px var(--glow-purple), 0 0 8px var(--glow-cyan);
}
.topnav a.btn-join { background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 60%, var(--gloss-cyan)); color: #fff; text-shadow: 0 1px 2px rgba(0,0,0,0.35); padding: 0.4rem 0.9rem; border-radius: 999px; font-weight: 600; transition: box-shadow 0.2s ease, filter 0.2s ease; }
.topnav a.btn-join:hover { filter: brightness(1.1); box-shadow: 0 0 16px var(--glow-purple), 0 0 16px var(--glow-cyan); }

.page {
    max-width: 960px;
    margin: 1.5rem auto;
    padding: 0 1rem;
}

.card {
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    border-radius: var(--radius);
    padding: 1.4rem;
    margin-bottom: 1.1rem;
    /* Luminous edge — a faint always-on gradient-tinted ring, not just on hover */
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(139, 92, 246,0.16), 0 0 14px rgba(34,211,238,0.10);
    transition: box-shadow 0.2s ease, transform 0.2s ease;
}
.card:hover { box-shadow: var(--shadow-md), 0 0 0 1px rgba(139, 92, 246,0.34), 0 0 26px rgba(139, 92, 246,0.20); }

/* Small glowing marker before every card subheading — a quiet, consistent premium cue */
.card h3 { display: flex; align-items: center; gap: 0.5rem; }
.card h3::before {
    content: '';
    width: 7px;
    height: 7px;
    flex-shrink: 0;
    border-radius: 50%;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 6px var(--glow-purple);
}

.hero {
    text-align: center;
    color: #fff;
    background:
        radial-gradient(circle at 15% 20%, rgba(212,164,55,0.35), transparent 45%),
        radial-gradient(circle at 88% 82%, rgba(139, 92, 246,0.4), transparent 50%),
        linear-gradient(135deg, var(--knms-primary) 0%, var(--knms-primary-dark) 100%);
    border: none;
    box-shadow: var(--shadow-lg), 0 0 0 rgba(0,0,0,0);
    position: relative;
    animation: hero-glow 6s ease-in-out infinite;
}
/* Rotating conic-gradient halo — an animated glowing ring traced around the hero card */
.hero::before {
    content: '';
    position: absolute;
    inset: -3px;
    z-index: 0;
    border-radius: inherit;
    padding: 3px;
    background: conic-gradient(from 0deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan), var(--gloss-purple));
    -webkit-mask: linear-gradient(#fff 0 0) content-box, linear-gradient(#fff 0 0);
    -webkit-mask-composite: xor;
    mask-composite: exclude;
    opacity: 0.85;
    animation: halo-spin 8s linear infinite;
    pointer-events: none;
}
@keyframes halo-spin { to { transform: rotate(360deg); } }
@keyframes hero-glow {
    0%, 100% { box-shadow: var(--shadow-lg), 0 0 36px var(--glow-purple); }
    50% { box-shadow: var(--shadow-lg), 0 0 44px var(--glow-cyan); }
}
/* Decorative accents (hexagon cluster, dashed ticks, wave lines) — inspired
   by the glossy AI-template reference; reused on any dark gradient banner. */
.hero-decor {
    position: absolute;
    inset: 0;
    z-index: 1;
    overflow: hidden;
    border-radius: inherit;
    pointer-events: none;
}
.decor-hex { position: absolute; top: 14px; right: 16px; opacity: 0.9; filter: drop-shadow(0 0 6px var(--glow-purple)); }
.decor-hex.decor-inline { position: static; display: inline-block; filter: drop-shadow(0 0 4px var(--glow-cyan)); margin: 0 0.3rem; }
.decor-dashes { position: absolute; top: 18px; left: 22px; opacity: 0.8; }
.decor-waves { position: absolute; bottom: -4px; left: -4px; width: 62%; height: 90px; }

.hero h1 { color: #fff; margin-bottom: 0.3rem; font-size: 1.9rem; font-family: 'Baloo 2', 'Poppins', sans-serif; }
.hero p { opacity: 0.88; margin-top: 0; }
.hero .eyebrow {
    display: inline-block;
    font-size: 0.72rem;
    font-weight: 700;
    letter-spacing: 0.12em;
    text-transform: uppercase;
    margin-bottom: 0.5rem;
    background: linear-gradient(90deg, var(--gloss-purple-light), var(--knms-accent-light), var(--gloss-cyan-light), var(--gloss-purple-light));
    background-size: 300% auto;
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
    animation: gradient-shift 6s linear infinite;
}
@keyframes gradient-shift { to { background-position: 300% center; } }
.hero-content { position: relative; z-index: 2; }

/* Compact hero banner for auth entry points (login/register) — same premium
   gradient + glow language, sized down and paired with a plain form body. */
.auth-card { max-width: 440px; margin: 0 auto; padding: 0; overflow: hidden; }
.auth-hero {
    text-align: center;
    color: #fff;
    padding: 1.75rem 1.5rem 1.4rem;
    position: relative;
    overflow: hidden;
    background:
        radial-gradient(circle at 15% 15%, rgba(212,164,55,0.35), transparent 45%),
        radial-gradient(circle at 90% 85%, rgba(139, 92, 246,0.4), transparent 50%),
        linear-gradient(135deg, var(--knms-primary) 0%, var(--knms-primary-dark) 100%);
}
.auth-hero .icon {
    width: 2.1rem;
    height: 2.1rem;
    color: var(--gloss-cyan-light);
    filter: drop-shadow(0 0 8px var(--glow-cyan));
    margin-bottom: 0.35rem;
}
.auth-hero-content { position: relative; z-index: 2; }
.auth-hero h1 { color: #fff; font-size: 1.3rem; margin: 0 0 0.2rem; font-family: 'Baloo 2', 'Poppins', sans-serif; }
.auth-hero p { opacity: 0.85; margin: 0; font-size: 0.85rem; }
.auth-body { padding: 1.4rem 1.4rem 1.6rem; }

/* Organic glowing "blob" shapes — soft blurred color pools sitting behind the
   spheres, echoing the teal/magenta glow pools from the reference artwork. */
.blob-field {
    position: absolute;
    inset: 0;
    z-index: 0;
    overflow: hidden;
    border-radius: inherit;
    pointer-events: none;
}
.blob {
    position: absolute;
    filter: blur(18px);
    opacity: 0.55;
    animation: blob-drift 10s ease-in-out infinite;
}
.blob-cyan { background: radial-gradient(circle, var(--gloss-cyan) 0%, transparent 70%); border-radius: 60% 40% 55% 45% / 45% 55% 40% 60%; }
.blob-purple { background: radial-gradient(circle, var(--gloss-purple) 0%, transparent 70%); border-radius: 45% 55% 40% 60% / 55% 45% 60% 40%; }
@keyframes blob-drift {
    0%, 100% { transform: translate(0, 0) scale(1); }
    50% { transform: translate(8px, -10px) scale(1.08); }
}

/* Glossy orb decorations — inspired by glossy sphere / liquid-bubble artwork.
   Pure CSS: a soft white highlight fading into a saturated color, with an
   inset shadow for depth, so each div reads as a glassy 3D sphere. */
.orb-field {
    position: absolute;
    inset: 0;
    z-index: 1;
    overflow: hidden;
    pointer-events: none;
}
.orb {
    position: absolute;
    border-radius: 50%;
    opacity: 0.9;
    filter: blur(0.5px);
    box-shadow: inset -10px -12px 26px rgba(0,0,0,0.28), inset 6px 8px 16px rgba(255,255,255,0.25), 0 12px 28px rgba(0,0,0,0.3), 0 0 30px var(--orb-glow, transparent);
    animation: orb-float 7s ease-in-out infinite;
}
.orb-purple { --orb-glow: var(--glow-purple); background: radial-gradient(circle at 32% 28%, #fff 0%, var(--gloss-purple-light) 18%, var(--gloss-purple) 55%, var(--gloss-purple-deep) 100%); }
.orb-cyan { --orb-glow: var(--glow-cyan); background: radial-gradient(circle at 32% 28%, #fff 0%, var(--gloss-cyan-light) 18%, var(--gloss-cyan) 55%, #0891a8 100%); }
.orb-navy { --orb-glow: var(--glow-gold); background: radial-gradient(circle at 32% 28%, #fff 0%, #5b7bc7 18%, var(--knms-primary-light) 55%, var(--gloss-deep) 100%); }

@keyframes orb-float {
    0%, 100% { transform: translateY(0) scale(1); }
    50% { transform: translateY(-12px) scale(1.03); }
}
@media (prefers-reduced-motion: reduce) {
    .orb, .blob, .hero, .hero::before, .hero .eyebrow, .btn-accent, .btn.is-loading { animation: none; }
}

.btn {
    display: inline-flex;
    align-items: center;
    gap: 0.4rem;
    background: linear-gradient(135deg, var(--knms-primary-light), var(--knms-primary));
    color: #fff;
    border: none;
    border-radius: 999px;
    padding: 0.6rem 1.3rem;
    font-size: 0.92rem;
    font-weight: 600;
    cursor: pointer;
    box-shadow: var(--shadow-sm);
    transition: transform 0.15s ease, box-shadow 0.15s ease;
    position: relative;
    overflow: hidden;
    isolation: isolate;
}
.btn:hover { transform: translateY(-1px); box-shadow: var(--shadow-md); color: #fff; text-decoration: none; }
.btn:active { transform: translateY(0); }
/* Static glass reflection — a soft highlight across the top half, always present */
.btn::before {
    content: '';
    position: absolute;
    inset: 0;
    background: linear-gradient(180deg, rgba(255,255,255,0.22) 0%, rgba(255,255,255,0.04) 45%, transparent 55%);
    pointer-events: none;
}
/* Glossy sheen sweep on hover — echoes the light reflecting off a glass sphere */
.btn::after {
    content: '';
    position: absolute;
    top: -60%;
    left: -30%;
    width: 30%;
    height: 220%;
    background: linear-gradient(120deg, transparent, rgba(255,255,255,0.65), transparent);
    transform: rotate(20deg);
    transition: left 0.55s ease;
    pointer-events: none;
}
.btn:hover::after { left: 130%; }
.btn-accent {
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 55%, var(--gloss-cyan));
    color: #fff;
    text-shadow: 0 1px 2px rgba(0,0,0,0.35);
    transition: transform 0.15s ease, box-shadow 0.25s ease;
    animation: btn-breathe 3s ease-in-out infinite;
}
.btn-accent:hover {
    box-shadow: 0 6px 20px rgba(12,18,32,0.25), 0 0 22px var(--glow-purple), 0 0 26px var(--glow-cyan);
    animation-play-state: paused;
}
@keyframes btn-breathe {
    0%, 100% { box-shadow: var(--shadow-sm), 0 0 10px var(--glow-purple); }
    50% { box-shadow: var(--shadow-sm), 0 0 18px var(--glow-cyan); }
}
.btn-secondary { background: var(--knms-surface); color: var(--knms-text); border: 1px solid var(--knms-border); box-shadow: none; }
.btn-secondary:hover { border-color: var(--knms-primary-light); color: var(--knms-text); }
.btn-danger { background: linear-gradient(135deg, #e14b42, var(--knms-error)); }

.form-group { margin-bottom: 1.1rem; }
/* Two-column field pairing for settings forms that would otherwise be a very
   long single stack (admin/mail.php has twelve inputs). auto-fit rather than a
   fixed `repeat(2, 1fr)`, so it collapses to one column on a narrow screen
   without needing its own media query. */
.form-grid-2 {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
    gap: 0 1.1rem;
}
.form-group label { display: block; margin-bottom: 0.35rem; font-weight: 600; font-size: 0.88rem; color: var(--knms-heading); }
.form-group input,
.form-group select,
.form-group textarea {
    width: 100%;
    padding: 0.65rem 0.8rem;
    border: 1.5px solid var(--knms-border);
    border-radius: var(--radius-sm);
    font-size: 0.95rem;
    font-family: inherit;
    background: var(--knms-surface);
    transition: border-color 0.15s ease, box-shadow 0.15s ease;
}
.form-group input:focus,
.form-group select:focus,
.form-group textarea:focus {
    outline: none;
    border-color: var(--gloss-purple);
    box-shadow: 0 0 0 3px rgba(139, 92, 246,0.15), 0 0 10px var(--glow-cyan);
}

.flash { padding: 0.75rem 1rem; border-radius: var(--radius-sm); margin-bottom: 1rem; font-size: 0.9rem; font-weight: 500; border-left: 3px solid transparent; animation: page-fade 0.25s ease-out; }
.flash-success { background: var(--knms-success-bg); color: var(--knms-success); border: 1px solid #bfe6cf; border-left: 3px solid var(--knms-success); box-shadow: 0 0 14px rgba(27,138,76,0.12); }
.flash-error { background: var(--knms-error-bg); color: var(--knms-error); border: 1px solid #f4c3bf; border-left: 3px solid var(--knms-error); box-shadow: 0 0 14px rgba(208,52,44,0.12); }

/* Avatar chip — gradient-ring initials, used anywhere a member is referenced */
.avatar {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 2rem;
    height: 2rem;
    border-radius: 50%;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 55%, var(--gloss-cyan));
    color: #fff;
    font-family: 'Poppins', sans-serif;
    font-weight: 700;
    font-size: 0.72rem;
    text-shadow: 0 1px 2px rgba(0,0,0,0.3);
    box-shadow: 0 0 0 2px var(--knms-surface), 0 0 8px var(--glow-purple);
    flex-shrink: 0;
    vertical-align: middle;
}
.avatar-sm { width: 1.5rem; height: 1.5rem; font-size: 0.6rem; }
.avatar-lg { width: 3.2rem; height: 3.2rem; font-size: 1.1rem; }
.name-row { display: inline-flex; align-items: center; gap: 0.5rem; }

/* Gradient capacity meter — event registration fill */
.capacity-meter { width: 100%; height: 8px; border-radius: 999px; background: var(--knms-border); overflow: hidden; margin-top: 0.4rem; }
.capacity-meter-fill {
    height: 100%;
    border-radius: 999px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 8px var(--glow-cyan);
    transition: width 0.3s ease;
}
.capacity-meter-fill.is-full { background: linear-gradient(90deg, var(--knms-error), var(--knms-warn)); box-shadow: 0 0 8px rgba(208,52,44,0.4); }

table { width: 100%; border-collapse: collapse; }
th, td { text-align: left; padding: 0.6rem 0.5rem; border-bottom: 1px solid var(--knms-border); font-size: 0.88rem; }
th { color: var(--knms-muted); font-weight: 600; text-transform: uppercase; font-size: 0.72rem; letter-spacing: 0.04em; }
tr:last-child td { border-bottom: none; }
/* Luminous row hover — a dashboard-table cue matching the rest of the accent language */
table tr:not(:first-child) {
    position: relative;
    transition: background 0.15s ease;
}
table tr:not(:first-child):hover {
    background: linear-gradient(90deg, rgba(139, 92, 246,0.14), rgba(34,211,238,0.04));
    box-shadow: inset 2px 0 0 var(--gloss-purple);
}

/* Wrap any <table> that can outgrow a phone screen — scrolls horizontally
   inside its own box instead of blowing out the page or wrapping awkwardly. */
.table-scroll { overflow-x: auto; -webkit-overflow-scrolling: touch; margin: 0 -0.2rem; }
.table-scroll table { min-width: 480px; }
@media (max-width: 600px) {
    .table-scroll { margin: 0 -1rem; padding: 0 1rem; }
}

/* Quick filter box above a table-scroll — instant client-side search */
.list-filter { position: relative; margin-bottom: 0.9rem; }
.list-filter input {
    width: 100%;
    padding: 0.6rem 0.8rem 0.6rem 2.3rem;
    border: 1.5px solid var(--knms-border);
    border-radius: var(--radius-sm);
    font-size: 0.9rem;
    font-family: inherit;
    background: var(--knms-surface);
    color: var(--knms-text);
}
.list-filter input:focus {
    outline: none;
    border-color: var(--gloss-purple);
    box-shadow: 0 0 0 3px rgba(139, 92, 246,0.15), 0 0 10px var(--glow-cyan);
}
.list-filter .icon { position: absolute; left: 0.75rem; top: 50%; transform: translateY(-50%); width: 1.1rem; height: 1.1rem; color: var(--knms-muted); pointer-events: none; transition: color 0.15s ease, filter 0.15s ease; }
.list-filter:focus-within .icon { color: var(--gloss-purple); filter: drop-shadow(0 0 4px var(--glow-cyan)); }
.list-filter-empty { color: var(--knms-muted); font-size: 0.88rem; padding: 0.5rem 0; display: none; }

/* Accessibility: visually-hidden skip link, revealed on keyboard focus —
   same gradient + glow language as the rest of the interface. */
.skip-link {
    position: absolute;
    left: -999px;
    top: auto;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 55%, var(--gloss-cyan));
    color: #fff;
    text-shadow: 0 1px 2px rgba(0,0,0,0.35);
    font-weight: 600;
    padding: 0.6rem 1rem;
    border-radius: var(--radius-sm);
    box-shadow: 0 0 16px var(--glow-purple), 0 0 16px var(--glow-cyan);
    z-index: 100;
    /* Sized here rather than under :focus — the box exists whether or not
       it is focused, and a rule that only fires on focus cannot be
       measured by anything that is not already holding focus on it. */
    display: inline-flex;
    align-items: center;
    min-height: 2.75rem;
}
.skip-link:focus {
    left: 0.75rem;
    top: 0.75rem;
    outline: none;
}

/* Disabled/submitting state for buttons — prevents double-submit confusion */
.btn[disabled] { opacity: 0.7; cursor: progress; pointer-events: none; }
.btn.is-loading { opacity: 0.85; cursor: progress; pointer-events: none; animation: btn-loading-glow 1.1s ease-in-out infinite; }
@keyframes btn-loading-glow {
    0%, 100% { box-shadow: var(--shadow-sm), 0 0 6px var(--glow-purple); }
    50% { box-shadow: var(--shadow-sm), 0 0 16px var(--glow-cyan); }
}

.badge-pill {
    display: inline-block;
    padding: 0.2rem 0.7rem;
    border-radius: 999px;
    font-size: 0.72rem;
    font-weight: 700;
    letter-spacing: 0.02em;
}
.badge-pending { background: var(--knms-warn-bg); color: var(--knms-warn); }
.badge-active { background: var(--knms-success-bg); color: var(--knms-success); }
.badge-rejected, .badge-suspended { background: var(--knms-error-bg); color: var(--knms-error); }

/* Decorative gradient badge — for achievements/highlights, not status (status stays
   flat semantic color so pending/active/rejected remain instantly readable). */
.badge-gradient {
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    color: #fff;
    text-shadow: 0 1px 2px rgba(0,0,0,0.35);
    box-shadow: 0 0 8px var(--glow-purple);
}

/* Leaderboard rank markers — gold/cyan/purple spotlight for the top 3 */
.rank-badge {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 1.7rem;
    height: 1.7rem;
    border-radius: 50%;
    font-size: 0.76rem;
    font-weight: 700;
    color: var(--knms-muted);
    background: var(--knms-bg);
    border: 1px solid var(--knms-border);
}
.rank-badge.rank-1 { background: linear-gradient(135deg, var(--knms-accent), var(--knms-accent-light)); color: #4a3403; box-shadow: 0 0 10px var(--glow-gold); border: none; }
.rank-badge.rank-2 { background: linear-gradient(135deg, var(--gloss-cyan), var(--gloss-cyan-light)); color: #013844; box-shadow: 0 0 10px var(--glow-cyan); border: none; }
.rank-badge.rank-3 { background: linear-gradient(135deg, var(--gloss-purple), var(--gloss-purple-light)); color: #fff; box-shadow: 0 0 10px var(--glow-purple); border: none; }

/* SaaS-style dashboard header — dark gradient panel with reflection sheen and
   a luminous bottom edge, used atop admin/analytics dashboards. */
.dashboard-header {
    position: relative;
    display: flex;
    align-items: center;
    gap: 0.9rem;
    color: #fff;
    padding: 1.1rem 1.4rem;
    border-radius: var(--radius);
    margin-bottom: 1.3rem;
    background: linear-gradient(135deg, var(--knms-primary) 0%, var(--knms-primary-dark) 100%);
    box-shadow: var(--shadow-md), 0 0 24px var(--glow-purple);
    overflow: hidden;
}
.dashboard-header::before {
    content: '';
    position: absolute;
    inset: 0;
    background: linear-gradient(180deg, rgba(255,255,255,0.08), transparent 55%);
    pointer-events: none;
}
.dashboard-header::after {
    content: '';
    position: absolute;
    left: 0; right: 0; bottom: 0;
    height: 3px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 10px var(--glow-cyan);
}
.dashboard-header .icon-badge {
    position: relative;
    z-index: 1;
    width: 2.6rem;
    height: 2.6rem;
    border-radius: 12px;
    display: flex;
    align-items: center;
    justify-content: center;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 55%, var(--gloss-cyan));
    box-shadow: 0 0 14px var(--glow-purple);
    flex-shrink: 0;
}
.dashboard-header .icon-badge .icon { width: 1.4rem; height: 1.4rem; color: #fff; }
.dashboard-header .dashboard-header-text { position: relative; z-index: 1; }
.dashboard-header h1 { color: #fff; margin: 0; font-size: 1.35rem; font-family: 'Baloo 2', 'Poppins', sans-serif; }
.dashboard-header p { margin: 0.15rem 0 0; opacity: 0.8; font-size: 0.85rem; }

.stat-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: 1rem; margin-bottom: 1.5rem; }
.stat-tile {
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    border-radius: var(--radius);
    padding: 1.1rem 1rem;
    text-align: center;
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(139, 92, 246,0.14);
    transition: transform 0.15s ease, box-shadow 0.15s ease;
    position: relative;
    overflow: hidden;
}
/* Luminous top edge — faintly present at rest, fully lit on hover */
.stat-tile::before {
    content: '';
    position: absolute;
    top: 0; left: 0; right: 0;
    height: 3px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    opacity: 0.35;
    box-shadow: 0 0 8px var(--glow-purple);
    transition: opacity 0.2s ease;
}
.stat-tile:hover { transform: translateY(-2px); box-shadow: var(--shadow-md), 0 0 22px rgba(139, 92, 246,0.28); }
.stat-tile:hover::before { opacity: 1; }
.stat-tile .value { font-family: 'Poppins', sans-serif; font-size: 1.7rem; font-weight: 700; color: var(--knms-heading); }
.stat-tile .label { font-size: 0.76rem; color: var(--knms-muted); margin-top: 0.15rem; }

/* Footer navigation — fixed, native-app style */
.footer-nav {
    position: fixed;
    bottom: 0;
    left: 0;
    right: 0;
    display: flex;
    justify-content: space-around;
    background: rgba(16, 12, 31, 0.88);
    backdrop-filter: blur(12px);
    -webkit-backdrop-filter: blur(12px);
    border-top: 1px solid var(--knms-border);
    box-shadow: 0 -4px 20px rgba(16,24,40,0.08);
    z-index: 50;
    padding-bottom: env(safe-area-inset-bottom, 0px);
}
.footer-link {
    flex: 1;
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 0.2rem;
    padding: 0.55rem 0.25rem 0.5rem;
    font-size: 0.68rem;
    font-weight: 600;
    color: var(--knms-muted);
    position: relative;
    transition: color 0.15s ease;
}
.footer-link .icon { width: 1.35em; height: 1.35em; transition: transform 0.15s ease; }
.footer-link:hover, .footer-link:focus, .footer-link:focus-within { color: var(--knms-heading); text-decoration: none; }
.footer-link:active .icon { transform: scale(0.88); }
.footer-link.is-active { color: var(--knms-heading); }
.footer-link.is-active::before {
    content: '';
    position: absolute;
    top: 2px;
    width: 22px;
    height: 3px;
    border-radius: 999px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 6px var(--glow-purple);
}
.footer-expandable { cursor: pointer; }
.footer-submenu {
    display: none;
    position: absolute;
    bottom: 100%;
    left: 50%;
    transform: translateX(-50%);
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    border-radius: var(--radius-sm);
    box-shadow: var(--shadow-lg);
    padding: 0.4rem;
    white-space: nowrap;
    margin-bottom: 0.6rem;
}
.footer-expandable:hover .footer-submenu,
.footer-expandable:focus-within .footer-submenu {
    display: flex;
    flex-direction: column;
}
.footer-submenu a { padding: 0.4rem 0.7rem; color: var(--knms-text); font-size: 0.8rem; font-weight: 500; border-radius: 6px; }
.footer-submenu a:hover { background: var(--knms-bg); }

/* Legacy/CMS photo showcase gallery */
.gallery-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(140px, 1fr));
    gap: 0.8rem;
}
.gallery-item {
    position: relative;
    display: block;
    padding: 0;
    border: none;
    border-radius: var(--radius-sm);
    overflow: hidden;
    cursor: pointer;
    aspect-ratio: 1 / 1;
    background: var(--knms-bg);
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(139, 92, 246,0.16);
    transition: transform 0.15s ease, box-shadow 0.2s ease;
}
.gallery-item:hover, .gallery-item:focus-visible {
    transform: translateY(-2px);
    box-shadow: var(--shadow-md), 0 0 18px var(--glow-purple);
}
.gallery-item img { width: 100%; height: 100%; object-fit: cover; display: block; }
.gallery-item-caption {
    position: absolute;
    left: 0; right: 0; bottom: 0;
    padding: 0.5rem 0.6rem 0.4rem;
    font-size: 0.72rem;
    font-weight: 600;
    color: #fff;
    text-align: left;
    background: linear-gradient(0deg, rgba(13,21,38,0.85), transparent);
    text-shadow: 0 1px 2px rgba(0,0,0,0.5);
}

/* ---------------------------------------------------------------
   CMS content blocks
   --------------------------------------------------------------- */
.cms-block-bare { margin-bottom: 1.1rem; }
.cms-richtext { line-height: 1.65; }
.cms-richtext > *:first-child { margin-top: 0; }
.cms-richtext > *:last-child { margin-bottom: 0; }
.cms-richtext img { max-width: 100%; height: auto; border-radius: var(--radius-sm); }
.cms-richtext blockquote {
    margin: 1rem 0;
    padding: 0.6rem 1rem;
    border-left: 3px solid var(--gloss-purple);
    background: var(--knms-bg);
    border-radius: 0 var(--radius-sm) var(--radius-sm) 0;
}

/* Milestone timeline — a glowing gradient rail with dotted markers */
.timeline { list-style: none; margin: 0; padding: 0 0 0 1.6rem; position: relative; }
.timeline::before {
    content: '';
    position: absolute;
    left: 5px; top: 6px; bottom: 6px;
    width: 2px;
    border-radius: 2px;
    background: linear-gradient(180deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 8px var(--glow-purple);
}
.timeline-item { position: relative; padding-bottom: 1.3rem; }
.timeline-item:last-child { padding-bottom: 0; }
.timeline-marker {
    position: absolute;
    left: -1.6rem;
    top: 0.35rem;
    width: 12px;
    height: 12px;
    border-radius: 50%;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 0 3px var(--knms-surface), 0 0 10px var(--glow-purple);
}
.timeline-year {
    display: inline-block;
    font-family: 'Baloo 2', 'Poppins', sans-serif;
    font-size: 0.78rem;
    font-weight: 700;
    letter-spacing: 0.06em;
    color: var(--gloss-purple);
    margin-bottom: 0.15rem;
}
.timeline-title { display: block; color: var(--knms-heading); font-family: 'Poppins', sans-serif; }
.timeline-text { margin: 0.25rem 0 0; color: var(--knms-muted); font-size: 0.9rem; line-height: 1.55; }

/* Pull quote */
.cms-quote {
    margin: 0 0 1.1rem;
    padding: 1.6rem 1.5rem;
    position: relative;
    overflow: hidden;
    background:
        radial-gradient(circle at 12% 18%, rgba(212,164,55,0.12), transparent 45%),
        radial-gradient(circle at 88% 82%, rgba(139, 92, 246,0.12), transparent 50%),
        var(--knms-surface);
}
.cms-quote::before {
    content: '"';
    position: absolute;
    top: -0.6rem; left: 0.7rem;
    font-family: 'Baloo 2', serif;
    font-size: 5rem;
    line-height: 1;
    color: var(--gloss-purple);
    opacity: 0.18;
}
.cms-quote blockquote {
    margin: 0;
    position: relative;
    font-size: 1.12rem;
    line-height: 1.6;
    color: var(--knms-text);
    font-style: italic;
}
.cms-quote figcaption {
    margin-top: 0.7rem;
    font-weight: 700;
    font-size: 0.88rem;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}

/* Call-to-action panel */
.cms-cta {
    text-align: center;
    color: #fff;
    background:
        radial-gradient(circle at 15% 20%, rgba(212,164,55,0.3), transparent 45%),
        radial-gradient(circle at 88% 82%, rgba(139, 92, 246,0.38), transparent 50%),
        linear-gradient(135deg, var(--knms-primary) 0%, var(--knms-primary-dark) 100%);
    border: none;
    box-shadow: var(--shadow-md), 0 0 26px var(--glow-purple);
}
.cms-cta h3 { color: #fff; justify-content: center; }
.cms-cta p { opacity: 0.9; margin-top: 0; }

/* Responsive video embed */
.cms-video { position: relative; padding-top: 56.25%; border-radius: var(--radius-sm); overflow: hidden; background: #000; }
.cms-video iframe { position: absolute; inset: 0; width: 100%; height: 100%; border: 0; }

/* ---------------------------------------------------------------
   News module
   --------------------------------------------------------------- */
.news-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(240px, 1fr));
    gap: 1rem;
    margin-bottom: 1.1rem;
}
.news-card {
    display: flex;
    flex-direction: column;
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    border-radius: var(--radius);
    overflow: hidden;
    color: inherit;
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(139, 92, 246,0.16);
    transition: transform 0.15s ease, box-shadow 0.2s ease;
}
.news-card:hover { transform: translateY(-2px); color: inherit; box-shadow: var(--shadow-md), 0 0 26px rgba(139, 92, 246,0.26); }
.news-card.is-featured { box-shadow: var(--shadow-md), 0 0 0 1px rgba(212,164,55,0.35), 0 0 20px var(--glow-gold); }
.news-card-media { width: 100%; height: 150px; object-fit: cover; display: block; background: var(--knms-bg); }
.news-card-body { display: flex; flex-direction: column; gap: 0.35rem; padding: 0.9rem 1rem 1rem; }
.news-card-meta { display: flex; gap: 0.35rem; flex-wrap: wrap; }
.news-card-body strong { color: var(--knms-heading); font-family: 'Poppins', sans-serif; line-height: 1.35; }
.news-card-excerpt { color: var(--knms-muted); font-size: 0.85rem; line-height: 1.5; }
.news-card-date { color: var(--knms-muted); font-size: 0.76rem; margin-top: 0.1rem; }

/* Filter chips (news categories) */
.chip-row { display: flex; gap: 0.45rem; flex-wrap: wrap; margin-bottom: 1.1rem; }
.chip {
    display: inline-block;
    padding: 0.35rem 0.85rem;
    border-radius: 999px;
    font-size: 0.82rem;
    font-weight: 600;
    color: var(--knms-muted);
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    transition: color 0.15s ease, box-shadow 0.2s ease;
}
.chip:hover { color: var(--knms-heading); }
.chip.is-active {
    color: #fff;
    border-color: transparent;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 60%, var(--gloss-cyan));
    text-shadow: 0 1px 2px rgba(0,0,0,0.3);
    box-shadow: 0 0 12px var(--glow-purple);
}

/* CMS page directory cards (pages/index.php) */
.page-card-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(220px, 1fr));
    gap: 1rem;
    margin-bottom: 1.1rem;
}
.page-card {
    display: flex;
    flex-direction: column;
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    border-radius: var(--radius);
    overflow: hidden;
    color: inherit;
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(139, 92, 246,0.16);
    transition: transform 0.15s ease, box-shadow 0.2s ease;
}
.page-card:hover {
    transform: translateY(-2px);
    color: inherit;
    box-shadow: var(--shadow-md), 0 0 26px rgba(139, 92, 246,0.26);
}
.page-card-media { width: 100%; height: 140px; object-fit: cover; display: block; background: var(--knms-bg); }
.page-card-media-empty {
    display: flex;
    align-items: center;
    justify-content: center;
    background: linear-gradient(135deg, var(--knms-primary), var(--knms-primary-dark));
}
.page-card-media-empty .icon { width: 2.2rem; height: 2.2rem; color: var(--knms-accent-light); filter: drop-shadow(0 0 8px var(--glow-gold)); }
.page-card-body { display: flex; flex-direction: column; gap: 0.3rem; padding: 0.9rem 1rem 1rem; }
.page-card-body strong { color: var(--knms-heading); font-family: 'Poppins', sans-serif; }
.page-card-sub { color: var(--knms-muted); font-size: 0.82rem; }
.page-card-body .badge-pill { align-self: flex-start; margin-top: 0.15rem; }

/* Lightbox modal for gallery photos + their elaborated details */
.lightbox { position: fixed; inset: 0; z-index: 200; display: flex; align-items: center; justify-content: center; padding: 1.5rem; }
.lightbox[hidden] { display: none; }
.lightbox-backdrop { position: absolute; inset: 0; background: rgba(6,10,20,0.82); backdrop-filter: blur(4px); }
.lightbox-dialog {
    position: relative;
    z-index: 1;
    max-width: 720px;
    width: 100%;
    max-height: 90vh;
    overflow-y: auto;
    background: var(--knms-surface);
    border-radius: var(--radius);
    box-shadow: var(--shadow-lg), 0 0 40px var(--glow-purple);
}
.lightbox-image { width: 100%; max-height: 60vh; object-fit: contain; background: #000; display: block; }
.lightbox-info { padding: 1.1rem 1.3rem 1.3rem; }
.lightbox-info h4 { margin: 0 0 0.4rem; color: var(--knms-heading); }
.lightbox-info p { margin: 0; color: var(--knms-muted); white-space: pre-line; }
.lightbox-close, .lightbox-nav {
    position: absolute;
    display: flex;
    align-items: center;
    justify-content: center;
    border: none;
    border-radius: 50%;
    background: rgba(13,21,38,0.55);
    color: #fff;
    cursor: pointer;
    z-index: 2;
}
.lightbox-close { top: 0.6rem; right: 0.6rem; width: 2.1rem; height: 2.1rem; font-size: 1.3rem; line-height: 1; }
.lightbox-nav { top: 50%; transform: translateY(-50%); width: 2.4rem; height: 2.4rem; font-size: 1.6rem; }
.lightbox-prev { left: 0.6rem; }
.lightbox-next { right: 0.6rem; }
.lightbox-close:hover, .lightbox-nav:hover { background: rgba(139, 92, 246,0.75); box-shadow: 0 0 12px var(--glow-purple); }

@media (max-width: 600px) {
    .topnav { display: none; }
    .page { margin: 1rem auto; }
    .hero h1 { font-size: 1.5rem; }
    .lightbox { padding: 0; }
    .lightbox-dialog { max-height: 100vh; height: 100%; border-radius: 0; }
}

/* ---------------------------------------------------------------
   Notification centre — bell badge + unread item treatment
   --------------------------------------------------------------- */

.nav-bell { position: relative; display: inline-flex; align-items: center; }
.nav-bell .icon { width: 1.15rem; height: 1.15rem; }
.nav-bell-count {
    position: absolute;
    top: -6px;
    right: -9px;
    min-width: 17px;
    height: 17px;
    padding: 0 4px;
    border-radius: 999px;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 60%, var(--gloss-cyan));
    color: #fff;
    font-size: 0.62rem;
    font-weight: 700;
    line-height: 17px;
    text-align: center;
    box-shadow: 0 0 8px var(--glow-purple);
}

.notification-item { transition: box-shadow 0.2s ease, transform 0.2s ease; }
.notification-item.is-unread {
    border-left: 3px solid transparent;
    border-image: linear-gradient(180deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan)) 1;
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(139, 92, 246,0.12), 0 0 18px rgba(139, 92, 246,0.08);
}
.notification-icon {
    width: 2.1rem;
    height: 2.1rem;
    border-radius: 10px;
    display: flex;
    align-items: center;
    justify-content: center;
    flex-shrink: 0;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 55%, var(--gloss-cyan));
    box-shadow: 0 0 10px var(--glow-purple);
}
.notification-icon .icon { width: 1.1rem; height: 1.1rem; color: #fff; }

/* Celebration row on the personalised dashboard */
.celebration-row { display: flex; align-items: center; gap: 0.6rem; padding: 0.35rem 0; }
.celebration-when {
    margin-left: auto;
    font-size: 0.75rem;
    font-weight: 700;
    padding: 0.15rem 0.6rem;
    border-radius: 999px;
    background: var(--knms-warn-bg);
    color: var(--knms-warn);
}
.celebration-when.is-today {
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 60%, var(--gloss-cyan));
    color: #fff;
    box-shadow: 0 0 10px var(--glow-purple);
}

/* ---------------------------------------------------------------
   Celebrations: today's birthday / anniversary cards + wish wall
   --------------------------------------------------------------- */
.celebration-card { position: relative; overflow: hidden; padding-top: 1.9rem; }
/* Gradient ribbon across the top of a celebrant's card */
.celebration-banner {
    position: absolute;
    top: 0; left: 0; right: 0;
    height: 6px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 14px var(--glow-purple);
}
.celebration-head { display: flex; align-items: center; gap: 0.9rem; flex-wrap: wrap; }
.celebration-photo {
    width: 3.2rem;
    height: 3.2rem;
    border-radius: 50%;
    object-fit: cover;
    flex-shrink: 0;
    box-shadow: 0 0 0 2px var(--knms-surface), 0 0 12px var(--glow-purple);
}
.celebration-head h3 { font-size: 1.12rem; }
.celebration-head h3::before { display: none; }

.wish-form { margin-top: 1rem; }
.wish-sent {
    margin-top: 0.9rem;
    display: inline-flex;
    align-items: center;
    gap: 0.4rem;
    font-size: 0.85rem;
    font-weight: 600;
    color: var(--knms-success);
}
.wish-sent .icon { width: 1rem; height: 1rem; }

.wish-wall { margin-top: 1.1rem; border-top: 1px solid var(--knms-border); padding-top: 0.9rem; }
.wish-wall h4 {
    margin: 0 0 0.7rem;
    font-family: 'Poppins', sans-serif;
    font-size: 0.86rem;
    color: var(--knms-muted);
    text-transform: uppercase;
    letter-spacing: 0.05em;
}
.wish-item { display: flex; gap: 0.6rem; align-items: flex-start; padding: 0.5rem 0; }
.wish-item p {
    margin: 0.2rem 0 0;
    font-size: 0.9rem;
    line-height: 1.55;
    padding: 0.5rem 0.75rem;
    border-radius: 0 var(--radius-sm) var(--radius-sm) var(--radius-sm);
    background: var(--knms-bg);
    border-left: 2px solid var(--gloss-purple);
}

/* ---------------------------------------------------------------
   Email template editor: merge-field chips + rendered preview
   --------------------------------------------------------------- */
.placeholder-help {
    background: var(--knms-bg);
    border: 1px dashed var(--knms-border);
    border-radius: var(--radius-sm);
    padding: 0.8rem 1rem;
    margin-bottom: 1.1rem;
}
.placeholder-help strong { color: var(--knms-heading); font-size: 0.88rem; }
.placeholder-help p { margin: 0.2rem 0 0.6rem; color: var(--knms-muted); font-size: 0.82rem; }
.placeholder-chips { display: flex; flex-wrap: wrap; gap: 0.35rem; }
.placeholder-chip {
    font-size: 0.76rem;
    padding: 0.2rem 0.55rem;
    border-radius: 6px;
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    color: var(--gloss-purple);
    font-weight: 600;
}

.email-preview {
    border: 1px solid var(--knms-border);
    border-radius: var(--radius-sm);
    overflow: hidden;
    max-width: 560px;
    background: var(--knms-surface);
    box-shadow: var(--shadow-sm);
}
.email-preview-header {
    background: linear-gradient(135deg, var(--knms-primary), var(--knms-primary-dark));
    padding: 1.1rem 1.3rem;
    display: flex;
    flex-direction: column;
    gap: 0.35rem;
}
.email-preview-eyebrow {
    color: var(--knms-accent-light);
    font-size: 0.66rem;
    letter-spacing: 0.16em;
    text-transform: uppercase;
    font-weight: 700;
}
.email-preview-heading { color: #fff; font-size: 1.12rem; font-weight: 700; font-family: 'Poppins', sans-serif; }
.email-preview-accent {
    height: 3px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
}
.email-preview-body { padding: 1.2rem 1.3rem; font-size: 0.92rem; line-height: 1.65; }
.email-preview-body p { margin: 0 0 0.8rem; }

/* Footer nav: badge on the Alerts tab so unread count is visible on phones,
   where the top bar is hidden entirely. */
.footer-icon-wrap { position: relative; display: inline-flex; }
.footer-badge {
    position: absolute;
    top: -5px;
    right: -8px;
    min-width: 15px;
    height: 15px;
    padding: 0 3px;
    border-radius: 999px;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 60%, var(--gloss-cyan));
    color: #fff;
    font-size: 0.58rem;
    font-weight: 700;
    line-height: 15px;
    text-align: center;
    box-shadow: 0 0 6px var(--glow-purple);
}

/* News cards: additive only — the base card styling (incl. the gold featured
   glow) is defined earlier and deliberately left intact. This just adds the
   three-colour top edge used on stat tiles, for consistency. */
.news-card { position: relative; }
.news-card::before {
    content: '';
    position: absolute;
    top: 0; left: 0; right: 0;
    height: 3px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    opacity: 0.35;
    transition: opacity 0.2s ease;
    z-index: 1;
}
.news-card:hover::before { opacity: 1; box-shadow: 0 0 10px var(--glow-purple); }

/* ---------------------------------------------------------------
   Mobile-native behaviour
   --------------------------------------------------------------- */
@media (max-width: 600px) {
    /* Comfortable tap targets (Apple/Google guidance is ~44px). */
    .btn { min-height: 44px; padding: 0.7rem 1.2rem; }
    .footer-link { min-height: 52px; justify-content: center; }

    /* Full-width primary actions read as native app buttons. */
    .auth-body .btn[type="submit"],
    .auth-body button.btn { width: 100%; justify-content: center; }

    /* Stat tiles: 2-up instead of cramped 4-up. */
    .stat-grid { grid-template-columns: repeat(2, 1fr); gap: 0.7rem; }
    .stat-tile { padding: 0.9rem 0.6rem; }
    .stat-tile .value { font-size: 1.35rem; }

    .card { padding: 1.1rem; border-radius: 12px; }
    .dashboard-header { flex-direction: row; padding: 0.9rem 1rem; }
    .dashboard-header h1 { font-size: 1.1rem; }
    .dashboard-header p { font-size: 0.78rem; }

    /* Never let a long email/URL blow out the page width. */
    body { overflow-x: hidden; }
    td, th { word-break: break-word; }

    /* ...but NOT inside a horizontal scroller. break-word there let the
       browser shatter ordinary words to squeeze the table into its 480px
       minimum instead of letting it grow and scroll, which rendered
       "Meetup" as "Meet up", "Webinar" as "Webi nar" and "Details" as
       "Det ails". Wrap between words only; the scroller handles the rest. */
    .table-scroll td, .table-scroll th {
        word-break: normal;
        overflow-wrap: normal;
    }

    .news-grid { grid-template-columns: 1fr; }
    .id-card-sheet { padding: 0.75rem; gap: 1rem; }
}

/* Momentum scrolling + snap for horizontally scrolling tables on touch. */
@media (hover: none) {
    .table-scroll { scroll-snap-type: x proximity; }
    .card:hover { transform: none; }
    .news-card:hover { transform: none; }
}

/* Ambient aurora behind the whole page: two vast, soft colour pools that make
   the background feel lit rather than flat black. Fixed + non-interactive. */
body::before {
    content: '';
    position: fixed;
    inset: 0;
    z-index: -1;
    pointer-events: none;
    background:
        radial-gradient(ellipse 80% 55% at 12% -8%, rgba(139, 92, 246, 0.20), transparent 60%),
        radial-gradient(ellipse 70% 50% at 92% 8%, rgba(34, 211, 238, 0.13), transparent 60%),
        radial-gradient(ellipse 90% 60% at 50% 108%, rgba(240, 184, 64, 0.09), transparent 65%);
}

/* Surfaces: a subtle top sheen so cards read as lit glass, not flat blocks. */
.card,
.stat-tile,
.news-card {
    background-image: linear-gradient(180deg, rgba(255, 255, 255, 0.045), transparent 42%);
    background-color: var(--knms-surface);
}

/* Inputs need to sit *below* the surface on dark, otherwise they disappear. */
.form-group input,
.form-group select,
.form-group textarea,
.list-filter input {
    background: var(--knms-bg-elev);
    color: var(--knms-text);
    border-color: var(--knms-border);
}
.form-group input::placeholder,
.form-group textarea::placeholder,
.list-filter input::placeholder { color: #7d75a6; }
/* Dark-theme date/time pickers ship black glyphs; invert so they stay visible. */
.form-group input[type="date"]::-webkit-calendar-picker-indicator,
.form-group input[type="datetime-local"]::-webkit-calendar-picker-indicator { filter: invert(0.8); }

.btn-secondary { background: var(--knms-surface-2); }
.btn-secondary:hover { border-color: var(--gloss-purple); box-shadow: 0 0 12px var(--glow-purple); }

/* Links: violet-tinted, gold on hover — readable against the dark surface. */
a { color: var(--gloss-purple-light); }
a:hover { color: var(--knms-accent-light); }

/* Headline treatment: gradient text for the biggest headings.
   Guarded by @supports — without background-clip:text the transparent fill
   would render the heading invisible rather than merely unstyled. */
@supports ((-webkit-background-clip: text) or (background-clip: text)) {
    .dashboard-header h1,
    .hero h1 {
        background: linear-gradient(100deg, #ffffff 20%, var(--gloss-cyan-light) 55%, var(--gloss-purple-light) 90%);
        -webkit-background-clip: text;
        background-clip: text;
        -webkit-text-fill-color: transparent;
        color: transparent;
    }
}

/* Brand mark + accent chips gain a true halo on dark. */
.brand-mark { box-shadow: 0 0 14px var(--glow-gold); color: #2a1e05; }
.rank-badge { background: var(--knms-surface-2); }
.avatar { box-shadow: 0 0 0 2px var(--knms-surface), 0 0 12px var(--glow-purple); }

/* Tables read better with a tinted header row than bare text on dark. */
th { background: rgba(139, 92, 246, 0.07); }
table tr:not(:first-child):hover {
    background: linear-gradient(90deg, rgba(139,92,246,0.10), rgba(34,211,238,0.10));
    box-shadow: inset 2px 0 0 var(--gloss-purple);
}

/* Section headings get a luminous underline accent. */
.card h3 { text-shadow: 0 0 18px rgba(139, 92, 246, 0.28); }

/* Selection + scrollbar tuned for the darker canvas. */
::selection { background: rgba(139, 92, 246, 0.40); color: #fff; }
::-webkit-scrollbar-track { background: var(--knms-bg-elev); }

/* Code/pre blocks (admin SMTP transcript) must not stay light. */
pre, code {
    background: var(--knms-bg-elev) !important;
    color: var(--gloss-cyan-light);
    border-color: var(--knms-border) !important;
}

/* Footer submenu floats above a dark page — give it real elevation. */
.footer-submenu { background: var(--knms-surface-2); box-shadow: var(--shadow-lg), 0 0 22px rgba(139,92,246,0.22); }
.footer-submenu a:hover { background: rgba(139, 92, 246, 0.16); }

/* The dark theme is the design; don't let the OS flip surfaces back to light. */
:root { color-scheme: dark; }

/* ===============================================================
   Community Vision + Legacy photo showcase
   =============================================================== */

.vision-card {
    position: relative;
    overflow: hidden;
    background:
        linear-gradient(135deg, rgba(139,92,246,0.14), transparent 55%),
        linear-gradient(315deg, rgba(34,211,238,0.10), transparent 55%),
        var(--knms-surface);
    border-color: rgba(139, 92, 246, 0.30);
}
/* Soft gold bloom behind the statement, echoing the hero. */
.vision-glow {
    position: absolute;
    inset: -40% -20% auto auto;
    width: 60%;
    height: 180%;
    background: radial-gradient(circle, rgba(240,184,64,0.14), transparent 62%);
    pointer-events: none;
}
.vision-content { position: relative; z-index: 1; }
.vision-eyebrow {
    display: inline-flex;
    align-items: center;
    gap: 0.45rem;
    font-size: 0.72rem;
    font-weight: 700;
    letter-spacing: 0.14em;
    text-transform: uppercase;
    color: var(--knms-accent-light);
    margin-bottom: 0.6rem;
}
.vision-eyebrow .icon { color: var(--gloss-cyan); filter: drop-shadow(0 0 6px var(--glow-cyan)); }
.vision-body {
    margin: 0;
    font-size: 1.02rem;
    line-height: 1.75;
    color: var(--knms-text);
    max-width: 62ch;
}

/* Horizontally scrolling photo strip — snaps like a native carousel on touch. */
.showcase-strip {
    display: flex;
    gap: 0.85rem;
    overflow-x: auto;
    scroll-snap-type: x mandatory;
    -webkit-overflow-scrolling: touch;
    padding: 0.2rem 0.2rem 0.9rem;
    margin: 0 -0.2rem;
}
.showcase-item {
    position: relative;
    flex: 0 0 auto;
    width: 190px;
    scroll-snap-align: start;
    border-radius: var(--radius-sm);
    overflow: hidden;
    border: 1px solid var(--knms-border);
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(139,92,246,0.14);
    transition: transform 0.18s ease, box-shadow 0.18s ease;
    display: block;
}
.showcase-item img {
    width: 100%;
    height: 145px;
    object-fit: cover;
    display: block;
    background: var(--knms-bg-elev);
}
.showcase-item:hover {
    transform: translateY(-3px);
    text-decoration: none;
    box-shadow: var(--shadow-md), 0 0 22px var(--glow-purple);
}
.showcase-caption {
    display: block;
    padding: 0.5rem 0.6rem 0.6rem;
    font-size: 0.78rem;
    line-height: 1.4;
    color: var(--knms-text);
    background: linear-gradient(180deg, rgba(255,255,255,0.04), transparent);
}

@media (max-width: 600px) {
    .showcase-item { width: 62vw; }
    .showcase-item img { height: 40vw; }
    .vision-body { font-size: 0.96rem; }
}

/* --- Panels (right rail + bottom row) --- */
.panel {
    position: relative;
    border-radius: 12px;
    padding: 1.1rem 1.2rem 1.2rem;
    background: linear-gradient(155deg, rgba(58, 26, 110, 0.86), rgba(30, 13, 62, 0.9));
    backdrop-filter: blur(6px);
    -webkit-backdrop-filter: blur(6px);
}

/* --- Mobile: single column, portrait shrinks, rail stacks under --- */
@media (max-width: 600px) {
    /* NOTE: portrait sizing for small screens lives in the late media block at
       the end of this file — a later unscoped rule redefines the same
       selector, so an override here would be dead. */
}

/* --- Top bar treatment to match the landing design: gold wordmark and a
   filled gold pill on the active nav item. --- */
.topbar { background: linear-gradient(135deg, rgba(42,18,89,0.94) 0%, rgba(26,11,61,0.96) 100%); }
.brand span:last-child {
    background: linear-gradient(92deg, #f4d98b, #e8bc5c 50%, #d4a437);
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}
.topnav a.is-active {
    background: linear-gradient(135deg, #f0c76a, #d4a437);
    color: #2a1259;
    padding: 0.35rem 1rem;
    border-radius: 999px;
    font-weight: 700;
    box-shadow: 0 0 16px var(--glow-gold);
}
/* The gradient underline is redundant once the pill is filled. */
.topnav a.is-active::after { display: none; }

/* Gentle twinkle for the existing landing starfield. */
@keyframes star-twinkle {
    0%, 100% { opacity: 0.38; }
    50% { opacity: 0.68; }
}

/* --- Gold-framed panels --------------------------------------- */
.card {
    border: 1px solid var(--knms-frame);
    box-shadow:
        var(--shadow-sm),
        inset 0 0 0 1px rgba(255, 185, 46, 0.10),
        0 0 18px rgba(255, 185, 46, 0.12);
}
.card:hover {
    border-color: rgba(255, 185, 46, 0.85);
    box-shadow:
        var(--shadow-md),
        inset 0 0 0 1px rgba(255, 185, 46, 0.20),
        0 0 30px rgba(255, 185, 46, 0.28);
}

/* Panel headings: gold, with the ✦ star ornaments either side. */
.card h3 {
    color: var(--knms-accent);
    text-shadow: 0 0 16px rgba(255, 185, 46, 0.45);
    letter-spacing: 0.01em;
}
/* Replace the old gradient dot with a gold star ornament. */
.card h3::before {
    content: '\2726';
    width: auto;
    height: auto;
    border-radius: 0;
    background: none;
    box-shadow: none;
    color: var(--knms-accent);
    font-size: 0.85em;
    filter: drop-shadow(0 0 6px var(--glow-gold));
}
.card h3::after {
    content: '\2726';
    margin-left: auto;
    color: var(--knms-accent);
    font-size: 0.85em;
    opacity: 0.75;
    filter: drop-shadow(0 0 6px var(--glow-gold));
}

/* Headings elsewhere follow the gold identity too. */
h1, h2 { color: var(--knms-heading); }

/* --- Buttons: gold primary, cyan secondary (as in the reference) --- */
.btn {
    background: linear-gradient(135deg, var(--knms-accent), var(--knms-accent-deep));
    color: #2a1a02;
    font-weight: 700;
    text-shadow: none;
    box-shadow: var(--shadow-sm), 0 0 14px rgba(255, 185, 46, 0.35);
}
.btn:hover { color: #2a1a02; box-shadow: var(--shadow-md), 0 0 24px var(--glow-gold); }
.btn-accent {
    background: linear-gradient(135deg, var(--knms-accent), var(--knms-accent-light));
    color: #2a1a02;
    text-shadow: none;
}
/* Cyan "Join Now"-style secondary action. */
.btn-cyan {
    background: linear-gradient(135deg, #22a6e0, #38d0f5);
    color: #04222e;
    box-shadow: var(--shadow-sm), 0 0 14px var(--glow-cyan);
}
.btn-cyan:hover { color: #04222e; box-shadow: var(--shadow-md), 0 0 26px var(--glow-cyan); }
.btn-secondary {
    background: rgba(45, 26, 92, 0.85);
    color: var(--knms-text);
    border: 1px solid var(--knms-frame);
    text-shadow: none;
}
.btn-secondary:hover { color: var(--knms-accent-light); border-color: var(--knms-accent); box-shadow: 0 0 16px var(--glow-gold); }

/* Top bar + footer gain the royal purple + gold rule. */
.topbar { background: linear-gradient(135deg, rgba(59,31,110,0.92) 0%, rgba(35,18,74,0.94) 100%); }
.topbar::after { box-shadow: 0 0 14px var(--glow-gold), 0 0 10px var(--glow-purple); }
.footer-nav { background: rgba(29, 15, 61, 0.92); border-top: 1px solid var(--knms-frame); }
.footer-link.is-active { color: var(--knms-accent-light); }

/* Stat tiles + news cards inherit the gold frame. */
.stat-tile, .news-card { border-color: var(--knms-frame); }
.stat-tile .value { color: var(--knms-accent); text-shadow: 0 0 14px rgba(255,185,46,0.35); }

/* Links read gold-warm on the royal purple. */
a { color: var(--knms-accent-light); }
a:hover { color: #fff3d6; }

/* Avatars ringed in gold, as the celebration portraits are in the reference. */
.avatar { box-shadow: 0 0 0 2px var(--knms-accent), 0 0 14px var(--glow-gold); }

/* --- Uploaded site logo in the top bar --- */
.brand-logo {
    width: 40px;
    height: 40px;
    border-radius: 50%;
    object-fit: cover;
    flex-shrink: 0;
    border: 2px solid rgba(232, 188, 92, 0.85);
    box-shadow: 0 0 12px var(--glow-gold);
}

/* --- Member directory --- */
.directory-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(160px, 1fr));
    gap: 0.9rem;
}
.directory-card {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 0.3rem;
    text-align: center;
    padding: 1rem 0.8rem;
    border: 1px solid var(--knms-border);
    border-radius: var(--radius);
    background: var(--knms-surface);
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(109, 40, 217, 0.05);
    transition: transform 0.15s ease, box-shadow 0.2s ease;
}
.directory-card:hover { transform: translateY(-2px); box-shadow: var(--shadow-md), 0 0 18px rgba(109, 40, 217, 0.14); }
.directory-card strong { color: var(--knms-heading); font-family: 'Poppins', sans-serif; font-size: 0.92rem; }
.directory-photo {
    width: 3.4rem; height: 3.4rem; border-radius: 50%; object-fit: cover;
    box-shadow: 0 0 0 2px var(--knms-surface), 0 0 10px var(--glow-purple);
}
.directory-meta { color: var(--knms-muted); font-size: 0.78rem; }

/* Gold glossy sphere — the dominant sphere colour in the design. */
.orb-gold {
    --orb-glow: var(--glow-gold);
    background: radial-gradient(circle at 32% 28%, #fff 0%, #ffe9b0 16%, var(--knms-accent) 52%, #8a6410 100%);
}
/* Amber/ember sphere for depth variation against the purple field. */
.orb-ember {
    --orb-glow: rgba(255, 138, 40, 0.55);
    background: radial-gradient(circle at 32% 28%, #fff 0%, #ffc98a 16%, #f08a2c 55%, #7a3908 100%);
}

/* Spheres sit above the sky wash but strictly BEHIND the content (z-index 0 vs
   the grid's 1), and are softened so they read as depth-of-field bokeh rather
   than solid balls sitting on top of the text. */
@keyframes orb-drift {
    0%, 100% { transform: translate3d(0, 0, 0) scale(1); }
    50%      { transform: translate3d(6px, -16px, 0) scale(1.04); }
}

/* Soft translucent bokeh — the out-of-focus glowing dots scattered along the
   golden arcs. Cheaper than a sphere: no inset shading, just a glow. */
@keyframes bokeh-twinkle {
    0%, 100% { opacity: 0.35; transform: scale(0.92); }
    50%      { opacity: 0.95; transform: scale(1.08); }
}

/* --- CMS hero crop tool ---------------------------------------- */
.crop-stage {
    position: relative;
    width: 100%;
    max-width: 340px;
    aspect-ratio: 4 / 5;
    overflow: hidden;
    border-radius: var(--radius-sm);
    border: 1px solid var(--knms-frame);
    box-shadow: 0 0 18px rgba(255, 185, 46, 0.18);
    cursor: crosshair;
    background: var(--knms-bg-elev);
    touch-action: none;
}
.crop-stage img {
    width: 100%;
    height: 100%;
    object-fit: cover;
    display: block;
    transform-origin: center;
    user-select: none;
    -webkit-user-drag: none;
}
.crop-crosshair {
    position: absolute;
    width: 22px;
    height: 22px;
    margin: -11px 0 0 -11px;
    border-radius: 50%;
    border: 2px solid var(--knms-accent);
    box-shadow: 0 0 10px var(--glow-gold), inset 0 0 6px rgba(255,255,255,0.5);
    pointer-events: none;
}
.crop-controls { margin-top: 0.7rem; max-width: 340px; }
.crop-controls input[type="range"] { width: 100%; accent-color: var(--knms-accent); }

/* Gold panel frames a touch hotter, matching the crisp borders in the art. */
.card { border-color: rgba(255, 198, 74, 0.62); }

/* ---------------------------------------------------------------
   Mobile: keep the same look, scaled — the glow and gradients must
   survive on phones rather than being switched off.
   --------------------------------------------------------------- */
@media (max-width: 600px) {
    /* Spheres stay glossy on phones — only their scale changes. */
}

/* --- Sparkle glints: fine 4-point stars, distinct from the soft bokeh --- */
@keyframes sparkle-pulse {
    0%, 100% { opacity: 0.25; transform: scale(0.7); }
    50%      { opacity: 1;    transform: scale(1); }
}
@media (prefers-reduced-motion: reduce) { .sparkle { animation: none; } }

/* --- Nav separators, as in the reference --- */
.topnav a + a::before {
    content: '';
    position: absolute;
    left: -0.75rem;
    top: 50%;
    width: 5px;
    height: 1px;
    background: rgba(255, 255, 255, 0.32);
}
.topnav a.is-active::before, .topnav a.is-active + a::before { display: none; }

/* Spheres a touch larger so they read at a glance.
   Uses the standalone `scale` property, not `transform` — orb-drift animates
   transform, and a static transform here would simply be overridden. */
@media (max-width: 600px) { .landing-orbs .orb { scale: 0.85; } }

/* Keep the animated glows/arcs/spheres on top of the artwork. */

@media (max-width: 600px) {
    /* Keep the sun and horizon in frame when the hero gets tall and narrow. */
}

/* ===============================================================
   Portal-wide cosmic ambience.
   Interior pages (auth, forum, events, admin) previously sat on a flat
   dark background while only the landing carried the reference artwork's
   atmosphere. This adds a QUIET version everywhere: faint starfield +
   one soft arc. Deliberately subtle so tables and forms stay readable.
   The landing's own sky sits on an opaque backdrop above this, so
   nothing doubles there.
   =============================================================== */
body::after {
    content: '';
    position: fixed;
    inset: 0;
    z-index: -1;
    pointer-events: none;
    opacity: 0.5;
    background-image:
        radial-gradient(1.4px 1.4px at 12% 18%, rgba(255,225,170,0.8), transparent),
        radial-gradient(1.2px 1.2px at 30% 64%, rgba(255,255,255,0.55), transparent),
        radial-gradient(1.6px 1.6px at 47% 28%, rgba(255,215,150,0.7), transparent),
        radial-gradient(1.1px 1.1px at 64% 72%, rgba(255,255,255,0.5), transparent),
        radial-gradient(1.7px 1.7px at 79% 36%, rgba(255,220,160,0.75), transparent),
        radial-gradient(1.2px 1.2px at 90% 80%, rgba(255,255,255,0.5), transparent),
        radial-gradient(1.3px 1.3px at 8% 84%, rgba(255,215,150,0.6), transparent),
        radial-gradient(1.5px 1.5px at 56% 90%, rgba(255,235,190,0.6), transparent),
        /* one soft gold arc sweeping low across the page */
        radial-gradient(ellipse 120% 90% at 50% 130%, transparent 58%, rgba(255,185,46,0.10) 60%, rgba(255,185,46,0.16) 61%, rgba(255,185,46,0.06) 63%, transparent 66%);
}

/* Panels: deeper and more translucent, so the backdrop glows through them
   the way it does behind the reference's cards. */
.panel {
    background: linear-gradient(155deg, rgba(46, 20, 92, 0.72), rgba(22, 10, 48, 0.82));
}

/* "HD glow" density pass: the reference has a denser field of fine light
   particles than our sparkle/bokeh counts were producing. Brighten what's
   already there rather than add more DOM nodes. */
.landing-sky .landing-stars,

/* File inputs (photo upload on registration) were rendering as the bare
   browser-default gray button — the only unstyled form control on the site,
   breaking the gold/purple theme on an otherwise fully-themed form. */
.form-group input[type="file"] {
    padding: 0.45rem;
    display: flex;
    align-items: center;
}
.form-group input[type="file"]::file-selector-button,
.form-group input[type="file"]::-webkit-file-upload-button {
    margin-right: 0.9rem;
    padding: 0.5rem 1.1rem;
    border: none;
    border-radius: 999px;
    background: linear-gradient(135deg, var(--knms-accent), var(--knms-accent-deep, var(--knms-accent)));
    color: #2a1a02;
    font-weight: 700;
    font-size: 0.85rem;
    cursor: pointer;
    box-shadow: 0 0 10px var(--glow-gold, rgba(255,185,46,0.4));
    transition: filter 0.15s ease, box-shadow 0.15s ease;
}
.form-group input[type="file"]::file-selector-button:hover,
.form-group input[type="file"]::-webkit-file-upload-button:hover {
    filter: brightness(1.08);
    box-shadow: 0 0 16px var(--glow-gold, rgba(255,185,46,0.55));
}

/* --- Per-photo crop widget in the CMS gallery editor --- */
.photo-crop { flex-shrink: 0; width: 150px; }
.photo-crop-stage {
    position: relative;
    width: 150px;
    height: 150px;
    /* Required: a zoomed image is scaled with transform, which does not
       affect layout, so without clipping it spills over the neighbours. */
    overflow: hidden;
    border-radius: var(--radius-sm);
    border: 1px solid var(--knms-border);
    cursor: crosshair;
    background: var(--knms-bg);
    touch-action: none;
}
.photo-crop-stage img {
    width: 100%;
    height: 100%;
    object-fit: cover;
    display: block;
    pointer-events: none;
    user-select: none;
}
.photo-crop-cross {
    position: absolute;
    width: 16px;
    height: 16px;
    margin: -8px 0 0 -8px;
    border-radius: 50%;
    border: 2px solid #fff;
    box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.6), 0 0 8px var(--glow-gold);
    pointer-events: none;
}
.photo-crop-zoom {
    display: block;
    margin-top: 0.45rem;
    font-size: 0.74rem;
    font-weight: 600;
    color: var(--knms-muted);
}
.photo-crop-zoom input[type="range"] { width: 100%; accent-color: var(--knms-accent); }

/* The drawn NadarUnityHub mark, used wherever no logo has been uploaded.
   It carries its own white ground, so unlike the emblem it needs no gold
   ring to separate it from the dark bar — only a soft lift. */
.brand-mark-hub {
    width: 38px;
    height: 38px;
    border-radius: 50%;
    flex-shrink: 0;
    filter: drop-shadow(0 2px 6px rgba(0, 0, 0, 0.35));
}

/* One word of the wordmark picked out in the accent colour —
   "Nadar<em>Unity</em>Hub". Which word is a Site Settings value, so this
   rule must stay purely about colour. Gold on the dark bar; the landing
   template repaints it orange on its own light bar. */
.brand-accent { color: var(--knms-accent); }

/* Header logo is the real circular Sangam emblem (as in the reference),
   not a lettermark tile. Ringed in gold so it reads on the dark bar. */
.brand-mark-emblem {
    width: 34px;
    height: 34px;
    border-radius: 50%;
    background: none;
    padding: 0;
    object-fit: cover;
    box-shadow: 0 0 0 2px var(--knms-accent), 0 0 12px var(--glow-gold);
}

/* ===============================================================
   Homepage sectioning + site footer
   The page was a flat stack of cards; these give it vertical rhythm
   and distinct bands, and finally surface the contact/social
   settings that were being stored but never rendered.
   =============================================================== */

.home-section { margin: 2.4rem 0; }
.home-section:first-of-type { margin-top: 1.8rem; }

.section-heading {
    margin: 0 0 1.1rem;
    font-family: 'Poppins', sans-serif;
    font-size: 1.25rem;
    text-align: center;
    position: relative;
    padding-bottom: 0.65rem;
}
.section-heading::after {
    content: '';
    position: absolute;
    left: 50%; bottom: 0;
    transform: translateX(-50%);
    width: 74px; height: 3px;
    border-radius: 999px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 10px var(--glow-gold);
}

/* --- Stats band --- */
.stat-band {
    display: grid;
    grid-template-columns: repeat(4, 1fr);
    gap: 1px;
    border-radius: var(--radius);
    overflow: hidden;
    background: rgba(232, 188, 92, 0.28);
    box-shadow: var(--shadow-md), 0 0 24px rgba(109, 40, 217, 0.18);
}
.stat-band-item {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 0.15rem;
    padding: 1.15rem 0.75rem;
    background: linear-gradient(155deg, rgba(46, 20, 92, 0.94), rgba(22, 10, 48, 0.96));
    text-align: center;
}
.stat-band-item .value {
    font-family: 'Baloo 2', 'Poppins', sans-serif;
    font-size: clamp(1.4rem, 3vw, 2rem);
    font-weight: 700;
    background: linear-gradient(92deg, #f4d98b, #e8bc5c 50%, #d4a437);
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}
.stat-band-item .label {
    font-size: 0.74rem;
    letter-spacing: 0.1em;
    text-transform: uppercase;
    color: rgba(255, 255, 255, 0.72);
}

/* --- "What we do" pillars --- */
.pillar-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(210px, 1fr));
    gap: 1rem;
}
.pillar {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 0.4rem;
    text-align: center;
    padding: 1.5rem 1.1rem;
    border-radius: var(--radius);
    border: 1px solid var(--knms-border);
    background: var(--knms-surface);
    color: inherit;
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(109, 40, 217, 0.06);
    transition: transform 0.15s ease, box-shadow 0.2s ease;
}
.pillar:hover { transform: translateY(-3px); color: inherit; box-shadow: var(--shadow-md), 0 0 22px rgba(109, 40, 217, 0.16); }
.pillar-icon {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 3rem; height: 3rem;
    border-radius: 14px;
    margin-bottom: 0.25rem;
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 58%, var(--gloss-cyan));
    box-shadow: 0 0 16px var(--glow-purple);
}
.pillar-icon .icon { width: 1.5rem; height: 1.5rem; color: #fff; }
.pillar strong { color: var(--knms-heading); font-family: 'Poppins', sans-serif; font-size: 0.98rem; }
.pillar span:last-child { color: var(--knms-muted); font-size: 0.84rem; line-height: 1.5; }

/* ---------------------------------------------------------------
   Site footer (distinct from the fixed mobile .footer-nav)
   --------------------------------------------------------------- */
.site-footer {
    /* The footer is a direct child of <body>, which has no max-width, so it is
       already full-bleed. A `calc(50% - 50vw)` negative margin here used to
       "break it out" of a container that isn't there — and because 50vw counts
       the scrollbar while 50% does not, it pushed the footer past the viewport
       by the scrollbar width, giving every page a few px of horizontal scroll
       on mobile. Percentages throughout keep it aligned to the content box. */
    margin: 3rem 0 0;
    padding: 2.6rem max(1rem, calc(50% - 700px)) 1.4rem;
    background: linear-gradient(168deg, #241050 0%, #180a38 55%, #110726 100%);
    color: rgba(255, 255, 255, 0.82);
    position: relative;
}
.site-footer::before {
    content: '';
    position: absolute;
    top: 0; left: 0; right: 0;
    height: 3px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--knms-accent), var(--gloss-cyan));
    box-shadow: 0 0 12px var(--glow-purple);
}
/* Auto-fit rather than four fixed tracks. The footer's columns are
   conditional — Business, Get the app and Contact each appear only when
   there is something to put in them — so a fixed count meant the fifth one
   dropped onto a row of its own with three columns of empty space beside
   it. The brand block spans two tracks to keep its old proportions. */
.site-footer-inner {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(100%, 165px), 1fr));
    gap: 1.8rem;
}
.site-footer-brand { grid-column: span 2; }
.site-footer h4 {
    margin: 0 0 0.7rem;
    color: #f4d98b;
    font-size: 0.82rem;
    letter-spacing: 0.12em;
    text-transform: uppercase;
    font-family: 'Poppins', sans-serif;
}
.site-footer-col a,
.site-footer-brand a {
    display: flex;
    align-items: center;
    gap: 0.4rem;
    padding: 0.22rem 0;
    color: rgba(255, 255, 255, 0.78);
    font-size: 0.88rem;
}
.site-footer-col a:hover { color: var(--knms-accent-light); }
/* A grid track refuses to shrink below the widest unbreakable thing inside
   it, because `min-width: auto` is the default on a grid item. The contact
   column holds a long email address and a support telephone number, neither
   of which contains a break opportunity, so the track held itself wider
   than its share and pushed the page 8px past the viewport — the site's
   only horizontal overflow, on EVERY page, at every width.
   Letting the tracks shrink and the strings break fixes it at the source.
   admin-shell.css has carried this same pair scoped to body.admin-area
   since the console hit it at 1440px; the footer is shared chrome, so the
   rule belongs here where the columns are defined, and the console's copy
   is now merely redundant rather than the only place it is true. */
.site-footer-col,
.site-footer-brand { min-width: 0; }
.site-footer-col a,
.site-footer-addr { overflow-wrap: anywhere; }
/* On a touch device these are the site's densest column of links — 24px
   tall and stacked, which is a row of near-misses. The padding grows
   rather than the type, so the footer reads the same and the targets get
   to 44px. */
@media (pointer: coarse) {
    .site-footer-col a,
    .site-footer-brand a { min-height: 2.75rem; padding: 0.5rem 0; }
}
.site-footer-col .icon { width: 0.95rem; height: 0.95rem; flex-shrink: 0; }
.site-footer-brand strong {
    display: block;
    font-family: 'Poppins', sans-serif;
    font-size: 1rem;
    background: linear-gradient(92deg, #f4d98b, #e8bc5c 50%, #d4a437);
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}
.site-footer-brand p { margin: 0.4rem 0 0; font-size: 0.85rem; line-height: 1.6; color: rgba(255, 255, 255, 0.7); max-width: 34ch; }
.site-footer-logo {
    width: 46px; height: 46px; border-radius: 50%; object-fit: cover;
    margin-bottom: 0.5rem;
    border: 2px solid rgba(232, 188, 92, 0.75);
    box-shadow: 0 0 12px var(--glow-gold);
}
.site-footer-addr { margin: 0 0 0.5rem; font-size: 0.86rem; line-height: 1.6; color: rgba(255, 255, 255, 0.75); }
.site-footer-social { display: flex; gap: 0.5rem; margin-top: 0.9rem; }
.site-footer-social a {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 2.1rem; height: 2.1rem;
    padding: 0;
    border-radius: 50%;
    border: 1px solid rgba(232, 188, 92, 0.42);
    color: var(--knms-accent-light);
    transition: background 0.18s ease, box-shadow 0.2s ease, color 0.18s ease;
}
.site-footer-social a:hover {
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 60%, var(--gloss-cyan));
    color: #fff;
    box-shadow: 0 0 14px var(--glow-purple);
}
.site-footer-social .icon { width: 1.05rem; height: 1.05rem; }
/* 34px circles are the right size for the design and the wrong size for a
   thumb. The circle keeps its drawn diameter and the target grows around
   it, so the row looks identical and stops being a row of near-misses. */
@media (pointer: coarse) {
    .site-footer-social { gap: 0.35rem; }
    .site-footer-social a { width: 2.75rem; height: 2.75rem; }
}

/* --- App download buttons --------------------------------------------
   Outlined rather than filled: they sit in the same column rhythm as the
   text links around them, and two solid buttons in a footer pull more
   attention than a download link has earned. */
/* Two classes, to beat `.site-footer-col a { display: flex }` — inherited,
   the buttons stretched to the full column width and read as bars rather
   than buttons. */
.site-footer-col a.site-footer-store,
.site-footer-store {
    display: inline-flex;
    width: fit-content;
    align-items: center;
    gap: 0.4rem;
    margin-bottom: 0.4rem;
    padding: 0.45rem 0.8rem;
    border: 1px solid rgba(255, 255, 255, 0.3);
    border-radius: 8px;
    font-size: 0.85rem;
}
.site-footer-store:hover { border-color: var(--knms-accent-light); }
.site-footer-store .icon { width: 1rem; height: 1rem; flex-shrink: 0; }
@media (pointer: coarse) {
    .site-footer-store { min-height: 2.75rem; }
}

.site-footer-base {
    display: flex;
    justify-content: space-between;
    gap: 1rem;
    flex-wrap: wrap;
    margin-top: 2rem;
    padding-top: 1rem;
    border-top: 1px solid rgba(255, 255, 255, 0.12);
    font-size: 0.79rem;
    color: rgba(255, 255, 255, 0.6);
}
/* The sign-off. Three classes deliberately: the landing stylesheet paints
   every span in the footer with `body.nuh-page .site-footer span`, which
   is two classes and an element, and anything shorter than this loses to
   it — the heart came out the same grey as the sentence around it, which
   is the one thing it is there not to be. */
.site-footer .site-footer-base .site-footer-made { font-size: 0.84rem; }
.site-footer .site-footer-base .site-footer-heart { color: #ff7a7a; font-size: 1.05em; }

@media (max-width: 860px) {
    .site-footer-inner { grid-template-columns: 1fr 1fr; gap: 1.4rem; }
    .stat-band { grid-template-columns: repeat(2, 1fr); }
}
@media (max-width: 600px) {
    .home-section { margin: 1.8rem 0; }
    .site-footer { padding: 2rem 1rem 1.2rem; }
    .site-footer-inner { grid-template-columns: 1fr; }
    .site-footer-brand { grid-column: auto; }   /* one track — nothing to span */
    .site-footer-base { justify-content: center; text-align: center; }
}
@media (prefers-reduced-motion: reduce) { .pillar:hover { transform: none; } }

/* --- Page headings: gold gradient with a soft bloom ---
   The bloom MUST be filter:drop-shadow, never text-shadow. With a clipped
   transparent fill Chrome paints the text-shadow and drops the gradient, so
   every heading in the portal rendered as a flat grey smudge instead of gold.
   Same defect that hit .kn-title on the landing. */
.page > h1,
.dashboard-header h1 {
    background: linear-gradient(92deg, #ffe6a8, #ffd77a 45%, #e8bc5c);
    -webkit-background-clip: text;
    background-clip: text;
    -webkit-text-fill-color: transparent;
    color: transparent;
    text-shadow: none;
    filter: drop-shadow(0 0 16px rgba(255, 200, 90, 0.34));
}

/* --- Cards: a luminous gradient rim plus a faint inner bloom --- */
.card {
    border-color: rgba(167, 139, 250, 0.26);
    box-shadow:
        var(--shadow-sm),
        0 0 0 1px rgba(255, 205, 110, 0.30),
        0 0 44px rgba(150, 70, 240, 0.45),
        0 0 90px rgba(255, 160, 50, 0.12),
        inset 0 0 70px rgba(110, 50, 190, 0.28);
}
.card:hover {
    border-color: rgba(255, 205, 110, 0.42);
    box-shadow:
        var(--shadow-md),
        0 0 0 1px rgba(255, 205, 110, 0.6),
        0 0 56px rgba(170, 90, 255, 0.6),
        0 0 110px rgba(255, 170, 60, 0.2),
        inset 0 0 80px rgba(120, 55, 205, 0.34);
}
/* The glowing dot before every card subheading, brightened. */
.card h3::before { box-shadow: 0 0 10px var(--glow-gold), 0 0 18px var(--glow-purple); }
.card h3 { color: #ffd77a; }

/* --- Buttons: always lit, brighter on hover --- */
.btn {
    box-shadow: var(--shadow-sm), 0 0 24px rgba(150, 70, 240, 0.75), 0 0 44px rgba(109, 40, 217, 0.4);
}
.btn:hover {
    box-shadow: var(--shadow-md), 0 0 24px rgba(150, 70, 240, 0.7), 0 0 40px rgba(34, 211, 238, 0.28);
}
.btn-accent { box-shadow: var(--shadow-sm), 0 0 18px var(--glow-gold), 0 0 30px var(--glow-purple); }
.btn-secondary {
    border-color: rgba(255, 205, 110, 0.35);
    box-shadow: 0 0 12px rgba(109, 40, 217, 0.28);
}
.btn-secondary:hover { border-color: rgba(255, 205, 110, 0.7); box-shadow: 0 0 20px var(--glow-gold); }
.btn-danger { box-shadow: var(--shadow-sm), 0 0 16px rgba(208, 52, 44, 0.55); }

/* --- Tables: glowing header rule and a lit row on hover --- */
th {
    color: #ffd77a;
    border-bottom: 1px solid rgba(255, 205, 110, 0.55);
    text-shadow: 0 0 10px rgba(255, 200, 90, 0.35);
}
tbody tr:hover, table tr:not(:first-child):hover {
    background: linear-gradient(90deg, rgba(150, 70, 240, 0.12), rgba(34, 211, 238, 0.07));
    box-shadow: inset 3px 0 0 var(--knms-accent), inset 0 0 30px rgba(109, 40, 217, 0.16);
}

/* --- Links --- */
a:hover { text-shadow: 0 0 12px rgba(255, 200, 90, 0.55); }

/* --- Inputs: lit border on focus --- */
.form-group input,
.form-group select,
.form-group textarea,
.list-filter input {
    border-color: rgba(167, 139, 250, 0.3);
    box-shadow: inset 0 0 30px rgba(110, 50, 190, 0.3), 0 0 16px rgba(109, 40, 217, 0.25);
}
.form-group input:focus,
.form-group select:focus,
.form-group textarea:focus,
.list-filter input:focus {
    border-color: var(--knms-accent);
    box-shadow: 0 0 0 3px rgba(255, 205, 110, 0.18), 0 0 22px var(--glow-gold), inset 0 0 22px rgba(88, 40, 150, 0.18);
}

/* --- Badges and meters --- */
.badge-pill { box-shadow: 0 0 12px rgba(109, 40, 217, 0.4); }
.badge-gradient { box-shadow: 0 0 14px var(--glow-purple), 0 0 22px var(--glow-gold); }
.capacity-meter-fill { box-shadow: 0 0 12px var(--glow-cyan), 0 0 20px var(--glow-purple); }

/* --- Dashboard header + stat tiles --- */
.dashboard-header { box-shadow: var(--shadow-md), 0 0 34px var(--glow-purple), inset 0 0 60px rgba(88, 40, 150, 0.24); }
.stat-tile {
    border-color: rgba(167, 139, 250, 0.24);
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(255, 205, 110, 0.28), 0 0 40px rgba(150, 70, 240, 0.45);
}
.stat-tile:hover { box-shadow: var(--shadow-md), 0 0 30px rgba(150, 70, 240, 0.38), 0 0 14px var(--glow-gold); }
.stat-tile .value { color: #ffd77a; text-shadow: 0 0 18px rgba(255, 200, 90, 0.35); }

/* --- Top bar + mobile nav --- */
.topbar { box-shadow: var(--shadow-md), 0 6px 44px rgba(150, 70, 240, 0.6); }
.footer-nav { box-shadow: 0 -6px 40px rgba(150, 70, 240, 0.55); }
.footer-link.is-active { text-shadow: 0 0 12px rgba(255, 200, 90, 0.6); }

/* --- News / page / directory cards --- */
.news-card, .page-card, .directory-card, .pillar {
    border-color: rgba(167, 139, 250, 0.24);
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(255, 205, 110, 0.28), 0 0 40px rgba(150, 70, 240, 0.45);
}
.news-card:hover, .page-card:hover, .directory-card:hover, .pillar:hover {
    border-color: rgba(255, 205, 110, 0.42);
    box-shadow: var(--shadow-md), 0 0 32px rgba(150, 70, 240, 0.34), 0 0 16px var(--glow-gold);
}

/* --- Gallery tiles --- */
.gallery-item { box-shadow: var(--shadow-sm), 0 0 0 1px rgba(255, 205, 110, 0.14), 0 0 18px rgba(109, 40, 217, 0.22); }
.gallery-item:hover { box-shadow: var(--shadow-md), 0 0 30px var(--glow-purple), 0 0 16px var(--glow-gold); }

/* --- Flash messages --- */
.flash-success { box-shadow: 0 0 20px rgba(27, 138, 76, 0.35); }
.flash-error   { box-shadow: 0 0 20px rgba(208, 52, 44, 0.35); }

/* Gold arcs burn brighter. */

@media (prefers-reduced-motion: reduce) {
    .card, .btn, .stat-tile, .news-card, .pillar { transition: none; }
}

/* --- Scroll reveal. The class is added by JS, so with JS off nothing
       is ever hidden. --- */
.reveal {
    opacity: 0;
    transform: translateY(22px);
    transition: opacity 0.6s cubic-bezier(.22,.61,.36,1), transform 0.6s cubic-bezier(.22,.61,.36,1);
    will-change: opacity, transform;
}
.reveal.is-visible { opacity: 1; transform: none; }

/* --- Gold arcs shimmer along their length --- */
@keyframes arc-shimmer {
    0%, 100% { opacity: 0.78; filter: drop-shadow(0 0 20px rgba(255,190,70,0.85)) drop-shadow(0 0 60px rgba(255,140,30,0.5)); }
    50%      { opacity: 1;    filter: drop-shadow(0 0 30px rgba(255,205,95,1))   drop-shadow(0 0 92px rgba(255,150,40,0.75)); }
}

/* --- Sun core breathes --- */
@keyframes burst-breathe {
    0%, 100% { opacity: 0.85; transform: translate(-50%, -50%) scale(1); }
    50%      { opacity: 1;    transform: translate(-50%, -50%) scale(1.08); }
}

/* --- Panels breathe very slightly, so the page never feels static --- */
@keyframes panel-breathe {
    0%, 100% { box-shadow: 0 0 34px rgba(255,180,60,0.4),  0 0 70px rgba(255,140,30,0.16), inset 0 0 46px rgba(88,34,160,0.3); }
    50%      { box-shadow: 0 0 46px rgba(255,196,80,0.55), 0 0 96px rgba(255,150,36,0.24), inset 0 0 56px rgba(96,40,175,0.36); }
}

/* --- Gold buttons get a slow light sweep, like polished metal --- */
@keyframes sheen {
    0%, 62%  { left: -140%; }
    82%,100% { left: 160%; }
}

/* --- Nav pill pulses gently so the current page is obvious --- */
@keyframes pill-pulse {
    0%, 100% { box-shadow: 0 0 16px var(--glow-gold); }
    50%      { box-shadow: 0 0 26px var(--glow-gold), 0 0 44px rgba(255,170,50,0.55); }
}
.topnav a.is-active { animation: pill-pulse 4s ease-in-out infinite; }

/* --- Celebration cards get a soft attention pulse on their ribbon --- */
@keyframes ribbon-glow {
    0%, 100% { box-shadow: 0 0 14px var(--glow-purple); }
    50%      { box-shadow: 0 0 26px var(--glow-gold), 0 0 40px var(--glow-purple); }
}
.celebration-banner { animation: ribbon-glow 5s ease-in-out infinite; }

/* --- Stat values lift as they count --- */
.stat-band-item .value { transition: text-shadow 0.4s ease; }
.stat-band-item:hover .value { text-shadow: 0 0 24px rgba(255, 205, 95, 0.75); }

@media (prefers-reduced-motion: reduce) {
    .reveal { opacity: 1 !important; transform: none !important; transition: none !important; }
}

/* ===============================================================
   VIVID PASS
   The reference palette is markedly more saturated and luminous than
   the muted base theme: brighter violets, hotter gold, electric cyan,
   and every accent carrying a visible bloom. Appended last.
   =============================================================== */

:root {
    /* Hotter, more saturated accent tokens. */
    --knms-accent:        #ffc94a;
    --knms-accent-light:  #ffe08a;
    --knms-heading:       #ffdf8c;
    --gloss-purple:       #8b3ff5;
    --gloss-purple-light: #c4a0ff;
    --gloss-cyan:         #35dcff;
    --gloss-cyan-light:   #a5f0ff;

    /* Glows roughly 1.6x the previous alpha. */
    --glow-purple: rgba(139, 63, 245, 0.85);
    --glow-gold:   rgba(255, 201, 74, 0.85);
    --glow-cyan:   rgba(53, 220, 255, 0.8);
}

/* --- Panels: brighter violet body, hotter rims --- */
.panel {
    background: linear-gradient(155deg, rgba(74, 34, 148, 0.78), rgba(38, 16, 78, 0.86));
}

/* --- Buttons: saturated fills with heavy bloom --- */
.btn-accent {
    background: linear-gradient(135deg, var(--gloss-purple), var(--knms-accent) 55%, var(--gloss-cyan));
    box-shadow: var(--shadow-sm), 0 0 28px var(--glow-gold), 0 0 52px var(--glow-purple);
}

/* --- Headline + headings burn brighter --- */
.card h3, .section-heading { color: #ffdf8c; }
.page > h1, .dashboard-header h1 {
    /* fit-content matters: an h1 is a block spanning the full page width, so
       the gradient was being mapped across ~1160px while a short heading like
       "Events" occupied the first 90px of it — the text sampled only the
       palest opening of the ramp and read as off-white. Shrinking the box to
       the text makes the whole gold ramp land on the letters. */
    display: inline-block;
    width: fit-content;
    max-width: 100%;
    background: linear-gradient(92deg, #fff2c4, #ffd45e 45%, #ffb628);
    -webkit-background-clip: text;
    background-clip: text;
    -webkit-text-fill-color: transparent;
    color: transparent;
    text-shadow: none;                 /* see the note on the rule above */
    filter: drop-shadow(0 0 20px rgba(255, 195, 70, 0.5));
}

/* --- Cards across the portal: brighter violet lift --- */
.card {
    border-color: rgba(190, 150, 255, 0.4);
    box-shadow:
        var(--shadow-sm),
        0 0 0 1px rgba(255, 205, 110, 0.34),
        0 0 50px rgba(150, 80, 255, 0.55),
        inset 0 0 76px rgba(130, 60, 220, 0.32);
}
.card:hover {
    border-color: rgba(255, 214, 130, 0.85);
    box-shadow:
        var(--shadow-md),
        0 0 0 1px rgba(255, 214, 130, 0.7),
        0 0 66px rgba(175, 100, 255, 0.7),
        inset 0 0 88px rgba(140, 66, 235, 0.4);
}

/* --- Stat band + tiles --- */
.stat-band { background: rgba(255, 201, 74, 0.4); box-shadow: var(--shadow-md), 0 0 40px rgba(150, 80, 255, 0.5); }
.stat-band-item { background: linear-gradient(155deg, rgba(74, 34, 148, 0.94), rgba(38, 16, 78, 0.96)); }
.stat-band-item .value { background: linear-gradient(92deg, #fff2c4, #ffd45e 50%, #ffb628); -webkit-background-clip: text; background-clip: text; color: transparent; }
.stat-tile .value { color: #ffdf8c; text-shadow: 0 0 24px rgba(255, 200, 80, 0.5); }

/* --- Table + form accents --- */
th { color: #ffdf8c; border-bottom-color: rgba(255, 205, 110, 0.7); }
.badge-gradient { box-shadow: 0 0 18px var(--glow-purple), 0 0 30px var(--glow-gold); }
.capacity-meter-fill { box-shadow: 0 0 16px var(--glow-cyan), 0 0 28px var(--glow-purple); }

/* --- Nav + chrome --- */
.topnav a.is-active {
    background: linear-gradient(135deg, #ffd968, #ffb61f);
    color: #3a1a02;
    box-shadow: 0 0 26px rgba(255, 190, 60, 0.9);
}
.topbar::after, .site-footer::before {
    box-shadow: 0 0 16px var(--glow-purple), 0 0 26px var(--glow-cyan);
}
.brand-logo, .brand-mark-emblem { box-shadow: 0 0 20px var(--glow-gold); }

/* --- 2. Panels: more translucent so the scene glows through ------- */
.panel {
    background: linear-gradient(155deg, rgba(84, 40, 168, 0.62), rgba(44, 19, 92, 0.74));
    backdrop-filter: blur(9px) saturate(1.25);
    -webkit-backdrop-filter: blur(9px) saturate(1.25);
}

/* --- 9. Particle drifts clustered along the arc paths ------------- */
@keyframes mote-drift {
    0%, 100% { opacity: 0.3; transform: translate3d(0,0,0) scale(0.85); }
    50%      { opacity: 1;   transform: translate3d(6px,-10px,0) scale(1.15); }
}

/* --- 10. Headline: heavier bloom, tighter tracking ---------------- */

@media (prefers-reduced-motion: reduce) { .mote { animation: none; } }

/* --- 4. Panels breathe a little more ----------------------------- */
.panel { padding: 1.25rem 1.35rem 1.35rem; }

/* --- 5. Hero copy: subtitle sits closer to reference scale -------- */

@media (max-width: 860px) {
    /* Stacked: let About size to its content so there's no dead space. */
}

/* --- Ghosted heritage figures along the left edge, as in the reference.
   Optional CMS upload: desaturated, violet-tinted and feathered so it
   reads as a memory behind the scene rather than a pasted photo. --- */
@media (max-width: 860px) { .landing-heritage { display: none; } }

/* ===============================================================
   Admin console — navigation, filter bars, permission matrix.
   Shared by every screen under /admin so the console reads as one
   surface rather than a set of unrelated forms.
   =============================================================== */

/* Collapsible console navigation. The old version printed every link in
   every group — forty-odd links before the page's own content began. Now
   each group is a <details> pill: closed by default, open where you are,
   dropdown panels on a desktop and stacked accordions on a phone. */
.admin-nav {
    display: flex;
    flex-wrap: wrap;
    gap: 0.45rem;
    padding: 0.7rem 0.8rem;
    margin-bottom: 1.5rem;
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    border-radius: var(--radius-sm);
    box-shadow: var(--shadow-sm, 0 1px 2px rgba(0,0,0,0.06));
}

.admin-nav-group { position: relative; }

.admin-nav-heading {
    display: inline-flex;
    align-items: center;
    gap: 0.4rem;
    padding: 0.42rem 0.85rem;
    border-radius: 999px;
    border: 1px solid transparent;
    font-size: 0.72rem;
    font-weight: 700;
    letter-spacing: 0.08em;
    text-transform: uppercase;
    color: var(--knms-muted);
    cursor: pointer;
    list-style: none;
    user-select: none;
}
.admin-nav-heading::-webkit-details-marker { display: none; }
.admin-nav-heading::after { content: '▾'; font-size: 0.7em; opacity: 0.7; }
.admin-nav-heading:hover { color: var(--knms-heading); border-color: var(--knms-border); }
.admin-nav-group[open] > .admin-nav-heading {
    color: var(--knms-heading);
    background: rgba(139, 92, 246, 0.14);
    border-color: rgba(139, 92, 246, 0.4);
}
.admin-nav-heading.is-here { color: var(--knms-accent); }

/* Desktop: the panel drops over the page. Narrow: it opens in flow, an
   accordion, because a dropdown wider than the screen is a scroll trap. */
.admin-nav-panel {
    display: flex;
    flex-direction: column;
    gap: 0.15rem;
    padding: 0.6rem 0.8rem;
}
@media (min-width: 900px) {
    .admin-nav-panel {
        position: absolute;
        top: calc(100% + 0.35rem);
        left: 0;
        z-index: 60;
        min-width: 220px;
        max-width: min(320px, calc(100vw - 2rem));
        background: var(--knms-panel, #1d1040);
        border: 1px solid rgba(139, 92, 246, 0.4);
        border-radius: 12px;
        box-shadow: 0 14px 34px rgba(0, 0, 0, 0.5);
    }
    /* The last groups sit near the right edge; a left-anchored panel there
       runs off screen on a narrow desktop. */
    .admin-nav-group:nth-last-child(-n+3) .admin-nav-panel { left: auto; right: 0; }
}

.admin-nav-link {
    display: inline-flex;
    align-items: center;
    gap: 0.4rem;
    font-size: 0.85rem;
    color: var(--knms-text);
    padding: 0.3rem 0.2rem;
    border-bottom: 1px solid transparent;
    width: fit-content;
}
@media (pointer: coarse) {
    .admin-nav-heading { min-height: 2.75rem; }
    .admin-nav-link { min-height: 2.4rem; }
}
.admin-nav-link:hover { color: var(--knms-heading); text-decoration: none; border-bottom-color: var(--gloss-purple); }
.admin-nav-link.is-active { color: var(--knms-heading); font-weight: 600; border-bottom-color: var(--knms-accent); }

.admin-nav-badge {
    background: var(--knms-warn-bg);
    color: var(--knms-warn);
    border-radius: 999px;
    font-size: 0.68rem;
    font-weight: 700;
    padding: 0.05rem 0.42rem;
    line-height: 1.5;
}

/* Card header with actions pushed to the right. */
.admin-toolbar {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 1rem;
    flex-wrap: wrap;
    margin-bottom: 0.9rem;
}
.admin-toolbar-actions { display: flex; gap: 0.5rem; flex-wrap: wrap; }

/* Horizontal row of filter controls that wraps cleanly on a phone. */
.filter-bar { display: flex; gap: 0.8rem; flex-wrap: wrap; align-items: flex-end; margin-bottom: 0.5rem; }
.filter-bar .form-group { margin-bottom: 0; flex: 1; min-width: 150px; }
.filter-bar-actions { display: flex; gap: 0.5rem; align-items: flex-end; padding-bottom: 0.05rem; }

/* Two-column form layout for the longer user record. */
.field-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(230px, 1fr)); gap: 0 1.2rem; }
.field-hint { display: block; font-size: 0.76rem; color: var(--knms-muted); margin-top: 0.3rem; }

.cell-sub { font-size: 0.78rem; color: var(--knms-muted); }
.result-count { font-size: 0.82rem; color: var(--knms-muted); margin: 0.4rem 0 0.8rem; }

.btn-sm { padding: 0.3rem 0.7rem; font-size: 0.8rem; }

.bulk-bar {
    display: flex;
    align-items: center;
    gap: 0.6rem;
    flex-wrap: wrap;
    margin-top: 1rem;
    padding-top: 0.9rem;
    border-top: 1px solid var(--knms-border);
}
.bulk-bar label { font-size: 0.85rem; font-weight: 600; color: var(--knms-heading); }
.bulk-bar select { padding: 0.45rem 0.6rem; border: 1px solid var(--knms-border); border-radius: var(--radius-sm); background: var(--knms-surface); color: var(--knms-text); }

.pagination { display: flex; align-items: center; gap: 0.8rem; justify-content: center; margin-top: 1.1rem; }

/* Role pills. Deliberately distinct from the status pills next to them
   so a scan down the table separates "what they are" from "how they are". */
.badge-role-5 { background: linear-gradient(135deg, var(--knms-accent), var(--knms-accent-light)); color: #4a3403; }
.badge-role-1 { background: rgba(139, 92, 246, 0.16); color: var(--gloss-purple-deep, #5b21b6); }
.badge-role-2 { background: rgba(53, 220, 255, 0.16); color: #04667a; }
.badge-role-3 { background: var(--knms-border); color: var(--knms-text); }
.badge-role-4 { background: transparent; color: var(--knms-muted); border: 1px solid var(--knms-border); }

/* Per-member permission overrides. */
.perm-group { margin-bottom: 1.3rem; }
.perm-group h4 { font-size: 0.8rem; text-transform: uppercase; letter-spacing: 0.07em; color: var(--knms-muted); margin: 0 0 0.5rem; }

.perm-row {
    display: flex;
    align-items: flex-start;
    justify-content: space-between;
    gap: 1rem;
    padding: 0.6rem 0;
    border-bottom: 1px solid var(--knms-border);
}
.perm-row:last-child { border-bottom: none; }
.perm-row-text { flex: 1; font-size: 0.87rem; }
.perm-row-text .badge-pill { margin-left: 0.4rem; }
.perm-row-control { flex-shrink: 0; min-width: 150px; }
.perm-row-control select { width: 100%; padding: 0.4rem 0.5rem; border: 1px solid var(--knms-border); border-radius: var(--radius-sm); background: var(--knms-surface); color: var(--knms-text); font-size: 0.83rem; }

/* Role × permission matrix. */
.matrix-heading { font-size: 0.8rem; text-transform: uppercase; letter-spacing: 0.07em; color: var(--knms-muted); margin: 1.4rem 0 0.5rem; }
.matrix-table th { white-space: nowrap; font-size: 0.78rem; }
.matrix-table td { vertical-align: top; }
.matrix-cell { text-align: center; vertical-align: middle; }
.matrix-cell input[type="checkbox"] { width: 1.05rem; height: 1.05rem; cursor: pointer; accent-color: var(--gloss-purple); }
.matrix-locked { color: var(--knms-success); font-weight: 700; }

/* Irreversible actions get their own visual bay, away from Save. */
.danger-card { border-color: rgba(208, 52, 44, 0.35); }
.danger-card h3 { color: var(--knms-error); }
.danger-card h3::before { background: var(--knms-error) !important; }

.user-table td { vertical-align: middle; }
.user-table input[type="checkbox"] { width: 1.05rem; height: 1.05rem; cursor: pointer; accent-color: var(--gloss-purple); }

@media (max-width: 640px) {
    .admin-nav { gap: 0.35rem; padding: 0.6rem; }
    .perm-row { flex-direction: column; align-items: stretch; }
    .perm-row-control { min-width: 0; }
}

/* Reduced-motion guard for the animated chrome that outlived the old landing.
   (The original guard also listed .landing-arc/.panel-gold and was removed
   with them during the dead-CSS sweep — these two selectors are still live.) */
@media (prefers-reduced-motion: reduce) {
    .topnav a.is-active,
    .celebration-banner { animation: none !important; }
}

/* ===============================================================
   Member profile: completeness meter, photo, references and the
   read-only profile readout in the admin console.
   =============================================================== */

.completeness { display: flex; align-items: center; gap: 0.8rem; }
.completeness-bar {
    flex: 1;
    height: 10px;
    border-radius: 999px;
    background: var(--knms-border);
    overflow: hidden;
}
.completeness-fill {
    height: 100%;
    border-radius: 999px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--gloss-cyan));
    box-shadow: 0 0 10px var(--glow-purple);
    transition: width 0.4s ease;
}
.completeness-fill.is-good { background: linear-gradient(90deg, var(--knms-success), var(--gloss-cyan)); }
.completeness-value { font-weight: 700; font-family: 'Poppins', sans-serif; color: var(--knms-heading); min-width: 3ch; text-align: right; }

.gap-list { margin: 0.3rem 0 0; padding-left: 1.1rem; font-size: 0.84rem; color: var(--knms-muted); }
.gap-list li { margin-bottom: 0.15rem; }

.photo-row { display: flex; gap: 1.2rem; align-items: flex-start; flex-wrap: wrap; }
.photo-preview {
    width: 108px;
    height: 108px;
    border-radius: var(--radius-sm);
    object-fit: cover;
    border: 1px solid var(--knms-border);
    flex-shrink: 0;
}
.photo-preview-empty {
    display: flex;
    align-items: center;
    justify-content: center;
    font-size: 1.8rem;
    font-weight: 700;
    color: #fff;
    background: linear-gradient(135deg, var(--gloss-purple), var(--gloss-cyan));
}

/* Section heading inside a long form (registration, profile). */
.form-section {
    font-size: 0.82rem;
    text-transform: uppercase;
    letter-spacing: 0.08em;
    color: var(--knms-muted);
    margin: 1.6rem 0 0.7rem;
    padding-bottom: 0.35rem;
    border-bottom: 1px solid var(--knms-border);
}
.form-section:first-of-type { margin-top: 0; }

/* One reference slot on the application form. */
.reference-block {
    border: 1px solid var(--knms-border);
    border-radius: var(--radius-sm);
    padding: 1rem 1.1rem 0.4rem;
    margin-bottom: 1rem;
    background: rgba(139, 92, 246, 0.035);
}
.reference-block h4 {
    margin: 0 0 0.7rem;
    font-size: 0.9rem;
    color: var(--knms-heading);
}
.reference-external[hidden] { display: none; }

/* An endorsement request awaiting the referee's answer. */
.endorsement-request {
    border: 1px solid var(--knms-border);
    border-left: 3px solid var(--knms-accent);
    border-radius: var(--radius-sm);
    padding: 1rem 1.1rem;
    margin-top: 1rem;
}
.endorsement-head { margin-bottom: 0.6rem; }

/* Read-only profile in the admin console: label/value pairs that
   collapse to a single column on a phone. */
.profile-readout {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
    gap: 0.7rem 1.4rem;
    margin: 0 0 1.1rem;
}
.profile-readout dt { font-size: 0.74rem; text-transform: uppercase; letter-spacing: 0.05em; color: var(--knms-muted); }
.profile-readout dd { margin: 0.1rem 0 0; font-size: 0.9rem; color: var(--knms-text); word-break: break-word; }

.directory-skills {
    font-style: italic;
    display: -webkit-box;
    -webkit-line-clamp: 2;
    -webkit-box-orient: vertical;
    overflow: hidden;
}

@media (max-width: 640px) {
    .photo-preview { width: 84px; height: 84px; }
    .profile-readout { grid-template-columns: 1fr; }
}

/* ===============================================================
   Multi-stage approval: the stage tracker and decision timeline.
   The track scrolls sideways rather than wrapping — a seven-stage
   pipeline should still read as one line of travel on a phone.
   =============================================================== */

.approval-tracker { overflow-x: auto; -webkit-overflow-scrolling: touch; padding-bottom: 0.4rem; }

.approval-track {
    display: flex;
    align-items: flex-start;
    gap: 0;
    min-width: min-content;
}

.approval-step {
    position: relative;
    flex: 1 0 132px;
    min-width: 132px;
    padding: 0 0.55rem;
    text-align: center;
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 0.22rem;
}

/* The connecting rail, drawn behind each marker. */
.approval-step::before {
    content: '';
    position: absolute;
    top: 15px;
    left: -50%;
    width: 100%;
    height: 2px;
    background: var(--knms-border);
    z-index: 0;
}
.approval-step:first-child::before { display: none; }
.approval-step.is-done::before,
.approval-step.is-current::before { background: var(--gloss-purple); }

.approval-step-marker {
    position: relative;
    z-index: 1;
    width: 32px;
    height: 32px;
    border-radius: 50%;
    display: flex;
    align-items: center;
    justify-content: center;
    font-weight: 700;
    font-size: 0.85rem;
    background: var(--knms-surface);
    color: var(--knms-muted);
    border: 2px solid var(--knms-border);
    flex-shrink: 0;
}

.approval-step-name { font-size: 0.82rem; font-weight: 600; color: var(--knms-heading); line-height: 1.25; }
.approval-step-meta { font-size: 0.7rem; color: var(--knms-muted); line-height: 1.3; }

.approval-step-flag {
    font-size: 0.66rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.04em;
    color: var(--knms-error);
    background: var(--knms-error-bg);
    border-radius: 999px;
    padding: 0.05rem 0.45rem;
}

.approval-step.is-done .approval-step-marker {
    background: var(--knms-success);
    border-color: var(--knms-success);
    color: #fff;
}
.approval-step.is-current .approval-step-marker {
    background: linear-gradient(135deg, var(--gloss-purple), var(--gloss-cyan));
    border-color: transparent;
    color: #fff;
    box-shadow: 0 0 0 4px rgba(139, 92, 246, 0.18), 0 0 14px var(--glow-purple);
}
.approval-step.is-current .approval-step-name { color: var(--knms-heading); }
.approval-step.is-upcoming .approval-step-name { color: var(--knms-muted); font-weight: 500; }

.approval-step.is-overdue .approval-step-marker {
    background: linear-gradient(135deg, var(--knms-error), var(--knms-warn));
    box-shadow: 0 0 0 4px rgba(208, 52, 44, 0.16);
}

/* A closed request recolours its stopping point. */
.approval-tracker.is-rejected .approval-step.is-current .approval-step-marker {
    background: var(--knms-error);
    border-color: var(--knms-error);
    box-shadow: none;
}
.approval-tracker.is-cancelled .approval-step .approval-step-marker { opacity: 0.6; }

/* Decision history. */
.approval-timeline { list-style: none; margin: 0; padding: 0 0 0 1.1rem; border-left: 2px solid var(--knms-border); }

.approval-timeline-item { position: relative; padding: 0 0 1rem 0.6rem; font-size: 0.88rem; }
.approval-timeline-item::before {
    content: '';
    position: absolute;
    left: -1.5rem;
    top: 0.34rem;
    width: 10px;
    height: 10px;
    border-radius: 50%;
    background: var(--knms-border);
    border: 2px solid var(--knms-surface);
}
.approval-timeline-item.is-approved::before { background: var(--knms-success); }
.approval-timeline-item.is-rejected::before { background: var(--knms-error); }
.approval-timeline-item.is-returned::before { background: var(--knms-warn); }
.approval-timeline-item.is-completed::before { background: var(--gloss-purple); }
.approval-timeline-item:last-child { padding-bottom: 0; }

.approval-timeline-remarks {
    margin-top: 0.3rem;
    padding: 0.45rem 0.7rem;
    background: rgba(139, 92, 246, 0.06);
    border-radius: var(--radius-sm);
    font-size: 0.85rem;
}

/* Stage editor cards carry a rail so a long pipeline stays readable. */
.stage-card { border-left: 3px solid var(--gloss-purple); }
.stage-card select[multiple] { min-height: 7rem; padding: 0.4rem; }

@media (max-width: 640px) {
    .approval-step { flex-basis: 116px; min-width: 116px; }
}

/* A decision retired by a rework: still on the record, no longer counted. */
.approval-timeline-item.is-superseded { opacity: 0.62; }
.approval-timeline-item.is-superseded .approval-timeline-head strong:first-child { text-decoration: line-through; }
.approval-timeline-item.is-superseded::before { background: var(--knms-border); }
.approval-superseded-flag {
    font-size: 0.68rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.04em;
    color: var(--knms-muted);
    border: 1px solid var(--knms-border);
    border-radius: 999px;
    padding: 0.02rem 0.42rem;
    margin-left: 0.3rem;
}

/* Bottleneck bars in the approval analytics table. */
.stage-bar {
    width: 100%;
    height: 8px;
    border-radius: 999px;
    background: var(--knms-border);
    overflow: hidden;
}
.stage-bar-fill {
    height: 100%;
    border-radius: 999px;
    background: linear-gradient(90deg, var(--gloss-purple), var(--gloss-cyan));
    transition: width 0.4s ease;
}
.stage-bar-fill.is-slowest { background: linear-gradient(90deg, var(--knms-error), var(--knms-warn)); }

/* A stage passed over rather than decided. */
.approval-step.is-skipped .approval-step-marker {
    background: var(--knms-surface);
    border-style: dashed;
    color: var(--knms-muted);
}
.approval-timeline-item.is-skipped::before { background: var(--knms-muted); }
.approval-timeline-item.is-escalated::before { background: var(--knms-warn); }
.approval-timeline-item.is-reminded { opacity: 0.75; }
.approval-timeline-item.is-reminded::before { background: var(--knms-border); }

/* --- Collapsible mobile navigation --------------------------------
   Below 600px .topnav is hidden, and the fixed bottom bar only carries five
   destinations — so About Us, Gallery and Join Us had no route on a phone.
   This button reveals the full menu. Desktop is untouched. */
.nav-toggle { display: none; }

@media (max-width: 600px) {
    /* The bar must not overflow, and on a narrow phone it did.
       .brand is a flex item, and a flex item's default min-width:auto means
       it refuses to shrink below its content — so at around 430px and under,
       "Kamarajar Nadar Munnetra Sangam" pushed the whole line wider than the
       viewport. Everything anchored to the right then went off-screen with
       it: the hamburger became unreachable (the only way to the full menu at
       this width) and the page gained a horizontal scroll that threw the
       full-bleed hero's `50% - 50vw` maths out with it.

       Letting the brand shrink and ellipsise is what fixes it. nowrap keeps
       the toggle on the same line rather than dropping it to a second row. */
    .topbar { flex-wrap: nowrap; padding-left: 1rem; padding-right: 1rem; }
    .brand { min-width: 0; flex: 1 1 auto; overflow: hidden; }
    .brand span {
        min-width: 0;
        overflow: hidden;
        text-overflow: ellipsis;
        white-space: nowrap;
    }
    .brand-mark, .brand-logo, .brand-mark-emblem { flex: 0 0 auto; }

    .nav-toggle {
        display: inline-flex;
        align-items: center;
        justify-content: center;
        width: 42px;
        height: 42px;
        flex: 0 0 auto;
        margin-left: auto;
        border: 1px solid rgba(255, 205, 110, 0.45);
        border-radius: 10px;
        background: rgba(255, 255, 255, 0.06);
        color: #fff;
        cursor: pointer;
        transition: border-color 0.2s ease, box-shadow 0.28s ease;
    }
    .nav-toggle:hover, .nav-toggle:focus-visible {
        border-color: rgba(255, 225, 160, 0.95);
        box-shadow: 0 0 16px rgba(255, 190, 60, 0.55);
    }

    /* Hamburger drawn from one span plus its two pseudo-elements, so the
       three bars can fold into an X without extra markup. */
    .nav-toggle__bars { position: relative; }
    .nav-toggle__bars,
    .nav-toggle__bars::before,
    .nav-toggle__bars::after {
        display: block;
        width: 20px;
        height: 2px;
        border-radius: 2px;
        background: currentColor;
        transition: transform 0.25s ease, background 0.2s ease, top 0.25s ease;
    }
    .nav-toggle__bars::before,
    .nav-toggle__bars::after { content: ''; position: absolute; left: 0; }
    .nav-toggle__bars::before { top: -6px; }
    .nav-toggle__bars::after  { top: 6px; }
    .nav-toggle[aria-expanded="true"] .nav-toggle__bars { background: transparent; }
    .nav-toggle[aria-expanded="true"] .nav-toggle__bars::before { top: 0; transform: rotate(45deg); }
    .nav-toggle[aria-expanded="true"] .nav-toggle__bars::after  { top: 0; transform: rotate(-45deg); }

    /* Panel. display:none while closed so the links leave the tab order
       rather than sitting invisible but focusable. */
    .topnav {
        display: none;
        position: absolute;
        top: 100%;
        left: 0;
        right: 0;
        flex-direction: column;
        align-items: stretch;
        gap: 0;
        padding: 0.3rem 0.95rem 0.85rem;
        background: linear-gradient(135deg, rgba(42, 18, 89, 0.98), rgba(26, 11, 61, 0.99));
        border-bottom: 1px solid rgba(255, 205, 110, 0.35);
        box-shadow: 0 18px 40px rgba(0, 0, 0, 0.5);
    }
    .topnav.is-open { display: flex; animation: nav-drop 0.22s ease; }
    .topnav a {
        padding: 0.8rem 0.35rem;
        border-bottom: 1px dashed rgba(255, 205, 110, 0.22);
        font-size: 0.98rem;
        background-size: 0 2px;        /* the hover underline is a row-layout idea */
    }
    .topnav a:last-child { border-bottom: 0; }
    .topnav a + a::before { display: none; }   /* ditto the separator dashes */
}
@keyframes nav-drop {
    from { opacity: 0; transform: translateY(-8px); }
    to   { opacity: 1; transform: none; }
}
@media (prefers-reduced-motion: reduce) {
    .topnav.is-open { animation: none; }
}

/* Configuration health findings. */
.health-finding {
    border-left: 3px solid var(--knms-border);
    padding: 0.7rem 0 0.7rem 0.9rem;
    margin-bottom: 0.9rem;
}
.health-finding.is-error { border-left-color: var(--knms-error); }
.health-finding.is-warning { border-left-color: var(--knms-warn); }
.health-finding-head { display: flex; align-items: center; gap: 0.55rem; flex-wrap: wrap; margin-bottom: 0.25rem; }
.health-finding-head strong { font-size: 0.93rem; color: var(--knms-heading); }
.health-finding p { margin: 0.2rem 0 0; }
.health-cmd {
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    border-radius: var(--radius-sm);
    padding: 0.6rem 0.8rem;
    font-size: 0.82rem;
    overflow-x: auto;
    margin: 0.5rem 0;
}

/* Automatic-verification check picker in the stage builder. */
.autocheck-box {
    border: 1px solid var(--knms-border);
    border-radius: var(--radius-sm);
    padding: 0.9rem 1rem;
    margin: 0 0 1rem;
    background: rgba(53, 220, 255, 0.04);
}
.autocheck-box legend {
    font-size: 0.78rem;
    text-transform: uppercase;
    letter-spacing: 0.06em;
    color: var(--knms-muted);
    padding: 0 0.4rem;
    font-weight: 700;
}
.autocheck-item {
    display: flex;
    align-items: flex-start;
    gap: 0.55rem;
    padding: 0.4rem 0;
    border-bottom: 1px solid var(--knms-border);
    font-size: 0.87rem;
}
.autocheck-item:last-of-type { border-bottom: none; }
.autocheck-item input[type="checkbox"] { margin-top: 0.2rem; accent-color: var(--gloss-cyan); flex-shrink: 0; }

.approval-timeline-item.is-checked::before { background: var(--gloss-cyan); }

/* --- Portal cards inherit the landing's corner brackets ------------
   The gold bracket ticks are the signature detail of the approved design's
   panels, but they only ever existed on the landing (.kn-panel), so every
   inner page — Events, Gallery, News, Forum, Profile, Admin — read as a flat
   dark box next to a homepage full of them. Same geometry and colour as
   .kn-panel::before/::after so the two match exactly.

   Appended last: .card is redefined five times earlier in this file, and a
   sixth competing block would be worse than one additive rule at the end. */
.card {
    position: relative;                /* the brackets are absolutely placed */
}
.card::before,
.card::after {
    content: '';
    position: absolute;
    width: 18px;
    height: 18px;
    border-style: solid;
    border-color: rgba(255, 226, 150, 0.85);
    pointer-events: none;
    opacity: calc(0.85 * var(--theme-glow, 1));
    transition: opacity 0.28s ease, border-color 0.28s ease;
}
.card::before { top: 6px; left: 6px; border-width: 2px 0 0 2px; border-radius: 4px 0 0 0; }
.card::after { bottom: 6px; right: 6px; border-width: 0 2px 2px 0; border-radius: 0 0 4px 0; }
.card:hover::before,
.card:hover::after { border-color: rgba(255, 240, 190, 1); opacity: 1; }

/* Cards used purely as a layout wrapper around a table or a form grid get
   crowded by the ticks; opt out with .card--plain. */
.card--plain::before, .card--plain::after { content: none; }

/* ===================================================================
   Icon interaction layer
   -------------------------------------------------------------------
   Nothing in the portal responded to hover on an icon. `.footer-link .icon`
   even carried `transition: transform` with no rule anywhere that changed the
   transform, so it animated nothing at all. Icons now lift and take the gold
   glow on hover, focus and active state, matching the buttons.
   =================================================================== */
.icon {
    transition: transform 0.22s ease, filter 0.3s ease, color 0.18s ease;
}

/* Mobile bottom bar — the primary navigation on a phone, so its icons need
   the clearest feedback of any in the app. */
.footer-link .icon { transform-origin: 50% 60%; }
.footer-link:hover .icon,
.footer-link:focus-visible .icon,
.footer-link.is-active .icon {
    transform: translateY(-2px) scale(1.1);
    filter: drop-shadow(0 0 8px rgba(255, 200, 90, calc(0.85 * var(--theme-glow, 1))))
            drop-shadow(0 0 16px rgba(255, 160, 40, calc(0.45 * var(--theme-glow, 1))));
}

/* Notification bell: a short swing reads as "ring" without being a toy. */
@keyframes kn-bell-ring {
    0%, 100% { transform: rotate(0); }
    15%      { transform: rotate(13deg); }
    35%      { transform: rotate(-11deg); }
    55%      { transform: rotate(7deg); }
    75%      { transform: rotate(-4deg); }
}
.nav-bell:hover .icon,
.nav-bell:focus-visible .icon {
    animation: kn-bell-ring 0.62s ease;
    filter: drop-shadow(0 0 9px rgba(255, 205, 110, calc(0.9 * var(--theme-glow, 1))));
}

/* Icons inside a card catch the light when the card itself is hovered, so the
   whole card reads as one object rather than a box with separate parts. */
.card:hover .icon,
.section-heading .icon { filter: drop-shadow(0 0 8px rgba(255, 200, 90, calc(0.6 * var(--theme-glow, 1)))); }

/* An icon inside a button nudges along with the press. */
.btn .icon, .kn-btn .icon, .kn-pbtn .icon { transition: transform 0.2s ease; }
.btn:hover .icon, .kn-btn:hover .icon, .kn-pbtn:hover .icon { transform: translateX(2px); }

/* Footer link icons in the site footer (contact rows, explore list). */
.site-footer-col a:hover .icon {
    filter: drop-shadow(0 0 8px rgba(255, 200, 90, calc(0.7 * var(--theme-glow, 1))));
}

/* --- Touch targets -------------------------------------------------
   Measured, not guessed: an audit of every public page at 320-414px
   found the footer's column links standing 24px tall and its social
   buttons 34px across — both under the 44px a fingertip needs, and the
   footer is precisely where someone hunts for "Contact" one-handed.

   Keyed on `pointer: coarse` rather than a width breakpoint because
   this is a question about the input device, not the screen: a phone
   in landscape still has fingers, and a narrow desktop window still
   has a mouse and does not want the extra height.

   Padding rather than min-height on the links: these sit in a column
   with a text baseline, and growing the box from the inside keeps the
   labels evenly spaced instead of stretching one row. */
@media (pointer: coarse) {
    .site-footer-col a,
    .site-footer-brand a {
        min-height: 2.75rem;
        padding: 0.75rem 0;
        font-size: 0.92rem;
    }
    .site-footer-social { gap: 0.65rem; }
    .site-footer-social a { width: 2.75rem; height: 2.75rem; }
    .site-footer-social .icon { width: 1.2rem; height: 1.2rem; }
}

@media (prefers-reduced-motion: reduce) {
    /* Glow still responds; only the movement is dropped. */
    .icon, .footer-link:hover .icon, .footer-link.is-active .icon,
    .btn:hover .icon, .kn-btn:hover .icon, .kn-pbtn:hover .icon { transform: none; }
    .nav-bell:hover .icon, .nav-bell:focus-visible .icon { animation: none; }
}

/* --- Mobile menu: scrim, staggered reveal, scroll lock -------------- */
.nav-only-mobile { display: none; }
.nav-scrim { display: none; }

@media (max-width: 600px) {
    .nav-only-mobile { display: block; }

    .nav-scrim {
        display: block;
        position: fixed;
        inset: 0;
        z-index: 30;                   /* under .topbar (40), over the page */
        background: rgba(8, 3, 20, 0.62);
        backdrop-filter: blur(2px);
        -webkit-backdrop-filter: blur(2px);
        opacity: 0;
        transition: opacity 0.24s ease;
        pointer-events: none;
    }
    .nav-scrim[hidden] { display: none; }
    .nav-scrim.is-open { opacity: 1; pointer-events: auto; }

    /* While the menu is open the page behind must not scroll under it. */
    body.nav-open { overflow: hidden; }

    /* Items arrive in sequence — a small thing that separates a considered
       menu from one that simply appears. */
    .topnav.is-open a {
        opacity: 0;
        animation: nav-item-in 0.26s ease forwards;
    }
    .topnav.is-open a:nth-child(1) { animation-delay: 0.03s; }
    .topnav.is-open a:nth-child(2) { animation-delay: 0.06s; }
    .topnav.is-open a:nth-child(3) { animation-delay: 0.09s; }
    .topnav.is-open a:nth-child(4) { animation-delay: 0.12s; }
    .topnav.is-open a:nth-child(5) { animation-delay: 0.15s; }
    .topnav.is-open a:nth-child(6) { animation-delay: 0.18s; }
    .topnav.is-open a:nth-child(n+7) { animation-delay: 0.21s; }

    /* The open panel sits above the scrim. */
    .topnav.is-open { z-index: 41; }
}
@keyframes nav-item-in {
    from { opacity: 0; transform: translateY(-6px); }
    to   { opacity: 1; transform: none; }
}
@media (prefers-reduced-motion: reduce) {
    .topnav.is-open a { opacity: 1; animation: none; }
    .nav-scrim { transition: none; }
}

/* ===============================================================
   Family tree. Generation bands stack oldest-first; connectors are
   drawn into the SVG overlay from measured card positions, so the
   layout can reflow freely without the lines going wrong.
   =============================================================== */

.tree-viewport {
    position: relative;
    overflow-x: auto;
    overflow-y: hidden;
    padding: 0.5rem 0 1rem;
    -webkit-overflow-scrolling: touch;
}

.tree-links {
    position: absolute;
    top: 0;
    left: 0;
    pointer-events: none;
    z-index: 0;
    overflow: visible;
}

.tree-canvas { position: relative; z-index: 1; min-width: min-content; }

.tree-band { margin-bottom: 2.2rem; }
.tree-band:last-child { margin-bottom: 0.5rem; }

.tree-band-label {
    display: block;
    font-size: 0.7rem;
    text-transform: uppercase;
    letter-spacing: 0.08em;
    color: var(--knms-muted);
    margin-bottom: 0.5rem;
    font-weight: 700;
}

.tree-row {
    display: flex;
    gap: 1rem;
    flex-wrap: wrap;
    align-items: flex-start;
}

.tree-node {
    position: relative;
    width: 128px;
    flex-shrink: 0;
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 0.28rem;
    padding: 0.7rem 0.5rem;
    background: var(--knms-surface);
    border: 1px solid var(--knms-border);
    border-radius: var(--radius-sm);
    text-align: center;
    cursor: pointer;
    transition: transform 0.15s ease, box-shadow 0.15s ease, opacity 0.15s ease, border-color 0.15s ease;
}
.tree-node:hover { transform: translateY(-2px); box-shadow: var(--shadow-md); }
.tree-node:focus-visible { outline: 2px solid var(--gloss-purple); outline-offset: 2px; }

.tree-node-photo {
    width: 48px;
    height: 48px;
    border-radius: 50%;
    object-fit: cover;
    border: 2px solid var(--knms-border);
}
.tree-node-initials {
    display: flex;
    align-items: center;
    justify-content: center;
    font-weight: 700;
    font-size: 0.95rem;
    color: #fff;
    background: linear-gradient(135deg, var(--gloss-purple), var(--gloss-cyan));
    border-color: transparent;
}

.tree-node-name { font-size: 0.82rem; font-weight: 600; color: var(--knms-heading); line-height: 1.25; }
.tree-node-meta { font-size: 0.68rem; color: var(--knms-muted); }

.tree-node-open {
    font-size: 0.68rem;
    color: var(--gloss-purple);
    margin-top: 0.15rem;
    opacity: 0;
    transition: opacity 0.15s ease;
}
.tree-node:hover .tree-node-open,
.tree-node:focus-within .tree-node-open,
.tree-node.is-focused .tree-node-open { opacity: 1; }

/* The person the tree is currently built around. */
.tree-node.is-root {
    border-color: transparent;
    background: linear-gradient(135deg, rgba(139,92,246,0.14), rgba(53,220,255,0.12));
    box-shadow: 0 0 0 2px var(--gloss-purple), 0 0 18px var(--glow-purple);
}
.tree-node.is-root .tree-node-photo { border-color: var(--gloss-purple); }

/* Someone outside the Sangam: no account to open. */
.tree-node.is-external { border-style: dashed; background: transparent; }
.tree-node.is-external .tree-node-initials { background: var(--knms-border); color: var(--knms-muted); }

.tree-node.is-dimmed { opacity: 0.28; }

/* Search and filter. Non-matching people are faded rather than removed: seeing
   that a match sits between two relatives is most of the value, and hiding them
   would leave connector lines running to nothing. */
.tree-node.is-filtered-out { opacity: 0.18; filter: saturate(0.4); }
.tree-node.is-match {
    border-color: var(--gloss-cyan);
    box-shadow: 0 0 0 2px rgba(34, 211, 238, 0.3), 0 0 16px rgba(34, 211, 238, 0.25);
}
.tree-filters {
    display: flex;
    flex-wrap: wrap;
    align-items: flex-end;
    gap: 0.6rem 0.9rem;
}
.tree-filter-field { display: flex; flex-direction: column; gap: 0.25rem; }
.tree-filter-field input,
.tree-filter-field select {
    min-width: 9rem;
    padding: 0.35rem 0.6rem;
    font-size: 0.85rem;
}
.tree-filter-count {
    font-size: 0.8rem;
    color: var(--gloss-cyan);
    align-self: center;
    min-height: 1em;
}
.tree-node.is-focused { border-color: var(--gloss-cyan); box-shadow: 0 0 0 2px var(--gloss-cyan); }

.tree-link {
    fill: none;
    stroke: var(--gloss-purple);
    stroke-width: 2;
    opacity: 0.55;
    transition: opacity 0.15s ease, stroke-width 0.15s ease;
}
.tree-link.is-pending { stroke-dasharray: 5 4; opacity: 0.4; }
.tree-link.is-unlinked { stroke: var(--knms-muted); stroke-dasharray: 2 4; opacity: 0.4; }
.tree-link.is-active { opacity: 1; stroke-width: 3; stroke: var(--gloss-cyan); }
.tree-link.is-dimmed { opacity: 0.1; }

.tree-controls { display: flex; gap: 1.4rem; flex-wrap: wrap; align-items: center; }
.tree-control-group { display: flex; gap: 0.35rem; align-items: center; flex-wrap: wrap; }
.tree-control-label { font-size: 0.76rem; color: var(--knms-muted); font-weight: 600; }

.tree-legend {
    display: flex;
    gap: 1.1rem;
    flex-wrap: wrap;
    align-items: center;
    margin-top: 0.9rem;
    padding-top: 0.8rem;
    border-top: 1px solid var(--knms-border);
    font-size: 0.76rem;
    color: var(--knms-muted);
}
.tree-key { display: inline-block; width: 22px; height: 0; border-top: 2px solid var(--gloss-purple); vertical-align: middle; margin-right: 0.3rem; }
.tree-key-claimed { border-top-style: dashed; }
.tree-key-external { border-top-color: var(--knms-muted); border-top-style: dotted; }

@media (max-width: 640px) {
    .tree-node { width: 104px; padding: 0.55rem 0.4rem; }
    .tree-node-photo { width: 40px; height: 40px; }
    .tree-node-open { opacity: 1; }
    .tree-band { margin-bottom: 1.8rem; }
}

/* ===============================================================
   Registration wizard
   =============================================================== */

/* Progress rail — gold for done/current, muted for upcoming. */
.wizard-rail {
    display: flex;
    align-items: flex-start;
    gap: 0.4rem;
    list-style: none;
    margin: 0 0 1.5rem;
    padding: 0;
    counter-reset: none;
}
.wizard-rail li {
    flex: 1;
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 0.35rem;
    position: relative;
    text-align: center;
}
/* Connector between dots. */
.wizard-rail li::before {
    content: '';
    position: absolute;
    top: 13px;
    left: 0;
    right: 50%;
    height: 2px;
    background: var(--knms-border);
}
.wizard-rail li:first-child::before { display: none; }
.wizard-rail li.is-done::before,
.wizard-rail li.is-current::before { background: var(--knms-accent); }
.wizard-dot {
    position: relative;
    z-index: 1;
    width: 28px;
    height: 28px;
    border-radius: 50%;
    display: flex;
    align-items: center;
    justify-content: center;
    font-size: 0.8rem;
    font-weight: 700;
    background: var(--knms-surface-2, #2d1a5c);
    color: var(--knms-muted);
    border: 2px solid var(--knms-border);
}
.wizard-rail li.is-current .wizard-dot {
    background: linear-gradient(135deg, var(--knms-accent), var(--knms-accent-light));
    color: #2a1a02;
    border-color: transparent;
    box-shadow: 0 0 14px var(--glow-gold);
}
.wizard-rail li.is-done .wizard-dot {
    background: transparent;
    color: var(--knms-accent);
    border-color: var(--knms-accent);
}
.wizard-label { font-size: 0.72rem; color: var(--knms-muted); line-height: 1.25; }
.wizard-rail li.is-current .wizard-label { color: var(--knms-accent-light); font-weight: 600; }

/* Navigation row. */
.wizard-nav {
    display: flex;
    align-items: center;
    gap: 0.8rem;
    margin-top: 1.4rem;
    padding-top: 1.1rem;
    border-top: 1px solid var(--knms-border);
}
.wizard-count { margin-left: auto; color: var(--knms-muted); font-size: 0.8rem; }
.wizard-nav [data-wizard-next],
.wizard-nav [data-wizard-submit] { order: 3; }

/* Inline field errors. */
.field-error {
    display: block;
    margin-top: 0.35rem;
    color: var(--knms-error);
    font-size: 0.8rem;
    line-height: 1.4;
}
.form-group.is-invalid input,
.form-group.is-invalid select,
.form-group.is-invalid textarea {
    border-color: var(--knms-error);
    box-shadow: 0 0 0 3px rgba(251, 113, 133, 0.16);
}
.reference-block.is-invalid { border-color: var(--knms-error); }

/* Async status line beside the email field. */
.field-status { display: block; margin-top: 0.35rem; font-size: 0.8rem; min-height: 1em; }
.field-status.is-checking { color: var(--knms-muted); }
.field-status.is-available { color: var(--knms-success); }
.field-status.is-taken { color: var(--knms-error); }

/* Fields the wizard fills in for you (age from DOB, WhatsApp from phone). */
input.is-derived {
    background: rgba(255, 185, 46, 0.07);
    border-color: rgba(255, 185, 46, 0.4);
    color: var(--knms-text);
}

/* Address autofill: pincode lookup and "use my location". */
.locate-bar {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 0.75rem 1rem;
    margin-bottom: 1.25rem;
    padding: 0.9rem 1rem;
    border: 1px solid rgba(34, 211, 238, 0.28);
    border-radius: 14px;
    background:
        linear-gradient(120deg, rgba(34, 211, 238, 0.09), rgba(139, 92, 246, 0.09));
}
.locate-bar .btn-locate {
    flex: 0 0 auto;
    display: inline-flex;
    align-items: center;
    gap: 0.45rem;
    margin: 0;
}
.locate-bar .btn-locate .icon { width: 1.05em; height: 1.05em; }
.locate-hint {
    flex: 1 1 14rem;
    margin: 0;
    font-size: 0.84rem;
    line-height: 1.5;
    color: var(--knms-muted);
}
.locate-hint strong { color: var(--knms-accent); font-weight: 600; }
.locate-status {
    flex: 1 1 100%;
    margin: 0;
    font-size: 0.82rem;
    min-height: 1em;
    color: var(--knms-muted);
}
.locate-status.is-available { color: var(--knms-success); }
.locate-status.is-taken { color: var(--knms-error); }

/* Brief cyan pulse marking a field the lookup just filled in, so the
   applicant can see what changed rather than finding it silently altered. */
input.is-autofilled,
textarea.is-autofilled {
    border-color: rgba(34, 211, 238, 0.55);
    box-shadow: 0 0 0 3px rgba(34, 211, 238, 0.16);
    transition: border-color 0.4s ease, box-shadow 0.4s ease;
}

/* Possible-duplicate panel, shown to staff who may override. */
.dup-panel {
    margin-bottom: 1.25rem;
    padding: 1rem 1.1rem;
    border: 1px solid rgba(255, 185, 46, 0.4);
    border-radius: 14px;
    background: linear-gradient(120deg, rgba(255, 185, 46, 0.1), rgba(139, 92, 246, 0.08));
}
.dup-panel h4 {
    display: flex;
    align-items: center;
    gap: 0.45rem;
    margin: 0 0 0.4rem;
    font-size: 0.95rem;
    color: var(--knms-accent);
}
.dup-panel h4 .icon { width: 1.05em; height: 1.05em; }
.dup-list { list-style: none; margin: 0.7rem 0; padding: 0; }
.dup-row {
    display: flex;
    flex-wrap: wrap;
    justify-content: space-between;
    gap: 0.25rem 0.75rem;
    padding: 0.5rem 0.65rem;
    border-radius: 9px;
    border-left: 3px solid rgba(255, 255, 255, 0.18);
    background: rgba(0, 0, 0, 0.18);
}
.dup-row + .dup-row { margin-top: 0.4rem; }
.dup-row.is-strong { border-left-color: var(--knms-error); }
.dup-name { font-weight: 600; font-size: 0.9rem; color: var(--knms-text); }
.dup-num {
    margin-left: 0.4rem;
    font-size: 0.76rem;
    font-weight: 500;
    color: var(--knms-accent);
}
.dup-why { font-size: 0.78rem; color: var(--knms-muted); }
.dup-confirm {
    display: flex;
    align-items: center;
    gap: 0.5rem;
    font-size: 0.86rem;
    color: var(--knms-text);
}

/* Password strength meter. */
.pw-strength { margin-top: 0.5rem; }
.pw-strength-bar {
    height: 5px;
    border-radius: 999px;
    background: var(--knms-border);
    overflow: hidden;
}
.pw-strength-bar span {
    display: block;
    height: 100%;
    width: 0;
    border-radius: 999px;
    transition: width 0.2s ease, background 0.2s ease;
    background: var(--knms-error);
}
.pw-strength-bar span[data-score="2"] { background: var(--knms-warn); }
.pw-strength-bar span[data-score="3"] { background: var(--gloss-cyan); }
.pw-strength-bar span[data-score="4"] { background: var(--knms-success); }
.pw-strength-label { display: block; margin-top: 0.3rem; font-size: 0.76rem; color: var(--knms-muted); }

/* Selected-photo preview, so the applicant can see what they picked. */
.photo-preview { display: flex; align-items: center; gap: 0.7rem; margin-top: 0.6rem; }
.photo-preview img {
    width: 56px;
    height: 70px;
    object-fit: cover;
    border-radius: 6px;
    border: 1px solid var(--knms-frame, var(--knms-border));
}
.photo-preview-meta { font-size: 0.76rem; color: var(--knms-muted); }

.inline-check {
    display: flex;
    align-items: center;
    gap: 0.45rem;
    margin-top: 0.45rem;
    font-size: 0.8rem;
    font-weight: 400;
    color: var(--knms-muted);
    text-transform: none;
    letter-spacing: 0;
}
.inline-check input { width: auto; }

@media (max-width: 600px) {
    /* Numbers stay, labels would wrap badly at four across. */
    .wizard-label { display: none; }
    .wizard-nav { flex-wrap: wrap; }
    .wizard-count { order: 1; width: 100%; margin-left: 0; text-align: center; }
}

/* Any `display` declared in a class rule outranks the user-agent's
   `[hidden] { display: none }`, because a class selector beats an attribute
   selector from the UA sheet. Every element given a display here — buttons are
   `inline-flex`, panes are `flex` — therefore stayed on screen while the
   markup and JavaScript both believed it was hidden.

   This was first patched as a list of four named selectors, and the bug simply
   came back on `.btn`: the wizard's Back, Submit and no-JS fallback buttons all
   showed at once on step 1. Stated once, for everything, so it cannot recur. */
[hidden] { display: none !important; }

/* Office-bearer badge in the member directory — gold, so the Sangam's elected
   officers are identifiable at a glance rather than needing to be hunted for. */
.office-badge {
    display: inline-flex;
    align-items: center;
    gap: 0.35rem;
    align-self: center;
    margin: 0.2rem 0 0.1rem;
    padding: 0.2rem 0.7rem;
    border-radius: 999px;
    font-size: 0.74rem;
    font-weight: 700;
    color: #2a1a02;
    background: linear-gradient(135deg, var(--knms-accent), var(--knms-accent-light));
    box-shadow: 0 0 12px var(--glow-gold);
}
.office-badge .icon { width: 0.85em; height: 0.85em; }
/* Lift the whole card so the leadership row reads as a distinct band. */
.directory-card:has(.office-badge) {
    border-color: var(--knms-accent);
    box-shadow: var(--shadow-sm), 0 0 0 1px rgba(255, 185, 46, 0.28), 0 0 20px rgba(255, 185, 46, 0.16);
}

/* Kinship badge — states WHY a viewer is seeing extra detail about someone.
   Derived access that isn't visible is access nobody can audit. */
.kin-badge {
    display: inline-flex;
    align-items: center;
    gap: 0.3rem;
    align-self: center;
    margin-top: 0.25rem;
    padding: 0.14rem 0.6rem;
    border-radius: 999px;
    font-size: 0.7rem;
    font-weight: 600;
    color: var(--gloss-cyan-light);
    background: rgba(34, 211, 238, 0.12);
    border: 1px solid rgba(34, 211, 238, 0.35);
}
.kin-badge .icon { width: 0.8em; height: 0.8em; }

/* Dependents in care + suggested relatives — shared row layout. */
.dependent-list, .suggestion-list { display: flex; flex-direction: column; gap: 0.55rem; }
.dependent-row, .suggestion-row {
    display: flex;
    align-items: center;
    gap: 0.75rem;
    padding: 0.6rem 0.75rem;
    border-radius: var(--radius-sm);
    border: 1px solid var(--knms-border);
    background: rgba(255, 255, 255, 0.02);
}
.dependent-row { border-color: rgba(255, 185, 46, 0.35); }
.suggestion-row { border-style: dashed; }
.dependent-photo {
    width: 38px; height: 38px;
    border-radius: 50%;
    object-fit: cover;
    flex-shrink: 0;
    border: 1px solid var(--knms-frame, var(--knms-border));
}
.dependent-name { display: flex; flex-direction: column; gap: 0.1rem; flex: 1; min-width: 0; }
.dependent-name strong { color: var(--knms-heading); }
.dependent-row .btn, .suggestion-row .btn { flex-shrink: 0; }

@media (max-width: 600px) {
    .dependent-row, .suggestion-row { flex-wrap: wrap; }
    .dependent-name { flex-basis: calc(100% - 3.5rem); }
    .dependent-row .btn, .suggestion-row .btn { width: 100%; justify-content: center; }
}

/* =======================================================================
   Admin dashboard — the command-centre layout.
   KPI cards with computed deltas, quick actions, CSS-only charts and the
   signals list. No chart library: the data is a dozen integers, and a
   rendering dependency for that is a supply chain for a bar chart.
   ======================================================================= */
.dash-welcome { margin: 0 0 1rem; font-size: 1.02rem; }
.dash-welcome span { display: block; font-size: 0.86rem; color: var(--knms-muted); margin-top: 0.15rem; }

.qa-row { display: flex; flex-wrap: wrap; gap: 0.5rem; margin-bottom: 1.2rem; }
.qa-btn {
    display: inline-flex; align-items: center; gap: 0.45rem;
    padding: 0.5rem 0.9rem; border-radius: 10px;
    background: linear-gradient(155deg, rgba(84,40,168,0.5), rgba(44,19,92,0.6));
    border: 1px solid rgba(139, 92, 246, 0.45);
    color: #fff; font-size: 0.86rem; font-weight: 600; text-decoration: none;
    transition: transform 0.15s ease, box-shadow 0.2s ease;
}
.qa-btn:hover { transform: translateY(-2px); box-shadow: 0 0 14px var(--glow-purple); }
.qa-btn .icon { width: 1rem; height: 1rem; }

.kpi-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(min(100%, 215px), 1fr));
    gap: 0.9rem;
    margin-bottom: 1.2rem;
}
.kpi-card {
    position: relative;
    display: flex; flex-direction: column; gap: 0.15rem;
    padding: 1rem 1.1rem;
    background: var(--knms-panel, rgba(30, 16, 60, 0.6));
    border: 1px solid rgba(139, 92, 246, 0.28);
    border-radius: 14px;
    text-decoration: none;
    transition: transform 0.15s ease, border-color 0.2s ease;
}
.kpi-card:hover { transform: translateY(-2px); border-color: rgba(139, 92, 246, 0.6); }
.kpi-icon {
    position: absolute; top: 0.85rem; right: 0.9rem;
    display: grid; place-items: center; width: 2rem; height: 2rem;
    border-radius: 50%; background: rgba(139, 92, 246, 0.16);
}
.kpi-icon .icon { width: 1rem; height: 1rem; color: var(--knms-accent-light, #ffe08a); }
.kpi-value { font-size: 1.7rem; font-weight: 700; color: #fff; font-family: 'Poppins', sans-serif; }
.kpi-label { font-size: 0.82rem; color: var(--knms-muted); }
.kpi-delta { font-size: 0.74rem; font-weight: 700; margin-top: 0.25rem; }
.kpi-delta--up { color: #4ade80; }
.kpi-delta--down { color: #f87171; }
.kpi-sub { font-size: 0.74rem; color: var(--knms-muted); }

.insight-list { display: grid; gap: 0.5rem; }
.insight {
    display: flex; align-items: center; gap: 0.7rem; flex-wrap: wrap;
    padding: 0.6rem 0.8rem; border-radius: 10px;
    background: rgba(139, 92, 246, 0.08);
    border-left: 3px solid var(--knms-muted);
}
.insight--opportunity { border-left-color: #35dcff; }
.insight--warning { border-left-color: var(--knms-warn, #eab308); }
.insight--info { border-left-color: var(--knms-accent, #ffc94a); }
.insight-sev {
    flex: 0 0 auto; padding: 0.1rem 0.55rem; border-radius: 999px;
    font-size: 0.68rem; font-weight: 700; letter-spacing: 0.05em; text-transform: uppercase;
    background: rgba(255, 255, 255, 0.1); color: #fff;
}
.insight-text { flex: 1 1 16rem; font-size: 0.9rem; }

.dash-charts {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(100%, 340px), 1fr));
    gap: 0.9rem;
}
.dash-charts .card { margin: 0 0 1.2rem; }
.chart-bars {
    display: flex; align-items: flex-end; gap: 4px;
    height: 170px; padding-top: 1.2rem;
}
.chart-col {
    flex: 1 1 0; min-width: 0;
    display: flex; flex-direction: column; align-items: center; justify-content: flex-end;
    height: 100%; gap: 0.2rem;
}
.chart-n { font-size: 0.68rem; color: var(--knms-muted); }
.chart-bar {
    width: 100%; max-width: 34px; border-radius: 4px 4px 0 0;
    background: linear-gradient(180deg, var(--gloss-cyan, #35dcff), var(--gloss-purple, #8b3ff5));
    min-height: 2px;
}
.chart-l { font-size: 0.64rem; color: var(--knms-muted); }
/* Two-year range: 24 labels cannot fit — every other one goes. */
.chart-bars .chart-col:nth-child(even) .chart-l { visibility: hidden; }
.chart-bars .chart-col:first-child .chart-l,
.chart-bars .chart-col:last-child .chart-l { visibility: visible; }

.hbar-list { display: grid; gap: 0.55rem; }
.hbar { display: grid; grid-template-columns: minmax(72px, 110px) 1fr 2.2em; align-items: center; gap: 0.6rem; }
.hbar-label { font-size: 0.82rem; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.hbar-track { height: 10px; border-radius: 999px; background: rgba(255, 255, 255, 0.08); overflow: hidden; }
.hbar-fill { display: block; height: 100%; border-radius: 999px;
    background: linear-gradient(90deg, var(--gloss-purple, #8b3ff5), var(--gloss-cyan, #35dcff)); }
.hbar-n { font-size: 0.8rem; font-weight: 700; text-align: right; }

@media (pointer: coarse) {
    .qa-btn { min-height: 2.75rem; }
}


/* ---------------------------------------------------------------
   Listing search — the box above a directory of things.

   Shared rather than page-local because it now appears on the events and
   news listings and is the obvious home for the other four when their
   hand-rolled boxes are unified. Colour comes from --nuh-* with literal
   fallbacks: these listings render on the light public theme, where the
   --knms-* set resolves to the dark application's violet.
   --------------------------------------------------------------- */
.listing-search {
    display: flex;
    gap: 0.5rem;
    align-items: center;
    flex-wrap: wrap;
    margin: 0 0 0.9rem;
}
.listing-search input[type="search"] {
    flex: 1 1 16rem;
    min-width: 0;
    padding: 0.55rem 0.8rem;
    border: 1px solid var(--nuh-line, rgba(27, 86, 164, 0.14));
    border-radius: 999px;
    background: var(--nuh-card, #fff);
    color: var(--nuh-ink, #17324f);
    font: inherit;
    font-size: 0.95rem;
}
.listing-search input[type="search"]::placeholder {
    color: var(--nuh-ink-muted, #52708c);
    opacity: 1;   /* Firefox dims placeholders by default, below AA */
}
.listing-search input[type="search"]:focus {
    outline: none;
    border-color: var(--nuh-blue, #1b56a4);
    box-shadow: 0 0 0 3px rgba(27, 86, 164, 0.15);
}
/* The clear link is a get-out, not a second action — it sits after the
   button and reads as text, so it cannot be mistaken for one. */
.listing-search a { text-decoration: underline; }

@media (max-width: 420px) {
    /* Below this the input, the button and the clear link cannot share a
       row without the input shrinking to a stub. The input takes the first
       row on its own and the controls follow. */
    .listing-search input[type="search"] { flex: 1 1 100%; }
}
