/* Contact Us page — scoped under .page-contact.
   Colour tokens (--surface, --line, --accent…) inherit from .shell on the layout. Scoped like the
   other page kits so the class names can't collide with the Bootstrap globals still linked in App;
   everything bespoke to this page is additionally ct- prefixed for the same reason.

   The page is a ranked escalation ladder (see docs/panopticon-conventions.md §7): the lead band is
   the fastest route to a human, the ticket band is the route for everything else, and the roster is
   the named people. It deliberately speaks the dashboard's vocabulary rather than its own —
   .panel + .section-head.tight from site/layout.css, the hover hairline and the micro-label/figure
   pairing from site/pages/soc.css — so moving between this page and the dashboard is continuous. */

.page-contact { display: flex; flex-direction: column; gap: 34px; }

/* ── Empty / loading states (same shapes as the other page kits) ── */
.page-contact .empty { padding: 40px 24px; text-align: center; color: var(--muted); }
.page-contact .empty-title { font-size: 14.5px; font-weight: 600; color: var(--text); margin: 0 0 6px; }
.page-contact .empty-detail { font-size: 13px; color: var(--faint); margin: 0; }

/* Skeleton shimmer for the <Skeleton> component. A scoped port of the admin-kit rules
   (css/admin-kit.css) because those are scoped to .admin-kit, which this page is not inside — so
   without this the loading state rendered as unstyled inline spans, i.e. an empty bordered box. The
   @keyframes it animates is global, declared once in admin-kit.css; only the rules need porting. */
.page-contact .shimmer {
    position: relative;
    overflow: hidden;
    background: var(--surface-2);
    border-radius: 0;
}
.page-contact .shimmer::after {
    content: "";
    position: absolute;
    inset: 0;
    transform: translateX(-100%);
    background: linear-gradient(90deg, transparent, rgba(120, 160, 220, .13), transparent);
    animation: shimmer-slide 1.3s ease-in-out infinite;
}
.page-contact .sk-line { display: block; height: 13px; }
.page-contact .sk-rows { display: flex; flex-direction: column; gap: 14px; padding: 20px 16px; }

@media (prefers-reduced-motion: reduce) {
    .page-contact .shimmer::after { animation: none; }
}

/* ════════════════════════════════════════════════════════════════
   Shared idioms, borrowed from the dashboard so this page reads as
   part of it.
   ════════════════════════════════════════════════════════════════ */

/* Section head: 16px accent icon + the 40px gradient rule breaking through the hairline. Mirrors
   .page-soc .section-head — kept here rather than promoted because soc.css scopes its own copy. */
.page-contact .section-head h2 { display: inline-flex; align-items: center; gap: 8px; }
.page-contact .sec-ic { display: inline-flex; flex: none; color: var(--accent); }
.page-contact .sec-ic svg { width: 16px; height: 16px; }
.page-contact .sec-ic.is-alert { color: var(--bad); }

.page-contact .section-head.tight {
    position: relative;
    width: 100%;
    margin-bottom: 4px;
    padding-bottom: 12px;
    border-bottom: 1px solid var(--line-soft);
}
.page-contact .section-head.tight::after {
    content: "";
    position: absolute;
    left: 0;
    bottom: -1px;
    width: 40px;
    height: 2px;
    background: linear-gradient(90deg, var(--accent), var(--accent-2));
}

/* Uppercase micro-label — the portal's label half of every figure. */
.page-contact .ct-micro {
    display: block;
    font-size: 11.5px;
    font-weight: 600;
    letter-spacing: 0.06em;
    text-transform: uppercase;
    color: var(--muted);
}

/* A phone number or address is a figure, so it gets the portal's figure treatment: tabular numerals
   under the micro-label, tight tracking, at .stat-value's weight. Read-only text, not a link — see
   the note on .ct-routes in Contact.razor. */
.page-contact .ct-figure {
    font-size: 19px;
    font-weight: 700;
    line-height: 1.1;
    letter-spacing: -0.015em;
    font-variant-numeric: tabular-nums;
    color: var(--text);
    word-break: break-word;
}
/* user-select:all so one click takes the whole number — with no tel:/mailto: to follow, copying it is
   the action, and nobody wants half a phone number. */
.page-contact .ct-figure.is-lg {
    font-size: 34px;
    letter-spacing: -0.02em;
    user-select: all;
    -webkit-user-select: all;
}

