/* CPE3326 portal — Beginner tier, Thai-primary, dual theme */
:root{
  /* one place for the monospace stack; the bit rows depend on every glyph
     being the same width, and a var that resolves to nothing falls back to the
     Thai body font, which is proportional */
  --mono:"SF Mono",Menlo,Consolas,"Courier New",monospace;
  --bg:#f7f8fa; --surface:#fff; --surface-2:#eef1f5; --border:#d8dee6;
  --text:#1a2029; --muted:#5b6675; --accent:#0b6fd4; --accent-soft:#e3eefb;
  --code-bg:#1e2530; --code-text:#e6edf3; --ok:#0f7b47; --warn:#a15c00;
  --shadow:0 1px 2px rgba(16,24,40,.06),0 4px 12px rgba(16,24,40,.05);
  --radius:12px; --maxw:920px;
}
@media (prefers-color-scheme:dark){
  :root:not([data-theme="light"]){
    --bg:#11151b; --surface:#171d25; --surface-2:#1e2630; --border:#2b3541;
    --text:#e4e9ef; --muted:#9aa7b6; --accent:#5aa9f8; --accent-soft:#16283f;
    --code-bg:#0d1117; --code-text:#e6edf3; --ok:#4ec98a; --warn:#e0a34a;
    --shadow:0 1px 2px rgba(0,0,0,.4),0 4px 14px rgba(0,0,0,.3);
  }
}
:root[data-theme="dark"]{
  --bg:#11151b; --surface:#171d25; --surface-2:#1e2630; --border:#2b3541;
  --text:#e4e9ef; --muted:#9aa7b6; --accent:#5aa9f8; --accent-soft:#16283f;
  --code-bg:#0d1117; --code-text:#e6edf3; --ok:#4ec98a; --warn:#e0a34a;
  --shadow:0 1px 2px rgba(0,0,0,.4),0 4px 14px rgba(0,0,0,.3);
}
*{box-sizing:border-box}

/* Keyboard focus. Nothing in the page showed a focus ring before, so anyone
   navigating by Tab had no idea where they were. */
:where(a, button, summary, .vid, .tab, input, select):focus-visible{
  outline:2px solid var(--accent); outline-offset:2px; border-radius:5px;
}
details.sol > summary:focus-visible, details.hint > summary:focus-visible{outline-offset:-2px}
body{
  margin:0; background:var(--bg); color:var(--text);
  font-family:"Noto Sans Thai","Sarabun",-apple-system,BlinkMacSystemFont,"Segoe UI",sans-serif;
  line-height:1.75; font-size:17px; -webkit-font-smoothing:antialiased;
}
.wrap{max-width:var(--maxw); margin:0 auto; padding:0 20px}
a{color:var(--accent)}
code,kbd{font-family:"SF Mono",Menlo,Consolas,monospace; font-size:.88em}

/* header */
header.top{
  position:sticky; top:0; z-index:20; background:var(--surface);
  border-bottom:1px solid var(--border); box-shadow:var(--shadow);
}
header.top .wrap{display:flex; flex-wrap:wrap; align-items:center; gap:10px 12px; min-height:58px; padding-top:8px; padding-bottom:8px}
.brand{font-weight:700; text-decoration:none; color:var(--text); white-space:nowrap}
.brand span{color:var(--accent)}
.spacer{flex:1}
.btn{
  background:var(--surface-2); color:var(--text); border:1px solid var(--border);
  border-radius:8px; padding:6px 12px; font:inherit; font-size:.85rem;
  cursor:pointer; text-decoration:none; display:inline-flex; align-items:center; gap:6px;
}
.btn:hover{border-color:var(--accent); color:var(--accent)}
.btn[aria-pressed="true"]{background:var(--accent-soft); border-color:var(--accent); color:var(--accent)}

/* hero */
.hero{padding:52px 0 34px; border-bottom:1px solid var(--border)}
.hero h1{font-size:2.05rem; margin:0 0 10px; line-height:1.3}
.hero p.lead{font-size:1.06rem; color:var(--muted); margin:0 0 22px; max-width:64ch}
.meta{display:flex; flex-wrap:wrap; gap:10px}
.chip{
  background:var(--surface); border:1px solid var(--border); border-radius:999px;
  padding:5px 14px; font-size:.83rem; color:var(--muted);
}

/* session + lab cards */
.session{margin:40px 0 0}
.session h2{font-size:1.15rem; margin:0 0 4px; display:flex; align-items:center; gap:10px}
.session .date{font-size:.85rem; color:var(--muted); font-weight:400}
.grid{display:grid; grid-template-columns:repeat(auto-fill,minmax(232px,1fr)); gap:14px; margin:16px 0 0}
.card{
  display:block; background:var(--surface); border:1px solid var(--border);
  border-radius:var(--radius); padding:16px; text-decoration:none; color:inherit;
  box-shadow:var(--shadow); transition:transform .12s, border-color .12s;
}
.card:hover{transform:translateY(-2px); border-color:var(--accent)}
.card .id{font-size:.75rem; font-weight:700; color:var(--accent); letter-spacing:.06em}
.card .name{font-weight:600; margin:5px 0 8px; line-height:1.45}
.card .tags{font-size:.76rem; color:var(--muted)}
.card.done{border-color:var(--ok)}
.card.done .id::after{content:" ✓"; color:var(--ok)}

/* lab page */
main{padding:30px 0 70px}
.crumb{font-size:.85rem; color:var(--muted); margin:0 0 6px}
h1.lab{font-size:1.75rem; margin:0 0 8px; line-height:1.35}
h2.sec{
  font-size:1.2rem; margin:38px 0 12px; padding-top:16px;
  border-top:1px solid var(--border); display:flex; align-items:center; gap:9px;
}
h2.sec .n{
  width:26px; height:26px; border-radius:7px; background:var(--accent-soft);
  color:var(--accent); font-size:.8rem; display:grid; place-items:center; flex:none;
}
.prose p{margin:.7em 0}
.prose ol,.prose ul{padding-left:1.4em; margin:.7em 0}
.prose li{margin:.35em 0}
.prose strong{font-weight:600}

figure{margin:20px 0; text-align:center}
figure img{
  max-width:100%; height:auto; border:1px solid var(--border);
  border-radius:10px; background:#fff; box-shadow:var(--shadow);
}
figcaption{font-size:.8rem; color:var(--muted); margin-top:7px}

pre{
  background:var(--code-bg); color:var(--code-text); border-radius:10px;
  padding:15px 17px; overflow-x:auto; font-size:.85rem; line-height:1.6; margin:14px 0;
}
pre code{color:inherit}

/* callouts */
.note{
  background:var(--accent-soft); border-left:3px solid var(--accent);
  border-radius:0 8px 8px 0; padding:13px 16px; margin:18px 0; font-size:.94rem;
}
.note.tip{background:color-mix(in srgb,var(--ok) 12%,transparent); border-color:var(--ok)}
.note strong{display:block; margin-bottom:3px}

