@hhoangphuoc/escape-room-cli
Version:
A CLI for playing AI-generated escape room games. Install globally with: npm install -g @hhoangphuoc/escape-room-cli
50 lines (49 loc) • 4.95 kB
JavaScript
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
import { Box, Text } from 'ink';
const Leaderboard = ({ entries, count }) => {
if (count === 0) {
return (_jsxs(Box, { flexDirection: "column", padding: 1, children: [_jsx(Box, { marginBottom: 1, children: _jsx(Text, { bold: true, color: "yellow", children: "\uD83C\uDFC6 LEADERBOARD" }) }), _jsx(Box, { children: _jsx(Text, { color: "gray", children: "No completed games found yet. Be the first to complete a game!" }) })] }));
}
const getRankColor = (rank) => {
switch (rank) {
case 1:
return 'yellow';
case 2:
return 'gray';
case 3:
return 'red';
default:
return 'white';
}
};
const getRankEmoji = (rank) => {
switch (rank) {
case 1:
return '🥇';
case 2:
return '🥈';
case 3:
return '🥉';
default:
return ' ';
}
};
const formatCost = (cost) => {
if (cost === undefined || cost === 0)
return 'N/A';
return cost < 0.01 ? `$${cost.toFixed(5)}` : `$${cost.toFixed(3)}`;
};
const formatTokens = (tokens) => {
if (tokens === undefined)
return 'N/A';
if (tokens >= 1_000_000)
return `${(tokens / 1_000_000).toFixed(2)}M`;
if (tokens >= 1_000)
return `${(tokens / 1_000).toFixed(1)}k`;
return `${tokens}`;
};
return (_jsxs(Box, { flexDirection: "column", padding: 1, children: [_jsx(Box, { marginBottom: 1, children: _jsx(Text, { bold: true, color: "yellow", children: "\uD83C\uDFC6 TOP 10 PLAYERS (Time \u2022 Tokens \u2022 Cost)" }) }), _jsx(Box, { marginBottom: 1, children: _jsx(Text, { color: "white", children: "Congrats!\uD83C\uDF89 Here are the top 10 most cost-efficient games" }) }), _jsxs(Box, { marginTop: 1, marginBottom: 1, children: [_jsx(Box, { width: 6, children: _jsx(Text, { bold: true, color: "cyan", children: "Rank" }) }), _jsx(Box, { width: 15, justifyContent: "flex-start", children: _jsx(Text, { bold: true, color: "cyan", children: "Player" }) }), _jsx(Box, { width: 10, justifyContent: "center", children: _jsx(Text, { bold: true, color: "cyan", children: "Time" }) }), _jsx(Box, { width: 10, justifyContent: "center", children: _jsx(Text, { bold: true, color: "cyan", children: "Hints" }) }), _jsx(Box, { width: 12, justifyContent: "flex-end", children: _jsx(Text, { bold: true, color: "cyan", children: "Tokens" }) }), _jsx(Box, { width: 15, justifyContent: "flex-end", children: _jsx(Text, { bold: true, color: "cyan", children: "Cost" }) }), _jsx(Box, { width: 18, justifyContent: "flex-end", children: _jsx(Text, { bold: true, color: "cyan", children: "Mode" }) })] }), _jsx(Box, { marginBottom: 1, children: _jsx(Text, { color: "white", children: "\u2500\u2500\u2500\u2500\u253C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u253C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u253C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u253C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u253C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u253C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500" }) }), entries.map((entry) => (_jsxs(Box, { marginBottom: 0, children: [_jsx(Box, { width: 6, children: _jsxs(Text, { color: getRankColor(entry.rank), children: [getRankEmoji(entry.rank), " ", entry.rank.toString().padStart(2, ' ')] }) }), _jsx(Box, { width: 15, justifyContent: "flex-start", children: _jsx(Text, { bold: true, color: "white", children: entry.userName.length > 10
? entry.userName.substring(0, 10) + '...'
: entry.userName.padEnd(12, ' ') }) }), _jsx(Box, { width: 10, justifyContent: "center", children: _jsxs(Text, { color: "white", children: [entry.timeElapsed, "s"] }) }), _jsx(Box, { width: 10, justifyContent: "center", children: _jsx(Text, { color: entry.hintsUsed > 0 ? 'yellow' : 'white', children: entry.hintsUsed }) }), _jsx(Box, { width: 12, justifyContent: "flex-end", children: _jsx(Text, { color: "cyan", children: formatTokens(entry.totalTokens) }) }), _jsx(Box, { width: 15, justifyContent: "flex-end", children: _jsx(Text, { color: entry.totalCost && entry.totalCost > 0.1 ? 'red' : 'green', children: formatCost(entry.totalCost).padStart(8, ' ') }) }), _jsx(Box, { width: 18, justifyContent: "flex-end", children: _jsx(Text, { color: "gray", children: entry.gameMode }) })] }, entry.rank))), _jsx(Box, { marginTop: 1, padding: 1, children: _jsx(Text, { color: "gray", children: "\uD83D\uDCA1 Your rank = Faster time + Lower cost + Fewer tokens!" }) })] }));
};
export default Leaderboard;