Refresh: full UI redesign + metrics explainer + AGENTS.md + mobile fixes
Browse files- .gitignore +4 -0
- AGENTS.md +58 -0
- README.md +2 -2
- app.py +352 -61
- theme.py +263 -11
.gitignore
CHANGED
|
@@ -25,3 +25,7 @@ SUPABASE_MIGRATION.md
|
|
| 25 |
builddemo.md
|
| 26 |
bdemo2.md
|
| 27 |
notes:.md.md
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 25 |
builddemo.md
|
| 26 |
bdemo2.md
|
| 27 |
notes:.md.md
|
| 28 |
+
|
| 29 |
+
# playwright MCP screenshot artifacts
|
| 30 |
+
.playwright-mcp/
|
| 31 |
+
_*.png
|
AGENTS.md
ADDED
|
@@ -0,0 +1,58 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# AGENTS.md — MO§ES SigRank
|
| 2 |
+
|
| 3 |
+
Guidance for AI coding agents (and humans) working in this repo. Read this before editing.
|
| 4 |
+
|
| 5 |
+
## What this is
|
| 6 |
+
**SIGRANK** (powered by MO§ES™) is a Gradio Space that ranks AI coding operators by
|
| 7 |
+
**architecture, not volume**. The core metric is **Υ = (Cache · Output) / Input²** — squaring
|
| 8 |
+
input punishes wasteful prompting while rewarding cache reuse and real output. Volume can't buy rank.
|
| 9 |
+
|
| 10 |
+
Live Space: `huggingface.co/spaces/burnmydays/sigrank`
|
| 11 |
+
|
| 12 |
+
## Run it
|
| 13 |
+
```bash
|
| 14 |
+
pip install -r requirements.txt
|
| 15 |
+
python app.py # launches the Gradio UI on :7860
|
| 16 |
+
python sigrank.py --help # local-first CLI importer (reads your own ccusage usage)
|
| 17 |
+
python metrics.py # prints the SEED corpus metrics (sanity check)
|
| 18 |
+
python -m pytest test_metrics.py # metric invariant tests
|
| 19 |
+
```
|
| 20 |
+
|
| 21 |
+
## Architecture (one job per file)
|
| 22 |
+
- `metrics.py` — the metric engine. `compute(i, o, cw, cr)` → full ledger (Υ, SNR, leverage,
|
| 23 |
+
velocity, 10x DEV, $/1M). Also holds the `SEED` corpus (MO§ES + wild operators from tokscale.ai).
|
| 24 |
+
- `ingest.py` — parsers. ccusage (Claude) and Codex JSON shapes → four token pillars. Codex input
|
| 25 |
+
is *estimated* (no native input field); see `_codex_input_estimate`.
|
| 26 |
+
- `app.py` — the Gradio UI. Tabs: **Home / Create / Leaders / VS / Reports**. Board rendering
|
| 27 |
+
(`board_html`), operator cards (`card_html`), compare (`compare_html`), insights (`insights_html`),
|
| 28 |
+
Home landing (`metric_features_html`, `home_html`).
|
| 29 |
+
- `theme.py` — all custom CSS (dark/gold). Mobile rules live in `@media (max-width: 700px)` blocks.
|
| 30 |
+
- `db.py` — optional Supabase persistence; falls back to `metrics.SEED` when unconfigured (works offline).
|
| 31 |
+
- `narrate.py` — optional MiniCPM-0.5B prose "operator reads" via `@spaces.GPU`; degrades to a
|
| 32 |
+
template when no GPU/torch (so the app runs fine on CPU).
|
| 33 |
+
- `sigrank.py` / `sigrank` — local-first CLI: reads your real ccusage usage on your machine, prints
|
| 34 |
+
your operator read, optional `--submit` to the board.
|
| 35 |
+
|
| 36 |
+
## Frozen invariants — DO NOT CHANGE without explicit instruction
|
| 37 |
+
- **`metrics.py` `SEED` numbers** — the canonical corpus. MO§ES row = `(1_251_211, 11_296_121,
|
| 38 |
+
128_196_310, 2_555_179_769)`. Changing these breaks the published leaderboard + tests.
|
| 39 |
+
- **The Υ formula** `(cache_read · output) / input²` and the telescoping identity
|
| 40 |
+
(10x DEV = log₁₀(leverage), Υ = leverage × velocity). `test_metrics.py` locks these.
|
| 41 |
+
- MO§ES Υ must print **18436.98**.
|
| 42 |
+
|
| 43 |
+
## Conventions
|
| 44 |
+
- **No secrets in the repo.** Keys live only in `SECRETS.local.md` (gitignored) and HF Space
|
| 45 |
+
Secrets. Never commit tokens/keys.
|
| 46 |
+
- **Supabase: new tables only.** Do not alter existing tables; SigRank uses its own.
|
| 47 |
+
- **Claude and Codex are measured separately** — never combine providers in one reading.
|
| 48 |
+
- **Deploy** by pushing to the Space git remote; the HF Space is the live deliverable. CI/tests
|
| 49 |
+
should stay green (`pytest`, `python -c "import app; app._build_demo()"`).
|
| 50 |
+
- Match the surrounding code style; keep changes minimal and verifiable.
|
| 51 |
+
|
| 52 |
+
## Metric definitions (match `metrics.compute` exactly)
|
| 53 |
+
- **Υ yield** = (cache_read · output) / input² — the rank metric.
|
| 54 |
+
- **SNR** = output / (input + output) — signal vs. noise.
|
| 55 |
+
- **leverage** = cache_read / input — cache reuse amplification.
|
| 56 |
+
- **velocity** = output / input — throughput.
|
| 57 |
+
- **10x DEV** = log₁₀(transmission × commitment × reuse) = log₁₀(leverage).
|
| 58 |
+
- **$/1M** = blended cost per million tokens across all states.
|
README.md
CHANGED
|
@@ -39,7 +39,7 @@ tags:
|
|
| 39 |
|
| 40 |
A leaderboard that judges AI coding operators by **architecture, not budget**.
|
| 41 |
Paste your token usage; get an operator profile with a tiny-model narration and
|
| 42 |
-
your rank. The ranking metric **Υ = (
|
| 43 |
padding quadratically — volume can't buy rank — but Υ is only the headline of a
|
| 44 |
larger metric system whose mathematical thesis is the **cascade decomposition**.
|
| 45 |
|
|
@@ -174,7 +174,7 @@ MO§ES occupies the **empty quadrant** — low scale, high amplification. The cl
|
|
| 174 |
| Leverage | C/I | cache reads per human token |
|
| 175 |
| Efficiency | (C+O)/I ÷ 4.0 | vs AA baseline |
|
| 176 |
| Avg $/1M | blended cost ÷ total | efficient architecture is also cheapest |
|
| 177 |
-
| **Υ (Yield)** | (
|
| 178 |
|
| 179 |
## Benchmark convergence — two independent instruments
|
| 180 |
|
|
|
|
| 39 |
|
| 40 |
A leaderboard that judges AI coding operators by **architecture, not budget**.
|
| 41 |
Paste your token usage; get an operator profile with a tiny-model narration and
|
| 42 |
+
your rank. The ranking metric **Υ = (cache_read · output) / input²** (here "Cache" = `cache_read`) penalizes raw-input
|
| 43 |
padding quadratically — volume can't buy rank — but Υ is only the headline of a
|
| 44 |
larger metric system whose mathematical thesis is the **cascade decomposition**.
|
| 45 |
|
|
|
|
| 174 |
| Leverage | C/I | cache reads per human token |
|
| 175 |
| Efficiency | (C+O)/I ÷ 4.0 | vs AA baseline |
|
| 176 |
| Avg $/1M | blended cost ÷ total | efficient architecture is also cheapest |
|
| 177 |
+
| **Υ (Yield)** | (Cr·O)/I² | **un-gameable ranking metric** (Cr = cache_read) |
|
| 178 |
|
| 179 |
## Benchmark convergence — two independent instruments
|
| 180 |
|
app.py
CHANGED
|
@@ -34,11 +34,18 @@ def _fmt_int(n):
|
|
| 34 |
if abs(n)>=d: return f"{n/d:.2f}{u}"
|
| 35 |
return str(int(n))
|
| 36 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 37 |
def _cost_str(m):
|
| 38 |
c = m.get("avg_cost_1m")
|
| 39 |
if not c: return "\u2014"
|
| 40 |
mark = "~" if m.get("cost_estimated") else ""
|
| 41 |
-
return f"{mark}${c
|
| 42 |
|
| 43 |
# ---------- leaderboard (HTML hero, log-scaled Υ, cost column) ----------
|
| 44 |
# column label -> metrics key, used by the "Rank by" control on the board
|
|
@@ -111,7 +118,8 @@ def board_html(extra=None, sort_key="yield"):
|
|
| 111 |
'<span class="mb-num">SNR</span><span class="mb-num">10x DEV</span>'
|
| 112 |
'<span class="mb-num">velocity</span><span class="mb-num">leverage</span>'
|
| 113 |
'<span class="mb-num">$/1M</span>'
|
| 114 |
-
'<span class="mb-y">\u03a5 yield</span>
|
|
|
|
| 115 |
for i,(n,m) in enumerate(rows,1):
|
| 116 |
y=m["yield"]; you = extra and n==extra[0]
|
| 117 |
orders=_math.log10(ymax/y) if y>0 else 99
|
|
@@ -129,7 +137,7 @@ def board_html(extra=None, sort_key="yield"):
|
|
| 129 |
est_mark = " <span class='mb-est' title='* structural estimation'>*</span>" if m.get("cost_estimated") else ""
|
| 130 |
out.append(f'<div class="{cls}">'
|
| 131 |
f'<span class="mb-rank {rank_cls}">{i}</span>'
|
| 132 |
-
f'<span class="mb-op"><b>{ne}{est_mark}</b><
|
| 133 |
f'<span class="mb-num">{m["snr"]:.3f}</span>'
|
| 134 |
f'<span class="mb-num">{d}</span>'
|
| 135 |
f'<span class="mb-num">{m["velocity"]:.2f}</span>'
|
|
@@ -137,6 +145,7 @@ def board_html(extra=None, sort_key="yield"):
|
|
| 137 |
f'<span class="mb-num">{_cost_str(m)}</span>'
|
| 138 |
f'<span class="mb-y"><span class="mb-bar" style="width:{barpct:.0f}%"></span>'
|
| 139 |
f'<span class="mb-yval">{y:,.0f}</span></span>'
|
|
|
|
| 140 |
f'</div>')
|
| 141 |
out.append('</div>')
|
| 142 |
out.append('<div class="mb-foot">\u03a5 bar is log-scaled \u00b7 MO\u00a7ES leads the field by ~4 orders of magnitude \u00b7 $/1M blended cost (~ = list-price estimate) \u00b7 * = structural estimation \u00b7 volume can\'t buy rank</div>')
|
|
@@ -184,6 +193,77 @@ def metrics_key_html():
|
|
| 184 |
f'{rows}</div></details>'
|
| 185 |
)
|
| 186 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 187 |
# ---------- profile ----------
|
| 188 |
def classify(m):
|
| 189 |
if m["non_compounding"]: return "Non-Compounding \u00b7 stateless pipe"
|
|
@@ -309,7 +389,7 @@ ranked **#{rank}** of {total_ops} by \u03a5{cav_line}{mode_line}
|
|
| 309 |
| Velocity | {m['velocity']:.3f}\u00d7 | output per input |
|
| 310 |
| Leverage | {m['leverage']:,.1f}\u00d7 | reads per human token |
|
| 311 |
| Efficiency | {m['efficiency']:,.1f}\u00d7 | vs AA baseline |
|
| 312 |
-
| Avg $/1M | ${m['avg_cost_1m']
|
| 313 |
| **\u03a5 Yield** | **{m['yield']:,.2f}** | un-gameable rank |
|
| 314 |
|
| 315 |
**cascade** \u2014 {m['cascade_str']} (transmission \u00d7 commitment \u00d7 reuse)
|
|
@@ -362,9 +442,9 @@ def run_ingest(blob, name, request: gr.Request):
|
|
| 362 |
"`ccusage codex --json` output, or `ccusage --json` "
|
| 363 |
"for all providers. You can also paste four numbers: "
|
| 364 |
"input output cache_create cache_read.\n\n"
|
| 365 |
-
f"_parser said: {e}_"), "", "", ""
|
| 366 |
if i+o+cw+cr==0:
|
| 367 |
-
return "Got zeros \u2014 check your paste.", "", "", ""
|
| 368 |
m=compute(i,o,cw,cr, cost_usd=meta.get("cost"))
|
| 369 |
if meta.get("estimated"):
|
| 370 |
m["_caveat"]=meta.get("caveat")
|
|
@@ -396,8 +476,7 @@ def run_ingest(blob, name, request: gr.Request):
|
|
| 396 |
return (profile,
|
| 397 |
comp_bar_html(m["composition"]),
|
| 398 |
card_html(name,m,rank,len(rows),read),
|
| 399 |
-
hits_html
|
| 400 |
-
board_html_slim((name,m)))
|
| 401 |
|
| 402 |
# ---------- interactive leaderboard helpers ----------
|
| 403 |
def resort_board(label):
|
|
@@ -405,16 +484,228 @@ def resort_board(label):
|
|
| 405 |
return board_html(sort_key=SORT_LABELS.get(label, "yield"))
|
| 406 |
|
| 407 |
def view_operator(name):
|
| 408 |
-
"""Render a corpus operator's full profile + share card
|
| 409 |
ops = operators()
|
| 410 |
if not name or name not in ops:
|
| 411 |
-
return "", ""
|
| 412 |
m = compute(*ops[name])
|
| 413 |
rows = sorted(((n, compute(*v)) for n, v in ops.items()),
|
| 414 |
key=lambda r: r[1]["yield"], reverse=True)
|
| 415 |
rank = next(i for i, (n, _) in enumerate(rows, 1) if n == name)
|
| 416 |
read = narrate(name, m, classify(m))
|
| 417 |
-
return profile_md(name, m, rank, len(rows), read),
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 418 |
|
| 419 |
# ---------- UI ----------
|
| 420 |
import os as _os
|
|
@@ -440,62 +731,32 @@ def _build_demo():
|
|
| 440 |
_names = list(_ops_now.keys())
|
| 441 |
_ys = sorted((compute(*v)["yield"] for v in _ops_now.values()), reverse=True)
|
| 442 |
_lead = (_ys[0] / _ys[1]) if len(_ys) > 1 and _ys[1] > 0 else 0.0
|
|
|
|
| 443 |
with _b:
|
| 444 |
with gr.Column(elem_id="moses-hero"):
|
| 445 |
gr.HTML(
|
| 446 |
-
"<div style='display: flex; justify-content: space-between;
|
| 447 |
-
" <div>"
|
| 448 |
-
" <
|
| 449 |
-
" <
|
| 450 |
" </div>"
|
| 451 |
-
" <div style='text-align: right;
|
| 452 |
-
"
|
| 453 |
-
"
|
| 454 |
" </div>"
|
| 455 |
"</div>"
|
| 456 |
)
|
| 457 |
-
|
| 458 |
-
|
| 459 |
-
f' <div style="border-right: 1px solid #3A3324; padding-right: 10px;">'
|
| 460 |
-
f' <div style="font-size: 9px; color: #8a7f68; text-transform: uppercase; letter-spacing: 0.08em; margin-bottom: 2px;">Operators Profiled</div>'
|
| 461 |
-
f' <div style="font-size: 20px; color: #E8E0CF; font-weight: 700;">{len(_ops_now)} <span style="font-size: 11px; color: #8a7f68; font-weight: normal;">nodes</span></div>'
|
| 462 |
-
f' </div>'
|
| 463 |
-
f' <div style="border-right: 1px solid #3A3324; padding-right: 10px; padding-left: 10px;">'
|
| 464 |
-
f' <div style="font-size: 9px; color: #8a7f68; text-transform: uppercase; letter-spacing: 0.08em; margin-bottom: 2px;">Empirical Delta</div>'
|
| 465 |
-
f' <div style="font-size: 20px; color: #C4923A; font-weight: 700;">{_lead:,.0f}\u00d7 <span style="font-size: 11px; color: #8a7f68; font-weight: normal;">max \u03a5</span></div>'
|
| 466 |
-
f' </div>'
|
| 467 |
-
f' <div style="border-right: 1px solid #3A3324; padding-right: 10px; padding-left: 10px;">'
|
| 468 |
-
f' <div style="font-size: 9px; color: #8a7f68; text-transform: uppercase; letter-spacing: 0.08em; margin-bottom: 2px;">Evaluation Strategy</div>'
|
| 469 |
-
f' <div style="font-size: 14px; color: #E8E0CF; font-weight: 700; line-height: 1.5; text-transform: uppercase; letter-spacing: 0.02em;">Compounding Loops</div>'
|
| 470 |
-
f' </div>'
|
| 471 |
-
f' <div style="padding-left: 10px;">'
|
| 472 |
-
f' <div style="font-size: 9px; color: #8a7f68; text-transform: uppercase; letter-spacing: 0.08em; margin-bottom: 2px;">Core Constraint</div>'
|
| 473 |
-
f' <div style="font-size: 14px; color: #8a7f68; font-weight: 700; line-height: 1.5; text-transform: uppercase; letter-spacing: 0.02em;"><span style="color: #E8E0CF;">Architecture</span> > Budget</div>'
|
| 474 |
-
f' </div>'
|
| 475 |
-
f'</div>'
|
| 476 |
-
)
|
| 477 |
|
| 478 |
-
# ---- TAB
|
| 479 |
-
with gr.Tab("
|
| 480 |
-
gr.
|
| 481 |
-
|
| 482 |
-
|
| 483 |
-
rank_by = gr.Radio(list(SORT_LABELS.keys()), value="\u03a5 yield",
|
| 484 |
-
label="Rank by", elem_id="rank-by")
|
| 485 |
-
lb = gr.HTML(board_html())
|
| 486 |
-
rank_by.change(resort_board, rank_by, lb)
|
| 487 |
-
gr.HTML(metrics_key_html())
|
| 488 |
-
gr.Markdown("*Curated corpus \u00b7 pasting scores you live but isn't persisted unless you sign in \u00b7 $/1M is a list-price recompute (~) \u00b7 \\* = structural estimation.*", elem_id="moses-foot")
|
| 489 |
-
with gr.Column(scale=5):
|
| 490 |
-
gr.Markdown("### Operator profile inspector")
|
| 491 |
-
op_pick = gr.Dropdown(_names, label="Select an operator to pull their card",
|
| 492 |
-
value=None, elem_id="op-pick")
|
| 493 |
-
op_card = gr.HTML(CARD_PLACEHOLDER)
|
| 494 |
-
op_prof = gr.Markdown(elem_id="moses-profile")
|
| 495 |
-
op_pick.change(view_operator, op_pick, [op_prof, op_card])
|
| 496 |
|
| 497 |
-
# ---- TAB
|
| 498 |
-
with gr.Tab("
|
| 499 |
gr.Markdown("### Primary path \u2014 run the local importer")
|
| 500 |
gr.Markdown("Reads your usage on your own machine. **Nothing leaves your computer.** Clone it once, then run:")
|
| 501 |
gr.Code(value="git clone https://github.com/Burnmydays/hf-\ncd hf-\n./sigrank",
|
|
@@ -525,8 +786,6 @@ npx ccusage@latest codex --json
|
|
| 525 |
blob = gr.Textbox(label="ccusage JSON \u2014or\u2014 four numbers (I O C R)", lines=5,
|
| 526 |
placeholder='Paste ccusage JSON here\n\nor four numbers: input output cache_create cache_read\n\nExample: 1251211 11296121 128196310 2555179769')
|
| 527 |
go = gr.Button("Clock My Signal", variant="primary", elem_id="compute-btn")
|
| 528 |
-
gr.Markdown("### Your live board placement")
|
| 529 |
-
ob = gr.HTML(board_html_slim())
|
| 530 |
gr.Markdown("### Greatest hits")
|
| 531 |
hits = gr.HTML()
|
| 532 |
with gr.Column(scale=6):
|
|
@@ -535,7 +794,7 @@ npx ccusage@latest codex --json
|
|
| 535 |
gr.Markdown("*Right-click \u2192 Save image to share your architectural footprint.*", elem_id="moses-foot")
|
| 536 |
prof_bar = gr.HTML()
|
| 537 |
prof = gr.Markdown(elem_id="moses-profile")
|
| 538 |
-
go.click(run_ingest, [blob, nm], [prof, prof_bar, card, hits
|
| 539 |
gr.Examples(
|
| 540 |
examples=[
|
| 541 |
['{"totals":{"inputTokens":1251211,"outputTokens":11296121,"cacheCreationTokens":128196310,"cacheReadTokens":2555179769}}','MO\u00a7ES'],
|
|
@@ -543,6 +802,38 @@ npx ccusage@latest codex --json
|
|
| 543 |
['1251211 11296121 128196310 2555179769', 'manual-paste'],
|
| 544 |
],
|
| 545 |
inputs=[blob, nm])
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 546 |
|
| 547 |
gr.Markdown(elem_id="moses-foot", value="""Four integers in, full ledger out. Architecture is the only variable that matters.
|
| 548 |
Wild corpus: tokscale.ai footprints \u00b7 MO\u00a7ES row verified ccusage \u00b7 * = structural estimation.""")
|
|
|
|
| 34 |
if abs(n)>=d: return f"{n/d:.2f}{u}"
|
| 35 |
return str(int(n))
|
| 36 |
|
| 37 |
+
def _fmt_cost(c):
|
| 38 |
+
"""Adaptive $/1M: keep sub-cent values legible instead of rounding to $0.00.
|
| 39 |
+
e.g. $0.000195 -> $0.0002 (2 sig figs) rather than $0.00."""
|
| 40 |
+
if c >= 1: return f"{c:,.2f}"
|
| 41 |
+
if c >= 0.01: return f"{c:.3f}"
|
| 42 |
+
return f"{c:.2g}"
|
| 43 |
+
|
| 44 |
def _cost_str(m):
|
| 45 |
c = m.get("avg_cost_1m")
|
| 46 |
if not c: return "\u2014"
|
| 47 |
mark = "~" if m.get("cost_estimated") else ""
|
| 48 |
+
return f"{mark}${_fmt_cost(c)}"
|
| 49 |
|
| 50 |
# ---------- leaderboard (HTML hero, log-scaled Υ, cost column) ----------
|
| 51 |
# column label -> metrics key, used by the "Rank by" control on the board
|
|
|
|
| 118 |
'<span class="mb-num">SNR</span><span class="mb-num">10x DEV</span>'
|
| 119 |
'<span class="mb-num">velocity</span><span class="mb-num">leverage</span>'
|
| 120 |
'<span class="mb-num">$/1M</span>'
|
| 121 |
+
'<span class="mb-y">\u03a5 yield</span>'
|
| 122 |
+
'<span class="mb-ledger">ledger \u00b7 R\u00b7C\u00b7I\u00b7O</span></div>')
|
| 123 |
for i,(n,m) in enumerate(rows,1):
|
| 124 |
y=m["yield"]; you = extra and n==extra[0]
|
| 125 |
orders=_math.log10(ymax/y) if y>0 else 99
|
|
|
|
| 137 |
est_mark = " <span class='mb-est' title='* structural estimation'>*</span>" if m.get("cost_estimated") else ""
|
| 138 |
out.append(f'<div class="{cls}">'
|
| 139 |
f'<span class="mb-rank {rank_cls}">{i}</span>'
|
| 140 |
+
f'<span class="mb-op"><b>{ne}{est_mark}</b></span>'
|
| 141 |
f'<span class="mb-num">{m["snr"]:.3f}</span>'
|
| 142 |
f'<span class="mb-num">{d}</span>'
|
| 143 |
f'<span class="mb-num">{m["velocity"]:.2f}</span>'
|
|
|
|
| 145 |
f'<span class="mb-num">{_cost_str(m)}</span>'
|
| 146 |
f'<span class="mb-y"><span class="mb-bar" style="width:{barpct:.0f}%"></span>'
|
| 147 |
f'<span class="mb-yval">{y:,.0f}</span></span>'
|
| 148 |
+
f'<span class="mb-ledger">R {_fmt_int(m["raw"]["cache_read"])} \u00b7 C {_fmt_int(m["raw"]["cache_create"])} \u00b7 I {_fmt_int(m["raw"]["input"])} \u00b7 O {_fmt_int(m["raw"]["output"])}</span>'
|
| 149 |
f'</div>')
|
| 150 |
out.append('</div>')
|
| 151 |
out.append('<div class="mb-foot">\u03a5 bar is log-scaled \u00b7 MO\u00a7ES leads the field by ~4 orders of magnitude \u00b7 $/1M blended cost (~ = list-price estimate) \u00b7 * = structural estimation \u00b7 volume can\'t buy rank</div>')
|
|
|
|
| 193 |
f'{rows}</div></details>'
|
| 194 |
)
|
| 195 |
|
| 196 |
+
_STANDARD_METRICS = [
|
| 197 |
+
("Total Tokens", "Input + Output", "Raw count of everything processed. Higher = more usage."),
|
| 198 |
+
("Input Tokens", "prompt / context", "How much you feed in \u2014 often the biggest cost driver."),
|
| 199 |
+
("Output Tokens", "model generation", "How much the model writes. Longer answers cost more."),
|
| 200 |
+
("Tokens/sec \u00b7 Latency", "speed", "How fast it runs \u2014 nothing about how well."),
|
| 201 |
+
("Cost ($)", "$ per 1M tokens", "Dollars from token pricing. Counts spend, not skill."),
|
| 202 |
+
]
|
| 203 |
+
_SIGRANK_METRICS = [
|
| 204 |
+
("\u03a5 \u2014 Upsilon", "(Cache \u00d7 Output) / Input\u00b2",
|
| 205 |
+
"Standard just adds Input + Output. \u03a5 squares input to punish waste while rewarding reuse (cache) and real output.",
|
| 206 |
+
"Encourages tight, smart prompts instead of long ones."),
|
| 207 |
+
("Signal-to-Noise (SNR)", "Out / (In + Out)",
|
| 208 |
+
"Standard counts every output token equally. SNR separates useful signal from repetitive fluff.",
|
| 209 |
+
"Rewards quality, not length."),
|
| 210 |
+
("Cache Leverage", "Cache-read / Input",
|
| 211 |
+
"Standard ignores reuse \u2014 every call is fresh. This measures the \u2018free\u2019 work you get from remembering prior results.",
|
| 212 |
+
"Big win for systems that avoid repeating work."),
|
| 213 |
+
("Cascade Velocity", "10 \u00d7 10 \u00d7 20",
|
| 214 |
+
"Standard might just time the whole run. This tracks smooth chaining of steps (10 focused ops \u2192 10 more \u2192 20\u00d7 leverage).",
|
| 215 |
+
"Rewards well-designed pipelines over messy long chains."),
|
| 216 |
+
]
|
| 217 |
+
_COMPARE_ROWS = [
|
| 218 |
+
("Focus", "How much you use", "How well you use it"),
|
| 219 |
+
("Penalizes", "Nothing \u2014 bigger is often \u2018better\u2019", "Wasteful inputs, fluff, poor reuse"),
|
| 220 |
+
("Rewards", "Volume & speed", "Efficiency, quality, smart architecture"),
|
| 221 |
+
("Easy to game?", "Very \u2014 just inflate prompts", "Hard \u2014 square penalty + quality checks"),
|
| 222 |
+
("Best for", "Billing & raw scale", "Hackathons, governance, Build Small"),
|
| 223 |
+
]
|
| 224 |
+
|
| 225 |
+
def metrics_explainer_html():
|
| 226 |
+
"""The full 'what the metrics mean' education: SigRank vs standard token metrics,
|
| 227 |
+
the thermodynamic grounding, and a side-by-side comparison."""
|
| 228 |
+
std = "".join(
|
| 229 |
+
f'<div class="mx-item"><div class="mx-item-head"><span class="mx-name">{n}</span>'
|
| 230 |
+
f'<span class="mx-form">{f}</span></div><div class="mx-desc">{d}</div></div>'
|
| 231 |
+
for n, f, d in _STANDARD_METRICS)
|
| 232 |
+
sig = "".join(
|
| 233 |
+
f'<div class="mx-item"><div class="mx-item-head"><span class="mx-name">{n}</span>'
|
| 234 |
+
f'<span class="mx-form">{f}</span></div>'
|
| 235 |
+
f'<div class="mx-vs"><b>vs standard:</b> {v}</div>'
|
| 236 |
+
f'<div class="mx-result">\u2192 {r}</div></div>'
|
| 237 |
+
for n, f, v, r in _SIGRANK_METRICS)
|
| 238 |
+
comp = "".join(
|
| 239 |
+
f'<tr><th class="mx-aspect">{a}</th><td>{s}</td><td class="mx-win">{g}</td></tr>'
|
| 240 |
+
for a, s, g in _COMPARE_ROWS)
|
| 241 |
+
return (
|
| 242 |
+
'<div class="mx-wrap">'
|
| 243 |
+
'<div class="mx-analogy">Standard token metrics are an <b>odometer</b> \u2014 they count '
|
| 244 |
+
'distance (tokens used). <span class="mx-gold">SigRank is a fuel-efficiency + '
|
| 245 |
+
'smart-driving score</span> \u2014 it judges how intelligently you drive.</div>'
|
| 246 |
+
'<div class="mx-cols">'
|
| 247 |
+
'<div class="mx-col mx-col-std"><div class="mx-col-head">Standard Token Metrics</div>'
|
| 248 |
+
f'{std}<div class="mx-foot">Rewards <b>volume & scale</b> \u2014 easy to track, easy to game '
|
| 249 |
+
'(this is \u201ctokenmaxxing\u201d).</div></div>'
|
| 250 |
+
'<div class="mx-col mx-col-sig"><div class="mx-col-head">SigRank Metrics</div>'
|
| 251 |
+
f'{sig}<div class="mx-foot">Rewards <b>efficiency, quality & architecture</b> \u2014 the same '
|
| 252 |
+
'numbers, turned into judgment.</div></div>'
|
| 253 |
+
'</div>'
|
| 254 |
+
'<table class="mx-table"><thead><tr><th>Aspect</th><th>Standard</th>'
|
| 255 |
+
'<th class="mx-win">SigRank</th></tr></thead><tbody>' + comp + '</tbody></table>'
|
| 256 |
+
'<div class="mx-thermo"><div class="mx-thermo-h">\u25c6 Why square the input? \u2014 the thermodynamic floor</div>'
|
| 257 |
+
'The metrics are grounded in <b>Landauer\u2019s principle</b>: processing or erasing information '
|
| 258 |
+
'carries a real, physical energy cost (on the order of kT\u00b7ln2 per bit). Tokens aren\u2019t free \u2014 '
|
| 259 |
+
'every input bit you push through has a price. SigRank takes that seriously: it rewards '
|
| 260 |
+
'<b>reusing</b> what you already computed (cache) and <b>minimizing fresh input</b>, the way an '
|
| 261 |
+
'efficient engine minimizes wasted heat. Squaring input in \u03a5 is that penalty made concrete.</div>'
|
| 262 |
+
'<div class="mx-bottom">Bottom line: standard metrics are great for paying the bill. '
|
| 263 |
+
'SigRank adds judgment \u2014 it ranks by <span class="mx-gold">cleverness, not consumption.</span> '
|
| 264 |
+
'That\u2019s \u201cown your loop.\u201d</div>'
|
| 265 |
+
'</div>')
|
| 266 |
+
|
| 267 |
# ---------- profile ----------
|
| 268 |
def classify(m):
|
| 269 |
if m["non_compounding"]: return "Non-Compounding \u00b7 stateless pipe"
|
|
|
|
| 389 |
| Velocity | {m['velocity']:.3f}\u00d7 | output per input |
|
| 390 |
| Leverage | {m['leverage']:,.1f}\u00d7 | reads per human token |
|
| 391 |
| Efficiency | {m['efficiency']:,.1f}\u00d7 | vs AA baseline |
|
| 392 |
+
| Avg $/1M | ${_fmt_cost(m['avg_cost_1m'])} |{cost_note} |
|
| 393 |
| **\u03a5 Yield** | **{m['yield']:,.2f}** | un-gameable rank |
|
| 394 |
|
| 395 |
**cascade** \u2014 {m['cascade_str']} (transmission \u00d7 commitment \u00d7 reuse)
|
|
|
|
| 442 |
"`ccusage codex --json` output, or `ccusage --json` "
|
| 443 |
"for all providers. You can also paste four numbers: "
|
| 444 |
"input output cache_create cache_read.\n\n"
|
| 445 |
+
f"_parser said: {e}_"), "", "", ""
|
| 446 |
if i+o+cw+cr==0:
|
| 447 |
+
return "Got zeros \u2014 check your paste.", "", "", ""
|
| 448 |
m=compute(i,o,cw,cr, cost_usd=meta.get("cost"))
|
| 449 |
if meta.get("estimated"):
|
| 450 |
m["_caveat"]=meta.get("caveat")
|
|
|
|
| 476 |
return (profile,
|
| 477 |
comp_bar_html(m["composition"]),
|
| 478 |
card_html(name,m,rank,len(rows),read),
|
| 479 |
+
hits_html)
|
|
|
|
| 480 |
|
| 481 |
# ---------- interactive leaderboard helpers ----------
|
| 482 |
def resort_board(label):
|
|
|
|
| 484 |
return board_html(sort_key=SORT_LABELS.get(label, "yield"))
|
| 485 |
|
| 486 |
def view_operator(name):
|
| 487 |
+
"""Render a corpus operator's full profile + share card + learn-from insights."""
|
| 488 |
ops = operators()
|
| 489 |
if not name or name not in ops:
|
| 490 |
+
return "", "", ""
|
| 491 |
m = compute(*ops[name])
|
| 492 |
rows = sorted(((n, compute(*v)) for n, v in ops.items()),
|
| 493 |
key=lambda r: r[1]["yield"], reverse=True)
|
| 494 |
rank = next(i for i, (n, _) in enumerate(rows, 1) if n == name)
|
| 495 |
read = narrate(name, m, classify(m))
|
| 496 |
+
return (profile_md(name, m, rank, len(rows), read),
|
| 497 |
+
card_html(name, m, rank, len(rows), read),
|
| 498 |
+
insights_html(name, m))
|
| 499 |
+
|
| 500 |
+
def insights_html(name, m):
|
| 501 |
+
"""Reader takeaways: what this operator does well + what to avoid."""
|
| 502 |
+
good, avoid = [], []
|
| 503 |
+
lev, snr, vel = m["leverage"], m["snr"], m["velocity"]
|
| 504 |
+
if lev >= 100: good.append("Exceptional cache reuse — context is re-read, not rebuilt each turn.")
|
| 505 |
+
elif lev >= 10: good.append("Solid cache leverage — compounding on prior work.")
|
| 506 |
+
else: avoid.append("Low cache leverage — mostly fresh input each turn (recompute waste).")
|
| 507 |
+
if snr >= 0.5: good.append("High signal — most tokens are model output, not prompt bloat.")
|
| 508 |
+
else: avoid.append("Low signal-to-noise — large input vs. output; tighten prompts.")
|
| 509 |
+
if m["non_compounding"]: avoid.append("No cache-create — stateless pipe, no architectural compounding.")
|
| 510 |
+
else: good.append("Compounding architecture — building reusable context, not one-shotting.")
|
| 511 |
+
if vel >= 1: good.append("Strong throughput — produces more than it consumes.")
|
| 512 |
+
elif vel < 0.3: avoid.append("Low velocity — heavy input for little output.")
|
| 513 |
+
g = "".join(f"<li>{x}</li>" for x in good) or "<li>—</li>"
|
| 514 |
+
a = "".join(f"<li>{x}</li>" for x in avoid) or "<li>Nothing major — clean architecture.</li>"
|
| 515 |
+
return (f'<div class="ins-wrap">'
|
| 516 |
+
f'<div class="ins-block ins-good"><div class="ins-h">✓ Doing well</div><ul>{g}</ul></div>'
|
| 517 |
+
f'<div class="ins-block ins-avoid"><div class="ins-h">✕ Watch out</div><ul>{a}</ul></div></div>')
|
| 518 |
+
|
| 519 |
+
def operator_segments():
|
| 520 |
+
"""Live counts: burners (spend, no reuse), builders (compounding), 10×ers (elite reuse)."""
|
| 521 |
+
burn = build = tenx = 0
|
| 522 |
+
for v in operators().values():
|
| 523 |
+
lev = compute(*v)["leverage"]
|
| 524 |
+
if lev < 2: burn += 1
|
| 525 |
+
elif lev >= 1000: tenx += 1
|
| 526 |
+
else: build += 1
|
| 527 |
+
return burn, build, tenx, burn + build + tenx
|
| 528 |
+
|
| 529 |
+
# ---------- VS / compare ----------
|
| 530 |
+
# (label, metrics key, winner = max|min, value formatter)
|
| 531 |
+
_CMP_ROWS = [
|
| 532 |
+
("Υ yield", "yield", "max", lambda v: f"{v:,.0f}"),
|
| 533 |
+
("SNR", "snr", "max", lambda v: f"{v:.3f}"),
|
| 534 |
+
("leverage", "leverage", "max", lambda v: f"{v:,.0f}×"),
|
| 535 |
+
("velocity", "velocity", "max", lambda v: f"{v:.2f}×"),
|
| 536 |
+
("10x DEV", "dev10x", "max", lambda v: f"{v:.2f}"),
|
| 537 |
+
("$/1M", "avg_cost_1m", "min", lambda v: f"${_fmt_cost(v)}"),
|
| 538 |
+
]
|
| 539 |
+
|
| 540 |
+
def compare_html(names):
|
| 541 |
+
"""Head-to-head table for 2–3 operators; best value per row gets the gold cell."""
|
| 542 |
+
ops = operators()
|
| 543 |
+
names = [n for n in (names or []) if n in ops][:3]
|
| 544 |
+
if len(names) < 2:
|
| 545 |
+
return ('<div class="cmp-empty">Pick <b>2–3 operators</b> above to put them '
|
| 546 |
+
'head-to-head. Winner takes each row.</div>')
|
| 547 |
+
ms = [(n, compute(*ops[n])) for n in names]
|
| 548 |
+
head = "".join(f'<th class="cmp-op">{_html.escape(n)}</th>' for n, _ in ms)
|
| 549 |
+
body = []
|
| 550 |
+
for label, key, mode, fmt in _CMP_ROWS:
|
| 551 |
+
vals = [m.get(key) for _, m in ms]
|
| 552 |
+
nums = [v for v in vals if v is not None]
|
| 553 |
+
best = (max if mode == "max" else min)(nums) if nums else None
|
| 554 |
+
cells = []
|
| 555 |
+
for v in vals:
|
| 556 |
+
win = v is not None and best is not None and v == best and len(nums) > 1
|
| 557 |
+
cells.append(f'<td class="{"cmp-win" if win else ""}">'
|
| 558 |
+
f'{fmt(v) if v is not None else "—"}</td>')
|
| 559 |
+
body.append(f'<tr><th class="cmp-rowlabel">{label}</th>{"".join(cells)}</tr>')
|
| 560 |
+
return (f'<table class="cmp-table"><thead><tr><th></th>{head}</tr></thead>'
|
| 561 |
+
f'<tbody>{"".join(body)}</tbody></table>'
|
| 562 |
+
'<div class="cmp-note">Gold = leads that metric · $/1M: lower wins · '
|
| 563 |
+
'Υ is the overall rank metric.</div>')
|
| 564 |
+
|
| 565 |
+
# ---------- Home / landing ----------
|
| 566 |
+
def profile_marquee_html():
|
| 567 |
+
"""Auto-scrolling band of operator chips (rank · name · Υ · leverage). Pure CSS loop."""
|
| 568 |
+
ops = operators()
|
| 569 |
+
rows = sorted(((n, compute(*v)) for n, v in ops.items()),
|
| 570 |
+
key=lambda r: r[1]["yield"], reverse=True)
|
| 571 |
+
def chip(rank, n, m):
|
| 572 |
+
rk = rarity_class(m)[0]
|
| 573 |
+
return (f'<div class="pm-chip species-{rk}">'
|
| 574 |
+
f'<span class="pm-rank">#{rank}</span>'
|
| 575 |
+
f'<span class="pm-name">{_html.escape(n)}</span>'
|
| 576 |
+
f'<span class="pm-stat">Υ {m["yield"]:,.0f}</span>'
|
| 577 |
+
f'<span class="pm-lev">{m["leverage"]:,.0f}× lev</span></div>')
|
| 578 |
+
chips = "".join(chip(i, n, m) for i, (n, m) in enumerate(rows, 1))
|
| 579 |
+
# chips duplicated so the translateX(-50%) loop is seamless
|
| 580 |
+
return f'<div class="pm-wrap"><div class="pm-track">{chips}{chips}</div></div>'
|
| 581 |
+
|
| 582 |
+
# ---- the metric standard (green feature row) ----
|
| 583 |
+
# (symbol, metrics key, equation, value-format, hover description)
|
| 584 |
+
_FEATURE_METRICS = [
|
| 585 |
+
("Υ", "yield", "(Cache·Output) / Input²", "{v:,.0f}",
|
| 586 |
+
"The efficiency score. Reused context (cache) × produced output, measured against "
|
| 587 |
+
"fresh input squared — squaring input is why raw volume can't buy rank."),
|
| 588 |
+
("SNR", "snr", "Out / (In+Out)", "{v:.2f}",
|
| 589 |
+
"Signal-to-noise. Share of the exchange that's model output vs. prompt/input. "
|
| 590 |
+
"Higher = focused, less bloat."),
|
| 591 |
+
("10x", "dev10x", "log₁₀(cascade)", "{v:.2f}",
|
| 592 |
+
"The cascade in orders of magnitude (log₁₀ of leverage) — the 10× developer multiplier."),
|
| 593 |
+
("$/1M", "avg_cost_1m", "blended cost / 1M", "${v}",
|
| 594 |
+
"Blended cost per million tokens across all states. Efficient architecture is also "
|
| 595 |
+
"the cheapest — so cost falls out of good design."),
|
| 596 |
+
]
|
| 597 |
+
|
| 598 |
+
def _corpus_metric_values(key):
|
| 599 |
+
vals = [compute(*v).get(key) for v in operators().values()]
|
| 600 |
+
return sorted(x for x in vals if x is not None)
|
| 601 |
+
|
| 602 |
+
def _median(vals):
|
| 603 |
+
n = len(vals)
|
| 604 |
+
if not n: return 0
|
| 605 |
+
return vals[n // 2] if n % 2 else (vals[n // 2 - 1] + vals[n // 2]) / 2
|
| 606 |
+
|
| 607 |
+
def _status_box_html():
|
| 608 |
+
"""Live system status + segment counters — rendered as a metric box."""
|
| 609 |
+
burn, build, tenx, tot = operator_segments()
|
| 610 |
+
return (
|
| 611 |
+
'<div class="mf-box mf-status">'
|
| 612 |
+
'<div class="ms-title"><span class="ms-dot">●</span> ONLINE</div>'
|
| 613 |
+
'<div class="ms-grid">'
|
| 614 |
+
f'<span>BURNERS</span><span class="hs-burn">{burn:03d}</span>'
|
| 615 |
+
f'<span>BUILDERS</span><span class="hs-build">{build:03d}</span>'
|
| 616 |
+
f'<span>10×ERS</span><span class="hs-tenx">{tenx:03d}</span>'
|
| 617 |
+
f'<span>SIGNALS</span><span class="ms-tot">{tot:03d}</span>'
|
| 618 |
+
'</div></div>')
|
| 619 |
+
|
| 620 |
+
def metric_features_html():
|
| 621 |
+
boxes = []
|
| 622 |
+
for sym, key, form, fmt, desc in _FEATURE_METRICS:
|
| 623 |
+
vals = _corpus_metric_values(key)
|
| 624 |
+
avg = sum(vals) / len(vals) if vals else 0
|
| 625 |
+
big = f"${_fmt_cost(avg)}" if key == "avg_cost_1m" else fmt.format(v=avg)
|
| 626 |
+
boxes.append(
|
| 627 |
+
f'<div class="mf-box" tabindex="0"><div class="mf-sym">{sym}</div>'
|
| 628 |
+
f'<div class="mf-big">{big}</div>'
|
| 629 |
+
f'<div class="mf-form">{form}</div>'
|
| 630 |
+
f'<div class="mf-tip">{desc}</div></div>')
|
| 631 |
+
boxes.insert(2, _status_box_html()) # between SNR and 10x
|
| 632 |
+
return ('<div class="mf-head">Introducing the new standard in '
|
| 633 |
+
'<span>AI metrics & benchmarks</span></div>'
|
| 634 |
+
f'<div class="mf-grid">{"".join(boxes)}</div>'
|
| 635 |
+
'<div class="mf-sub">field average · live counts · hover any metric for what it means</div>')
|
| 636 |
+
|
| 637 |
+
# ---- real mini renders of each page (live HTML, scaled into a framed thumbnail) ----
|
| 638 |
+
def _top_rows(n):
|
| 639 |
+
return sorted(((k, compute(*v)) for k, v in operators().items()),
|
| 640 |
+
key=lambda r: r[1]["yield"], reverse=True)[:n]
|
| 641 |
+
|
| 642 |
+
def _mini(cap, inner, accent):
|
| 643 |
+
"""Frame real page HTML as a browser-chrome thumbnail; CSS scales it down."""
|
| 644 |
+
return (f'<div class="mini mini-{accent}">'
|
| 645 |
+
f'<div class="mini-chrome"><span></span><span></span><span></span>'
|
| 646 |
+
f'<div class="mini-cap">{cap}</div></div>'
|
| 647 |
+
f'<div class="mini-view"><div class="mini-scale">{inner}</div></div></div>')
|
| 648 |
+
|
| 649 |
+
def _mini_leaders():
|
| 650 |
+
return _mini("sigrank · leaders", board_html(), "gold")
|
| 651 |
+
|
| 652 |
+
def _mini_reports():
|
| 653 |
+
k, m = _top_rows(1)[0]
|
| 654 |
+
read = narrate(k, m, classify(m))
|
| 655 |
+
return _mini("sigrank · reports",
|
| 656 |
+
card_html(k, m, 1, len(operators()), read), "purple")
|
| 657 |
+
|
| 658 |
+
def _mini_vs():
|
| 659 |
+
return _mini("sigrank · vs", compare_html([k for k, _ in _top_rows(3)]), "blue")
|
| 660 |
+
|
| 661 |
+
def _mini_create():
|
| 662 |
+
inner = (
|
| 663 |
+
'<div class="cr-mock">'
|
| 664 |
+
'<div class="cr-code">$ ./sigrank --submit</div>'
|
| 665 |
+
'<div class="cr-box">paste ccusage JSON — or four numbers:<br>'
|
| 666 |
+
'<b>1251211 11296121 128196310 2555179769</b></div>'
|
| 667 |
+
'<div class="cr-btn">⬡ Clock My Signal</div>'
|
| 668 |
+
'<div class="cr-res">Υ 18,437 · CASCADE MATRIX</div></div>')
|
| 669 |
+
return _mini("sigrank · create", inner, "green")
|
| 670 |
+
|
| 671 |
+
_HOME_SECTIONS = [
|
| 672 |
+
("Leaders", "Prove your signal",
|
| 673 |
+
"The burn-vs-build board — who wins on architecture, not spend.", _mini_leaders, "gold"),
|
| 674 |
+
("Reports", "Study the field",
|
| 675 |
+
"Pull any operator's full read. R&D — improve yourself.", _mini_reports, "purple"),
|
| 676 |
+
("VS", "Head-to-head",
|
| 677 |
+
"Who's actually 10×? Who's amplifying signal — and at what cost?", _mini_vs, "blue"),
|
| 678 |
+
("Create", "Clock your signal",
|
| 679 |
+
"Drop your ledger, get scored, claim your operator card.", _mini_create, "green"),
|
| 680 |
+
]
|
| 681 |
+
|
| 682 |
+
def home_html():
|
| 683 |
+
boxes = "".join(
|
| 684 |
+
f'<div class="hm-box hm-{accent}">{mini()}'
|
| 685 |
+
f'<div class="hm-title">◢ {t}</div>'
|
| 686 |
+
f'<div class="hm-sub">{s}</div><div class="hm-desc">{d}</div>'
|
| 687 |
+
f'<div class="hm-cta">open the {t} tab →</div></div>'
|
| 688 |
+
for t, s, d, mini, accent in _HOME_SECTIONS
|
| 689 |
+
)
|
| 690 |
+
return f'<div class="hm-grid">{boxes}</div>'
|
| 691 |
+
|
| 692 |
+
def home_footer_html():
|
| 693 |
+
loom = "https://www.loom.com/share/edc345e2e5164e20aed3acb6436a08c3"
|
| 694 |
+
return (
|
| 695 |
+
'<div class="hm-foot">'
|
| 696 |
+
'<div class="hf-col"><div class="hf-h">Watch the demo</div>'
|
| 697 |
+
f'<a class="hf-btn" href="{loom}" target="_blank" rel="noopener">▶ Play demo video</a></div>'
|
| 698 |
+
'<div class="hf-col"><div class="hf-h">Get ranked in 3 steps</div>'
|
| 699 |
+
'<ol class="hf-steps">'
|
| 700 |
+
'<li>Run <code>npx ccusage@latest claude --json</code></li>'
|
| 701 |
+
'<li>Open <b>Create</b>, paste it (or four numbers)</li>'
|
| 702 |
+
'<li>Get your Υ score + operator card</li></ol></div>'
|
| 703 |
+
'<div class="hf-col"><div class="hf-h">More</div>'
|
| 704 |
+
'<a class="hf-link" href="https://mos2es.com" target="_blank" rel="noopener">mos2es.com</a>'
|
| 705 |
+
'<a class="hf-link" href="https://mos2es.com/benchmarks" target="_blank" rel="noopener">benchmarks</a>'
|
| 706 |
+
'<a class="hf-link" href="https://x.com/burnmydays/status/2066666214143758576" target="_blank" rel="noopener">@burnmydays on X</a>'
|
| 707 |
+
'</div></div>'
|
| 708 |
+
)
|
| 709 |
|
| 710 |
# ---------- UI ----------
|
| 711 |
import os as _os
|
|
|
|
| 731 |
_names = list(_ops_now.keys())
|
| 732 |
_ys = sorted((compute(*v)["yield"] for v in _ops_now.values()), reverse=True)
|
| 733 |
_lead = (_ys[0] / _ys[1]) if len(_ys) > 1 and _ys[1] > 0 else 0.0
|
| 734 |
+
_burn, _build, _tenx, _tot = operator_segments()
|
| 735 |
with _b:
|
| 736 |
with gr.Column(elem_id="moses-hero"):
|
| 737 |
gr.HTML(
|
| 738 |
+
"<div style='display: flex; align-items: flex-end; justify-content: space-between; gap: 28px; border-bottom: 2px solid #C4923A; padding: 4px 0 12px; margin-bottom: 10px;'>"
|
| 739 |
+
" <div style='text-align: left; flex: none;'>"
|
| 740 |
+
" <div style='color: #8a7f68; font-size: 11px; letter-spacing: 0.3em; text-transform: uppercase; margin-bottom: 2px;'>Powered by MO\u00a7ES\u2122</div>"
|
| 741 |
+
" <h1 style='margin: 0 !important; line-height: 0.9; text-shadow: 0 0 24px rgba(196,146,58,0.25);'>SIGRANK</h1>"
|
| 742 |
" </div>"
|
| 743 |
+
" <div style='text-align: right; color: #E8E0CF; font-size: 14px; font-weight: 600; line-height: 1.5; max-width: 440px; padding-top: 34px;'>"
|
| 744 |
+
" Ranking AI operators on performance, production, architecture & cost efficiency. "
|
| 745 |
+
" <span style='color:#C4923A;'>Identifying Burners, Builders, and 10\u00d7ers.</span>"
|
| 746 |
" </div>"
|
| 747 |
"</div>"
|
| 748 |
)
|
| 749 |
+
# full-width live leaderboard scroller (replaces the old static stat strip)
|
| 750 |
+
gr.HTML(profile_marquee_html())
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 751 |
|
| 752 |
+
# ---- TAB: Home (landing — metric standard + section minis + links) ----
|
| 753 |
+
with gr.Tab("Home"):
|
| 754 |
+
gr.HTML(metric_features_html())
|
| 755 |
+
gr.HTML(home_html())
|
| 756 |
+
gr.HTML(home_footer_html())
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 757 |
|
| 758 |
+
# ---- TAB: Create (clock your signal \u2014 the importer) ----
|
| 759 |
+
with gr.Tab("Create"):
|
| 760 |
gr.Markdown("### Primary path \u2014 run the local importer")
|
| 761 |
gr.Markdown("Reads your usage on your own machine. **Nothing leaves your computer.** Clone it once, then run:")
|
| 762 |
gr.Code(value="git clone https://github.com/Burnmydays/hf-\ncd hf-\n./sigrank",
|
|
|
|
| 786 |
blob = gr.Textbox(label="ccusage JSON \u2014or\u2014 four numbers (I O C R)", lines=5,
|
| 787 |
placeholder='Paste ccusage JSON here\n\nor four numbers: input output cache_create cache_read\n\nExample: 1251211 11296121 128196310 2555179769')
|
| 788 |
go = gr.Button("Clock My Signal", variant="primary", elem_id="compute-btn")
|
|
|
|
|
|
|
| 789 |
gr.Markdown("### Greatest hits")
|
| 790 |
hits = gr.HTML()
|
| 791 |
with gr.Column(scale=6):
|
|
|
|
| 794 |
gr.Markdown("*Right-click \u2192 Save image to share your architectural footprint.*", elem_id="moses-foot")
|
| 795 |
prof_bar = gr.HTML()
|
| 796 |
prof = gr.Markdown(elem_id="moses-profile")
|
| 797 |
+
go.click(run_ingest, [blob, nm], [prof, prof_bar, card, hits])
|
| 798 |
gr.Examples(
|
| 799 |
examples=[
|
| 800 |
['{"totals":{"inputTokens":1251211,"outputTokens":11296121,"cacheCreationTokens":128196310,"cacheReadTokens":2555179769}}','MO\u00a7ES'],
|
|
|
|
| 802 |
['1251211 11296121 128196310 2555179769', 'manual-paste'],
|
| 803 |
],
|
| 804 |
inputs=[blob, nm])
|
| 805 |
+
gr.Markdown("### What the metrics mean")
|
| 806 |
+
gr.HTML(metrics_explainer_html())
|
| 807 |
+
|
| 808 |
+
# ---- TAB: Leaders (the board) ----
|
| 809 |
+
with gr.Tab("Leaders"):
|
| 810 |
+
gr.Markdown("**The ledger doesn't care what you claim.** Ranked by **\u03a5 = (Cache\u00b7Output)/Input\u00b2** \u2014 raw Read\u00b7Create\u00b7In\u00b7Out stacked under each operator. $/1M is blended cost; efficient architecture is also the cheapest.")
|
| 811 |
+
rank_by = gr.Radio(list(SORT_LABELS.keys()), value="\u03a5 yield",
|
| 812 |
+
label="Rank by", elem_id="rank-by")
|
| 813 |
+
lb = gr.HTML(board_html())
|
| 814 |
+
rank_by.change(resort_board, rank_by, lb)
|
| 815 |
+
gr.HTML(metrics_key_html())
|
| 816 |
+
gr.Markdown("*Curated corpus \u00b7 pasting scores you live but isn't persisted unless you sign in \u00b7 $/1M is a list-price recompute (~) \u00b7 \\* = structural estimation.*", elem_id="moses-foot")
|
| 817 |
+
|
| 818 |
+
# ---- TAB: VS (head-to-head compare) ----
|
| 819 |
+
with gr.Tab("VS"):
|
| 820 |
+
gr.Markdown("### Put operators head-to-head\nSelect 2\u20133 operators. Gold cell wins each metric. **This is where architecture beats budget in plain sight.**")
|
| 821 |
+
cmp_pick = gr.Dropdown(_names, label="Operators (pick 2\u20133)", value=None,
|
| 822 |
+
multiselect=True, max_choices=3, elem_id="cmp-pick")
|
| 823 |
+
cmp_out = gr.HTML(compare_html(None))
|
| 824 |
+
cmp_pick.change(compare_html, cmp_pick, cmp_out)
|
| 825 |
+
|
| 826 |
+
# ---- TAB: Reports (operator profile inspector) ----
|
| 827 |
+
with gr.Tab("Reports"):
|
| 828 |
+
gr.Markdown("### Full architectural read on any operator\nPick a name to pull their complete profile, a shareable card, and **what to learn from them**.")
|
| 829 |
+
with gr.Row():
|
| 830 |
+
with gr.Column(scale=5):
|
| 831 |
+
op_pick = gr.Dropdown(_names, label="Operator", value=None, elem_id="op-pick")
|
| 832 |
+
op_card = gr.HTML(CARD_PLACEHOLDER)
|
| 833 |
+
with gr.Column(scale=6):
|
| 834 |
+
op_prof = gr.Markdown(elem_id="moses-profile")
|
| 835 |
+
op_insights = gr.HTML()
|
| 836 |
+
op_pick.change(view_operator, op_pick, [op_prof, op_card, op_insights])
|
| 837 |
|
| 838 |
gr.Markdown(elem_id="moses-foot", value="""Four integers in, full ledger out. Architecture is the only variable that matters.
|
| 839 |
Wild corpus: tokscale.ai footprints \u00b7 MO\u00a7ES row verified ccusage \u00b7 * = structural estimation.""")
|
theme.py
CHANGED
|
@@ -14,20 +14,23 @@ CSS = """
|
|
| 14 |
--species-cascade: #C4923A;
|
| 15 |
}
|
| 16 |
.gradio-container, .gradio-container * { font-family: ui-monospace, "SF Mono", Menlo, monospace !important; }
|
| 17 |
-
.gradio-container { background: var(--moses-bg) !important; max-width: 1100px !important; margin: 0 auto !important; }
|
| 18 |
.dark .gradio-container, body { background: var(--moses-bg) !important; }
|
| 19 |
|
| 20 |
#moses-hero {
|
| 21 |
border-bottom: 1px solid var(--moses-gold);
|
| 22 |
-
padding:
|
| 23 |
-
margin-bottom:
|
| 24 |
position: relative;
|
| 25 |
}
|
|
|
|
|
|
|
|
|
|
| 26 |
#moses-hero h1 {
|
| 27 |
color: var(--moses-gold) !important;
|
| 28 |
-
font-size:
|
| 29 |
-
letter-spacing: 0.
|
| 30 |
-
font-weight:
|
| 31 |
margin: 0 !important;
|
| 32 |
}
|
| 33 |
#moses-hero p { color: var(--moses-dim) !important; font-size: 12px !important; margin: 6px 0 0 !important; }
|
|
@@ -44,11 +47,14 @@ CSS = """
|
|
| 44 |
.tabitem {
|
| 45 |
background: transparent !important;
|
| 46 |
border: none !important;
|
| 47 |
-
padding:
|
| 48 |
}
|
| 49 |
-
.tabitem > div { gap:
|
| 50 |
button.selected { color: var(--moses-gold) !important; border-bottom: 2px solid var(--moses-gold) !important; }
|
| 51 |
-
|
|
|
|
|
|
|
|
|
|
| 52 |
|
| 53 |
.dataframe, table { background: var(--moses-card) !important; color: var(--moses-ink) !important;
|
| 54 |
border: 1px solid var(--moses-line) !important; font-size: 12px !important; width: 100% !important; }
|
|
@@ -84,8 +90,14 @@ button.primary:hover, #compute-btn:hover { background: #d8a449 !important; }
|
|
| 84 |
|
| 85 |
/* Structural Board Alignment Layout */
|
| 86 |
.moses-board { font-family: ui-monospace, monospace; margin-top: 6px; width: 100% !important; box-sizing: border-box !important; }
|
| 87 |
-
.mb-head, .mb-row { display: grid; grid-template-columns:
|
| 88 |
-
align-items: center; gap:
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 89 |
.mb-head { color: #C4923A; font-size: 10px; letter-spacing: 0.06em; text-transform: uppercase;
|
| 90 |
border-bottom: 1px solid #C4923A; }
|
| 91 |
.mb-row { border-bottom: 1px solid #3A3324; color: #8a7f68; font-size: 12px; }
|
|
@@ -114,6 +126,228 @@ button.primary:hover, #compute-btn:hover { background: #d8a449 !important; }
|
|
| 114 |
background: linear-gradient(90deg, rgba(196,146,58,0.28), rgba(196,146,58,0.72)); border-radius: 2px; }
|
| 115 |
.mb-row.you .mb-bar { background: linear-gradient(90deg, rgba(196,146,58,0.4), #C4923A); }
|
| 116 |
.mb-yval { position: relative; z-index: 2; color: #E8E0CF; font-weight: 700; font-size: 12px; padding-right: 4px; }
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 117 |
.mb-foot { color: #5f573f; font-size: 10.5px; padding: 10px 8px 0; line-height: 1.6; }
|
| 118 |
|
| 119 |
/* composition bar */
|
|
@@ -275,6 +509,24 @@ footer { display: none !important; }
|
|
| 275 |
.mb-row span:nth-child(3), .mb-row span:nth-child(4) { display: none !important; }
|
| 276 |
.mb-op { min-width: 0; overflow-wrap: anywhere; }
|
| 277 |
.mb-raw { font-size: 9px; line-height: 1.35; }
|
|
|
|
| 278 |
.mb-y, .mb-yval { font-size: 11px !important; }
|
| 279 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 280 |
"""
|
|
|
|
| 14 |
--species-cascade: #C4923A;
|
| 15 |
}
|
| 16 |
.gradio-container, .gradio-container * { font-family: ui-monospace, "SF Mono", Menlo, monospace !important; }
|
| 17 |
+
.gradio-container { background: var(--moses-bg) !important; max-width: 1100px !important; margin: 0 auto !important; overflow-x: hidden !important; }
|
| 18 |
.dark .gradio-container, body { background: var(--moses-bg) !important; }
|
| 19 |
|
| 20 |
#moses-hero {
|
| 21 |
border-bottom: 1px solid var(--moses-gold);
|
| 22 |
+
padding: 10px 0 4px;
|
| 23 |
+
margin-bottom: 0;
|
| 24 |
position: relative;
|
| 25 |
}
|
| 26 |
+
/* kill the dead space: Blocks root column adds a 16px gap between hero and tabs */
|
| 27 |
+
.column:has(> #moses-hero) { gap: 4px !important; }
|
| 28 |
+
.tab-wrapper { margin: 0 0 2px 0 !important; padding: 0 !important; }
|
| 29 |
#moses-hero h1 {
|
| 30 |
color: var(--moses-gold) !important;
|
| 31 |
+
font-size: 66px !important;
|
| 32 |
+
letter-spacing: 0.14em !important;
|
| 33 |
+
font-weight: 800 !important;
|
| 34 |
margin: 0 !important;
|
| 35 |
}
|
| 36 |
#moses-hero p { color: var(--moses-dim) !important; font-size: 12px !important; margin: 6px 0 0 !important; }
|
|
|
|
| 47 |
.tabitem {
|
| 48 |
background: transparent !important;
|
| 49 |
border: none !important;
|
| 50 |
+
padding: 2px 0px !important;
|
| 51 |
}
|
| 52 |
+
.tabitem > div { gap: 10px !important; }
|
| 53 |
button.selected { color: var(--moses-gold) !important; border-bottom: 2px solid var(--moses-gold) !important; }
|
| 54 |
+
/* centered nav links (Gradio 6.x uses .tab-container, not .tab-nav) */
|
| 55 |
+
.tab-nav, .tab-container { justify-content: center !important; gap: 6px; }
|
| 56 |
+
.tab-nav button, .tab-container > button { color: var(--moses-dim) !important; font-size: 14px !important;
|
| 57 |
+
letter-spacing: 0.08em; text-transform: uppercase; font-weight: 700 !important; padding: 8px 16px !important; }
|
| 58 |
|
| 59 |
.dataframe, table { background: var(--moses-card) !important; color: var(--moses-ink) !important;
|
| 60 |
border: 1px solid var(--moses-line) !important; font-size: 12px !important; width: 100% !important; }
|
|
|
|
| 90 |
|
| 91 |
/* Structural Board Alignment Layout */
|
| 92 |
.moses-board { font-family: ui-monospace, monospace; margin-top: 6px; width: 100% !important; box-sizing: border-box !important; }
|
| 93 |
+
.mb-head, .mb-row { display: grid; grid-template-columns: 26px 0.95fr 0.5fr 0.55fr 0.5fr 0.55fr 0.5fr 0.9fr 1.5fr;
|
| 94 |
+
align-items: center; gap: 8px; padding: 7px 12px; width: 100%; box-sizing: border-box; }
|
| 95 |
+
.mb-ledger { color: #7a7060; font-size: 10px; font-family: ui-monospace, monospace; text-align: right;
|
| 96 |
+
white-space: nowrap; overflow: hidden; text-overflow: ellipsis; border-left: 1px solid #2c2718; padding-left: 8px; }
|
| 97 |
+
.mb-head .mb-ledger { color: #C4923A; }
|
| 98 |
+
/* sharp tabular separators between numeric columns */
|
| 99 |
+
.mb-head .mb-num, .mb-row .mb-num, .mb-head .mb-y, .mb-row .mb-y {
|
| 100 |
+
border-left: 1px solid #2c2718; padding-left: 8px; }
|
| 101 |
.mb-head { color: #C4923A; font-size: 10px; letter-spacing: 0.06em; text-transform: uppercase;
|
| 102 |
border-bottom: 1px solid #C4923A; }
|
| 103 |
.mb-row { border-bottom: 1px solid #3A3324; color: #8a7f68; font-size: 12px; }
|
|
|
|
| 126 |
background: linear-gradient(90deg, rgba(196,146,58,0.28), rgba(196,146,58,0.72)); border-radius: 2px; }
|
| 127 |
.mb-row.you .mb-bar { background: linear-gradient(90deg, rgba(196,146,58,0.4), #C4923A); }
|
| 128 |
.mb-yval { position: relative; z-index: 2; color: #E8E0CF; font-weight: 700; font-size: 12px; padding-right: 4px; }
|
| 129 |
+
/* warmer, more inviting rows: subtle gold wash on hover, breathing room for the ledger line */
|
| 130 |
+
.mb-row { transition: background 0.12s ease; }
|
| 131 |
+
.mb-row:hover { background: rgba(196,146,58,0.07); }
|
| 132 |
+
.mb-raw { display: inline-block; margin-top: 3px; letter-spacing: 0.02em; opacity: 0.82; }
|
| 133 |
+
/* warm focus ring on the operator pickers */
|
| 134 |
+
#op-pick input:focus, #cmp-pick input:focus { box-shadow: 0 0 0 1px var(--moses-gold) !important; }
|
| 135 |
+
|
| 136 |
+
/* ---------- VS / compare table ---------- */
|
| 137 |
+
.cmp-table { width: 100%; border-collapse: collapse; background: var(--moses-card);
|
| 138 |
+
border: 1px solid var(--moses-line); border-radius: 6px; overflow: hidden; margin-top: 6px; }
|
| 139 |
+
.cmp-table th, .cmp-table td { padding: 10px 12px; text-align: right; font-size: 13px;
|
| 140 |
+
border-bottom: 1px solid var(--moses-line); }
|
| 141 |
+
.cmp-table thead th { color: var(--moses-gold); text-transform: uppercase; font-size: 11px;
|
| 142 |
+
letter-spacing: 0.05em; border-bottom: 1px solid var(--moses-gold); }
|
| 143 |
+
.cmp-table th.cmp-op { color: var(--moses-ink); font-weight: 700; }
|
| 144 |
+
.cmp-rowlabel { text-align: left !important; color: var(--moses-dim); text-transform: uppercase;
|
| 145 |
+
font-size: 10px; letter-spacing: 0.05em; }
|
| 146 |
+
.cmp-win { color: var(--moses-bg) !important; background: var(--moses-gold) !important;
|
| 147 |
+
font-weight: 700; }
|
| 148 |
+
.cmp-empty { padding: 26px; text-align: center; color: var(--moses-dim);
|
| 149 |
+
border: 1px dashed var(--moses-line); border-radius: 6px; background: rgba(196,146,58,0.03); }
|
| 150 |
+
.cmp-note { color: var(--moses-dim); font-size: 10px; margin-top: 8px; }
|
| 151 |
+
@media (max-width: 700px) { .cmp-table th, .cmp-table td { padding: 7px 6px; font-size: 11px; } }
|
| 152 |
+
|
| 153 |
+
/* ---------- Home / landing ---------- */
|
| 154 |
+
.hm-lead { color: var(--moses-dim); font-size: 11px; letter-spacing: 0.04em;
|
| 155 |
+
text-transform: uppercase; margin: 2px 2px 6px; }
|
| 156 |
+
.pm-wrap { overflow: hidden; border: 1px solid var(--moses-line); border-radius: 6px;
|
| 157 |
+
background: var(--moses-card); padding: 8px 0; margin-bottom: 14px; }
|
| 158 |
+
.pm-track { display: flex; gap: 10px; width: max-content; animation: pm-scroll 70s linear infinite; }
|
| 159 |
+
.pm-wrap:hover .pm-track { animation-play-state: paused; }
|
| 160 |
+
@keyframes pm-scroll { from { transform: translateX(0); } to { transform: translateX(-50%); } }
|
| 161 |
+
.pm-chip { display: flex; align-items: center; gap: 8px; padding: 6px 12px; white-space: nowrap;
|
| 162 |
+
border-left: 3px solid var(--moses-line); background: rgba(196,146,58,0.04); border-radius: 4px; }
|
| 163 |
+
.pm-chip.species-throughput { border-left-color: var(--species-throughput); }
|
| 164 |
+
.pm-chip.species-converter { border-left-color: var(--species-converter); }
|
| 165 |
+
.pm-chip.species-architect { border-left-color: var(--species-architect); }
|
| 166 |
+
.pm-chip.species-cascade { border-left-color: var(--species-cascade); }
|
| 167 |
+
.pm-rank { color: var(--moses-dim); font-size: 10px; font-weight: 700; }
|
| 168 |
+
.pm-name { color: var(--moses-ink); font-size: 12px; font-weight: 700; }
|
| 169 |
+
.pm-stat { color: var(--moses-gold); font-size: 11px; font-weight: 700; }
|
| 170 |
+
.pm-lev { color: var(--moses-dim); font-size: 10px; }
|
| 171 |
+
|
| 172 |
+
.hm-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; }
|
| 173 |
+
.hm-box { border: 1px solid var(--moses-line); border-radius: 6px; background: var(--moses-card);
|
| 174 |
+
padding: 16px 18px; transition: border-color 0.12s ease, background 0.12s ease; }
|
| 175 |
+
.hm-box:hover { border-color: var(--moses-gold); background: rgba(196,146,58,0.06); }
|
| 176 |
+
.hm-title { color: var(--moses-gold); font-size: 15px; font-weight: 800; letter-spacing: 0.04em; }
|
| 177 |
+
.hm-sub { color: var(--moses-ink); font-size: 12px; font-weight: 600; margin-top: 3px; }
|
| 178 |
+
.hm-desc { color: var(--moses-dim); font-size: 11px; margin-top: 6px; line-height: 1.45; }
|
| 179 |
+
.hm-cta { color: var(--moses-gold); font-size: 10px; text-transform: uppercase;
|
| 180 |
+
letter-spacing: 0.06em; margin-top: 12px; }
|
| 181 |
+
@media (max-width: 700px) { .hm-grid { grid-template-columns: 1fr; } }
|
| 182 |
+
|
| 183 |
+
/* metric standard (feature row) */
|
| 184 |
+
.mf-head { text-align: center; color: var(--moses-ink); font-size: 26px; font-weight: 800;
|
| 185 |
+
letter-spacing: 0.01em; margin: 0 0 14px; line-height: 1.2; }
|
| 186 |
+
.mf-head span { color: var(--moses-gold); text-shadow: 0 0 18px rgba(196,146,58,0.35); }
|
| 187 |
+
@media (max-width: 700px) { .mf-head { font-size: 20px; } }
|
| 188 |
+
.mf-grid { display: grid; grid-template-columns: repeat(5, 1fr); gap: 10px; margin-bottom: 14px; }
|
| 189 |
+
/* live-status box (sits between SNR and 10x) */
|
| 190 |
+
.mf-status { text-align: left; }
|
| 191 |
+
.ms-title { color: #4ade80; font-size: 12px; font-weight: 800; letter-spacing: 0.06em;
|
| 192 |
+
text-transform: uppercase; margin-bottom: 8px; }
|
| 193 |
+
.ms-dot { color: #22c55e; }
|
| 194 |
+
.ms-grid { display: grid; grid-template-columns: 1fr auto; gap: 3px 8px; font-size: 11px; align-items: baseline; }
|
| 195 |
+
.ms-grid > span:nth-child(odd) { color: var(--moses-dim); text-transform: uppercase; letter-spacing: 0.03em; }
|
| 196 |
+
.ms-grid > span:nth-child(even) { text-align: right; font-weight: 800; }
|
| 197 |
+
.ms-tot { color: var(--moses-ink); }
|
| 198 |
+
.mf-box { border: 1px solid var(--moses-gold); border-radius: 6px; background: rgba(196,146,58,0.06);
|
| 199 |
+
padding: 12px; text-align: center; }
|
| 200 |
+
.mf-sym { color: var(--moses-dim); font-size: 12px; font-weight: 700; text-transform: uppercase; letter-spacing: 0.08em; }
|
| 201 |
+
.mf-big { color: var(--moses-gold); font-size: 32px; font-weight: 800; line-height: 1.05; margin: 4px 0 2px;
|
| 202 |
+
text-shadow: 0 0 16px rgba(196,146,58,0.3); }
|
| 203 |
+
.mf-form { color: var(--moses-dim); font-size: 9.5px; font-family: ui-monospace, monospace; }
|
| 204 |
+
.mf-tag { color: var(--moses-dim); font-size: 10px; text-transform: uppercase; letter-spacing: 0.04em; margin-top: 4px; }
|
| 205 |
+
@media (max-width: 700px) { .mf-grid { grid-template-columns: 1fr 1fr; } }
|
| 206 |
+
|
| 207 |
+
/* mini samples inside section boxes */
|
| 208 |
+
.hm-sample { margin: 10px 0; padding: 8px 10px; border: 1px solid var(--moses-line);
|
| 209 |
+
border-radius: 4px; background: var(--moses-bg); font-size: 11px; }
|
| 210 |
+
.sm-row { display: flex; gap: 8px; align-items: center; padding: 2px 0; }
|
| 211 |
+
.sm-rk { color: var(--moses-dim); font-size: 10px; width: 22px; }
|
| 212 |
+
.sm-nm { color: var(--moses-ink); font-weight: 700; flex: 1; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
|
| 213 |
+
.sm-y { color: var(--moses-gold); font-weight: 700; }
|
| 214 |
+
.sm-y2 { color: var(--moses-dim); font-weight: 700; }
|
| 215 |
+
.sm-card .sm-nm { font-size: 12px; }
|
| 216 |
+
.sm-kv { color: var(--moses-dim); font-size: 10px; margin-top: 3px; }
|
| 217 |
+
.sm-vs { display: flex; gap: 6px; align-items: center; flex-wrap: wrap; }
|
| 218 |
+
.sm-vsx { color: var(--moses-gold); font-size: 10px; text-transform: uppercase; }
|
| 219 |
+
.sm-create { display: flex; gap: 6px; align-items: center; flex-wrap: wrap; }
|
| 220 |
+
.sm-create code { color: var(--moses-dim); font-size: 10px; }
|
| 221 |
+
.sm-arrow { color: var(--moses-gold); }
|
| 222 |
+
|
| 223 |
+
/* home footer: demo video + steps + links */
|
| 224 |
+
.hm-foot { display: grid; grid-template-columns: 1fr 1.4fr 0.8fr; gap: 16px; margin-top: 14px;
|
| 225 |
+
padding-top: 14px; border-top: 1px solid var(--moses-line); }
|
| 226 |
+
.hf-h { color: var(--moses-gold); font-size: 11px; text-transform: uppercase; letter-spacing: 0.05em; margin-bottom: 8px; }
|
| 227 |
+
.hf-btn { display: inline-block; background: var(--moses-gold); color: var(--moses-bg) !important;
|
| 228 |
+
padding: 8px 14px; border-radius: 5px; font-weight: 700; font-size: 12px; text-decoration: none; }
|
| 229 |
+
.hf-steps { margin: 0; padding-left: 18px; color: var(--moses-dim); font-size: 11px; line-height: 1.7; }
|
| 230 |
+
.hf-steps code { color: var(--moses-ink); font-size: 10px; }
|
| 231 |
+
.hf-steps b { color: var(--moses-gold); }
|
| 232 |
+
.hf-link { display: block; color: var(--moses-gold) !important; font-size: 12px; margin-bottom: 6px; text-decoration: none; }
|
| 233 |
+
.hf-link:hover { text-decoration: underline; }
|
| 234 |
+
@media (max-width: 700px) { .hm-foot { grid-template-columns: 1fr; } }
|
| 235 |
+
|
| 236 |
+
/* ---------- mini page thumbnails (real HTML scaled down) ---------- */
|
| 237 |
+
.mini { border-radius: 8px; overflow: hidden; background: var(--moses-card);
|
| 238 |
+
border: 1px solid var(--moses-line); box-shadow: 0 6px 20px rgba(0,0,0,0.5); margin-bottom: 12px; }
|
| 239 |
+
.mini-chrome { display: flex; align-items: center; gap: 5px; padding: 6px 9px;
|
| 240 |
+
border-bottom: 1px solid var(--moses-line); background: linear-gradient(90deg,#241f17,#15130f); }
|
| 241 |
+
.mini-chrome span { width: 7px; height: 7px; border-radius: 50%; background: #3A3324; flex: none; }
|
| 242 |
+
.mini-cap { margin-left: auto; font-size: 8.5px; text-transform: uppercase;
|
| 243 |
+
letter-spacing: 0.08em; color: var(--moses-dim); }
|
| 244 |
+
.mini-view { position: relative; height: 190px; overflow: hidden; background: var(--moses-bg); }
|
| 245 |
+
.mini-scale { position: absolute; top: 0; left: 0; width: 323%;
|
| 246 |
+
transform: scale(0.31); transform-origin: top left; pointer-events: none; }
|
| 247 |
+
/* per-section accent on the chrome dot + frame + glow */
|
| 248 |
+
.mini-gold { border-color: rgba(196,146,58,0.55); } .mini-gold .mini-chrome span:first-child { background: #C4923A; }
|
| 249 |
+
.mini-purple { border-color: rgba(139,92,246,0.55); } .mini-purple .mini-chrome span:first-child { background: #8b5cf6; }
|
| 250 |
+
.mini-blue { border-color: rgba(59,130,246,0.55); } .mini-blue .mini-chrome span:first-child { background: #3b82f6; }
|
| 251 |
+
.mini-green { border-color: rgba(34,197,94,0.55); } .mini-green .mini-chrome span:first-child { background: #22c55e; }
|
| 252 |
+
|
| 253 |
+
/* colorful section accents */
|
| 254 |
+
.hm-gold { border-top: 3px solid #C4923A; } .hm-gold .hm-title { color: #C4923A; }
|
| 255 |
+
.hm-purple { border-top: 3px solid #8b5cf6; } .hm-purple .hm-title { color: #a78bfa; }
|
| 256 |
+
.hm-blue { border-top: 3px solid #3b82f6; } .hm-blue .hm-title { color: #60a5fa; }
|
| 257 |
+
.hm-green { border-top: 3px solid #22c55e; } .hm-green .hm-title { color: #4ade80; }
|
| 258 |
+
.hm-gold:hover { box-shadow: 0 0 0 1px #C4923A, 0 10px 26px rgba(196,146,58,0.18); border-color: #C4923A; }
|
| 259 |
+
.hm-purple:hover { box-shadow: 0 0 0 1px #8b5cf6, 0 10px 26px rgba(139,92,246,0.18); border-color: #8b5cf6; }
|
| 260 |
+
.hm-blue:hover { box-shadow: 0 0 0 1px #3b82f6, 0 10px 26px rgba(59,130,246,0.18); border-color: #3b82f6; }
|
| 261 |
+
.hm-green:hover { box-shadow: 0 0 0 1px #22c55e, 0 10px 26px rgba(34,197,94,0.18); border-color: #22c55e; }
|
| 262 |
+
|
| 263 |
+
/* create-tab mock (rendered inside its thumbnail) */
|
| 264 |
+
.cr-mock { padding: 16px; font-size: 14px; }
|
| 265 |
+
.cr-code { color: #4ade80; background: #0f0d0a; padding: 10px 12px; border-radius: 5px;
|
| 266 |
+
font-family: ui-monospace, monospace; }
|
| 267 |
+
.cr-box { color: var(--moses-dim); border: 1px dashed var(--moses-line); padding: 12px;
|
| 268 |
+
margin: 10px 0; border-radius: 5px; }
|
| 269 |
+
.cr-box b { color: var(--moses-ink); }
|
| 270 |
+
.cr-btn { background: var(--moses-gold); color: var(--moses-bg); text-align: center;
|
| 271 |
+
padding: 10px; border-radius: 5px; font-weight: 800; }
|
| 272 |
+
.cr-res { color: var(--moses-gold); margin-top: 10px; font-weight: 800; text-align: center; }
|
| 273 |
+
|
| 274 |
+
/* ---------- metrics explainer (SigRank vs standard) ---------- */
|
| 275 |
+
.mx-wrap { margin-top: 8px; }
|
| 276 |
+
.mx-analogy { color: var(--moses-ink); font-size: 14px; line-height: 1.55; text-align: center;
|
| 277 |
+
max-width: 760px; margin: 0 auto 18px; }
|
| 278 |
+
.mx-analogy .mx-gold, .mx-bottom .mx-gold { color: var(--moses-gold); font-weight: 700; }
|
| 279 |
+
.mx-cols { display: grid; grid-template-columns: 1fr 1fr; gap: 14px; }
|
| 280 |
+
.mx-col { border: 1px solid var(--moses-line); border-radius: 8px; padding: 14px 16px; background: var(--moses-card); }
|
| 281 |
+
.mx-col-sig { border-color: rgba(196,146,58,0.5); background: rgba(196,146,58,0.05); }
|
| 282 |
+
.mx-col-head { font-size: 13px; font-weight: 800; letter-spacing: 0.05em; text-transform: uppercase;
|
| 283 |
+
margin-bottom: 12px; padding-bottom: 8px; border-bottom: 1px solid var(--moses-line); }
|
| 284 |
+
.mx-col-std .mx-col-head { color: var(--moses-dim); }
|
| 285 |
+
.mx-col-sig .mx-col-head { color: var(--moses-gold); }
|
| 286 |
+
.mx-item { padding: 9px 0; border-bottom: 1px solid #2c2718; }
|
| 287 |
+
.mx-item:last-of-type { border-bottom: 0; }
|
| 288 |
+
.mx-item-head { display: flex; justify-content: space-between; align-items: baseline; gap: 10px; flex-wrap: wrap; }
|
| 289 |
+
.mx-name { color: var(--moses-ink); font-weight: 700; font-size: 12.5px; }
|
| 290 |
+
.mx-form { color: var(--moses-gold); font-family: ui-monospace, monospace; font-size: 11px; }
|
| 291 |
+
.mx-desc { color: var(--moses-dim); font-size: 11.5px; line-height: 1.45; margin-top: 3px; }
|
| 292 |
+
.mx-vs { color: #a89e85; font-size: 11.5px; line-height: 1.45; margin-top: 4px; }
|
| 293 |
+
.mx-vs b { color: var(--moses-dim); }
|
| 294 |
+
.mx-result { color: var(--moses-gold); font-size: 11.5px; margin-top: 3px; font-weight: 600; }
|
| 295 |
+
.mx-foot { color: var(--moses-dim); font-size: 11px; margin-top: 12px; padding-top: 10px;
|
| 296 |
+
border-top: 1px dashed var(--moses-line); }
|
| 297 |
+
.mx-foot b { color: var(--moses-ink); }
|
| 298 |
+
.mx-table { width: 100%; border-collapse: collapse; margin: 18px 0; background: var(--moses-card);
|
| 299 |
+
border: 1px solid var(--moses-line); border-radius: 8px; overflow: hidden; }
|
| 300 |
+
.mx-table th, .mx-table td { padding: 10px 12px; text-align: left; font-size: 12px;
|
| 301 |
+
border-bottom: 1px solid var(--moses-line); }
|
| 302 |
+
.mx-table thead th { color: var(--moses-gold); text-transform: uppercase; font-size: 10.5px;
|
| 303 |
+
letter-spacing: 0.05em; border-bottom: 1px solid var(--moses-gold); }
|
| 304 |
+
.mx-table .mx-aspect { color: var(--moses-dim); font-weight: 700; text-transform: uppercase;
|
| 305 |
+
font-size: 10px; letter-spacing: 0.04em; }
|
| 306 |
+
.mx-table td { color: #a89e85; }
|
| 307 |
+
.mx-table .mx-win { color: var(--moses-ink); font-weight: 600; background: rgba(196,146,58,0.06); }
|
| 308 |
+
.mx-thermo { border-left: 3px solid var(--moses-gold); background: rgba(196,146,58,0.05);
|
| 309 |
+
border-radius: 0 6px 6px 0; padding: 12px 16px; margin: 16px 0; color: #a89e85; font-size: 12px; line-height: 1.6; }
|
| 310 |
+
.mx-thermo b { color: var(--moses-ink); }
|
| 311 |
+
.mx-thermo-h { color: var(--moses-gold); font-weight: 800; font-size: 12px; letter-spacing: 0.03em; margin-bottom: 6px; }
|
| 312 |
+
.mx-bottom { text-align: center; color: var(--moses-ink); font-size: 13px; line-height: 1.55;
|
| 313 |
+
max-width: 760px; margin: 16px auto 0; }
|
| 314 |
+
@media (max-width: 700px) { .mx-cols { grid-template-columns: 1fr; } .mx-analogy { font-size: 13px; } }
|
| 315 |
+
|
| 316 |
+
/* ---------- middle nav link (Leaders) emphasized ---------- */
|
| 317 |
+
.tab-container > button:nth-child(3), .tab-nav > button:nth-child(3) {
|
| 318 |
+
color: var(--moses-gold) !important; font-size: 17px !important; font-weight: 800 !important;
|
| 319 |
+
text-shadow: 0 0 14px rgba(196,146,58,0.4); }
|
| 320 |
+
|
| 321 |
+
/* ---------- hero status + live counters (top-right) ---------- */
|
| 322 |
+
.hero-stat { text-align: right; font-size: 10px; letter-spacing: 0.06em; line-height: 1.65;
|
| 323 |
+
font-weight: 700; color: var(--moses-dim); white-space: nowrap; min-width: 196px;
|
| 324 |
+
margin-top: 34px; } /* clear the HF Space pill (burnmydays/sigrank ♡) in embedded view */
|
| 325 |
+
.hs-row { display: flex; justify-content: space-between; gap: 16px; }
|
| 326 |
+
.hs-div { height: 1px; background: var(--moses-line); margin: 5px 0; }
|
| 327 |
+
.hs-burn { color: #ef6b6b; } .hs-build { color: #4ade80; } .hs-tenx { color: var(--moses-gold); }
|
| 328 |
+
@media (max-width: 700px) { .hero-stat { display: none; } }
|
| 329 |
+
|
| 330 |
+
/* ---------- equation boxes: median/avg + hover description ---------- */
|
| 331 |
+
.mf-box { position: relative; cursor: help; }
|
| 332 |
+
.mf-stat { color: var(--moses-dim); font-size: 9.5px; margin-top: 5px; letter-spacing: 0.02em; }
|
| 333 |
+
.mf-tip { position: absolute; left: 50%; bottom: calc(100% + 8px); transform: translateX(-50%);
|
| 334 |
+
width: 220px; max-width: 70vw; background: #0f0d0a; color: var(--moses-ink);
|
| 335 |
+
border: 1px solid var(--moses-gold); border-radius: 6px; padding: 10px 12px; font-size: 11px;
|
| 336 |
+
line-height: 1.45; text-align: left; opacity: 0; visibility: hidden; transition: opacity 0.15s ease;
|
| 337 |
+
z-index: 60; box-shadow: 0 8px 24px rgba(0,0,0,0.6); }
|
| 338 |
+
.mf-box:hover .mf-tip, .mf-box:focus .mf-tip { opacity: 1; visibility: visible; }
|
| 339 |
+
.mf-sub { text-align: center; color: var(--moses-dim); font-size: 10px; margin: -4px 0 14px; }
|
| 340 |
+
|
| 341 |
+
/* ---------- reports: learn-from insights ---------- */
|
| 342 |
+
.ins-wrap { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; margin-top: 14px; }
|
| 343 |
+
.ins-block { border: 1px solid var(--moses-line); border-radius: 6px; padding: 12px 14px; }
|
| 344 |
+
.ins-good { border-left: 3px solid #4ade80; background: rgba(34,197,94,0.05); }
|
| 345 |
+
.ins-avoid { border-left: 3px solid #ef6b6b; background: rgba(239,107,107,0.05); }
|
| 346 |
+
.ins-h { font-size: 11px; text-transform: uppercase; letter-spacing: 0.05em; font-weight: 800; margin-bottom: 6px; }
|
| 347 |
+
.ins-good .ins-h { color: #4ade80; } .ins-avoid .ins-h { color: #ef6b6b; }
|
| 348 |
+
.ins-block ul { margin: 0; padding-left: 16px; }
|
| 349 |
+
.ins-block li { color: var(--moses-dim); font-size: 11.5px; line-height: 1.5; margin-bottom: 4px; }
|
| 350 |
+
@media (max-width: 700px) { .ins-wrap { grid-template-columns: 1fr; } }
|
| 351 |
.mb-foot { color: #5f573f; font-size: 10.5px; padding: 10px 8px 0; line-height: 1.6; }
|
| 352 |
|
| 353 |
/* composition bar */
|
|
|
|
| 509 |
.mb-row span:nth-child(3), .mb-row span:nth-child(4) { display: none !important; }
|
| 510 |
.mb-op { min-width: 0; overflow-wrap: anywhere; }
|
| 511 |
.mb-raw { font-size: 9px; line-height: 1.35; }
|
| 512 |
+
.mb-ledger { display: none !important; }
|
| 513 |
.mb-y, .mb-yval { font-size: 11px !important; }
|
| 514 |
}
|
| 515 |
+
|
| 516 |
+
@media (max-width: 700px) {
|
| 517 |
+
/* Mobile overflow fix. Two real causes (found via live DOM inspection):
|
| 518 |
+
1) Gradio's fillable container + flex children (default min-width:auto) refuse
|
| 519 |
+
to shrink below content, pinning the page at ~1100px and scrolling sideways.
|
| 520 |
+
2) the marquee track is ~5000px wide; its wrapper must hard-clip.
|
| 521 |
+
min-width:0 lets the flex children collapse to the viewport. */
|
| 522 |
+
html, body { overflow-x: hidden !important; max-width: 100vw !important; }
|
| 523 |
+
.gradio-container, .main, .wrap, .contain, .column, .block {
|
| 524 |
+
max-width: 100% !important; min-width: 0 !important; }
|
| 525 |
+
.pm-wrap { max-width: 100% !important; overflow: hidden !important; }
|
| 526 |
+
.gradio-container { padding-left: 8px !important; padding-right: 8px !important; }
|
| 527 |
+
#moses-hero h1 { font-size: 34px !important; letter-spacing: 0.08em !important; }
|
| 528 |
+
#moses-hero { padding-top: 26px; } /* clear the HF Space pill on phones */
|
| 529 |
+
#moses-hero p { font-size: 12px !important; }
|
| 530 |
+
#rank-by, #rank-by .wrap { flex-wrap: wrap !important; } /* Rank-by chips wrap, not overflow */
|
| 531 |
+
}
|
| 532 |
"""
|