File size: 6,343 Bytes
daefd86 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 |
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>LeRobot Worldwide Hackathon โ Winners</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<!-- Tailwind CSS -->
<script src="https://cdn.tailwindcss.com"></script>
<!-- React 18 UMD -->
<script crossorigin src="https://unpkg.com/react@18/umd/react.development.js"></script>
<script crossorigin src="https://unpkg.com/react-dom@18/umd/react-dom.development.js"></script>
</head>
<body class="bg-[#FF9D00]">
<div id="root"></div>
<script type="text/javascript">
const { useState, useEffect } = React;
/**
* Utility: extract rank & team # from a filename "<rank>-<team>-... .mp4"
*/
function parseRankTeam(filepath) {
const name = filepath.split("/").pop();
const m = name.match(/^(\d+)-(\d+)-/);
return m ? { rank: +m[1], team: +m[2] } : { rank: null, team: null };
}
function App() {
const [videos, setVideos] = useState([]);
const [teamDatasets, setTeamDatasets] = useState({});
useEffect(() => {
async function fetchAssets() {
// Fetch video files
const tree = await (
await fetch(
"https://huggingface.co/api/datasets/maringetxway/all-winners/tree/main"
)
).json();
const videoFiles = tree
.filter((f) => f.path.endsWith(".mp4"))
.map((f) => {
const { rank, team } = parseRankTeam(f.path);
return {
url: `https://huggingface.co/datasets/maringetxway/all-winners/resolve/main/${encodeURIComponent(
f.path
)}`,
rank,
team,
};
})
.sort((a, b) => a.rank - b.rank);
setVideos(videoFiles);
// Fetch datasets by team (optional links)
const datasets = await (
await fetch(
"https://huggingface.co/api/datasets?author=maringetxway"
)
).json();
const map = {};
datasets.forEach(({ id }) => {
const m = id.match(/maringetxway\/team[_-]?(\d+)/i);
if (m) {
const t = +m[1];
if (!map[t]) map[t] = [];
map[t].push(
`https://huggingface.co/spaces/lerobot/visualize_dataset?dataset=${id}`
);
}
});
setTeamDatasets(map);
}
fetchAssets();
}, []);
return React.createElement(
"div",
{ className: "min-h-screen py-10 px-4 max-w-3xl mx-auto" },
/* Heading */
React.createElement(
"h1",
{
className:
"text-center text-4xl font-bold text-white mb-4 drop-shadow-lg",
},
"LeRobot Worldwide Hackathon โ Winners"
),
/* Description */
React.createElement(
"p",
{
className:
"font-bold text-white text-center whitespace-pre-line mb-10 leading-relaxed",
},
`๐ โฌ15,000 in robotics hardware prizes \n\n `
),
React.createElement(
"p",
{
className:
"text-white text-center whitespace-pre-line mb-10 leading-relaxed",
},
`๐ Hereโs a sneak peek at the prizes up for grabs in collaboration with SeeedStudio:\n\n๐ฅ 1st to 3rd place teams: 1 Hope Jr Arm & 1 LeKiwi per team\n\n๐ฅ 4th and 5th place teams: 1 Hope Jr Arm per team\n\n๐ฅ 6th to 24th place teams: 1 LeKiwi per team\n\n๐ฅ 25th to 30th place teams: 1 SO-101 per team\n\nA huge shoutout to everyone for your hard work and passion! It was truly tough to pick the top 30 โ there were so many amazing demo videos, and weโre absolutely blown away. We also had a lot of laughs along the way!`
),
/* Logos */
React.createElement(
"div",
{ className: "flex justify-center items-center gap-6 mb-4" },
React.createElement("img", {
src: "seeedstudio.png",
alt: "Seeed Studio logo",
className: "h-12 w-auto",
}),
React.createElement("img", {
src: "hf.png",
alt: "Hugging Face logo",
className: "h-12 w-auto",
})
),
/* Videos */
...videos.map((video, idx) =>
React.createElement(
"section",
{ key: idx, className: "mb-16" },
React.createElement(
"h2",
{
className:
"text-2xl font-semibold text-white mb-4 flex items-center gap-2",
},
`#${video.rank}`,
React.createElement(
"span",
{ className: "text-base font-normal text-white/80" },
`โ Team ${video.team ?? "?"}`
)
),
React.createElement("video", {
src: video.url,
controls: true,
className: "w-full rounded-xl shadow-2xl",
}),
teamDatasets[video.team] &&
React.createElement(
"div",
{ className: "mt-2 space-y-1" },
teamDatasets[video.team].map((url, j) =>
React.createElement(
"a",
{
key: j,
href: url,
target: "_blank",
className:
"text-sm text-blue-200 underline hover:text-white",
},
`Dataset: ${url.split("=")[1]}`
)
)
)
)
),
/* Sponsors section */
React.createElement(
"div",
{
className:
"bg-white rounded-xl shadow-lg p-8 mt-20 flex justify-center",
},
React.createElement("img", {
src: "sponsors.png",
alt: "Sponsors",
className: "max-w-full h-auto",
})
)
);
}
ReactDOM.createRoot(document.getElementById("root")).render(
React.createElement(App)
);
</script>
</body>
</html>
|