/* Chip — availability and severity. Same construction as the status lozenges on the ops dashboard. */
.page-contact .ct-chip {
    display: inline-block;
    flex: none;
    padding: 3px 9px;
    border: 1px solid var(--line);
    background: var(--surface-2);
    font-size: 11px;
    font-weight: 600;
    color: var(--muted);
    white-space: nowrap;
}
.page-contact .ct-chip.is-accent {
    color: var(--accent-2);
    border-color: var(--accent-line);
    background: var(--accent-soft);
}
/* Bordered icon puck. The alert variant is the only red on the band now — the heading says
   "Emergency contacts", so a chip repeating it was redundant. */
.page-contact .ct-icon {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    flex: none;
    width: 32px;
    height: 32px;
    border: 1px solid var(--line);
    background: var(--surface-2);
    color: var(--accent);
}
.page-contact .ct-icon svg { width: 16px; height: 16px; }
.page-contact .ct-icon.is-lg { width: 38px; height: 38px; }
.page-contact .ct-icon.is-lg svg { width: 19px; height: 19px; }
.page-contact .ct-icon.is-alert {
    color: var(--bad);
    border-color: color-mix(in srgb, var(--bad) 38%, transparent);
    background: color-mix(in srgb, var(--bad) 10%, transparent);
}

/* Hover language, matching the dashboard's cards: the accent hairline fades in along the top edge,
   the surface lifts, and the border brightens to --hair (a token, because the literal it replaces
   was a dark-theme white that vanished in light mode — see site/layout.css). */
.page-contact .ct-ticket::before {
    content: "";
    position: absolute;
    inset: 0 0 auto 0;
    height: 2px;
    background: linear-gradient(90deg, var(--accent), var(--accent-2));
    opacity: 0;
    transition: opacity .22s ease;
    pointer-events: none;
    z-index: 1;
}
.page-contact .ct-ticket {
    position: relative;
    transition: border-color .2s ease, background .2s ease, box-shadow .2s ease;
}
.page-contact .ct-ticket:hover {
    border-color: var(--hair);
    background: var(--surface-2);
    box-shadow: 0 18px 36px -22px rgba(0, 0, 0, 0.75);
}
.page-contact .ct-ticket:hover::before { opacity: 0.9; }

/* ════════════════════════════════════════════════════════════════
   Rung 1 — the lead band: the fastest route to a human.
   Split at the 1.6 / 1 proportion the dashboard's overview row uses,
   with the SOC's own guidance in the aside.
   ════════════════════════════════════════════════════════════════ */

.page-contact .ct-lead {
    display: flex;
    flex-direction: column;
    gap: 22px;
    padding: 22px 24px 26px;
    min-width: 0;
}

.page-contact .ct-routes { display: flex; flex-direction: column; gap: 20px; }

/* Not interactive, so it carries no hover state — nothing here is clickable and it must not pretend
   to be. */
.page-contact .ct-route {
    display: flex;
    align-items: flex-start;
    gap: 15px;
    min-width: 0;
}
.page-contact .ct-route .ct-icon { margin-top: 4px; }

.page-contact .ct-route-text { display: flex; flex-direction: column; gap: 6px; min-width: 0; }
/* Centred, not baseline-aligned: against the 34px lead figure a baseline sits the small chip down near
   the number's feet and reads as misaligned. */
.page-contact .ct-route-line { display: flex; align-items: center; gap: 12px; flex-wrap: wrap; }

/* ════════════════════════════════════════════════════════════════
   Rung 2 — the two ticket routes. A fixed pair, so this band is the
   one part of the page no publishing decision can leave thin.
   ════════════════════════════════════════════════════════════════ */

.page-contact .ct-tickets { display: grid; grid-template-columns: 1fr 1fr; gap: 16px; }

/* Always paired with .panel in the markup, which supplies the border, surface and overflow clip
   (the clip is what keeps the hover hairline above inside the panel's edges). */
.page-contact .ct-ticket {
    display: flex;
    flex-direction: column;
    gap: 13px;
    padding: 20px 22px 22px;
}

.page-contact .ct-ticket-head { display: flex; align-items: center; gap: 13px; }
.page-contact .ct-ticket-title { font-size: 15px; font-weight: 600; color: var(--text); }
.page-contact .ct-ticket-body { margin: 0; font-size: 13px; line-height: 1.55; color: var(--muted); }

