:root {
   --bg:#fafaf9; 
   --fg:#1c1917; 
   --muted:#78716c; 
   --line:#e7e5e4; 
   --accent:#1f7a4d;
}

* { 
   box-sizing: border-box; 
}

body { 
   margin:0; 
   font:15px/1.5 -apple-system, "Segoe UI", system-ui, sans-serif;
   background:var(--bg); 
   color:var(--fg);
   height: 100vh;
   overflow: hidden;
}

app-header, app-menu, app-content {
   display: block;
}

app-header {
   position: fixed;
   top: 0;
   left: 0;
   right: 0;
   height: 71px;
   background: var(--bg);
   z-index: 20;
}

app-shell {
   display: block;
   height: 100vh;
   overflow: hidden;
}

.shell {
   display: flex;
   align-items: flex-start;
   height: 100vh;
}

app-menu {
   position: fixed;
   top: 71px;
   left: 0;
   width: 240px;
   height: calc(100vh - 60px);
   overflow-y: auto;
   z-index: 10;
}

app-content {
   margin-top: 60px;
   margin-left: 240px;
   flex: 1;
   height: calc(100vh - 60px);
   overflow-y: auto;
}

main {
   max-width: 640px;
   margin: 0 auto;
   padding:48px 24px; 
}

h1 { 
   font-size: 28px;
   font-weight: 700;
   color: #1a1a1a;
   margin:0 0 20px; 
   letter-spacing:-0.01em; 
}

.sub { 
   color:var(--muted); 
   font-size:14px; 
   margin:0 0 32px; 
}

/* ---------- surfaces ---------- */
.card { 
   background:#fff; 
   border:1px solid var(--line); 
   border-radius:8px; 
   padding:20px; 
   margin-bottom:16px; 
}

.row { 
   display:flex; 
   align-items:center; 
   justify-content:space-between; 
   gap:12px; 
}

.row + .row { 
   margin-top:12px; 
   padding-top:12px; 
   border-top:1px solid var(--line); 
}

/* ---------- form controls ---------- */
label {
   display:block; 
   font-size:13px; 
   color:var(--muted); 
   margin-bottom:6px; 
}

input { 
   width:100%; 
   padding:8px 10px; 
   border:1px solid var(--line); 
   border-radius:6px; 
   font:inherit; 
}

button { 
   padding:8px 14px; 
   border:0; 
   border-radius:6px; 
   background:var(--accent); 
   color:#fff;
   font:inherit; 
   font-weight:500; 
   cursor:pointer; 
}

button:disabled { 
   opacity:.5; 
   cursor:default; 
}

button.ghost { 
   background:transparent; 
   color:var(--muted); 
   border:1px solid var(--line); 
}

/* ---------- messages / status text ---------- */
.msg { 
   font-size:13px; 
   margin-top:10px; 
   min-height:18px; 
}

.msg.err { 
   color:#b91c1c; 
}

.msg.ok {
   color:#15803d;
}

.email { 
   font-variant-numeric:tabular-nums; 
}

.when { 
   color:var(--muted); font-size:13px; 
}

.empty { 
   color:var(--muted); font-size:14px; 
}

[hidden] { 
   display:none !important; 
}

/* Class card: who teaches it. Muted variant marks the fallback to the creator,
   so a name shown under a class nobody is enrolled to teach does not read as an
   assertion that they teach it. */
