|
7 | 7 | <title>pingping — link quality oscilloscope</title> |
8 | 8 | <style> |
9 | 9 | :root { |
10 | | - --bg:#0a0c0e; --panel:#101613; --screen:#060808; --line:#1e242a; |
11 | | - --phos:#7ce38b; --amber:#e8b44a; --alert:#ff5c57; --ink:#c7d0c9; --dim:#5c6b60; |
12 | | - --grid-axis:#2a332c; --grid-split:#10281a; |
13 | | - --smoke:rgba(124,227,139,.16); --lossbar:rgba(255,92,87,.55); --glow:6; |
14 | | - --smoke-hot:#d8ffe2; --smoke-mid:#7ce38b; --smoke-cool:#8a7a3a; |
| 10 | + --bg:#14161a; --panel:#1c2027; --screen:#0d0f13; --line:#2b323c; |
| 11 | + --phos:#22d3ee; --amber:#fbbf24; --alert:#fb3b53; --ink:#c0c6ce; --dim:#78848f; |
| 12 | + --grid-axis:#333b47; --grid-split:#1c222a; |
| 13 | + --smoke:rgba(251,191,36,.20); --lossbar:rgba(251,59,83,.7); --glow:5; |
| 14 | + --smoke-hot:#b86e14; --smoke-mid:#8c3f0d; --smoke-cool:#452740; |
| 15 | + --shadow:0 1px 2px rgba(0,0,0,.45); --shadow-lg:0 12px 32px rgba(0,0,0,.45); |
15 | 16 | --mono: ui-monospace,"SF Mono","Cascadia Mono",Consolas,"Noto Sans Mono",monospace; |
| 17 | + /* Interface text gets the system UI face; numbers and axis labels stay monospace |
| 18 | + so digits line up and keep the instrument feel. Mixing the two is what separates |
| 19 | + a product from terminal output. */ |
| 20 | + --sans: system-ui,-apple-system,"Segoe UI",Roboto,"Helvetica Neue",Arial,sans-serif; |
| 21 | + /* A real scale instead of everything crowded between 10 and 13px. */ |
| 22 | + --fs-micro:10px; --fs-small:11px; --fs-body:13px; --fs-lead:15px; |
| 23 | + --fs-title:19px; --fs-metric:30px; |
16 | 24 | } |
17 | | - /* Daylight: warm paper — the trace printed on lab graph paper */ |
| 25 | + |
| 26 | + /* Daylight — ink on lab paper. Core burns terracotta, edges cool to slate. */ |
18 | 27 | html[data-theme="daylight"] { |
19 | | - --bg:#f4f1e8; --panel:#faf8f1; --screen:#fffef9; --line:#e0dbc9; |
20 | | - --phos:#177245; --amber:#986a00; --alert:#c23a32; --ink:#2b2f28; --dim:#8b8a7a; |
21 | | - --grid-axis:#cfc9b4; --grid-split:#ebe6d4; |
22 | | - --smoke:rgba(23,114,69,.20); --lossbar:rgba(194,58,50,.5); --glow:0; |
23 | | - --smoke-hot:#0e5e37; --smoke-mid:#2f9e63; --smoke-cool:#b08a2e; |
| 28 | + --bg:#f2efe6; --panel:#fbf9f3; --screen:#fffdf7; --line:#ddd6c4; |
| 29 | + --phos:#1d4ed8; --amber:#b45309; --alert:#be123c; --ink:#3e4346; --dim:#8a8677; |
| 30 | + --grid-axis:#cdc6b2; --grid-split:#e9e3d3; |
| 31 | + --smoke:rgba(180,83,9,.22); --lossbar:rgba(190,18,60,.6); --glow:0; |
| 32 | + --smoke-hot:#e07a3a; --smoke-mid:#e8a878; --smoke-cool:#cfc8b8; |
| 33 | + --shadow:0 1px 3px rgba(80,70,40,.12); --shadow-lg:0 12px 30px rgba(80,70,40,.16); |
24 | 34 | } |
25 | | - /* Arctic: cool morning light — teal trace on frosted glass */ |
| 35 | + |
| 36 | + /* Arctic — near-black trace. Cloud runs from deep sea to pale frost. */ |
26 | 37 | html[data-theme="arctic"] { |
27 | | - --bg:#edf1f5; --panel:#f6f9fb; --screen:#fbfdfe; --line:#d7e0e8; |
28 | | - --phos:#0b7285; --amber:#b45309; --alert:#d1433f; --ink:#24313d; --dim:#7f8f9d; |
29 | | - --grid-axis:#c3d0db; --grid-split:#e3ebf2; |
30 | | - --smoke:rgba(11,114,133,.18); --lossbar:rgba(209,67,63,.5); --glow:0; |
31 | | - --smoke-hot:#064a57; --smoke-mid:#1596ad; --smoke-cool:#b3722f; |
32 | | - } |
33 | | - /* Nord — the arctic palette that ships in half the terminals on earth. |
34 | | - Desaturated blue-greys with a single frost accent; nothing shouts. */ |
35 | | - html[data-theme="nord"] { |
36 | | - --bg:#2e3440; --panel:#3b4252; --screen:#292e39; --line:#434c5e; |
37 | | - --phos:#88c0d0; --amber:#ebcb8b; --alert:#bf616a; --ink:#e5e9f0; --dim:#7b88a1; |
38 | | - --grid-axis:#4c566a; --grid-split:#373e4c; |
39 | | - --smoke:rgba(136,192,208,.18); --lossbar:rgba(191,97,106,.55); --glow:5; |
40 | | - --smoke-hot:#eceff4; --smoke-mid:#88c0d0; --smoke-cool:#5e81ac; |
41 | | - --shadow:0 1px 2px rgba(0,0,0,.35); --shadow-lg:0 10px 30px rgba(0,0,0,.30); |
| 38 | + --bg:#eaeff4; --panel:#f7fafc; --screen:#fdfeff; --line:#d3dce5; |
| 39 | + --phos:#0f172a; --amber:#0369a1; --alert:#dc2626; --ink:#3a4353; --dim:#7d8b99; |
| 40 | + --grid-axis:#c2cdd8; --grid-split:#e2e9f0; |
| 41 | + --smoke:rgba(56,132,199,.22); --lossbar:rgba(220,38,38,.55); --glow:0; |
| 42 | + --smoke-hot:#4a9fd4; --smoke-mid:#8dc0e0; --smoke-cool:#cfe0ec; |
| 43 | + --shadow:0 1px 3px rgba(30,50,70,.10); --shadow-lg:0 12px 30px rgba(30,50,70,.14); |
42 | 44 | } |
43 | | - /* Solarized Light — Ethan Schoonover's palette, tuned for long reading sessions. |
44 | | - Warm paper base, muted cyan trace, red reserved strictly for loss. */ |
45 | | - html[data-theme="solarized"] { |
46 | | - --bg:#fdf6e3; --panel:#fffbf0; --screen:#fffdf6; --line:#e5ddc8; |
47 | | - --phos:#2aa198; --amber:#b58900; --alert:#dc322f; --ink:#586e75; --dim:#93a1a1; |
48 | | - --grid-axis:#d6cfba; --grid-split:#efe8d5; |
49 | | - --smoke:rgba(42,161,152,.22); --lossbar:rgba(220,50,47,.45); --glow:0; |
50 | | - --smoke-hot:#0f5f5a; --smoke-mid:#2aa198; --smoke-cool:#93a1a1; |
51 | | - --shadow:0 1px 3px rgba(101,123,131,.12); --shadow-lg:0 10px 28px rgba(101,123,131,.16); |
| 45 | + |
| 46 | + /* Budapest — Anderson's plum and rose. Core is deep raspberry, edges go powder. */ |
| 47 | + html[data-theme="budapest"] { |
| 48 | + --bg:#f7ebe8; --panel:#fdf5f2; --screen:#fffaf8; --line:#e6cfc8; |
| 49 | + --phos:#5b2a4f; --amber:#c9754f; --alert:#c1362f; --ink:#4c3d41; --dim:#9c8087; |
| 50 | + --grid-axis:#dcc0b8; --grid-split:#f0e0da; |
| 51 | + --smoke:rgba(216,133,140,.26); --lossbar:rgba(193,54,47,.55); --glow:0; |
| 52 | + --smoke-hot:#e0748c; --smoke-mid:#eaa8ae; --smoke-cool:#f0dbd2; |
| 53 | + --shadow:0 1px 3px rgba(120,80,80,.12); --shadow-lg:0 12px 30px rgba(120,80,80,.16); |
52 | 54 | } |
53 | | - /* Amber CRT — a DEC VT220 in a dim room. One hue, three intensities, that is it. */ |
| 55 | + |
| 56 | + /* Amber CRT — a VT220 left on overnight. The cloud is pure phosphor decay: |
| 57 | + white-hot core, amber body, dying green at the fringe, exactly how a long |
| 58 | + persistence tube fades. The trace stays a cooler gold so it sits above it. */ |
54 | 59 | html[data-theme="amber"] { |
55 | | - --bg:#100c04; --panel:#1a1409; --screen:#0a0702; --line:#3a2c14; |
56 | | - --phos:#ffb000; --amber:#ffcc55; --alert:#ff5f2e; --ink:#f0c674; --dim:#8a6d3a; |
57 | | - --grid-axis:#463a1c; --grid-split:#221a0c; |
58 | | - --smoke:rgba(255,176,0,.16); --lossbar:rgba(255,95,46,.5); --glow:8; |
59 | | - --smoke-hot:#fff3d0; --smoke-mid:#ffb000; --smoke-cool:#7a5410; |
60 | | - --shadow:0 1px 2px rgba(0,0,0,.6); --shadow-lg:0 10px 30px rgba(0,0,0,.55); |
| 60 | + --bg:#12100a; --panel:#1c1810; --screen:#0a0806; --line:#38301c; |
| 61 | + --phos:#ffd75e; --amber:#ffd98a; --alert:#ff5f2e; --ink:#cebd95; --dim:#8f7b4e; |
| 62 | + --grid-axis:#443a20; --grid-split:#1e1a10; |
| 63 | + --smoke:rgba(255,176,0,.20); --lossbar:rgba(255,95,46,.65); --glow:7; |
| 64 | + --smoke-hot:#a86a10; --smoke-mid:#7d4508; --smoke-cool:#2f4429; |
| 65 | + --shadow:0 1px 2px rgba(0,0,0,.6); --shadow-lg:0 12px 32px rgba(0,0,0,.55); |
61 | 66 | } |
| 67 | + |
62 | 68 | * { box-sizing:border-box; margin:0; } |
63 | | - body { background:var(--bg); color:var(--ink); font-family:var(--mono); padding:18px 22px; } |
| 69 | + body { background:var(--bg); color:var(--ink); font-family:var(--sans); |
| 70 | + font-size:var(--fs-body); line-height:1.5; padding:20px 24px; |
| 71 | + -webkit-font-smoothing:antialiased; text-rendering:optimizeLegibility; } |
64 | 72 | header { display:flex; align-items:baseline; gap:14px; margin-bottom:14px; flex-wrap:wrap; } |
65 | | - .mark { color:var(--phos); font-weight:700; font-size:20px; letter-spacing:.05em; } |
66 | | - .tag { color:var(--dim); font-size:12px; } |
| 73 | + .mark { color:var(--phos); font-family:var(--mono); font-weight:700; |
| 74 | + font-size:var(--fs-title); letter-spacing:.04em; } |
| 75 | + .tag { color:var(--dim); font-size:var(--fs-small); font-weight:400; letter-spacing:.01em; } |
67 | 76 | .row { display:flex; gap:12px; align-items:flex-start; margin-bottom:14px; flex-wrap:wrap; } |
68 | 77 | .pills { display:flex; gap:8px; flex-wrap:wrap; } |
69 | | - .pill { font-family:var(--mono); font-size:13px; background:var(--panel); color:var(--ink); |
70 | | - border:1px solid var(--line); border-radius:4px; padding:7px 14px; cursor:pointer; |
71 | | - display:flex; align-items:center; gap:8px; } |
72 | | - .pill.on { border-color:var(--phos); color:var(--phos); } |
| 78 | + .pill { font-family:var(--sans); font-size:var(--fs-body); font-weight:500; |
| 79 | + background:var(--panel); color:var(--ink); |
| 80 | + border:1px solid var(--line); border-radius:6px; padding:7px 14px; cursor:pointer; |
| 81 | + display:flex; align-items:center; gap:8px; transition:border-color .12s, color .12s; } |
| 82 | + .pill.on { border-color:var(--phos); color:var(--phos); font-weight:600; } |
73 | 83 | .led { width:8px; height:8px; border-radius:50%; background:var(--phos); box-shadow:0 0 6px var(--phos); } |
74 | 84 | .led.bad { background:var(--alert); box-shadow:0 0 6px var(--alert); } |
75 | 85 | .rng { display:flex; background:var(--panel); border:1px solid var(--line); border-radius:4px; overflow:hidden; } |
76 | | - .rng span { color:var(--dim); font-size:11px; padding:8px 10px 0 12px; letter-spacing:.1em; } |
77 | | - .rng button { font-family:var(--mono); font-size:12px; background:none; border:0; color:var(--dim); |
78 | | - padding:8px 14px; cursor:pointer; } |
79 | | - .rng button.on { background:#1a2018; color:var(--amber); } |
| 86 | + .rng span { color:var(--dim); font-family:var(--sans); font-size:var(--fs-micro); |
| 87 | + font-weight:600; padding:9px 10px 0 12px; letter-spacing:.14em; } |
| 88 | + .rng button { font-family:var(--mono); font-size:var(--fs-small); background:none; border:0; |
| 89 | + color:var(--dim); padding:8px 13px; cursor:pointer; transition:color .12s; } |
| 90 | + .rng button:hover { color:var(--ink); } |
| 91 | + .rng button.on { background:color-mix(in srgb, var(--amber) 15%, transparent); |
| 92 | + color:var(--amber); font-weight:700; } |
80 | 93 | .scope { background:var(--panel); border:1px solid var(--line); border-radius:6px; padding:14px; } |
81 | 94 | .crt { position:relative; } |
82 | 95 | #chart { height:420px; background:var(--screen); border-radius:4px; } |
|
87 | 100 | radial-gradient(120% 90% at 50% 42%, transparent 55%, rgba(0,0,0,.38) 100%); |
88 | 101 | } |
89 | 102 | .readouts { display:flex; gap:34px; margin-top:12px; flex-wrap:wrap; align-items:flex-end; } |
90 | | - .ro .v { font-size:24px; color:var(--phos); } |
| 103 | + .ro .v { font-family:var(--mono); font-size:var(--fs-metric); font-weight:600; |
| 104 | + color:var(--phos); line-height:1.1; font-variant-numeric:tabular-nums; } |
91 | 105 | .ro .v.bad { color:var(--alert); } |
92 | | - .ro .l { font-size:10px; color:var(--dim); letter-spacing:.12em; margin-top:2px; } |
| 106 | + .ro .l { font-family:var(--sans); font-size:var(--fs-micro); font-weight:600; |
| 107 | + color:var(--dim); letter-spacing:.13em; margin-top:4px; text-transform:uppercase; } |
93 | 108 | .sp { flex:1; } |
94 | | - footer { margin-top:12px; color:var(--dim); font-size:12px; display:flex; gap:10px; flex-wrap:wrap; } |
95 | | - #conclusion { color:var(--ink); } |
96 | | - .legend { color:var(--dim); } |
| 109 | + footer { margin-top:14px; color:var(--dim); font-size:var(--fs-small); |
| 110 | + display:flex; gap:14px; flex-wrap:wrap; align-items:baseline; } |
| 111 | + #conclusion { color:var(--ink); font-family:var(--mono); font-weight:600; |
| 112 | + font-size:var(--fs-body); } |
| 113 | + .legend { color:var(--dim); font-family:var(--sans); font-size:var(--fs-small); } |
97 | 114 | .promos { display:grid; grid-template-columns:1fr 1fr; gap:14px; margin-top:16px; } |
98 | 115 | @media (max-width:720px) { .promos { grid-template-columns:1fr; } } |
99 | 116 | .promo { background:var(--panel); border:1px solid var(--line); border-radius:12px; padding:14px 16px; |
100 | 117 | box-shadow:var(--shadow); text-decoration:none; display:block; } |
101 | 118 | .promo.sponsor { border-style:dashed; } |
102 | 119 | .promo.sponsor:hover { border-color:var(--phos); } |
103 | | - .promo-h { font-family:var(--mono); font-size:10px; letter-spacing:.16em; color:var(--dim); margin-bottom:6px; } |
104 | | - .promo-b { color:var(--ink); font-size:13px; } |
| 120 | + .promo-h { font-family:var(--sans); font-size:var(--fs-micro); font-weight:700; |
| 121 | + letter-spacing:.16em; color:var(--dim); margin-bottom:7px; text-transform:uppercase; } |
| 122 | + .promo-b { color:var(--ink); font-size:var(--fs-body); } |
105 | 123 | .share .promo-b { display:flex; gap:14px; align-items:center; flex-wrap:wrap; } |
106 | 124 | .share a { color:var(--phos); text-decoration:none; font-weight:600; } |
107 | 125 | .share a:hover { text-decoration:underline; } |
|
0 commit comments