/* solution reveal */
details.sol{
  border:1px solid var(--border); border-radius:var(--radius);
  background:var(--surface); margin:18px 0; overflow:hidden;
}
details.sol > summary{
  cursor:pointer; padding:14px 17px; font-weight:600; list-style:none;
  display:flex; align-items:center; gap:9px; user-select:none;
}
details.sol > summary::-webkit-details-marker{display:none}
details.sol > summary::before{content:"🔒"; font-size:.95em}
details.sol[open] > summary::before{content:"🔓"}
details.sol > summary:hover{color:var(--accent)}
details.sol > summary .hint{font-weight:400; font-size:.83rem; color:var(--muted); margin-left:auto}
details.sol .body{padding:0 17px 16px; border-top:1px solid var(--border)}
details.sol .body > .note:first-child{margin-top:16px}

/* questions */
ol.q{counter-reset:q; list-style:none; padding:0}
ol.q > li{
  counter-increment:q; background:var(--surface); border:1px solid var(--border);
  border-radius:10px; padding:14px 16px 14px 50px; margin:10px 0; position:relative;
}
ol.q > li::before{
  content:counter(q); position:absolute; left:15px; top:14px;
  width:23px; height:23px; border-radius:6px; background:var(--accent-soft);
  color:var(--accent); font-size:.78rem; font-weight:700; display:grid; place-items:center;
}

/* nav */
.pager{display:flex; gap:12px; margin:46px 0 0; border-top:1px solid var(--border); padding-top:22px}
.pager a{
  flex:1; padding:13px 16px; border:1px solid var(--border); border-radius:var(--radius);
  text-decoration:none; color:inherit; background:var(--surface);
}
.pager a:hover{border-color:var(--accent)}
.pager .dir{font-size:.75rem; color:var(--muted); display:block}
.pager .t{font-weight:600; font-size:.92rem}
.pager .next{text-align:right}

footer{border-top:1px solid var(--border); padding:26px 0; color:var(--muted); font-size:.83rem}
footer .warn{color:var(--warn)}

@media (max-width:600px){
  body{font-size:16px}
  .hero{padding:36px 0 26px}
  .hero h1{font-size:1.6rem}
  .pager{flex-direction:column}
}

h3.dev{
  font-size:.9rem; font-weight:700; margin:22px 0 -6px; color:var(--accent);
  letter-spacing:.02em; display:inline-block; background:var(--accent-soft);
  padding:4px 11px; border-radius:7px;
}
.note.errata{background:color-mix(in srgb,var(--warn) 14%,transparent); border-color:var(--warn)}
.note.errata code{background:var(--surface-2); padding:1px 5px; border-radius:4px}
.cont{margin:.3em 0 .3em 0; padding:6px 12px; background:var(--surface-2);
      border-radius:7px; font-family:"SF Mono",Menlo,monospace; font-size:.85rem}

/* identity */
.who{display:flex; align-items:center; gap:9px; font-size:.84rem}
/* now a link to your own details, so it has to look like one you can press */
.who-name{
  color:var(--muted); max-width:170px; overflow:hidden; text-overflow:ellipsis;
  white-space:nowrap; text-decoration:none; border-bottom:1px dotted var(--border);
  transition:color .14s ease, border-color .14s ease;
}
.who-name:hover{color:var(--text); border-bottom-color:var(--accent)}
.who-name:focus-visible{outline:2px solid var(--accent); outline-offset:3px; border-radius:3px}
.who-local{color:var(--muted); opacity:.8}
.navlink{font-size:.82rem}

/* progress */
.progress{margin:22px 0 0; max-width:520px}
.progress .track{height:8px; background:var(--surface-2); border-radius:99px; overflow:hidden}
.progress .fill{height:100%; width:0; background:var(--accent); border-radius:99px; transition:width .35s ease}
.progress.complete .fill{background:var(--ok)}
.progress .row{display:flex; align-items:center; gap:12px; margin-top:9px}
.progress .label{font-size:.83rem; color:var(--muted); flex:1}
.btn.tiny{font-size:.75rem; padding:3px 9px}
.scount{
  font-size:.75rem; font-weight:600; color:var(--muted); background:var(--surface-2);
  border-radius:99px; padding:2px 10px;
}
.scount.done{background:color-mix(in srgb,var(--ok) 20%,transparent); color:var(--ok)}
.session .theme{color:var(--muted); margin:0}

/* mark complete */
.markbox{display:flex; align-items:center; gap:14px; margin:40px 0 0; flex-wrap:wrap}
.mark{
  display:inline-flex; align-items:center; gap:10px; font:inherit; font-size:.95rem;
  font-weight:600; cursor:pointer; padding:12px 22px; border-radius:var(--radius);
  border:1px solid var(--border); background:var(--surface); color:var(--text);
}
.mark:hover{border-color:var(--ok)}
.mark[aria-pressed="true"]{
  background:color-mix(in srgb,var(--ok) 16%,transparent); border-color:var(--ok); color:var(--ok);
}
.stamp{font-size:.8rem; color:var(--muted)}

/* getting-started */
ol.steps{list-style:none; counter-reset:s; padding:0}
ol.steps > li{
  counter-increment:s; position:relative; padding:0 0 4px 46px; margin:0 0 26px;
}
ol.steps > li::before{
  content:counter(s); position:absolute; left:0; top:0; width:30px; height:30px;
  border-radius:9px; background:var(--accent); color:#fff; font-weight:700;
  font-size:.85rem; display:grid; place-items:center;
}
ol.steps .st{padding-top:4px; font-weight:500}
ol.steps figure{margin:12px 0 0; text-align:left}
.tabs{display:flex; gap:8px; margin:18px 0 14px; flex-wrap:wrap}
.tab{
  font:inherit; font-size:.88rem; cursor:pointer; padding:8px 16px; border-radius:9px;
  border:1px solid var(--border); background:var(--surface); color:var(--text);
}
.tab[aria-selected="true"]{background:var(--accent-soft); border-color:var(--accent); color:var(--accent); font-weight:600}
.pane ol{padding-left:1.3em}
.pane li{margin:.5em 0}
kbd{
  background:var(--surface-2); border:1px solid var(--border); border-bottom-width:2px;
  border-radius:5px; padding:1px 6px; font-size:.85em;
}

