/* Curriculum planner (/curriculum) -- self-contained page, own tiny CSS file
   on top of main.css's shared primitives (.btn/.form-group/.form-row/
   .settings-section/.settings-card/.empty-state/.hidden/.toast-container),
   same convention as public/css/grades.css. Classes prefixed cp- throughout.

   --cp-accent is this page's own identity color (violet) -- distinct from
   Grades' blue and from the user's general theme --accent, so the page
   reads as its own product rather than Grades-with-different-copy. Used
   for the category-card border, progress fill, and the small icon marks. */
:root { --cp-accent: #8B5CF6; }
:root[data-theme="dark"] { --cp-accent: #A78BFA; }

#cp-loading {
  position: fixed; inset: 0; display: flex; flex-direction: column;
  align-items: center; justify-content: center; gap: 1.625rem;
  background: var(--bg);
}

/* Row layout: sidebar (Grades' own, reused here) + this page's own content
   column, same shell shape as #ng-app in grades.css. */
#cp-app { display: flex; height: 100vh; height: 100dvh; overflow: hidden; }
.ng-content { flex: 1; min-width: 0; display: flex; flex-direction: column; overflow: hidden; }

.cp-wordmark-hero { font-weight: 800; letter-spacing: -1.5px; color: #6D28D9; font-size: 2.625rem; }
:root[data-theme="dark"] .cp-wordmark-hero { color: #C4A5FF; }
/* Header's own copy is smaller than the loading screen's -- same
   proportions Grades uses for its header vs. loading-screen wordmark. */
.cp-header .cp-wordmark-hero { font-size: 1.625rem; }

/* Full icon+wordmark lockup (not just plain text) -- same structural
   pattern as .grades-logo-lockup/.grades-logomark in main.css. */
.cp-logo-lockup { display: flex; align-items: center; gap: 0.4em; }

/* The cap icon here is the exact sidebar curriculum mark (same chip shape,
   white mortarboard glyph -- the sidebar-portal-mark SVG is copied into
   the header and loading screen verbatim) so the icon renders identically
   everywhere in the app. This modifier supplies the violet chip background
   that .sidebar-curriculum-link .sidebar-portal-mark in main.css gives the
   sidebar's copy of the mark; copied verbatim so the two match pixel for
   pixel. */
.sidebar-portal-mark--curriculum {
  background:
    radial-gradient(circle at 30% 22%, rgba(255,255,255,0.5) 0%, rgba(255,255,255,0.08) 55%, rgba(255,255,255,0) 100%),
    linear-gradient(135deg, #D9C6FF 0%, #8B5CF6 55%, #4C1D95 100%);
}

/* Flex row (hamburger, actions pushed right via margin-left:auto) with the
   wordmark absolutely centered on top of it -- NOT a 1fr/auto/1fr grid: a
   bare 1fr column claims its full proportional share of the row regardless
   of its content's actual width, so a lone hamburger button still got a
   track as wide as the whole actions cluster, leaving a huge dead gap and
   squashing everything toward the edges. Absolute centering is immune to
   that since it's positioned purely off the header's own width. */
.cp-header {
  display: flex; align-items: center; gap: 1rem;
  padding: 0.75rem 1.25rem; border-bottom: 1px solid var(--border);
  flex-shrink: 0; position: relative;
}
.cp-logo-lockup {
  flex-shrink: 0; position: absolute; left: 50%; transform: translateX(-50%);
  transition: transform 0.2s ease;
}
.cp-header-actions {
  margin-left: auto; display: flex; align-items: center; gap: 0.75rem;
}
.cp-header .logo { display: flex; align-items: center; gap: 0.5rem; font-weight: 800; color: var(--text); }

@keyframes cpFadeIn { from { opacity: 0; } to { opacity: 1; } }
.cp-fade-in { animation: cpFadeIn 0.2s ease; }

.cp-main {
  flex: 1; overflow-y: auto; padding: 1.25rem 1.25rem 3rem;
  max-width: 42rem; width: 100%; margin: 0 auto;
}

/* Overall progress summary, above the category cards */
.cp-summary {
  display: flex; align-items: center; justify-content: space-between; gap: 1rem;
  padding: 0.875rem 1.125rem; border-radius: var(--radius); background: var(--surface2);
  margin-bottom: 1.125rem; font-size: 0.8125rem; font-weight: 600; color: var(--text);
}

.cp-empty {
  display: flex; flex-direction: column; align-items: flex-start; gap: 0.5rem;
  padding: 1.125rem 1.25rem; border-radius: var(--radius); border: 1px dashed var(--border2);
  background: var(--surface2);
}
.cp-empty-icon {
  width: 2.25rem; height: 2.25rem; border-radius: 0.625rem; flex-shrink: 0;
  display: flex; align-items: center; justify-content: center; margin-bottom: 0.25rem;
  background: color-mix(in srgb, var(--cp-accent) 16%, transparent);
  color: var(--cp-accent);
}
.cp-empty-title { font-size: 0.9375rem; font-weight: 700; color: var(--text); }
.cp-empty-actions { display: flex; gap: 0.5rem; margin-top: 0.375rem; flex-wrap: wrap; }
/* Its one section is a :last-child (margin 0), so the gap to School & major
   has to come from the wrapper. */
#cp-el-picker { margin-bottom: 1.75rem; }
.cp-hint { font-size: 0.71875rem; color: var(--text-dim); margin-top: 0.375rem; line-height: 1.4; }

/* Country/year summary card: what it currently says on the left, the control
   that changes it on the right, which is where every other row in the app
   keeps its action. The summary takes the slack so the button lands on the
   card's edge; margin-top is reset since the two sit side by side rather
   than in the usual .cp-hint-below-content stack. */
.cp-hs-country-row { display: flex; align-items: center; gap: 0.75rem; }
.cp-hs-country-row .cp-hint { margin-top: 0; flex: 1; min-width: 0; }
.cp-hs-country-row .btn { flex-shrink: 0; }

.cp-draft-actions { display: flex; gap: 0.5rem; margin-top: 0.75rem; }
.cp-draft-row {
  display: flex; align-items: center; gap: 0.5rem; padding: 0.5rem 0;
  border-bottom: 1px solid var(--border);
}
.cp-draft-row:first-of-type { border-top: 1px solid var(--border); }
.cp-draft-row-name { flex: 1; font-size: 0.8125rem; color: var(--text); display: flex; align-items: center; gap: 0.4375rem; }
.cp-draft-row input[type="number"] { width: 5rem; }
.cp-draft-sources { display: inline; }
.cp-draft-sources a { color: var(--cp-accent); }
.cp-draft-row-remove { background: none; border: none; color: var(--text-dim); cursor: pointer; padding: 0.125rem; }
.cp-draft-row-remove:hover { color: var(--red); }

/* Where the courses come from: one quiet row, no card. When connected, the
   system and when it last synced; the actions sit beside it. */
.cp-sources {
  display: flex; align-items: center; gap: 0.75rem; flex-wrap: wrap;
  margin-bottom: 1.125rem;
}
.cp-sources-status { flex: 1; min-width: 0; display: flex; flex-wrap: wrap; gap: 0.375rem 1rem; }
.cp-sources-status:empty { display: none; }
.cp-sources-actions { display: flex; gap: 0.5rem; flex-wrap: wrap; }
.cp-source { display: inline-flex; align-items: center; gap: 0.4375rem; font-size: 0.8125rem; min-width: 0; }
.cp-source-dot { width: 0.4375rem; height: 0.4375rem; border-radius: 50%; background: var(--green); flex-shrink: 0; }
.cp-source-dot-error { background: var(--red); }
.cp-source-name { font-weight: 700; color: var(--text); white-space: nowrap; }
.cp-source-when { color: var(--text-dim); font-size: 0.75rem; white-space: nowrap; }
.cp-source-when-error { color: var(--red); }
#cp-transcript-review { margin-bottom: 1.25rem; }
.cp-transcript-status {
  font-size: 0.6875rem; font-weight: 600; border-radius: 62.4375rem; padding: 0.125rem 0.5rem; white-space: nowrap;
  color: var(--green); background: color-mix(in srgb, var(--green) 12%, transparent);
}
.cp-transcript-status-in_progress { color: var(--text-muted); background: var(--surface2); }
.cp-transcript-status-failed { color: var(--red); background: color-mix(in srgb, var(--red) 12%, transparent); }

/* Draft and transcript rows: the name, with a quiet second line under it. */
.cp-draft-row-title { display: flex; flex-direction: column; gap: 0.125rem; min-width: 0; }
.cp-draft-row-courses { font-size: 0.71875rem; color: var(--text-dim); }

/* Category cards */
.cp-category-card {
  border: 1px solid var(--border); border-left: 0.1875rem solid var(--cp-accent);
  border-radius: var(--radius); padding: 0.875rem 1rem;
  margin-bottom: 0.875rem; background: var(--surface);
  transition: box-shadow 0.15s var(--ease), transform 0.15s var(--ease);
}
.cp-category-card:hover { box-shadow: var(--shadow-sm); transform: translateY(-1px); }
.cp-category-head { display: flex; align-items: center; gap: 0.375rem; margin-bottom: 0.5rem; }
.cp-category-name { font-weight: 700; font-size: 0.875rem; color: var(--text); flex: 1; }
.cp-category-progress-label { font-size: 0.75rem; color: var(--text-muted); white-space: nowrap; }
.cp-category-move, .cp-category-edit, .cp-category-delete {
  background: none; border: none; color: var(--text-dim); cursor: pointer; padding: 0.125rem; flex-shrink: 0;
  display: flex; align-items: center;
}
.cp-category-move:hover, .cp-category-edit:hover { color: var(--cp-accent); }
.cp-category-delete:hover { color: var(--red); }
.cp-category-move:disabled { opacity: 0.3; cursor: default; }
.cp-category-move:disabled:hover { color: var(--text-dim); }

.cp-progress-track {
  height: 0.5rem; border-radius: 62.4375rem; background: var(--surface2); overflow: hidden; margin-bottom: 0.625rem;
}
.cp-progress-fill {
  height: 100%; border-radius: 62.4375rem;
  background: linear-gradient(90deg, var(--cp-accent), color-mix(in srgb, var(--cp-accent) 70%, white));
  transition: width 0.3s var(--ease);
}

.cp-course-row {
  display: flex; align-items: center; gap: 0.5rem; padding: 0.4375rem 0;
  border-top: 1px solid var(--border); font-size: 0.8125rem;
  border-radius: 0.375rem;
}
.cp-course-row:first-of-type { border-top: none; }
.cp-course-row:hover { background: var(--surface2); }
.cp-course-status {
  background: none; border: 1.5px solid var(--border2); border-radius: 0.3125rem; width: 1.125rem; height: 1.125rem;
  flex-shrink: 0; cursor: pointer; padding: 0; display: flex; align-items: center; justify-content: center;
}
.cp-course-status svg { width: 0.625rem; height: 0.625rem; opacity: 0; }
.cp-course-status.completed { background: var(--cp-accent); border-color: var(--cp-accent); }
.cp-course-status.completed svg { opacity: 1; color: #fff; }
/* Being taken now: the box half-filled, the same violet as done. */
.cp-course-status.in-progress {
  border-color: var(--cp-accent);
  background: linear-gradient(135deg, color-mix(in srgb, var(--cp-accent) 45%, transparent) 50%, transparent 50%);
}
.cp-course-grade {
  font-size: 0.6875rem; font-weight: 700; color: var(--cp-accent); white-space: nowrap;
  background: color-mix(in srgb, var(--cp-accent) 12%, transparent); border-radius: 62.4375rem; padding: 0.09375rem 0.5rem;
}
.cp-edit-row select { width: auto; flex: 1; min-width: 7rem; }
.cp-course-name { flex: 1; color: var(--text); }
.cp-course-name.completed { text-decoration: line-through; color: var(--text-muted); }
.cp-course-credits { color: var(--text-muted); font-weight: 600; white-space: nowrap; }
.cp-course-term {
  color: var(--text-muted); font-size: 0.6875rem; white-space: nowrap;
  background: var(--surface2); border-radius: 62.4375rem; padding: 0.09375rem 0.5rem;
}
.cp-course-move, .cp-course-edit, .cp-course-delete {
  background: none; border: none; color: var(--text-dim); cursor: pointer; padding: 0.125rem; flex-shrink: 0;
  display: flex; align-items: center;
}
.cp-course-move:hover, .cp-course-edit:hover { color: var(--cp-accent); }
.cp-course-delete:hover { color: var(--red); }
.cp-course-move:disabled { opacity: 0.3; cursor: default; }
.cp-course-move:disabled:hover { color: var(--text-dim); }

.cp-inline-form { display: flex; gap: 0.5rem; margin-top: 0.625rem; flex-wrap: wrap; }
.cp-inline-form .cp-edit-cancel { align-self: center; }
/* "+ Add course": quiet until wanted; the form opens in its place. */
.cp-add-course-toggle {
  background: none; border: none; cursor: pointer; padding: 0.5rem 0 0.125rem;
  font: inherit; font-size: 0.78125rem; font-weight: 600; color: var(--text-dim);
}
.cp-add-course-toggle:hover { color: var(--cp-accent); }
.cp-inline-form input, .cp-inline-form select { width: auto; flex: 1; min-width: 7.5rem; }

/* Edit-in-place mode (category head / course row swap to this) */
.cp-edit-row { display: flex; align-items: center; gap: 0.4375rem; flex: 1; flex-wrap: wrap; }
.cp-edit-row input[type="text"] { flex: 2; min-width: 6rem; }
.cp-edit-row input[type="number"] { width: 4.5rem; }
.cp-edit-save, .cp-edit-cancel {
  background: none; border: none; cursor: pointer; padding: 0.125rem; flex-shrink: 0;
  display: flex; align-items: center;
}
/* CP_ICON_CHECK (also used by .cp-course-status, sized separately there)
   carries no width/height of its own -- unsized here it would render at
   the SVG spec's 300x150 default intrinsic size. */
.cp-edit-save svg { width: 0.75rem; height: 0.75rem; }
.cp-edit-save { color: var(--cp-accent); }
.cp-edit-cancel { color: var(--text-dim); }
.cp-edit-cancel:hover { color: var(--red); }

/* School combobox -- same positioning shape as grades.css's .ng-school-*,
   duplicated per this page's self-contained convention. */
.cp-school-combobox { position: relative; }
.cp-school-results {
  position: absolute; top: calc(100% + 0.25rem); left: 0; right: 0;
  background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius);
  box-shadow: var(--shadow);
  max-height: 13.75rem; overflow-y: auto; z-index: 20;
}
.cp-school-result {
  padding: 0.5rem 0.75rem; cursor: pointer; font-size: 0.8125rem;
  display: flex; align-items: baseline; gap: 0.375rem;
}
.cp-school-result-country { color: var(--text-muted); font-size: 0.71875rem; }
.cp-school-result:hover, .cp-school-result.active { background: var(--surface2); }
.cp-school-result-empty { padding: 0.5rem 0.75rem; font-size: 0.8125rem; color: var(--text-muted); }

/* High-school branch: country picker, Italy credito scolastico calculator */
.cp-checkbox-row {
  display: flex; align-items: center; gap: 0.5rem; font-size: 0.8125rem;
  color: var(--text); margin: 0.75rem 0; cursor: pointer;
}
.cp-checkbox-row input { width: auto; margin: 0; }

.cp-hs-result {
  margin-top: 0.75rem; border: 1px solid var(--border); border-radius: var(--radius);
  background: var(--surface); overflow: hidden;
}
.cp-hs-result-row {
  display: flex; align-items: center; justify-content: space-between; gap: 1rem;
  padding: 0.5rem 0.875rem; font-size: 0.8125rem; color: var(--text);
  border-top: 1px solid var(--border);
}
.cp-hs-result-row:first-child { border-top: none; }
.cp-hs-result-value { font-weight: 700; color: var(--cp-accent); white-space: nowrap; }
.cp-hs-result-band { font-weight: 500; color: var(--text-muted); }
.cp-hs-result-total { background: var(--surface2); font-weight: 700; }
.cp-hs-result-total .cp-hs-result-value { font-size: 0.9375rem; }
.cp-hs-year-hint { font-size: 0.6875rem; color: var(--text-dim); margin-top: 0.25rem; display: block; }

/* Loading screen: grades uses 32 viewBox at 46px; our 20 viewBox must render
   at 28.75px (46 × 20/32) to match visual proportion. Header already 28px. */
#cp-loading .sidebar-portal-mark--curriculum { width: 2.875rem; height: 2.875rem; overflow: visible; }
#cp-loading .sidebar-portal-mark--curriculum svg { width: 1.7969rem; height: 1.7969rem; }
.cp-header .sidebar-portal-mark--curriculum { width: 1.75rem; height: 1.75rem; overflow: visible; }
/* Same 20/32 viewBox-to-grades-logomark scaling as the loading screen's own
   svg override above (28.75 = 46 × 20/32) -- without this, main.css's
   generic `.sidebar-portal-mark svg` rule (sized for the tiny 23px sidebar
   chip) silently clamped this 28px header badge's glyph down to 15px,
   making the cap look undersized relative to its chip. */
.cp-header .sidebar-portal-mark--curriculum svg { width: 1.0938rem; height: 1.0938rem; }

/* Loading-screen wordmark — same pulse + size as grades (grades.css .ng-loading-logo). */
.ng-loading-logo {
  display: flex;
  font-size: 2.625rem;
  letter-spacing: -1.5px;
  animation: pulse 1.5s ease-in-out infinite;
}

/* ── Chrono, embedded: same .zeno-* classes/styles as zenow's own panel
   (main.css), just re-scoped from #screen-app.chrono-open to
   #cp-app.chrono-open since this is a different page shell. ──────────── */
#cp-app.chrono-open .zeno-panel { flex-basis: var(--zeno-w, 21.25rem); }
#cp-app.chrono-open .zeno-panel-inner { box-shadow: -0.25rem 0 1.5rem rgba(0,0,0,0.06); }
#cp-app.chrono-open #cp-btn-chrono { display: none; }
#cp-app.chrono-open.chrono-max .zeno-panel-inner { box-shadow: none; }

@media (max-width: 768px) {
  #cp-app.chrono-open .zeno-panel { width: 100%; transform: translateX(0); }
  #cp-app.chrono-open .zeno-panel-inner { box-shadow: none; }
  #cp-app.chrono-open #cp-chrono-backdrop { opacity: 1; pointer-events: auto; }
}

/* Quick Ask (main.css's .chrono-quick-bar) is a fixed-position overlay
   pinned to #cp-btn-chrono's right edge. The wordmark never moves for it: the bar
   is sized to the room beside the wordmark (positionChronoQuickBarNG), and
   only where there is too little does it cover the wordmark, which then
   fades. Desktop-only: on mobile the bar docks to the bottom of the screen. */
@media (min-width: 769px) {
  #cp-app.chrono-quick-open.chrono-quick-covers .cp-logo-lockup { opacity: 0; transition: opacity 0.2s ease; }
}

/* Phones: same header rhythm as zenow's .topbar and Grades' .ng-header --
   hamburger 8px from the edge, 36px controls, 0.5rem padding -- and a
   wordmark small enough to stay clear of the Chrono/exit buttons. */
@media (max-width: 480px) {
  /* A course on a phone: its name gets the whole first line, and what is
     known about it (grade, credits, term) and its controls share a second,
     lined up under the name. */
  .cp-course-row { flex-wrap: wrap; row-gap: 0.25rem; }
  .cp-course-name { flex: 1 1 calc(100% - 2rem); }
  .cp-course-row > .cp-course-grade,
  .cp-course-row > .cp-course-credits { margin-left: 1.625rem; }
  .cp-course-row > .cp-course-grade + .cp-course-credits { margin-left: 0; }
  .cp-course-row > .cp-course-move[data-action="move-course-up"] { margin-left: auto; }
  .cp-header { padding: 0.5rem; gap: 0.25rem; }
  .cp-header .cp-wordmark-hero { font-size: 1.25rem; }
}

/* ── High school: your classes (curriculum.js, models/classes.js) ──
   Grouped by term, oldest first, then the years planned ahead. A class is
   two quiet lines -- its name, and under it the level, credits and the
   requirement it counts toward -- with the grade on the right; a tap opens
   what can be changed. Room to breathe over density: this is a record. */
.cp-classes { margin: 2.5rem 0 1rem; display: flex; flex-direction: column; gap: 1.25rem; }
.cp-classes-head { display: flex; align-items: flex-end; justify-content: space-between; gap: 1.25rem; }
.cp-classes-head .settings-section-title { margin: 0 0 0.375rem; padding: 0; font-size: 1.25rem; font-weight: 700; text-transform: none; letter-spacing: -0.015em; color: var(--text); }
.cp-classes-lede { margin: 0; font-size: 0.875rem; line-height: 1.55; color: var(--text-muted); max-width: 36rem; }
.cp-classes-sort { flex-shrink: 0; }
.cp-classes-empty { margin: 0; padding: 1.5rem 1.25rem; border-radius: 1rem; background: var(--surface2); font-size: 0.875rem; line-height: 1.55; color: var(--text-muted); text-align: center; }

.cp-class-reqs { display: grid; grid-template-columns: repeat(auto-fill, minmax(12rem, 1fr)); gap: 0.75rem; }
.cp-class-reqchip { padding: 0.875rem 1rem; border-radius: 1rem; border: 1px solid var(--border); background: var(--surface); display: flex; flex-direction: column; gap: 0.5rem; }
.cp-class-reqchip-top { display: flex; align-items: baseline; justify-content: space-between; gap: 0.75rem; font-size: 0.8125rem; font-weight: 600; color: var(--text); min-width: 0; }
.cp-class-reqchip-top span { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cp-class-reqchip-top b { flex-shrink: 0; font-variant-numeric: tabular-nums; color: var(--text-muted); font-weight: 700; }
.cp-class-reqchip.is-met .cp-class-reqchip-top b { color: var(--cp-accent); }
.cp-class-reqbar { position: relative; display: flex; height: 0.375rem; border-radius: 62.4375rem; background: var(--surface2); overflow: hidden; }
.cp-class-reqbar i { display: block; height: 100%; background: var(--cp-accent); transition: width .5s var(--ease); }
.cp-class-reqbar i.is-now { background: repeating-linear-gradient(135deg, color-mix(in srgb, var(--cp-accent) 55%, transparent) 0 4px, color-mix(in srgb, var(--cp-accent) 25%, transparent) 4px 8px); }
.cp-class-reqchip small { font-size: 0.75rem; color: var(--text-muted); }

.cp-class-group { border: 1px solid var(--border); border-radius: 1.25rem; background: var(--surface); padding: 0.5rem 0.625rem 0.625rem; }
.cp-class-group-head { display: flex; align-items: center; gap: 0.625rem; padding: 0.875rem 0.875rem 0.625rem; }
.cp-class-group-name { font-size: 1rem; font-weight: 700; letter-spacing: -0.01em; color: var(--text); min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cp-class-group-head em { flex-shrink: 0; font-style: normal; font-size: 0.6875rem; font-weight: 600; letter-spacing: 0.02em; padding: 0.1875rem 0.5625rem; border-radius: 62.4375rem; background: var(--surface2); color: var(--text-muted); }
.cp-class-group.is-current .cp-class-group-head em { color: var(--cp-accent); background: color-mix(in srgb, var(--cp-accent) 12%, transparent); }
.cp-class-group-sum { flex-shrink: 0; margin-left: auto; font-size: 0.8125rem; font-weight: 600; color: var(--text-muted); font-variant-numeric: tabular-nums; }
.cp-class-group.is-planned { border-style: dashed; background: transparent; }

/* A row: rounded on its own, separated by a hairline inset past the dot. */
.cp-class { position: relative; display: flex; align-items: center; gap: 0.875rem; width: 100%; min-height: 3.5rem; padding: 0.75rem 0.875rem; box-sizing: border-box;
  border: 0; border-radius: 0.875rem; background: none; font: inherit; color: var(--text); text-align: left; min-width: 0; transition: background .15s; }
.cp-class + .cp-class::before, .cp-class-open + .cp-class::before, .cp-class + .cp-class-open::before { content: ''; position: absolute; top: 0; left: 2.25rem; right: 0.875rem; height: 1px; background: var(--border); }
.cp-class-open { position: relative; }
.cp-class.is-editable { cursor: pointer; }
.cp-class.is-editable:hover, .cp-class.is-editable:focus-visible { background: var(--surface2); outline: none; }
.cp-class.is-editable:hover + .cp-class::before, .cp-class.is-editable:hover + .cp-class-open::before, .cp-class-open + .cp-class::before { opacity: 0; }
.cp-class.is-editable:focus-visible { box-shadow: 0 0 0 2px color-mix(in srgb, var(--cp-accent) 45%, transparent); }
.cp-class-dot { flex-shrink: 0; width: 0.5rem; height: 0.5rem; border-radius: 50%; background: var(--c); box-shadow: 0 0 0 3px color-mix(in srgb, var(--c) 18%, transparent); }
.cp-class.is-planned .cp-class-dot { background: transparent; box-shadow: inset 0 0 0 1.5px var(--border2); }
.cp-class-main { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 0.3125rem; }
.cp-class-name { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; font-size: 0.9375rem; font-weight: 600; line-height: 1.3; transition: color .15s; }
.cp-class.is-taken .cp-class-name { color: var(--text-muted); font-weight: 500; }
.cp-class-meta { display: flex; flex-wrap: wrap; align-items: center; gap: 0.375rem 0.5rem; min-width: 0; font-size: 0.75rem; color: var(--text-muted); }
.cp-class-level { flex-shrink: 0; font-size: 0.6875rem; font-weight: 700; letter-spacing: 0.02em; padding: 0.125rem 0.5rem; border-radius: 62.4375rem; color: var(--cp-accent); background: color-mix(in srgb, var(--cp-accent) 12%, transparent); }
.cp-class-credits { flex-shrink: 0; font-variant-numeric: tabular-nums; }
.cp-class-req { min-width: 0; max-width: 100%; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cp-class-credits + .cp-class-req { margin-left: 0.625rem; }
.cp-class-req.is-none { color: var(--text-dim); font-style: italic; }
.cp-class-grade { flex-shrink: 0; min-width: 2.75rem; padding: 0.375rem 0.625rem; border-radius: 0.625rem; box-sizing: border-box; text-align: center;
  font-size: 0.9375rem; font-weight: 700; color: var(--text); background: var(--surface2); font-variant-numeric: tabular-nums; }
.cp-class.is-taken .cp-class-grade { background: none; color: var(--text-muted); }
.cp-class.is-editing { background: color-mix(in srgb, var(--cp-accent) 7%, transparent); border-radius: 0.875rem 0.875rem 0 0; }
.cp-class.is-editing .cp-class-name { color: var(--cp-accent); }

.cp-class-edit { display: grid; grid-template-columns: repeat(auto-fit, minmax(9rem, 1fr)); align-items: end; gap: 0.875rem 1rem; padding: 1rem 0.875rem 1rem 2.25rem;
  border-radius: 0 0 0.875rem 0.875rem; background: color-mix(in srgb, var(--cp-accent) 4%, transparent); margin-bottom: 0.25rem; }
.cp-class-edit label { display: flex; flex-direction: column; gap: 0.375rem; min-width: 0; font-size: 0.75rem; font-weight: 600; color: var(--text-muted); }
.cp-class-edit select, .cp-class-edit input { width: 100%; min-width: 0; box-sizing: border-box; }
.cp-class-edit-actions { grid-column: 1 / -1; display: flex; gap: 0.5rem; justify-content: flex-end; padding-top: 0.25rem; }
.cp-class-remove { color: var(--red); margin-right: auto; }

.cp-class-plan-toggle { align-self: flex-start; }
.cp-class-plan { display: flex; flex-wrap: wrap; align-items: center; gap: 0.625rem; padding: 1rem; border-radius: 1.25rem; border: 1px dashed var(--border2); }
.cp-class-plan input[name="name"] { flex: 1; min-width: 12rem; }
.cp-class-plan select { width: auto; }
.cp-category-classes { font-size: 0.75rem; color: var(--text-muted); padding: 0.125rem 0 0.375rem; }

/* Under the classes: how many, and their average, in the student's marks. */
.cp-class-total { display: flex; align-items: center; justify-content: space-between; gap: 1rem; padding: 1.125rem 1.375rem; border-radius: 1.25rem;
  border: 1px solid var(--border); background: radial-gradient(120% 140% at 100% 0%, color-mix(in srgb, var(--accent) 9%, var(--surface)) 0%, var(--surface) 65%); }
.cp-class-total-text { display: flex; flex-direction: column; gap: 0.25rem; min-width: 0; }
.cp-class-total-label { font-size: 0.6875rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.06em; color: var(--text-dim); }
.cp-class-total-n { font-size: 0.9375rem; font-weight: 600; color: var(--text); }
.cp-class-total-avg { display: flex; flex-direction: column; align-items: flex-end; gap: 0.125rem; }
.cp-class-total-avg small { font-size: 0.6875rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.06em; color: var(--text-dim); }
.cp-class-total-avg b { font-size: 1.75rem; line-height: 1.1; font-weight: 800; letter-spacing: -0.02em; color: var(--text); font-variant-numeric: tabular-nums; }

@media (max-width: 640px) {
  .cp-classes { margin-top: 2rem; gap: 1rem; }
  .cp-classes-head { flex-direction: column; align-items: stretch; gap: 0.875rem; }
  .cp-classes-sort { align-self: flex-start; }
  .cp-class-reqs { grid-template-columns: 1fr 1fr; gap: 0.625rem; }
  .cp-class-group { border-radius: 1.125rem; padding: 0.375rem 0.25rem 0.375rem; }
  .cp-class-group-head { padding: 0.875rem 0.875rem 0.5rem; }
  .cp-class { padding: 0.8125rem 0.875rem; gap: 0.75rem; }
  .cp-class-edit { grid-template-columns: 1fr 1fr; padding: 1rem 0.875rem; }
  .cp-class-edit-actions .btn { flex: 1; }
  .cp-class-edit-actions .cp-class-remove { flex: 0 0 auto; }
  .cp-class-plan { flex-direction: column; align-items: stretch; }
  .cp-class-plan input[name="name"], .cp-class-plan select { width: 100%; min-width: 0; }
  .cp-class-plan .cp-edit-cancel { align-self: flex-end; order: -1; }
  .cp-class-total { padding: 1rem 1.125rem; }
}
@media (max-width: 380px) {
  .cp-class-reqs { grid-template-columns: 1fr; }
}
