/* What the three pages are made of: the palette, the page, and the controls.
   index.html keeps the emulator's own chrome — the screen, the lamps, the
   keyboard — edit-dos.html keeps the catalog's and edit-agc.html the
   container's; this is what they share, and it is linked rather than copied so
   that one of them cannot quietly stop looking like the others. */

:root {
  color-scheme: dark;
  --bg: #14161a; --panel: #1d2026; --edge: #2c313a;
  --ink: #d7dbe2; --dim: #8b93a1; --accent: #79c0ff;
  /* The status line's two colors: something to be told, and something that
     is going right. Nowhere else on the page — a lamp is red because a drive
     LED is, and a keycap is red because the machine's own is. */
  --warn: #ff9c8a; --ok: #6fd08c;
  /* 768 of canvas — three 256-pixel columns — plus the panel's padding and
     border, so the picture lands on a whole multiple of its own raster. */
  --page: 790px;
  --mono: 12.5px ui-monospace, SFMono-Regular, Menlo, monospace;
}
* { box-sizing: border-box; }
body {
  margin: 0; background: var(--bg); color: var(--ink);
  font: 14px/1.5 ui-sans-serif, system-ui, "Segoe UI", Roboto, sans-serif;
  display: flex; flex-direction: column; align-items: center;
  min-height: 100vh; padding: 12px 12px 32px;
}
h1 { font-size: 17px; font-weight: 600; margin: 0; }
a { color: var(--accent); }

/* ---- the top row, on all three pages ------------------------------------
   The logo, then the page's name, then at the far right the one button that
   leads to the other two pages. src/topbar.js builds the button and its menu;
   the masthead beside it is the page's own. */
.top {
  width: min(94vw, var(--page)); margin-bottom: 10px; position: relative;
  display: flex; align-items: center; gap: 9px;
}
/* The wordmark, laid on its own height: it is 230x80, and what has to line
   up with the page name beside it is how tall it is. */
.top .logo { display: block; height: 26px; width: auto; opacity: .85; }
/* The logo is the way to the emulator, and on the emulator page it is the way
   back to a bare machine — where it carries the page's name with it, because
   there the masthead is the control. Neither is worth the page's link color
   above the picture, so both say so by hovering instead. */