/* resources */
.reshint{color:var(--muted); font-size:.9rem; margin:0 0 14px}
.reshint.small{font-size:.8rem; margin-top:10px}
.vids{display:grid; grid-template-columns:repeat(auto-fill,minmax(230px,1fr)); gap:13px; margin:0 0 18px}
.vid{
  position:relative; padding:0; border:1px solid var(--border); border-radius:11px;
  background:var(--surface); cursor:pointer; overflow:hidden; text-align:left;
  font:inherit; color:inherit; display:block; transition:transform .12s,border-color .12s;
}
.vid:hover{transform:translateY(-2px); border-color:var(--accent)}
.vid img{width:100%; aspect-ratio:16/9; object-fit:cover; display:block; background:var(--surface-2)}
.vid .play{
  position:absolute; top:calc(50% - 30px); left:50%; transform:translate(-50%,-50%);
  width:46px; height:46px; border-radius:50%; background:rgba(0,0,0,.72); color:#fff;
  display:grid; place-items:center; font-size:1.05rem; padding-left:3px;
}
.vid:hover .play{background:#e23}
.vid .vt{
  padding:10px 12px; font-size:.82rem; line-height:1.5; font-weight:500;
  display:-webkit-box; -webkit-line-clamp:2; -webkit-box-orient:vertical;
  overflow:hidden; min-height:calc(2 * 1.5em + 20px);
}
.vids iframe{width:100%; aspect-ratio:16/9; border:0; border-radius:11px; display:block}
ul.reslist{list-style:none; padding:0; margin:0}
ul.reslist li{
  display:flex; gap:10px; align-items:baseline; padding:9px 13px; margin:7px 0;
  background:var(--surface); border:1px solid var(--border); border-radius:9px; font-size:.9rem;
}
ul.reslist .ic{flex:none}

.module{margin:0 0 10px}
.labref{
  display:inline-block; font-size:.75rem; font-weight:600; text-decoration:none;
  background:var(--accent-soft); color:var(--accent); border-radius:6px; padding:2px 8px; margin:0 2px;
}
.labref:hover{background:var(--accent); color:#fff}
h2.sec .scount{margin-left:auto}

ol.examlist{padding-left:1.5em; margin:12px 0 0; columns:2; column-gap:26px}
ol.examlist li{margin:.4em 0; font-size:.88rem; break-inside:avoid}
ol.examlist a{text-decoration:none}
ol.examlist a:hover{text-decoration:underline}
@media (max-width:640px){ ol.examlist{columns:1} }

.vid .src{
  position:absolute; top:8px; right:8px; font-size:.66rem; font-weight:600;
  background:rgba(0,0,0,.72); color:#fff; padding:2px 7px; border-radius:5px;
  max-width:60%; overflow:hidden; text-overflow:ellipsis; white-space:nowrap;
}
.credits{
  margin:40px 0 0; padding:16px 18px; border:1px solid var(--border);
  border-radius:var(--radius); background:var(--surface); font-size:.85rem;
}
.credits strong{display:block; margin-bottom:5px}
.credits p{margin:0; color:var(--muted); line-height:1.7}

/* planted-discrepancy nudge — deliberately quieter than the solution reveal */
details.hint{
  border:1px dashed var(--border); border-radius:var(--radius);
  background:var(--surface); margin:18px 0; overflow:hidden;
}
details.hint > summary{
  cursor:pointer; padding:12px 16px; font-weight:600; font-size:.92rem;
  list-style:none; display:flex; align-items:center; gap:9px; user-select:none;
}
details.hint > summary::-webkit-details-marker{display:none}
details.hint > summary::before{content:"💡"}
details.hint > summary:hover{color:var(--accent)}
details.hint .hint-x{margin-left:auto; font-weight:400; font-size:.8rem; color:var(--muted)}
details.hint .body{padding:2px 16px 14px}
details.hint .sym{
  font-size:.88rem; color:var(--warn); font-weight:600; margin:.4em 0;
}
ol.probe{padding-left:1.3em; margin:.6em 0}
ol.probe li{margin:.5em 0; font-size:.93rem}
details.hint.inner{margin:14px 0 4px; border-style:solid}
details.hint.inner > summary::before{content:"🔑"}

ul.reslist.docs li{align-items:center; gap:12px}
ul.reslist.docs .doc{flex:1; min-width:0; overflow:hidden; text-overflow:ellipsis}
ul.reslist.docs .docrefs{flex:none; display:flex; gap:4px; flex-wrap:wrap}
@media (max-width:600px){
  ul.reslist.docs li{flex-wrap:wrap}
  ul.reslist.docs .docrefs{width:100%; padding-left:26px}
}

ul.sub, ul.dash{list-style:none; padding-left:0; margin:.5em 0 .2em}
ul.sub li, ul.dash li{
  margin:.3em 0; padding:5px 12px; background:var(--surface-2);
  border-radius:7px; font-size:.9rem;
}
ul.dash li::before{content:"– "; color:var(--muted)}
.sublabel{font-weight:600; color:var(--accent); margin-right:5px}
ul.sub .cont{margin:.25em 0 0; background:transparent; padding:0 0 0 34px; font-size:.95em}

ul.certs{list-style:none; padding:0; margin:0}
ul.certs li{
  display:flex; align-items:baseline; gap:14px; padding:11px 15px; margin:8px 0;
  background:var(--surface); border:1px solid var(--border); border-radius:9px; font-size:.9rem;
}
ul.certs .cn{flex:1}
ul.certs .cy{flex:none; color:var(--muted); font-size:.82rem; font-variant-numeric:tabular-nums}
ul.certs .flagship{
  border-color:var(--accent); background:var(--accent-soft);
}
ul.certs .flagship .cn{font-weight:700; color:var(--accent)}
ul.reslist.areas li{display:block}
ul.reslist.areas li::before{content:"▸ "; color:var(--accent)}

ul.certs .cv{
  flex:none; font-size:.75rem; font-weight:600; color:var(--ok);
  background:color-mix(in srgb,var(--ok) 16%,transparent);
  padding:2px 9px; border-radius:99px; white-space:nowrap;
}

ul.certs.credly li{align-items:center}
ul.certs .org{display:block; font-size:.76rem; color:var(--muted); margin-top:2px}
ul.certs .cn a{text-decoration:none}
ul.certs .cn a:hover{text-decoration:underline}
ul.certs li.lapsed{opacity:.55}
ul.certs .cv.lapsed{color:var(--muted); background:var(--surface-2)}

/* profile header */
.wrap.profile-head{display:flex; align-items:center; gap:26px; flex-wrap:wrap}
.wrap.profile-head .who-block{flex:1; min-width:260px}
.avatar{
  width:156px; height:156px; border-radius:50%; flex:none; object-fit:cover;
  border:3px solid var(--surface); box-shadow:0 0 0 2px var(--accent), var(--shadow);
  background:var(--surface-2);
}
.avatar.initials{
  display:grid; place-items:center; font-size:2.7rem; font-weight:700;
  color:var(--accent); background:var(--accent-soft); letter-spacing:.02em;
}

/* certificate marks */
ul.certs .tile{
  flex:none; width:56px; height:56px; border-radius:12px; display:grid;
  place-items:center; align-content:center; gap:1px; background:var(--surface-2);
  border:1px solid var(--border); text-align:center; line-height:1.15;
}
ul.certs .tile .ab{font-size:.8rem; font-weight:800; color:var(--accent)}
ul.certs .tile .vendor{font-size:.55rem; color:var(--muted); text-transform:uppercase; letter-spacing:.04em}
ul.certs .flagship .tile{background:var(--surface); border-color:var(--accent)}
ul.certs img.badge{width:56px; height:56px; flex:none; object-fit:contain}
ul.certs li{gap:15px}
@media (max-width:520px){
  .avatar{width:112px; height:112px}
  .avatar.initials{font-size:2rem}
  ul.certs .tile, ul.certs img.badge{width:46px; height:46px}
}

ul.certs .cid{
  display:block; font-size:.74rem; font-weight:700; color:var(--muted);
  letter-spacing:.05em; margin-top:3px;
}
ul.certs .flagship .cid{color:var(--accent)}

.avatar-col{display:flex; flex-direction:column; align-items:center; gap:10px; flex:none}
.ccie-tag{
  font-size:.78rem; font-weight:700; letter-spacing:.04em; color:var(--accent);
  background:var(--accent-soft); border:1px solid var(--accent);
  padding:4px 13px; border-radius:99px; white-space:nowrap;
}
h1 .nick{font-weight:400; color:var(--muted); font-size:.72em}

ul.timeline{list-style:none; padding:0; margin:6px 0 0; position:relative}
ul.timeline::before{
  content:""; position:absolute; left:96px; top:6px; bottom:6px;
  width:2px; background:var(--border);
}
ul.timeline li{display:flex; gap:22px; padding:9px 0; position:relative}
ul.timeline .tspan{
  flex:none; width:84px; text-align:right; font-size:.8rem; color:var(--muted);
  font-variant-numeric:tabular-nums; padding-top:2px;
}
ul.timeline li::before{
  content:""; position:absolute; left:91px; top:14px; width:12px; height:12px;
  border-radius:50%; background:var(--surface); border:2px solid var(--accent);
}
ul.timeline li.edu::before{border-color:var(--ok)}
ul.timeline .tbody{padding-left:26px}
ul.timeline .tt{display:block; font-weight:600}
ul.timeline .to{display:block; font-size:.87rem; color:var(--muted); margin-top:1px}
ul.timeline .tn{display:block; font-size:.83rem; color:var(--muted); margin-top:5px}
@media (max-width:600px){
  ul.timeline::before, ul.timeline li::before{display:none}
  ul.timeline li{flex-direction:column; gap:2px}
  ul.timeline .tspan{width:auto; text-align:left}
  ul.timeline .tbody{padding-left:0}
}

ul.timeline .tspan{display:flex; flex-direction:column; gap:2px}
ul.timeline .tdur{font-size:.72rem; opacity:.72}
ul.timeline li.current::before{background:var(--accent)}
ul.timeline li.current .tt::after{
  content:"ปัจจุบัน"; margin-left:9px; font-size:.68rem; font-weight:700;
  color:var(--accent); background:var(--accent-soft); padding:2px 8px; border-radius:99px;
  vertical-align:middle;
}

.intro{margin:0 0 8px; max-width:68ch}
.intro p{margin:0 0 .9em; font-size:1.02rem; line-height:1.85}
.intro p:first-child{font-size:1.08rem}
.intro p:last-child{margin-bottom:0; color:var(--muted)}

/* Narrow screens: the header is the one row that cannot shrink on its own,
   so give it explicit rules rather than letting it widen the whole document. */
@media (max-width:700px){
  header.top .wrap{gap:8px}
  .brand{font-size:.95rem}
  .navlink{font-size:.76rem; padding:5px 9px}
  .who{font-size:.76rem}
  .who-name{max-width:96px}
  .who-local{font-size:0}
  .who-local::before{content:"📴"; font-size:.9rem}
  #theme{padding:5px 9px; font-size:.76rem}
}
@media (max-width:430px){
  .brand{width:100%; }
  .spacer{display:none}
  header.top .wrap{gap:6px}
}

/* jump bar — the questions used to sit ~75% down the page */
/* Counts are facts about the page, not places to go. They used to be
   .chip, which is the same pill the jump links use: ten identical
   buttons where three do nothing when clicked. */
p.tally{margin:6px 0 14px; color:var(--muted); font-size:.88rem}
nav.jump{display:flex; flex-wrap:wrap; gap:8px; margin:4px 0 20px}
nav.jump a{
  font-size:.8rem; text-decoration:none; color:var(--muted);
  background:var(--surface); border:1px solid var(--border);
  padding:5px 13px; border-radius:99px; transition:color .12s,border-color .12s;
}
nav.jump a:hover{color:var(--accent); border-color:var(--accent)}
h2.sec, details.sol{scroll-margin-top:76px}

ul.prelist{list-style:none; padding:0; margin:8px 0 0}
ul.prelist li{margin:5px 0; font-size:.92rem; padding-left:22px; position:relative}
ul.prelist li::before{content:"▶"; position:absolute; left:0; font-size:.7rem; color:var(--accent); top:5px}
ul.prelist li.more::before{content:"…"}
ul.prelist li.more{font-size:.85rem}

/* resume card */
a.resume{
  display:flex; align-items:center; gap:16px; margin:0 0 20px;
  padding:17px 20px; border-radius:var(--radius); text-decoration:none;
  background:var(--accent-soft); border:1px solid var(--accent); color:var(--text);
  transition:transform .12s;
}
a.resume:hover{transform:translateY(-2px)}
a.resume .rk{
  flex:none; font-size:.73rem; font-weight:700; letter-spacing:.05em;
  color:var(--accent); text-transform:uppercase;
}
a.resume .rt{flex:1; font-weight:600; line-height:1.5}
a.resume .rgo{flex:none; font-size:1.3rem; color:var(--accent)}
a.resume.done{background:color-mix(in srgb,var(--ok) 14%,transparent); border-color:var(--ok)}
a.resume.done .rk, a.resume.done .rgo{color:var(--ok)}
@media (max-width:600px){
  a.resume{flex-wrap:wrap; gap:6px 14px}
  a.resume .rt{flex:1 1 100%; order:3}
}

/* glossary */
ul.glossary{list-style:none; padding:0; margin:0}
ul.glossary li{
  padding:16px 18px; margin:10px 0; background:var(--surface);
  border:1px solid var(--border); border-radius:var(--radius);
}
ul.glossary h3{margin:0 0 6px; font-size:1.02rem; color:var(--accent)}
ul.glossary p{margin:0; font-size:.95rem}
ul.glossary .gl-labs{margin-top:9px; font-size:.78rem; color:var(--muted)}
ul.glossary li:target{border-color:var(--accent); box-shadow:0 0 0 3px var(--accent-soft)}
ul.glossary li{scroll-margin-top:80px}

/* per-lab term chips */
.terms{display:flex; flex-wrap:wrap; align-items:center; gap:7px; margin:0 0 18px}
.terms .tk{font-size:.76rem; color:var(--muted); margin-right:2px}
a.term{
  font-size:.78rem; text-decoration:none; color:var(--muted);
  background:var(--surface-2); border:1px solid var(--border);
  padding:3px 10px; border-radius:99px;
}
a.term:hover{color:var(--accent); border-color:var(--accent)}


/* Topic identity. Each of the seven topics carries its own hue so a student can
   tell where they are in the course at a glance. Every value clears WCAG AA
   (4.5:1) on the surface of the theme it belongs to. */
.hue-sky{--h:#0e6ebc; --h-soft:#e3eefb}
.hue-green{--h:#0f7b47; --h-soft:#e0f3e9}
.hue-violet{--h:#6b3fc7; --h-soft:#ece5fb}
.hue-amber{--h:#8a5000; --h-soft:#fbeeda}
.hue-rose{--h:#b8305c; --h-soft:#fce4ec}
.hue-indigo{--h:#3a4fc4; --h-soft:#e6e9fb}
.hue-teal{--h:#0a6e73; --h-soft:#dcf1f2}
@media (prefers-color-scheme:dark){
:root:not([data-theme="light"]) .hue-sky{--h:#5aa9f8; --h-soft:#16283f}
:root:not([data-theme="light"]) .hue-green{--h:#4ec98a; --h-soft:#122b21}
:root:not([data-theme="light"]) .hue-violet{--h:#b49bf7; --h-soft:#241d3b}
:root:not([data-theme="light"]) .hue-amber{--h:#e3ab52; --h-soft:#2e2312}
:root:not([data-theme="light"]) .hue-rose{--h:#f58aa8; --h-soft:#33161f}
:root:not([data-theme="light"]) .hue-indigo{--h:#9aa8f7; --h-soft:#1c2040}
:root:not([data-theme="light"]) .hue-teal{--h:#4fc7cf; --h-soft:#0f2a2c}
}
:root[data-theme="dark"] .hue-sky{--h:#5aa9f8; --h-soft:#16283f}
:root[data-theme="dark"] .hue-green{--h:#4ec98a; --h-soft:#122b21}
:root[data-theme="dark"] .hue-violet{--h:#b49bf7; --h-soft:#241d3b}
:root[data-theme="dark"] .hue-amber{--h:#e3ab52; --h-soft:#2e2312}
:root[data-theme="dark"] .hue-rose{--h:#f58aa8; --h-soft:#33161f}
:root[data-theme="dark"] .hue-indigo{--h:#9aa8f7; --h-soft:#1c2040}
:root[data-theme="dark"] .hue-teal{--h:#4fc7cf; --h-soft:#0f2a2c}

.session h2 .ticon{font-size:1.15em; margin-right:2px}
.session h2{color:var(--h,var(--accent)); gap:10px}
.session .scount.done{background:color-mix(in srgb,var(--h,var(--ok)) 22%,transparent); color:var(--h,var(--ok))}

.card{position:relative; overflow:hidden; padding:18px 16px 16px}
.card::before{content:""; position:absolute; inset:0 0 auto 0; height:3px;
  background:var(--h,var(--accent)); opacity:.85}
.card .id{font-size:.82rem; letter-spacing:.08em; color:var(--h,var(--accent))}
.card .name{font-size:1.02rem; margin:6px 0 10px}
.card:hover{transform:translateY(-3px); border-color:var(--h,var(--accent))}
.card.done{border-color:var(--ok)}
.card.done::before{background:var(--ok)}

.wrap[class*="hue-"] h2.sec .n{background:var(--h-soft); color:var(--h)}
.crumb .ticon{margin-right:6px}

h1.lab{font-size:1.9rem; letter-spacing:-.01em}
h2.sec{margin-top:46px; font-size:1.26rem}
.hero h1{letter-spacing:-.015em}
main{padding-bottom:88px}

.progress .track{height:10px}
.progress.complete .track{box-shadow:0 0 0 3px color-mix(in srgb,var(--ok) 22%,transparent)}
.progress.complete .label{color:var(--ok); font-weight:600}

/* inline notes inside a console transcript (LAB02) */
pre .ann{font-family:"Noto Sans Thai",-apple-system,sans-serif; font-size:.82em;
  color:#9fb4c9; opacity:.9; margin-left:10px; white-space:normal}

/* The instructor's walkthrough is watched and followed step by step, so it gets
   a real player size - unlike the theory clips, which are a browse-and-pick grid. */
.vids.walk{grid-template-columns:1fr; max-width:680px; gap:16px}
.vids.walk .vid img{aspect-ratio:16/9}
.vids.walk .play{width:64px; height:64px; font-size:1.5rem; top:calc(50% - 26px)}
.vids.walk .vt{font-size:.95rem; padding:13px 16px; -webkit-line-clamp:2}
.vids.walk .src{font-size:.72rem}
@media (max-width:600px){ .vids.walk .play{width:52px; height:52px; font-size:1.2rem} }

/* Progress ring beside each topic heading. Decorative - the "2/3" chip next to
   it carries the same value as text. */
.ring{position:relative; width:34px; height:34px; flex:none; display:inline-grid; place-items:center}
.ring svg{width:34px; height:34px; transform:rotate(-90deg); display:block}
.ring circle{fill:none; stroke-width:3.2; stroke-linecap:round}
.ring .rt{stroke:var(--surface-2)}
.ring .rf{stroke:var(--h,var(--accent)); transition:stroke-dashoffset .5s cubic-bezier(.22,1,.36,1)}
.ring .rn{position:absolute; font-size:.8rem; font-weight:700; line-height:1}
.ring.full .rf{stroke:var(--ok)}
.ring.full .rn{color:var(--ok)}

p.left{margin:-12px 0 22px; font-size:.86rem; color:var(--muted); padding-left:2px}

@media (prefers-reduced-motion:reduce){
  .ring .rf{transition:none}
  a.resume:hover{transform:none}
  .card:hover{transform:none}
}

/* Instructor dashboard. A dense grid on purpose: the question is "who is stuck
   and who is coasting", which is a scan across 17 columns, not a browse. */
.wrap.wide{max-width:1180px}
.sum{font-size:.95rem; color:var(--muted); margin:0 0 16px}
.sum b{color:var(--text); font-variant-numeric:tabular-nums}

.tablewrap{overflow-x:auto; border:1px solid var(--border); border-radius:var(--radius); background:var(--surface)}
/* Named .matrix, not .grid: the lab cards on the index page use
   .grid{display:grid}, which also matched <table class="grid"> and turned the
   dashboard into a grid container. Its head and first row were then two items
   in one grid row -- same y, columns two pixels wide, nothing lining up. A
   display:table override would have fixed the symptom and left the collision.

   border-collapse:collapse and position:sticky cannot both apply to a cell:
   collapsing merges cell borders into the table's own box, and the sticky cell
   is then laid out apart from the row it belongs to. The header detached and
   sat on top of the first data rows. separate + border-spacing:0 keeps the
   same visual result and lets the header stick. */
/* sized by its columns, not stretched to the box: max-width on a cell does
   not bound a table column, so stretching handed the slack to the name
   column and left a gap between the names and the first lab */
table.matrix{border-collapse:separate; border-spacing:0; font-size:.8rem}
table.matrix th, table.matrix td{border-bottom:1px solid var(--border); padding:0}
table.matrix thead th{
  /* sticky resolves against .tablewrap, which scrolls, not against the page,
     so offsetting by the site header's height pushed this down over the rows */
  position:sticky; top:0; z-index:2; background:var(--surface-2);
  font-weight:600; color:var(--muted); font-size:.7rem; padding:8px 4px; text-align:center;
}
table.matrix th.who, table.matrix td.who{
  text-align:left; padding:7px 12px; white-space:nowrap; position:sticky; left:0;
  background:var(--surface); z-index:1;
  /* a cap with no floor let the column shrink to three characters once the
     lab columns claimed the width; every name read the same */
  min-width:190px; max-width:230px; overflow:hidden; text-overflow:ellipsis;
}
table.matrix thead th.who{z-index:3; background:var(--surface-2)}
/* still only an address: this row cannot be matched to a grade sheet yet */
table.matrix td.who.nopf{color:var(--muted); font-style:italic}
table.matrix td{width:34px; height:30px}
table.matrix td.u{background:var(--surface)}
table.matrix td.o{background:color-mix(in srgb,var(--accent) 26%,transparent)}
table.matrix td.d{background:color-mix(in srgb,var(--ok) 46%,transparent)}
table.matrix td.r{box-shadow:inset 0 0 0 2px var(--warn)}
table.matrix td.tot, table.matrix th.tot{
  /* Every other column states a width, so in an auto layout this one absorbed
     all the slack from width:100% -- 900px of it -- and squeezed the seventeen
     lab columns to two pixels each. */
  width:72px; text-align:right; padding-right:12px; white-space:nowrap;
  font-variant-numeric:tabular-nums; color:var(--muted);
}
table.matrix tbody tr:hover td{filter:brightness(1.15)}

ul.legend{list-style:none; display:flex; flex-wrap:wrap; gap:18px; padding:0; margin:14px 0 0; font-size:.82rem; color:var(--muted)}
ul.legend i{display:inline-block; width:15px; height:15px; border-radius:4px; vertical-align:-3px; margin-right:7px; border:1px solid var(--border)}
ul.legend i.u{background:var(--surface)}
ul.legend i.o{background:color-mix(in srgb,var(--accent) 26%,transparent)}
ul.legend i.d{background:color-mix(in srgb,var(--ok) 46%,transparent)}
ul.legend i.d.r{box-shadow:inset 0 0 0 2px var(--warn)}


/* ── profile form ─────────────────────────────────────────────────────────── */
form.pform{display:flex; flex-direction:column; gap:14px; max-width:26rem; margin:18px 0 0}
form.pform label{display:flex; flex-direction:column; gap:6px; font-weight:600; font-size:.92rem}
form.pform input{
  font:inherit; font-weight:400; padding:10px 12px; border-radius:10px;
  border:1px solid var(--border); background:var(--surface); color:var(--text);
}
form.pform input:focus-visible{outline:2px solid var(--accent); outline-offset:2px}
form.pform .req{color:var(--warn)}
form.pform button{align-self:flex-start; margin-top:4px}
.note.warnbox{border-color:var(--warn)}

/* the prompt shown until a student has told us who they are */
.pfbanner{
  display:flex; flex-wrap:wrap; align-items:center; gap:12px;
  margin:0 0 16px; padding:12px 16px; border-radius:var(--radius);
  border:1px solid var(--accent); background:var(--accent-soft); font-size:.92rem;
}
.pfbanner a.btn{margin-left:auto}


/* ── IPv4 bit arithmetic ──────────────────────────────────────────────────
   The whole point of this page is that the columns line up: a student reads
   down a column to see which bits the mask keeps. Everything here is in
   service of that, which is why the binary is monospace and never wraps. */
.bitbox{
  margin:16px 0; padding:14px 16px; border:1px solid var(--border);
  border-radius:var(--radius); background:var(--surface-2); overflow-x:auto;
}
.brow{display:flex; align-items:baseline; gap:14px; padding:3px 0; white-space:nowrap}
.brow.head{color:var(--muted); font-size:.78rem; padding-bottom:6px}
.blab{flex:none; width:9.5rem; text-align:right; font-size:.84rem; color:var(--muted)}
.bbin{
  flex:none; font-family:var(--mono); font-size:.86rem; letter-spacing:.06em;
  font-variant-numeric:tabular-nums;
}
.bbin b{font-weight:600}
.bbin b.n{color:var(--accent)}          /* network bits */
.bbin b.h{color:var(--muted)}           /* host bits */
.bbin i.dot{color:var(--muted); font-style:normal; opacity:.55}
.bdec{flex:none; width:9rem; font-family:var(--mono); font-size:.84rem; color:var(--text)}
/* the binary must never wrap; the note may, so a long one is readable
   rather than clipped at the edge of the scroll box */
.bnote{color:var(--muted); font-size:.8rem; white-space:normal}
.bline{border-top:1px solid var(--accent); margin:6px 0 6px 9.5rem; max-width:22rem}
.bitbox.calc .brow:last-child .bdec{font-weight:700}

/* the legend swatches reuse the same two colours */
.reshint b.n{color:var(--accent)}
.reshint b.h{color:var(--muted)}

p.formula{
  font-family:var(--mono); font-size:1rem; text-align:center; margin:14px 0;
  padding:12px; border:1px dashed var(--accent); border-radius:var(--radius);
  background:var(--accent-soft);
}

table.ref{border-collapse:separate; border-spacing:0; width:100%; font-size:.88rem}
table.ref th, table.ref td{
  padding:8px 12px; border-bottom:1px solid var(--border); text-align:left;
  font-variant-numeric:tabular-nums;
}
table.ref th{background:var(--surface-2); color:var(--muted); font-size:.8rem; font-weight:600}
table.ref td:first-child{font-family:var(--mono); font-weight:600}

@media (max-width:640px){
  .blab{width:7rem; font-size:.76rem}
  .bbin{font-size:.72rem; letter-spacing:.03em}
  .bdec{width:7.5rem; font-size:.76rem}
  .bnote{display:none}
  .bline{margin-left:7rem}
}


/* ── course unit: watch, then build ───────────────────────────────────────
   Replaces a grid of equal cards. A grid says "pick any"; a course has an
   order, and a beginner following one needs to be told what it is. */
.unit{margin:38px 0 0; padding-top:26px; border-top:1px solid var(--border)}
.unit:first-of-type{border-top:0; padding-top:6px}
.unit h2{display:flex; align-items:center; gap:11px; flex-wrap:wrap; margin:0 0 6px}
.unit .theme{margin:0 0 16px; color:var(--muted); max-width:68ch; text-wrap:pretty}
.unit h3{
  font-size:.82rem; font-weight:700; letter-spacing:.02em; color:var(--muted);
  margin:0 0 8px;
}

/* theory first — named clips, not a link to a wall of a hundred */
.pre{margin:0 0 18px}
ul.unit-watch{list-style:none; padding:0; margin:0; display:flex; flex-wrap:wrap; gap:8px}
ul.unit-watch li{margin:0}
ul.unit-watch a{
  display:inline-block; padding:7px 13px; border-radius:99px; text-decoration:none;
  border:1px solid var(--border); background:var(--surface); font-size:.86rem;
  color:var(--text); transition:border-color .16s ease, background .16s ease;
}
ul.unit-watch a::before{content:"▶ "; color:var(--h, var(--accent)); font-size:.8em}
ul.unit-watch a:hover{border-color:var(--h, var(--accent)); background:var(--h-soft, var(--accent-soft))}
ul.unit-watch li.doc a::before{content:"📄 "}
ul.unit-watch li.doc .sub{display:none}
ul.unit-watch li.more a{border-style:dashed; color:var(--muted)}
ul.unit-watch li.more a::before{content:""}

/* the labs, as the sequence they are */
ol.unit-labs{list-style:none; padding:0; margin:0; display:flex; flex-direction:column; gap:7px}
ol.unit-labs li{margin:0}
a.lab-row{
  display:flex; align-items:center; gap:14px; padding:13px 16px; text-decoration:none;
  border:1px solid var(--border); border-radius:var(--radius); background:var(--surface);
  color:var(--text); transition:border-color .16s ease, transform .16s ease, background .16s ease;
}
a.lab-row:hover{border-color:var(--h, var(--accent)); transform:translateX(3px)}
a.lab-row .sn{
  flex:none; width:2.1rem; font-family:var(--mono); font-size:1.02rem; font-weight:700;
  color:var(--h, var(--accent)); font-variant-numeric:tabular-nums;
}
a.lab-row .name{flex:1; font-weight:600; font-size:.98rem; min-width:0}
a.lab-row .dur{flex:none; color:var(--muted); font-size:.82rem; white-space:nowrap}
a.lab-row .tick{
  flex:none; width:20px; height:20px; border-radius:50%; border:1.5px solid var(--border);
  display:grid; place-items:center; font-size:.72rem; color:var(--surface);
}
a.lab-row.done{background:var(--surface-2); border-color:var(--ok)}
a.lab-row.done .tick{background:var(--ok); border-color:var(--ok); color:#fff}
a.lab-row.done .tick::after{content:"✓"}
a.lab-row.done .name{color:var(--muted)}

@media (prefers-reduced-motion: reduce){
  a.lab-row, ul.unit-watch a{transition:none}
  a.lab-row:hover{transform:none}
}

@media (max-width:560px){
  a.lab-row{gap:10px; padding:11px 13px}
  a.lab-row .dur{display:none}
  a.lab-row .name{font-size:.92rem}
}


/* ── past the end of the course ───────────────────────────────────────────
   97 clips that are not part of this course but are worth keeping. Closed by
   default: present when wanted, never in the way of the 114 that are. */
details.beyond{
  border:1px solid var(--border); border-radius:var(--radius);
  background:var(--surface); margin:10px 0 0;
}
details.beyond > summary{
  display:flex; align-items:center; gap:10px; padding:13px 16px; cursor:pointer;
  font-weight:600; font-size:.95rem; list-style:none;
}
details.beyond > summary::-webkit-details-marker{display:none}
details.beyond > summary::before{
  content:"▸"; color:var(--accent); font-size:.9em; transition:transform .16s ease;
}
details.beyond[open] > summary::before{transform:rotate(90deg)}
details.beyond > summary:hover{background:var(--surface-2)}
details.beyond > summary .bt{flex:1; min-width:0}
details.beyond > .reshint, details.beyond > .vids, details.beyond > .examlist{
  padding:0 16px 16px;
}
details.beyond > .reshint{margin-top:0}

@media (prefers-reduced-motion: reduce){
  details.beyond > summary::before{transition:none}
}


/* ── sign-in ──────────────────────────────────────────────────────────────
   The only page a student sees before they are known, and often the only one
   they see if something is wrong. It says what to do and, when it refuses,
   which address it refused. */
.wrap.narrow{max-width:34rem}
.signin{
  display:flex; flex-direction:column; align-items:center; gap:16px;
  padding:30px 24px; margin:8px 0 22px;
  border:1px solid var(--border); border-radius:var(--radius); background:var(--surface);
}
.signin .hint{margin:0; min-height:1.4em; font-size:.9rem; color:var(--muted); text-align:center}
.signin .hint.bad{color:var(--warn); font-weight:600}


/* ── access management ────────────────────────────────────────────────────
   The instructor's own tool. Density is fine here; what matters is that a
   name is findable and a removal is hard to do by accident. */
form.raddform{
  display:flex; flex-wrap:wrap; gap:12px; align-items:flex-end;
  margin:16px 0 18px; padding:16px; border:1px solid var(--border);
  border-radius:var(--radius); background:var(--surface);
}
form.raddform label{display:flex; flex-direction:column; gap:6px; font-size:.85rem;
  font-weight:600; flex:1; min-width:14rem}
form.raddform input, form.raddform select, .rtools input{
  font:inherit; font-weight:400; padding:9px 12px; border-radius:9px;
  border:1px solid var(--border); background:var(--surface-2); color:var(--text);
}
form.raddform label:first-child{flex:3}
form.raddform select{min-width:9rem}
.rtools{margin:0 0 10px}
.rtools input{width:100%; max-width:26rem}
form.raddform input:focus-visible, form.raddform select:focus-visible,
.rtools input:focus-visible{outline:2px solid var(--accent); outline-offset:2px}

table.rtable td, table.rtable th{padding:9px 12px; text-align:left; width:auto; height:auto}
table.rtable td.rmail{font-family:var(--mono); font-size:.82rem}
table.rtable td.rrole, table.rtable td.rnum{white-space:nowrap; color:var(--muted); font-size:.86rem}
table.rtable td.rnum{text-align:right; font-variant-numeric:tabular-nums}
table.rtable .rdel{color:var(--warn); border-color:var(--border)}
table.rtable .rdel:disabled{opacity:.4; cursor:not-allowed; color:var(--muted)}
table.rtable tbody tr:hover{background:var(--surface-2)}


/* ── course rail ──────────────────────────────────────────────────────────
   Modelled on a lesson player: the whole course stays in view with the
   current lab marked, so "how much is left" and "what comes next" stop
   costing a trip back to the index and a hunt for your place.

   Fixed rather than sticky because the lab pages are long documents; the rail
   scrolls on its own. */
:root{--rail-w:310px}

.rail{
  position:fixed; inset:0 auto 0 0; width:var(--rail-w); z-index:20;
  display:flex; flex-direction:column; overflow-y:auto; overscroll-behavior:contain;
  background:var(--surface-2); border-right:1px solid var(--border);
}
.rail-head{padding:16px 18px 14px; border-bottom:1px solid var(--border)}
.rail-back{font-size:.82rem; color:var(--muted); text-decoration:none}
.rail-back:hover{color:var(--accent)}
.rail-title{margin:8px 0 12px; font-weight:700; font-size:.95rem; line-height:1.45}
.rail-prog{margin:0}
.rail-prog .label{font-size:.78rem}
.rail-prog .row{margin-top:5px}
.rail-count{margin:10px 0 0; font-size:.76rem; color:var(--muted)}

.rail-units{padding:6px 0 30px}
details.ru-unit{border-bottom:1px solid var(--border)}
details.ru-unit > summary{
  display:flex; align-items:center; gap:9px; padding:12px 18px; cursor:pointer;
  list-style:none; font-size:.86rem;
}
details.ru-unit > summary::-webkit-details-marker{display:none}
details.ru-unit > summary:hover{background:var(--surface)}
.ru-ico{flex:none; font-size:.95rem}
.ru-name{flex:1; min-width:0; font-weight:600; overflow:hidden; text-overflow:ellipsis;
  white-space:nowrap}
.ru-sub{display:none}
.ru-pct{
  flex:none; font-size:.74rem; color:var(--muted); font-variant-numeric:tabular-nums;
  border:1px solid var(--border); border-radius:99px; padding:2px 8px;
}
details.ru-unit[open] > summary .ru-name{color:var(--h, var(--accent))}

details.ru-unit ul{list-style:none; margin:0; padding:0 0 8px}
a.ru-lab{
  display:flex; align-items:center; gap:10px; padding:8px 18px 8px 16px;
  text-decoration:none; color:var(--text); font-size:.85rem;
  border-left:3px solid transparent;
}
a.ru-lab:hover{background:var(--surface)}
a.ru-lab .ru-n{
  flex:none; width:1.7rem; font-family:var(--mono); font-size:.8rem; font-weight:700;
  color:var(--muted); font-variant-numeric:tabular-nums;
}
a.ru-lab .ru-t{flex:1; min-width:0; overflow:hidden; text-overflow:ellipsis; white-space:nowrap}
a.ru-lab .ru-d{flex:none; font-size:.74rem; color:var(--muted); white-space:nowrap}
a.ru-lab .tick{
  flex:none; width:15px; height:15px; border-radius:4px; border:1.5px solid var(--border);
  display:grid; place-items:center; font-size:.6rem; color:transparent;
}
a.ru-lab.done .tick{background:var(--ok); border-color:var(--ok); color:#fff}
a.ru-lab.done .tick::after{content:"✓"}
a.ru-lab.done .ru-t{color:var(--muted)}

/* where you are */
a.ru-lab[aria-current="page"]{
  background:var(--h-soft, var(--accent-soft)); border-left-color:var(--h, var(--accent));
  font-weight:600;
}
a.ru-lab[aria-current="page"] .ru-n{color:var(--h, var(--accent))}
a.ru-lab:focus-visible{outline:2px solid var(--accent); outline-offset:-2px}

/* the page beside it */
body.has-rail header.top,
body.has-rail main,
body.has-rail footer{margin-left:var(--rail-w)}
body.has-rail.rail-hidden .rail{transform:translateX(-100%)}
body.has-rail.rail-hidden header.top,
body.has-rail.rail-hidden main,
body.has-rail.rail-hidden footer{margin-left:0}
.rail{transition:transform .18s cubic-bezier(.22,1,.36,1)}
body.has-rail header.top, body.has-rail main, body.has-rail footer{
  transition:margin-left .18s cubic-bezier(.22,1,.36,1);
}
.railtoggle{flex:none; margin-right:4px; font-size:1rem; line-height:1}

@media (prefers-reduced-motion: reduce){
  .rail, body.has-rail header.top, body.has-rail main, body.has-rail footer{transition:none}
}

/* Narrow: the rail would leave no room for the lab itself, so it slides over
   the page instead of beside it and starts closed. A student on a laptop has
   Packet Tracer taking half the screen. */
@media (max-width:1100px){
  body.has-rail header.top,
  body.has-rail main,
  body.has-rail footer{margin-left:0}
  .rail{transform:translateX(-100%); box-shadow:var(--shadow)}
  body.has-rail.rail-open .rail{transform:none}
}

/* ── หน้าแนะนำวิชา (course.html) ─────────────────────────────────────────────
   The one page a stranger can open. It carries no lesson material -- unit
   names, goals and lab counts only -- so it is laid out to be read once and
   acted on, not browsed: the way in sits above the syllabus, because someone
   who is already on the course should not have to scroll past a description
   they no longer need. */
.enrol-box{
  margin:30px 0 8px; padding:22px 24px;
  border:1px solid var(--accent); border-radius:var(--radius);
  background:var(--accent-soft);
}
.enrol-box h2{margin:0 0 12px; font-size:1.12rem}
.enrol-box .reshint{margin:14px 0 0; color:var(--muted)}
@media (max-width:560px){ .enrol-box{padding:18px 16px} }

/* The address Google vouched for, shown back so it is obvious which account a
   request will be filed under -- students sign in to more than one. */
/* An address is one unbreakable token; a long one pushes the whole page wider
   than the phone it is being read on. */
.en-who{margin:0 0 4px; color:var(--muted); font-size:.92rem; overflow-wrap:anywhere}
.en-who b{color:var(--text); font-weight:600}
.en-state{margin:0 0 6px; font-size:1.05rem; font-weight:600; color:var(--ok)}
.en-note{margin:0; color:var(--muted); font-size:.93rem}
.en-note.bad{color:var(--warn)}
.enrol-box form.pform{margin-top:12px}
.enrol-box form.pform label{font-size:.88rem}
.opt{font-weight:400; color:var(--muted)}

/* The filled button: one per screen, and it is always the thing to do next. */
.btn.primary{
  background:var(--accent); border-color:var(--accent); color:#fff;
  font-size:.95rem; padding:9px 18px; font-weight:600;
}
.btn.primary:hover{filter:brightness(1.08); color:#fff; border-color:var(--accent)}

/* What the course covers, at the depth of a syllabus. Not links: there is
   nothing behind them yet for the person reading this. */
ul.courseunits{list-style:none; margin:14px 0 0; padding:0; display:grid; gap:10px}
ul.courseunits li{
  display:flex; align-items:flex-start; gap:14px; padding:14px 16px;
  border:1px solid var(--border); border-radius:var(--radius); background:var(--surface);
}
.cu-ico{flex:none; font-size:1.3rem; line-height:1.4}
.cu-b{display:flex; flex-direction:column; gap:2px; flex:1; min-width:0}
.cu-b b{font-weight:600; font-size:.98rem}
.cu-b span{color:var(--muted); font-size:.89rem; line-height:1.6}
.cu-n{
  flex:none; color:var(--muted); font-size:.82rem; white-space:nowrap;
  font-variant-numeric:tabular-nums; padding-top:2px;
}
@media (max-width:560px){
  ul.courseunits li{gap:11px; padding:12px 13px}
  .cu-n{display:none}   /* the count matters least on the narrowest screen */
}

/* ── คิวคำขอเข้าเรียน (teacher/access.html) ──────────────────────────────────
   Above the roster and hidden when empty: a permanently visible empty queue
   trains the eye to skip the region, and then a real request arrives into a
   space that is no longer being read. */
.pendbox{
  margin:0 0 22px; padding:18px 20px;
  border:1px solid var(--warn); border-radius:var(--radius);
  background:var(--surface);
}
.pendbox h2{margin:0 0 12px; font-size:1.02rem}
.pcount{color:var(--warn); font-variant-numeric:tabular-nums}
ul.pendlist{list-style:none; margin:0; padding:0; display:grid; gap:9px}
ul.pendlist li{
  display:flex; align-items:center; gap:14px; flex-wrap:wrap;
  padding:11px 14px; border:1px solid var(--border);
  border-radius:10px; background:var(--surface-2);
}
.pendlist .pw{display:flex; flex-direction:column; gap:1px; flex:1; min-width:14rem}
.pendlist .pw b{font-weight:600; font-size:.94rem; word-break:break-all}
.pendlist .pnote{color:var(--text); font-size:.88rem; overflow-wrap:anywhere}
.pendlist .pwhen{color:var(--muted); font-size:.78rem}
.pendlist .pbtn{display:flex; gap:8px; flex:none}
.pendlist .pok{border-color:var(--ok); color:var(--ok)}
.pendlist .pok:hover{background:var(--ok); color:#fff}
.pendlist .pno:hover{border-color:var(--warn); color:var(--warn)}
.pendlist .btn:disabled{opacity:.5; cursor:default}