.class-owner { font-size: 12px; color: #4b5563; margin-top: 2px; }
.class-owner.muted { color: #9ca3af; font-style: italic; }

/* ---- Convert view ---------------------------------------------------------
   Scoped cv-* names so moving the form out of its own page cannot collide with
   the portal's existing form styling. */
.cv-card { background:#fff; border:1px solid #d6dae2; border-radius:10px;
           padding:20px 22px; margin-bottom:18px; max-width:760px; }
.cv-tabs { display:flex; gap:8px; margin-bottom:16px; }
.cv-tab { padding:8px 16px; border:1px solid #d6dae2; background:#fff;
          border-radius:8px; cursor:pointer; font-size:14px; }
.cv-tab.on { background:#1F6FEB; color:#fff; border-color:#1F6FEB; }
.cv-card label { display:block; font-size:13px; font-weight:600; margin:12px 0 4px; }
.cv-card .hint { font-weight:400; color:#7a828f; }
.cv-card input[type=text], .cv-card input[type=number],
.cv-card select, .cv-card input[type=file] {
   width:100%; padding:9px 10px; border:1px solid #d6dae2; border-radius:7px;
   font-size:14px; background:#fff; }
.cv-row { display:flex; gap:14px; } .cv-row > div { flex:1; }
.cv-check { display:flex; align-items:flex-start; gap:8px; margin-top:14px;
            font-size:14px; font-weight:600; }
.cv-check input { width:auto; margin-top:3px; }
.cv-go { margin-top:18px; background:#43C59E; color:#08301f; border:none;
         border-radius:8px; padding:11px 20px; font-size:15px; font-weight:700; cursor:pointer; }
.cv-go:disabled { opacity:.5; cursor:default; }
.cv-msg { margin-top:14px; font-size:14px; padding:10px 12px; border-radius:8px; display:none; }
.cv-msg.show { display:block; }
.cv-msg.ok { background:#e6f7f0; color:#0b6b4b; }
.cv-msg.err { background:#fdecec; color:#a12020; }
/* The upload SUCCEEDED but the stored file measurably cannot do something it was
   probably meant to do: an inert blackout, a visible answer sheet, a converter
   whose report disagrees with the bytes it produced. Not an error (the assignment
   exists and grades) and not plain success either, and a warning printed in green
   at the end of a success line gets read as decoration. Added 2026-09-02 with
   assignment_build.capabilities.
   ⚠️ It is `.cv-msg.warn`, not `.msg.warn`: this component's msg() writes
   `class="cv-msg show <kind>"`, and the two message systems are separate. */
.cv-msg.warn { background:#fdf6e3; color:#8a6100; }
/* The per-file warning row under a batch result. Text, not a badge, because the
   warnings are sentences a professor has to read and act on.
   📌 Found while writing this and deliberately NOT fixed here: `.pill`, used by
   the batch status column since it was written, has no rule in any stylesheet.
   Those badges have always rendered as plain text. It degrades harmlessly, so it
   is a separate cosmetic fix rather than something to bundle into a data change. */
.cv-row-warn { font-size:13px; color:#8a6100; background:#fdf6e3; padding:6px 10px; }

/* ---- Export Grades --------------------------------------------------------- */
.ex-bar { display:flex; align-items:flex-end; gap:16px; margin:12px 0 6px; }
.ex-bar label { font-size:13px; font-weight:600; display:flex; flex-direction:column; gap:4px; }
.ex-bar select { padding:8px 10px; border:1px solid #d6dae2; border-radius:7px;
                 font-size:14px; background:#fff; min-width:280px; }
.ex-btn { background:#43C59E; color:#08301f; border:none; border-radius:8px;
          padding:9px 18px; font-size:14px; font-weight:700; cursor:pointer; }
.ex-btn:disabled { opacity:.45; cursor:default; }
.ex-note { font-size:12px; color:#6b7280; margin:4px 0 14px; }
.ex-status { font-size:14px; color:#4b5563; margin:10px 0; }
.ex-status.err { color:#a12020; }
.ex-table-wrap { overflow:auto; border:1px solid #e5e7eb; border-radius:8px; background:#fff; }
.ex-table { width:100%; border-collapse:collapse; font-size:13px; }
.ex-table th, .ex-table td { text-align:left; padding:7px 10px; border-bottom:1px solid #eef0f3; }
.ex-table th { background:#f9fafb; font-weight:600; position:sticky; top:0; }
.ex-table td.muted { color:#9ca3af; }

/* ---- Checkbox dropdown (Export Grades filters) ------------------------------
   A button that opens a scrollable checkbox list. Not a <select multiple>: that
   needs ctrl-click for a second item and offers no "all". */
.pick { position:relative; display:inline-block; }
.pick-btn { padding:8px 12px; border:1px solid #d6dae2; border-radius:7px;
            background:#fff; font-size:14px; cursor:pointer; min-width:170px;
            text-align:left; }
.pick-menu { position:absolute; z-index:40; top:calc(100% + 4px); left:0;
             min-width:280px; max-width:420px; background:#fff;
             border:1px solid #d6dae2; border-radius:8px;
             box-shadow:0 6px 20px rgba(16,24,40,.12); }
.pick-actions { display:flex; gap:8px; padding:8px 10px; border-bottom:1px solid #eef0f3; }
.pick-actions button { font-size:12px; padding:4px 10px; border:1px solid #d6dae2;
                       background:#f9fafb; border-radius:6px; cursor:pointer; }
.pick-list { max-height:260px; overflow:auto; padding:6px 0; }
.pick-row { display:flex; align-items:center; gap:8px; padding:5px 12px;
            font-size:13px; font-weight:400; margin:0; cursor:pointer; }
.pick-row:hover { background:#f6f8fa; }
.pick-row input { width:auto; margin:0; }
.pick-note { margin-left:auto; font-size:11px; color:#6b7280;
             background:#f3f4f6; padding:1px 7px; border-radius:10px; }

/* Professor filter on the Classes view. Matters most for admins, who see every
   class on the platform including other people's dev and demo classes. */
.classes-actions { display:flex; align-items:flex-end; gap:14px; }
.owner-filter { font-size:13px; font-weight:600; display:flex; flex-direction:column; gap:4px; }
.owner-filter select { padding:8px 10px; border:1px solid #d6dae2; border-radius:7px;
                       font-size:14px; background:#fff; min-width:200px; font-weight:400; }