.top .brand {
  display: flex; align-items: center; gap: 9px;
  color: inherit; text-decoration: none;
}
.top .brand:hover h1 { color: var(--accent); }
.top .brand:hover .logo { opacity: 1; }
.top .burger { margin-left: auto; padding: 4px 10px; line-height: 1.3; }
.top .menu {
  position: absolute; top: 100%; right: 0; z-index: 5; margin-top: 5px;
  display: flex; flex-direction: column; min-width: 14em; padding: 4px;
  background: var(--panel); border: 1px solid var(--edge); border-radius: 6px;
  box-shadow: 0 6px 18px #0008;
}
/* The class's own display beats the [hidden] attribute's, as in .panel .row. */
.top .menu[hidden] { display: none; }
.top .menu a, .top .menu .here {
  padding: 5px 9px; border-radius: 4px; white-space: nowrap;
}
.top .menu a { color: var(--ink); text-decoration: none; }
.top .menu a:hover { background: #ffffff12; color: var(--accent); }
/* The page the menu is on, which is a word and not a link to itself. */
.top .menu .here { color: var(--dim); }

select, button, label.file {
  font: inherit; color: var(--ink); background: var(--panel);
  border: 1px solid var(--edge); border-radius: 5px; padding: 5px 10px;
  cursor: pointer;
}
button:hover, select:hover, label.file:hover { border-color: var(--accent); }
button:active { transform: translateY(1px); }
select:disabled, button:disabled, label.file:has(input:disabled) {
  opacity: .45; cursor: default;
}
button:disabled:hover { border-color: var(--edge); }
input[type=file] { display: none; }
label.dim { color: var(--dim); font-size: 12.5px; cursor: default; }
input[type=text] {
  font: inherit; color: var(--ink); background: var(--bg);
  border: 1px solid var(--edge); border-radius: 5px; padding: 4px 8px;
}
input[type=text]:focus, textarea:focus { outline: 1px solid var(--accent); }

/* A panel: a card under the bar, holding rows of controls with a dim word at
   the head of each. Under the bar rather than over it — on the emulator page
   the screen is above, so opening one moves the keyboard and the help and
   never the picture. */
.panel {
  width: min(94vw, var(--page)); margin-top: 8px;
  background: var(--panel); border: 1px solid var(--edge);
  border-radius: 6px; padding: 8px 10px;
}
.panel .row { display: flex; flex-wrap: wrap; gap: 8px; align-items: center; }
/* The class's own display beats the [hidden] attribute's, so hidden has to be
   said again at the class's strength — a row that opens on a button, like the
   disk panel's Name, is drawn regardless otherwise. */
.panel .row[hidden] { display: none; }
.panel .row + .row { margin-top: 8px; }
.panel .key { color: var(--dim); font-size: 12.5px; min-width: 8ch; }
/* A note is something the panel says about itself, not a control. */
.panel .note { color: var(--dim); font-size: 12.5px; }
/* The far end of a row: a Close that belongs to the panel rather than
   to the controls beside it. */
.panel .sp { margin-left: auto; }
/* A rule between two halves of a panel, at the weight of every other line in
   it: the browser's own <hr> is a groove several pixels deep. */
.panel hr { border: 0; border-top: 1px solid var(--edge); margin: 8px 0; }

/* ---- the saves in the browser, in the Load panel ------------------------ */

/* One row a save, scrolling inside the panel: the list is as long as somebody
   has been playing, and the Open file… above it is what a long one is read
   against. */
.saves { margin-top: 6px; max-height: 40vh; overflow-y: auto; }
.saves .note { display: block; color: var(--dim); font-size: 12.5px; padding: 4px 0; }
.save { display: flex; gap: 8px; align-items: baseline; padding: 3px 0; }
.save + .save { border-top: 1px solid var(--edge); }
/* The name is the control: the row is loaded by clicking what it is called,
   which is the thing being read anyway. */
.save-name {
  border: 0; background: none; padding: 3px 0; color: var(--ink);
  text-align: left; flex: 1 1 12ch; min-width: 0;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.save-name:hover { color: var(--accent); border-color: transparent; }
.save-in, .save-when, .save-what { color: var(--dim); font-size: 12.5px; }
.save-in, .save-what { flex: 0 0 auto; }
/* The same middot the machine and the size are already joined by, so the whole
   tail of the row reads as one list. Drawn rather than written into the text,
   which keeps it out of what a narrow screen drops with .save-what. */
.save-when::before, .save-what::before { content: '·'; margin-right: 6px; }
/* The machine and the size are on the row's title as well, so a narrow screen
   drops the column rather than wrapping the row onto two lines. */
@media (max-width: 560px) {
  .save-what { display: none; }
}
.save-del { border: 0; background: none; padding: 3px 6px; }
.save-del:hover { border-color: transparent; }

/* The status line: what just happened, in the font the machine's own bytes are
   written in. One row, cut rather than wrapped. */
.status {
  color: var(--dim); font: var(--mono);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.status.err { color: var(--warn); }

/* ---- the DOS file manager, in whatever page mounts it ------------------- */

.dos { font-size: 12.5px; }
.dos.drag { outline: 1px dashed var(--accent); outline-offset: 5px; }
.dos-head { display: flex; gap: .5em; align-items: baseline; flex-wrap: wrap; }
.dos .dim { color: var(--dim); }
.dos .key { color: var(--dim); min-width: 8ch; }
.dos-note {
  display: flex; gap: 8px; align-items: center;
  color: var(--dim); margin-top: 4px;
}
/* Said again at the class's strength, as `.panel .row[hidden]` is: the note is
   put up for a read-only disk and taken down for a writable one. */
.dos-note[hidden] { display: none; }
/* The catalog scrolls inside the panel rather than the page: the footer's
   Add file… and the disk's own free count are what a long list is read
   against, and both are worth keeping in view. */
.dos-list {
  margin-top: 6px; max-height: 52vh; overflow-y: auto;
  overscroll-behavior: contain;
}
.dos-file { border-top: 1px solid var(--edge); }
/* Monospace, and the columns in the order DOS prints them: the lock mark, the
   type letter, the sector count, the name. */
.dos-row {
  display: flex; gap: .75em; align-items: baseline; padding: 2px 2px;
  font: var(--mono); cursor: pointer;
}
.dos-row:hover { background: #ffffff0a; }
.dos-file.open > .dos-row { background: #ffffff12; }
.dos-row.gone { opacity: .45; cursor: default; }
.dos-row.gone:hover { background: none; }
.dos-mark { width: 1ch; color: var(--dim); }
.dos-type { width: 1ch; }
.dos-sect { color: var(--dim); font-variant-numeric: tabular-nums; }
/* A file that contradicts itself, which is the one thing in the row worth a
   color. Everything else it says about itself is under the row. */
.dos-sect.bad, .dos-facts .bad { color: var(--warn); }
/* The name takes the row, and shrinks last: it is what the catalog is read
   for, and on a phone it is most of what fits. */
.dos-name {
  flex: 1 1 auto; min-width: 6ch;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
/* How long the file is — the one number DOS does not print and a person wants
   anyway. Right up against the ⋯, and it gives way to the name. */
.dos-len {
  color: var(--dim); text-align: right; flex: 0 1 auto;
  font-variant-numeric: tabular-nums;
  overflow: hidden; text-overflow: clip; white-space: nowrap;
}
.dos-more { color: var(--dim); }
/* The rest of what the file says, under it, in the same monospace as the row
   so the numbers line up with the ones above them. */
.dos-facts { font: var(--mono); color: var(--dim); gap: 1em; }
/* The actions, under the row they belong to. */
.dos-strip { padding: 2px 0 8px 2.5ch; }
.dos-acts {
  display: flex; gap: 6px; align-items: center; flex-wrap: wrap; margin-top: 5px;
}
.dos-acts button { padding: 2px 9px; font-size: 12px; }
.dos-sum {
  color: var(--dim); border-top: 1px solid var(--edge);
  margin-top: 4px; padding-top: 5px;
}
.dos-foot { display: flex; gap: 10px; align-items: center; margin-top: 8px; }
.dos-foot button, .dos-foot label.file { padding: 3px 9px; font-size: 12px; }
.dos-foot label { color: var(--dim); }
.dos-form { margin-top: 8px; border-top: 1px solid var(--edge); }
/* The editor fills the popup it opens in, and is dragged taller by the corner
   past that. Its Save is under it, inside the box, so a tall one cannot push
   its own Save out of reach. */
.dos-text textarea {
  display: block; width: 100%; min-height: 7em; margin-top: 6px;
  font: var(--mono); color: var(--ink); background: var(--bg);
  border: 1px solid var(--edge); border-radius: 5px; padding: 6px 8px;
  resize: vertical; overscroll-behavior: contain;
}
.dos-pop .dos-text textarea { min-height: 55vh; }

/* Looking inside a file: the page's one popup, over everything, because a hex
   dump is 70 columns wide and the catalog it opens from is a list that
   scrolls. Fixed to the viewport rather than to the panel — on the emulator
   page the panel is somewhere down a page that is taller than the window. */
/* A scroll port of its own, with nothing in it to scroll: a wheel over the
   backdrop, or past the end of the list inside it, stops here instead of
   moving the page behind the popup. */
.dos-pop {
  position: fixed; inset: 0; z-index: 20; padding: 4vh 3vw;
  background: #00000099; display: flex; align-items: center;
  justify-content: center;
  overflow: auto; overscroll-behavior: contain;
}
.dos-pop-box {
  display: flex; flex-direction: column; gap: 6px;
  width: min(94vw, 820px); max-height: 92vh; padding: 12px 14px;
  background: var(--panel); border: 1px solid var(--edge); border-radius: 8px;
  box-shadow: 0 12px 40px #000000a6;
}
.dos-pop-head {
  display: flex; gap: 8px; align-items: baseline; flex-wrap: wrap;
  border-bottom: 1px solid var(--edge); padding-bottom: 8px;
}
.dos-pop-head button { padding: 2px 9px; font-size: 12px; }
/* Which of the four is showing. The accent is the page's word for "this one",
   and it is a border rather than a fill so the row stays a row of buttons. */
.dos-pop-head button.on { border-color: var(--accent); color: var(--accent); }
/* The dump scrolls both ways: a line is as wide as it is, and wrapping one
   would take the columns apart. */
.dos-pop-view {
  flex: 1 1 auto; overflow: auto; overscroll-behavior: contain; font: var(--mono);
  background: var(--bg); border: 1px solid var(--edge); border-radius: 5px;
  padding: 6px 8px;
}
.dos-pop-view pre { margin: 0; font: inherit; }
/* A BASIC listing. The line number sits in a column of its own so the program
   reads down its left edge, and the three colors are the ones the page already
   has: what the machine reserved a token for, what it will print as it stands,
   and what it will not run at all. */
.dos-bas .n {
  display: inline-block; width: 6ch; color: var(--dim);
  text-align: right; padding-right: 1ch;
}
.dos-bas .kw { color: var(--accent); }
.dos-bas .str { color: var(--ok); }
.dos-bas .rem { color: var(--dim); font-style: italic; }
.dos-bas .bad { color: var(--warn); padding-top: 6px; }
/* A disassembly. Four columns of fixed width so the mnemonics line up down the
   page, and the undocumented opcodes are marked: a run of them is a stretch of
   data being read as code, which is what a linear disassembly cannot know. */
.dos-dis span { display: inline-block; }
.dos-dis .a { width: 6ch; color: var(--dim); }
.dos-dis .b { width: 10ch; color: var(--dim); }
.dos-dis .op { width: 5ch; color: var(--accent); }
.dos-dis .ill { width: 5ch; color: var(--warn); }
.dos-nm { width: 22ch; }
.dos-ad { width: 9ch; }
