/* =============================================================================
 * The look every page shares, from v1.27.0.
 *
 * Until then the site had three: the warm paper of the front page and the
 * student pages, the dark navy glass of the teacher and admin pages, and a
 * third on the course pages. The owner chose one — the paper, navy and serif
 * the front page was rebuilt in for v1.26.0 — and this file is where it lives.
 *
 * What is here:
 *   - the palette and type as custom properties, so a page's own stylesheet
 *     names a role (--line, --muted) rather than a colour it has to keep in step
 *   - the base every page starts from: body, headings, links, form controls
 *   - `table.stack`, which turns a table into one card per row on a phone
 *
 * The header, the tab bar and the menu are drawn by js/app-nav.js, and the
 * sheets that replace the browser's prompt and confirm boxes by
 * js/app-sheet.js. Both inject their own styles against these properties, so a
 * page that loads the script gets the component without a second stylesheet.
 * ========================================================================== */

@import url('https://fonts.googleapis.com/css2?family=IBM+Plex+Mono:wght@400;500&family=IBM+Plex+Sans:wght@400;500;600;700&family=Newsreader:opsz,wght@6..72,500;6..72,600&display=swap');

:root {
    --paper: #F6F3EC;
    --paper-2: #EFEADF;
    --card: #FFFFFF;
    --ink: #16233A;
    --muted: #4A5566;
    --faint: #6B7585;
    --line: #DCD6CA;
    --navy: #1B365D;
    --navy-2: #24467A;
    --navy-soft: #E3E9F3;
    --gold: #8A5A12;
    --gold-soft: #F3E6CF;
    --good: #1F6B45;
    --good-soft: #E1F0E6;
    --warn: #8A5A12;
    --warn-soft: #F7EBD3;
    --bad: #A3322A;
    --bad-soft: #F7E1DE;
    --focus: #8A5A12;
    --serif: "Newsreader", Georgia, "Times New Roman", serif;
    --sans: "IBM Plex Sans", system-ui, -apple-system, "Segoe UI", sans-serif;
    --mono: "IBM Plex Mono", ui-monospace, SFMono-Regular, Menlo, monospace;
    --radius: 14px;
    --tap: 44px;
    /* The height of js/app-nav.js's tab bar on a phone, which anything pinned
       to the bottom of the screen has to sit above. 0 where there is no bar. */
    --tabs-h: 0px;
    /* Four page widths, from v1.28.0. There were thirteen. */
    --w-wide: 1180px;   /* dashboards, registers, the generator, the home page */
    --w-main: 920px;    /* forms and tools */
    --w-read: 720px;    /* reading */
    --w-auth: 420px;    /* sign in, create account */
    color-scheme: light;
}

* { box-sizing: border-box; }

html { -webkit-text-size-adjust: 100%; }

body {
    margin: 0;
    font-family: var(--sans);
    font-size: 15px;
    line-height: 1.5;
    color: var(--ink);
    background: var(--paper);
    min-height: 100vh;
}

h1, h2, h3 { font-family: var(--serif); font-weight: 600; color: var(--ink); text-wrap: balance; }
a { color: var(--navy); }
:focus-visible { outline: 2px solid var(--focus); outline-offset: 2px; }

input, select, textarea, button { font-family: inherit; }

/* The parts every page draws, defined once (v1.28.0) -----------------------
 *
 * Until v1.28.0 every admin page, student/student.css and teacher/teacher.css
 * each defined its own .card and .btn, and they had drifted: teacher buttons
 * were 40px tall with a 10px radius, everyone else's 44px and 12px. A page's
 * own stylesheet can still refine these; it no longer has to invent them.
 *
 * Every selector is wrapped in :where(), which weighs nothing, so any rule a
 * page already has for the same class wins without a fight.
 */
:where(.page) { max-width: var(--w-main); margin: 0 auto; padding: 0 20px 48px; }
:where(.page.wide) { max-width: var(--w-wide); }
:where(.page.read) { max-width: var(--w-read); }
:where(.page.auth) { max-width: var(--w-auth); }

:where(.page-head) { margin: 8px 0 22px; }
/* A heading with an action beside it (Admin › System's "Check again"). */
:where(.page-head.split) {
    display: flex; justify-content: space-between; align-items: flex-end; gap: 10px 16px; flex-wrap: wrap;
}
:where(.page-head h1) { font-size: 2rem; line-height: 1.15; margin: 0; }
:where(.page-head .sub, .page-head p) { color: var(--muted); margin: 6px 0 0; }

:where(.card) {
    background: var(--card); border: 1px solid var(--line);
    border-radius: var(--radius); padding: 22px; margin-bottom: 18px;
    scroll-margin-top: 80px;   /* clear of the sticky strip when jumped to */
}
:where(.card-title) { font: 600 1.25rem/1.2 var(--serif); margin: 0 0 12px; }

