import { useEffect, useState } from 'react'; import { Link, Navigate, useParams } from 'react-router-dom'; import { api, formatCredits } from '../api'; import { useAuth } from '../AuthContext'; import CaseReel from '../components/CaseReel'; import ItemTile from '../components/ItemTile'; import { rarityColor } from '../rarities'; export default function CasePage() { const { id } = useParams(); const { user, loading, updateBalance } = useAuth(); const [crate, setCrate] = useState(null); const [error, setError] = useState(''); const [spinning, setSpinning] = useState(false); const [winnerId, setWinnerId] = useState(null); const [wonItem, setWonItem] = useState(null); const [showResult, setShowResult] = useState(false); useEffect(() => { let cancelled = false; (async () => { try { const data = await api.case(id); if (!cancelled) setCrate(data.case); } catch (err) { if (!cancelled) setError(err.message); } })(); return () => { cancelled = true; }; }, [id]); if (loading) return

Loading…

; if (!user) return ; if (user.role === 'admin') return ; const canOpen = crate && !spinning && user.balance >= crate.price && crate.items.length > 0; const openCase = async () => { if (!canOpen) return; setError(''); setWonItem(null); setShowResult(false); setWinnerId(null); setSpinning(false); try { const result = await api.openCase(crate.id); updateBalance(result.user.balance); setWonItem(result.item); setWinnerId(result.item.id); // start spin on next frame so reel rebuilds with winner requestAnimationFrame(() => setSpinning(true)); } catch (err) { setError(err.message); } }; return (
← Back to cases {!crate && !error &&

Loading case…

} {error &&
{error}
} {crate && ( <>

{crate.name}

Cost {formatCredits(crate.price)} cr · Balance {formatCredits(user.balance)} cr

{(spinning || winnerId) && ( { setSpinning(false); setShowResult(true); }} /> )} {showResult && wonItem && (
{wonItem.imageUrl ? ( ) : null}
You unboxed
{wonItem.name}
{wonItem.rarity}
{formatCredits(wonItem.marketValue)} cr
)}

Possible drops

Relative drop odds for this case.

{crate.items.map((item) => (
{item.chance}%
))}
)}
); }