// The first screen, drawn before the index is read: the pictograms, and the hero from first.json (written by the deploy // step from the index commit of the day) when that commit is the one the page reads. app.js draws the hero from the // index itself when it has read it (data.js totals; portal.py first_screen counts alike). import { fmtBytes, fmtCompact, fmtDate, fmtInt } from './charts.js'; import { loadRevision } from './commit.js'; import { onLanguage, t } from './i18n.js'; import { icon } from './icons.js'; const reduced = () => matchMedia('(prefers-reduced-motion: reduce)').matches; const FACTS = { ready_sources: fmtInt, answers: fmtInt, raw_rows: fmtCompact, sources: fmtInt }; const shown = new Map(); /** Pictograms for every [data-icon] element, once. */ export function decorate(root = document) { for (const n of root.querySelectorAll('[data-icon]:not([data-drawn])')) { n.dataset.drawn = '1'; const inBar = n.closest('.progress'); n.prepend(icon(n.dataset.icon, { size: Number(n.dataset.size || (inBar ? 14 : 20)) })); } } /** Write value into node. The first value is written as it is (no count from 0: the first screen shows the true * numbers at once). A later, different value (main has moved past the commit first.json names, or the page reads * preview data) is written and briefly highlighted as an update. */ export function setNumber(node, key, value, fmt) { if (!node) return; const was = shown.get(key); shown.set(key, value); node.textContent = fmt(value); node.dataset.v = String(value); if (was == null || was === value || reduced()) return; node.classList.remove('updated'); void node.offsetWidth; node.classList.add('updated'); node.addEventListener('animationend', () => node.classList.remove('updated'), { once: true }); } /** The size line (#364): distinct content and the rows without a size, not in it; the words of docs/sources.md of the * index. */ function drawSize(v) { const node = document.getElementById('hero-size'); if (!node || !('distinct_bytes' in v)) return; if (v.distinct_bytes == null) { node.replaceChildren(t('hero.sizeUnknown')); return; } const big = document.createElement('b'); const unsized = v.unsized_rows ? ` ยท ${t('hero.unsized', { count: v.unsized_rows, n: fmtInt(v.unsized_rows) })}` : ''; node.replaceChildren(big, ` ${t('hero.distinct')}${unsized}`); setNumber(big, 'distinct_bytes', v.distinct_bytes, fmtBytes); } let last = null; /** v: {ready_units, ready_sources, answers, raw_rows, sources, distinct_bytes, unsized_rows, index, date}. */ export function drawHero(v) { if (!v) return; last = v; setNumber(document.getElementById('hero-big'), 'ready_units', v.ready_units, fmtInt); setNumber(document.getElementById('material-n'), 'material_units', v.ready_units, fmtInt); drawSize(v); for (const li of document.querySelectorAll('#hero-facts .fact-tile')) { const k = li.dataset.k; if (v[k] != null) setNumber(li.querySelector('.fact-num'), k, v[k], FACTS[k]); } const pin = document.getElementById('pin-link'); if (v.index && pin) { pin.textContent = fmtDate(v.date); pin.href = `https://huggingface.co/datasets/Battam/agentic-env-index/tree/${v.index}`; pin.title = t('hero.commit', { sha: v.index }); } const foot = document.getElementById('foot-pin'); if (v.index && foot) foot.textContent = t('foot.index', { sha: v.index.slice(0, 7), date: fmtDate(v.date) }); } decorate(); // the hero in the new language: the same numbers, written again onLanguage(() => drawHero(last)); let drawnFromIndex = false; export const markFromIndex = () => { drawnFromIndex = true; }; // first.json was computed at deploy from one commit of the index; it is drawn only when that is the commit the page reads // (?rev= or main as it is now), else the hero waits for the page's own count. With ?catalog= or ?vocabulary= the page // shows other data at the same commit, so the hero waits too (the file is still read: the page preloads it). const params = new URLSearchParams(location.search); const override = params.has('catalog') || params.has('vocabulary'); Promise.all([ fetch('first.json', { cache: 'no-cache' }).then((r) => (r.ok ? r.json() : null)), loadRevision(params.get('rev')), ]) .then(([j, rev]) => { if (j && !override && !drawnFromIndex && rev.sha && j.index === rev.sha) drawHero(j); }) .catch(() => {});