:where(.btn) {
    display: inline-flex; align-items: center; justify-content: center; gap: 8px;
    min-height: var(--tap); padding: 0 18px; border-radius: 12px; cursor: pointer;
    border: 1.5px solid var(--navy); background: var(--card); color: var(--navy);
    font: 600 .95rem var(--sans); text-decoration: none; white-space: nowrap;
}
:where(.btn:hover:not(:disabled)) { background: var(--navy-soft); }
:where(.btn:disabled) { opacity: .55; cursor: not-allowed; }
:where(.btn-primary, .btn.primary) { background: var(--navy); color: #fff; }
:where(.btn-primary:hover:not(:disabled), .btn.primary:hover:not(:disabled)) { background: var(--navy-2); }
:where(.btn-quiet, .btn.quiet) { border-color: var(--line); color: var(--ink); }
:where(.btn-danger, .btn.danger) { border-color: #E2B2AB; color: var(--bad); }
:where(.btn-danger:hover:not(:disabled), .btn.danger:hover:not(:disabled)) { background: var(--bad-soft); }
:where(.btn-lg) { min-height: 50px; font-size: 1rem; width: 100%; }

:where(.field) { display: grid; gap: 6px; margin-bottom: 16px; }
:where(.field > label, .field > .label) { font-size: .88rem; font-weight: 600; color: var(--muted); }
:where(.field .hint) { font-size: .82rem; color: var(--faint); font-weight: 400; }
:where(.field input[type="text"], .field input[type="email"], .field input[type="password"], .field select, .field textarea) {
    width: 100%; min-height: 48px; padding: 0 14px; font-size: 1rem; color: var(--ink);
    background: var(--card); border: 1px solid var(--line); border-radius: 12px;
}
:where(.field textarea) { padding: 12px 14px; min-height: 96px; }
:where(.field input:focus, .field select:focus, .field textarea:focus) { outline: 2px solid var(--focus); outline-offset: 1px; }

:where(.pill) { display: inline-block; padding: 2px 9px; border-radius: 999px; font-size: .78rem; font-weight: 600; white-space: nowrap; }
:where(.pill.good) { background: var(--good-soft); color: var(--good); }
:where(.pill.warn) { background: var(--warn-soft); color: var(--warn); }
:where(.pill.bad) { background: var(--bad-soft); color: var(--bad); }
:where(.pill.quiet) { background: var(--paper-2); color: var(--muted); }

:where(.alert) { border-radius: 12px; padding: 12px 16px; margin-bottom: 16px; }
:where(.alert.good) { background: var(--good-soft); border: 1px solid #BFDCC9; color: var(--good); }
:where(.alert.warn) { background: var(--warn-soft); border: 1px solid #E5CFA4; color: var(--ink); }
:where(.alert.bad) { background: var(--bad-soft); border: 1px solid #E9BDB7; color: var(--bad); }

@media (max-width: 720px) {
    :where(.page) { padding: 0 16px 40px; }
    :where(.page-head h1) { font-size: 1.6rem; }
    :where(.card) { padding: 18px 16px; }
}

/* A table that is one card per row on a phone ----------------------------
 *
 * Every staff page had tables of six to eight columns inside a box 300px wide
 * on a phone, so everything past the second column — the grade, the actions,
 * Review and Pass/Fail — sat off the right edge. Under 720px a table marked
 * `stack` drops its header and lays each row out as a card; each cell names
 * itself from its `data-label`, which the page's renderer writes.
 *
 * A cell marked `data-role="title"` leads the card in bold with no label, and
 * `data-role="actions"` goes last with its buttons full width.
 */
@media (max-width: 720px) {
    table.stack, table.stack tbody, table.stack tr, table.stack td { display: block; width: 100%; }
    table.stack thead { display: none; }
    table.stack tr {
        background: var(--card);
        border: 1px solid var(--line);
        border-radius: 12px;
        padding: 12px 14px;
        margin-bottom: 10px;
    }
    table.stack td {
        border: 0 !important;
        padding: 3px 0 !important;
        text-align: left !important;
        white-space: normal !important;
        display: flex;
        gap: 10px;
        align-items: baseline;
        min-width: 0;
    }
    table.stack td[data-label]::before {
        content: attr(data-label);
        flex: 0 0 38%;
        font-size: .78rem;
        color: var(--muted);
        font-family: var(--sans);
    }
    table.stack td[data-label=""]::before,
    table.stack td[data-role]::before { content: none; }
    table.stack td[data-role="title"] { display: block; font-weight: 600; font-size: 1rem; padding-bottom: 6px !important; }
    table.stack td[data-role="actions"] {
        display: flex; flex-wrap: wrap; gap: 8px; padding-top: 10px !important;
    }
    table.stack td[data-role="actions"] > * { flex: 1 1 auto; min-height: var(--tap); }
    table.stack td.empty { display: block; text-align: center !important; }
    table.stack tr.warn { border-left: 4px solid var(--bad); }
    .tablewrap:has(> table.stack) { overflow: visible; }
}

/* On a phone, the bug button and the version pill stay out of the way of the
   tab bar rather than sitting on it. The owner kept the 🐞 button where it is;
   it simply moves up by the height of the bar. */
@media (max-width: 720px) {
    body.has-tabs { --tabs-h: 64px; padding-bottom: calc(var(--tabs-h) + 24px + env(safe-area-inset-bottom, 0px)); }
    body.has-tabs #bugReportButton { bottom: calc(var(--tabs-h) + 14px + env(safe-area-inset-bottom, 0px)) !important; right: 14px !important; }
    body.has-tabs #versionPill { display: none !important; }
}

@media print {
    .appnav, .appnav-tabs, .appnav-drawer, #appSheet { display: none !important; }
    body { background: #fff; padding-bottom: 0; }
}
