cbtogu's picture
update leaderboard
920632a
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>World Model Track Leaderboard | GigaBrain Challenge 2026</title>
<script src="https://cdn.tailwindcss.com"></script>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@300;400;600;700&display=swap" rel="stylesheet">
<style>
body { font-family: 'Inter', sans-serif; scroll-behavior: smooth; }
.glass { background: rgba(255, 255, 255, 0.7); backdrop-filter: blur(12px); -webkit-backdrop-filter: blur(12px); }
</style>
</head>
<body class="bg-gray-50 text-gray-800">
<div class="min-h-screen">
<header class="relative overflow-hidden bg-gradient-to-br from-slate-900 via-slate-800 to-green-700 text-white">
<div class="absolute inset-0 opacity-20"></div>
<div class="relative max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-12">
<div>
<div>
<p class="text-sm uppercase tracking-[0.2em] text-green-200">GigaBrain Challenge 2026 · Track 2</p>
<h1 class="text-4xl md:text-5xl font-bold mt-3">World Model Track Leaderboard</h1>
<p class="mt-4 text-green-100 text-lg max-w-3xl">
Official leaderboard for the GigaBrain Challenge 2026 World Model Track.
</p>
<div class="mt-6 flex flex-wrap gap-3">
<a href="mailto:gigabrainchallenge@163.com?subject=World%20Model%20Track%20Submission" class="inline-flex items-center gap-2 rounded-full bg-green-500 hover:bg-green-600 px-5 py-2.5 text-sm font-semibold shadow">
Submit your run
</a>
<a href="#leaderboard" class="inline-flex items-center gap-2 rounded-full bg-white/10 px-5 py-2.5 text-sm font-semibold text-white ring-1 ring-white/30 hover:bg-white/20">
View rankings
</a>
</div>
</div>
</div>
</div>
</header>
<main class="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-12 space-y-10">
<section class="grid gap-6 md:grid-cols-3">
<div class="bg-white rounded-2xl shadow-sm border border-gray-100 p-6">
<div class="text-sm font-semibold text-green-700 uppercase tracking-wide">Accepted evidence</div>
<p class="mt-2 text-gray-700">Submit by email to <a class="text-green-700 underline" href="mailto:gigabrainchallenge@163.com">gigabrainchallenge@163.com</a> with your ZIP package and metadata JSON (max ZIP size: 200 MB).</p>
</div>
<div class="bg-white rounded-2xl shadow-sm border border-gray-100 p-6">
<div class="text-sm font-semibold text-green-700 uppercase tracking-wide">Submission format</div>
<p class="mt-2 text-gray-700">Zip your run package with the task/episode folder structure shown in the Submission section. Maximum ZIP file size is 200 MB.</p>
</div>
<div class="bg-white rounded-2xl shadow-sm border border-gray-100 p-6">
<div class="text-sm font-semibold text-green-700 uppercase tracking-wide">Update cadence</div>
<p class="mt-2 text-gray-700">Submissions ingest daily, verification weekly, leaderboard publish weekly (UTC).</p>
</div>
</section>
<section id="leaderboard" class="bg-white rounded-2xl shadow-sm border border-gray-100 p-6">
<div class="flex flex-col md:flex-row md:items-center md:justify-between gap-4 mb-5">
<div>
<h2 class="text-2xl font-bold text-gray-900">Leaderboard</h2>
</div>
<div class="flex flex-wrap gap-2">
<input id="search-input" type="text" placeholder="Search team or model" class="rounded-full border border-gray-300 px-4 py-2 text-sm focus:outline-none focus:ring-2 focus:ring-green-500" />
<button id="sort-score" class="inline-flex items-center gap-2 rounded-full bg-green-50 px-4 py-2 text-sm font-semibold text-green-700 ring-1 ring-inset ring-green-200 hover:bg-green-100">Sort: best score</button>
<button id="sort-updated" class="inline-flex items-center gap-2 rounded-full bg-gray-100 px-4 py-2 text-sm font-semibold text-gray-700 ring-1 ring-inset ring-gray-200 hover:bg-gray-200">Sort: latest</button>
</div>
</div>
<p id="load-state" class="text-sm text-gray-500 mb-3">Loading results.json...</p>
<div class="overflow-x-auto">
<table class="min-w-full divide-y divide-gray-200">
<thead class="bg-gray-50">
<tr>
<th class="px-4 py-3 text-left text-xs font-semibold text-gray-600 uppercase tracking-wide">Rank</th>
<th class="px-4 py-3 text-left text-xs font-semibold text-gray-600 uppercase tracking-wide">Team / Model</th>
<th class="px-4 py-3 text-left text-xs font-semibold text-gray-600 uppercase tracking-wide">Round 1</th>
<th class="px-4 py-3 text-left text-xs font-semibold text-gray-600 uppercase tracking-wide">Round 2</th>
<th class="px-4 py-3 text-left text-xs font-semibold text-gray-600 uppercase tracking-wide">Round 3</th>
<th class="px-4 py-3 text-left text-xs font-semibold text-gray-600 uppercase tracking-wide">Best</th>
<th class="px-4 py-3 text-left text-xs font-semibold text-gray-600 uppercase tracking-wide">Submitted</th>
<th class="px-4 py-3 text-left text-xs font-semibold text-gray-600 uppercase tracking-wide">Status</th>
</tr>
</thead>
<tbody id="table-body" class="divide-y divide-gray-100 bg-white"></tbody>
</table>
</div>
</section>
<section id="submit" class="bg-white rounded-2xl shadow-sm border border-gray-100 p-6 space-y-5">
<h3 class="text-2xl font-bold text-gray-900">Submission</h3>
<div class="flex flex-wrap gap-3">
<a href="mailto:gigabrainchallenge@163.com?subject=World%20Model%20Track%20Submission" class="inline-flex items-center gap-2 rounded-full bg-green-600 px-5 py-3 text-sm font-semibold text-white shadow hover:bg-green-700">
Submit via email
</a>
<a href="#schema" class="inline-flex items-center gap-2 rounded-full bg-gray-100 px-4 py-2.5 text-sm font-semibold text-gray-800 ring-1 ring-inset ring-gray-200 hover:bg-gray-200">
View JSON schema
</a>
</div>
<div class="grid md:grid-cols-3 gap-4">
<div class="bg-green-50 border border-green-100 rounded-xl p-4">
<h4 class="text-sm font-semibold text-green-800 uppercase tracking-wide">Step 1</h4>
<p class="mt-2 text-sm text-green-900">Prepare videos, metadata JSON, and contact details.</p>
</div>
<div class="bg-blue-50 border border-blue-100 rounded-xl p-4">
<h4 class="text-sm font-semibold text-blue-800 uppercase tracking-wide">Step 2</h4>
<p class="mt-2 text-sm text-blue-900">Email your ZIP package and metadata JSON to gigabrainchallenge@163.com with team/contact information.</p>
</div>
<div class="bg-amber-50 border border-amber-100 rounded-xl p-4">
<h4 class="text-sm font-semibold text-amber-800 uppercase tracking-wide">Step 3</h4>
<p class="mt-2 text-sm text-amber-900">Ensure each ZIP attachment is 200 MB or less. We verify evidence and publish validated results in weekly leaderboard updates.</p>
</div>
</div>
<div class="bg-gray-900 text-gray-100 rounded-xl p-4 overflow-x-auto text-sm">
<pre>outputs/
--video_quality_eval/
--task1/
--episode_0.mp4
--...
--...
--evaluator_test/
--task1/
--episode_0.mp4
--...
--...</pre>
</div>
</section>
<section id="schema" class="bg-white rounded-2xl shadow-sm border border-gray-100 p-6">
<h3 class="text-2xl font-bold text-gray-900 mb-3">Submission JSON schema</h3>
<div class="bg-gray-900 text-gray-100 rounded-xl p-4 overflow-x-auto text-sm">
<pre>{
"team_name": "Your Team Name",
"contact_email": "team@example.com",
"affiliation": "Example University",
"model_name": "Your Model Name",
"model_version": "v1.1",
"eval_setting": "Open-vocab tabletop; seed=5; 50 episodes",
"composite_score": 89.3,
"videos": [
{ "label": "long-horizon demo", "url": "https://huggingface.co/spaces/your-space/video1" }
],
"notes": "Any deviations from reference protocol."
}</pre>
</div>
</section>
<section class="bg-white rounded-2xl shadow-sm border border-gray-100 p-6 space-y-3">
<h3 class="text-2xl font-bold text-gray-900">Ranking updates and governance</h3>
<ul class="list-disc list-inside text-gray-700 space-y-2">
<li><span class="font-semibold">Ingest daily:</span> new submissions are queued.</li>
<li><span class="font-semibold">Validate weekly:</span> videos and metadata are checked.</li>
<li><span class="font-semibold">Publish weekly:</span> rankings refresh after validation.</li>
<li><span class="font-semibold">Tie-break:</span> best score, then earlier submission.</li>
</ul>
</section>
</main>
</div>
<script>
let rows = [];
let sortBy = 'score';
function escapeHtml(s) {
return String(s ?? '')
.replace(/&/g, '&amp;')
.replace(/</g, '&lt;')
.replace(/>/g, '&gt;')
.replace(/"/g, '&quot;')
.replace(/'/g, '&#39;');
}
const ROUND_KEYS = ['score(round1)', 'score(round2)', 'score(round3)'];
function formatRoundScore(v) {
if (v === null || v === undefined || v === '') return 'N/A';
const n = Number(v);
if (Number.isNaN(n)) return 'N/A';
return String(parseFloat(n.toFixed(2)));
}
/** Numeric value for sorting by best score; missing → -Infinity so rows sink to bottom when sorted desc. */
function getBestScoreSortValue(item) {
if (item.best_score != null && item.best_score !== '') {
const b = Number(item.best_score);
if (!Number.isNaN(b)) return b;
}
const rounds = ROUND_KEYS.map((k) => item[k]).filter((v) => v !== null && v !== undefined && v !== '');
const nums = rounds.map(Number).filter((n) => !Number.isNaN(n));
if (nums.length) return Math.max(...nums);
if (item.composite != null && item.composite !== '') {
const c = Number(item.composite);
if (!Number.isNaN(c)) return c;
}
return Number.NEGATIVE_INFINITY;
}
function renderTable() {
const tbody = document.getElementById('table-body');
const scoreBtn = document.getElementById('sort-score');
const latestBtn = document.getElementById('sort-updated');
if (scoreBtn && latestBtn) {
if (sortBy === 'score') {
scoreBtn.classList.remove('bg-gray-100', 'text-gray-700', 'ring-gray-200');
scoreBtn.classList.add('bg-green-50', 'text-green-700', 'ring-green-200');
latestBtn.classList.remove('bg-green-50', 'text-green-700', 'ring-green-200');
latestBtn.classList.add('bg-gray-100', 'text-gray-700', 'ring-gray-200');
} else {
latestBtn.classList.remove('bg-gray-100', 'text-gray-700', 'ring-gray-200');
latestBtn.classList.add('bg-green-50', 'text-green-700', 'ring-green-200');
scoreBtn.classList.remove('bg-green-50', 'text-green-700', 'ring-green-200');
scoreBtn.classList.add('bg-gray-100', 'text-gray-700', 'ring-gray-200');
}
}
const q = (document.getElementById('search-input')?.value || '').toLowerCase().trim();
let filtered = rows.filter((r) => {
const text = `${r.team || ''} ${r.model || ''}`.toLowerCase();
return !q || text.includes(q);
});
filtered.sort((a, b) => {
if (sortBy === 'latest') return new Date(b.submitted || 0) - new Date(a.submitted || 0);
return getBestScoreSortValue(b) - getBestScoreSortValue(a);
});
tbody.innerHTML = filtered.map((item, idx) => {
const r1 = formatRoundScore(item['score(round1)']);
const r2 = formatRoundScore(item['score(round2)']);
const r3 = formatRoundScore(item['score(round3)']);
let bestDisplay;
if (item.best_score != null && item.best_score !== '') {
const b = Number(item.best_score);
bestDisplay = Number.isNaN(b) ? 'N/A' : formatRoundScore(item.best_score);
} else {
const sortVal = getBestScoreSortValue(item);
bestDisplay = sortVal === Number.NEGATIVE_INFINITY ? 'N/A' : formatRoundScore(sortVal);
}
return `
<tr class="${idx % 2 === 0 ? 'bg-white' : 'bg-gray-50'}">
<td class="px-4 py-3 text-sm font-semibold text-gray-900">${idx + 1}</td>
<td class="px-4 py-3">
<div class="text-sm font-semibold text-gray-900">${escapeHtml(item.team)}</div>
<div class="text-xs text-gray-600">${escapeHtml(item.model)} · ${escapeHtml(item.version)}</div>
</td>
<td class="px-4 py-3 text-sm text-gray-900 tabular-nums">${escapeHtml(r1)}</td>
<td class="px-4 py-3 text-sm text-gray-900 tabular-nums">${escapeHtml(r2)}</td>
<td class="px-4 py-3 text-sm text-gray-900 tabular-nums">${escapeHtml(r3)}</td>
<td class="px-4 py-3 text-sm font-semibold text-gray-900 tabular-nums">${escapeHtml(bestDisplay)}</td>
<td class="px-4 py-3 text-sm text-gray-600">${escapeHtml(item.submitted)}</td>
<td class="px-4 py-3 text-xs"><span class="inline-flex rounded-full bg-green-100 px-2 py-1 font-semibold text-green-800">${escapeHtml(item.status || 'pending')}</span></td>
</tr>
`;
}).join('');
if (!filtered.length) {
tbody.innerHTML = '<tr><td colspan="8" class="px-4 py-8 text-center text-sm text-gray-500">No leaderboard rows match your search.</td></tr>';
}
}
async function init() {
const state = document.getElementById('load-state');
try {
const res = await fetch('./results.json', { cache: 'no-store' });
if (!res.ok) throw new Error(`HTTP ${res.status}`);
rows = await res.json();
state.textContent = `Loaded ${rows.length} rows from results.json`;
} catch (err) {
rows = [];
state.textContent = `Failed to load results.json (${String(err)}).`;
}
renderTable();
}
document.getElementById('sort-score')?.addEventListener('click', () => {
sortBy = 'score';
renderTable();
});
document.getElementById('sort-updated')?.addEventListener('click', () => {
sortBy = 'latest';
renderTable();
});
document.getElementById('search-input')?.addEventListener('input', renderTable);
init();
</script>
</body>
</html>