.page-contact .ct-ticket-foot {
    display: flex;
    align-items: center;
    gap: 14px;
    flex-wrap: wrap;
    margin-top: auto;
    padding-top: 4px;
}
/* Links, not buttons — they navigate. ct- prefixed to stay clear of Bootstrap's .btn-primary. */
.page-contact .ct-btn {
    display: inline-flex;
    align-items: center;
    gap: 7px;
    padding: 9px 16px;
    border: 1px solid var(--line);
    border-radius: var(--radius-sm);
    background: var(--surface);
    color: var(--text);
    font: 600 13px var(--font-body);
    text-decoration: none;
    cursor: pointer;
    transition: border-color .18s ease, background .18s ease, filter .18s ease, transform .18s ease;
}
.page-contact .ct-btn:hover {
    border-color: var(--accent-line);
    background: var(--surface-2);
    transform: translateY(-1px);
}
.page-contact .ct-btn.is-primary {
    border-color: var(--accent);
    background: var(--accent);
    color: #04201D;
}
.page-contact .ct-btn.is-primary:hover {
    background: var(--accent);
    filter: brightness(1.08);
}

/* ════════════════════════════════════════════════════════════════
   Rung 3 — the roster. One panel with internal dividers rather than a
   card per person, so two, three or four contacts all fill the band
   and none is ever stranded on a row of its own.

   The 1px grid gap over a --line-soft ground draws every divider,
   including between wrapped rows, without a :first-child reset that
   breaks the moment the row wraps.
   ════════════════════════════════════════════════════════════════ */

.page-contact .ct-roster {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
    gap: 1px;
    background: var(--line-soft);
}

.page-contact .ct-person {
    display: flex;
    align-items: center;
    gap: 13px;
    padding: 17px 20px;
    min-width: 0;
    background: var(--surface);
}

.page-contact .ct-person-text { display: flex; flex-direction: column; gap: 1px; min-width: 0; }
.page-contact .ct-person-name { font-size: 13.5px; font-weight: 600; color: var(--text); }
.page-contact .ct-person-role { font-size: 12px; color: var(--muted); }

.page-contact .ct-person-mail {
    font-size: 12px;
    color: var(--accent-2);
    text-decoration: none;
    overflow-wrap: anywhere;
}
.page-contact .ct-person-mail:hover { text-decoration: underline; }

/* ════════════════════════════════════════════════════════════════
   The quiet strip — anything else the SOC published. Deliberately the
   lightest thing on the page (the ladder above is the intended path),
   but a wrapping flex row, so nothing breaks at one item or five.
   ════════════════════════════════════════════════════════════════ */

.page-contact .ct-others {
    display: flex;
    align-items: center;
    gap: 10px 26px;
    flex-wrap: wrap;
    padding: 13px 20px;
    border: 1px solid var(--line-soft);
    border-radius: var(--radius);
}

.page-contact .ct-others-label {
    flex: none;
    font-size: 11px;
    font-weight: 600;
    letter-spacing: 0.06em;
    text-transform: uppercase;
    color: var(--faint);
}

.page-contact .ct-other {
    display: inline-flex;
    align-items: center;
    gap: 9px;
    font-size: 13px;
    color: var(--muted);
    text-decoration: none;
}
.page-contact .ct-other b {
    font-weight: 600;
    font-variant-numeric: tabular-nums;
    color: var(--text);
    transition: color .15s ease;
}
.page-contact .ct-other:hover b { color: var(--accent-2); }
.page-contact .ct-other-icon { display: inline-flex; flex: none; color: var(--faint); }
.page-contact .ct-other-icon svg { width: 14px; height: 14px; }
.page-contact .ct-other-label { color: var(--muted); }

/* ════════════════════════════════════════════════════════════════
   Responsive — Bootstrap 5.3 breakpoints (see site/variables.css).
   ════════════════════════════════════════════════════════════════ */

@media (max-width: 992px) {
    .page-contact .ct-tickets { grid-template-columns: 1fr; }
}

@media (max-width: 576px) {
    .page-contact .ct-figure.is-lg { font-size: 26px; }
    .page-contact .ct-ticket-foot { align-items: flex-start; flex-direction: column; gap: 10px; }
}
