'use client' /** * Breakpilot Drive - Game Dashboard * * Admin-Interface fuer das Lernspiel: * - Uebersicht: Statistiken und KPIs * - Spielen: Embedded WebGL Game * - Statistiken: Detaillierte Auswertungen */ import AdminLayout from '@/components/admin/AdminLayout' import SystemInfoSection, { SYSTEM_INFO_CONFIGS } from '@/components/admin/SystemInfoSection' import Link from 'next/link' import { useState, useEffect, useCallback } from 'react' // Types interface GameStats { activePlayers: number totalSessions: number questionsAnswered: number averageAccuracy: number totalPlayTimeHours: number } interface LeaderboardEntry { rank: number displayName: string score: number accuracy: number } type TabType = 'overview' | 'play' | 'stats' // Mock data - in production this would come from the API const mockStats: GameStats = { activePlayers: 42, totalSessions: 1234, questionsAnswered: 8567, averageAccuracy: 0.78, totalPlayTimeHours: 156.5, } const mockLeaderboard: LeaderboardEntry[] = [ { rank: 1, displayName: 'Max M.', score: 25000, accuracy: 0.92 }, { rank: 2, displayName: 'Lisa K.', score: 23500, accuracy: 0.88 }, { rank: 3, displayName: 'Tim S.', score: 21000, accuracy: 0.85 }, { rank: 4, displayName: 'Anna B.', score: 19500, accuracy: 0.82 }, { rank: 5, displayName: 'Paul R.', score: 18000, accuracy: 0.79 }, ] // Stat Card Component function StatCard({ title, value, suffix = '', icon, trend, }: { title: string value: string | number suffix?: string icon: React.ReactNode trend?: { value: number; positive: boolean } }) { return (

{title}

{value}{suffix}

{trend && (

{trend.positive ? '+' : ''}{trend.value}% vs. letzte Woche

)}
{icon}
) } // Leaderboard Component function Leaderboard({ entries }: { entries: LeaderboardEntry[] }) { return (

Top 5 Spieler

{entries.map((entry) => (
{entry.rank} {entry.displayName}
{entry.score.toLocaleString()} Punkte {Math.round(entry.accuracy * 100)}%
))}
) } // Main Page Component export default function GameDashboardPage() { const [activeTab, setActiveTab] = useState('overview') const [stats, setStats] = useState(mockStats) const [leaderboard, setLeaderboard] = useState(mockLeaderboard) const [loading, setLoading] = useState(false) const [gameLoaded, setGameLoaded] = useState(false) // Game URL - in production this would be from environment const GAME_URL = process.env.NEXT_PUBLIC_GAME_URL || 'http://localhost:3001' // Fetch stats from API const fetchStats = useCallback(async () => { setLoading(true) try { // In production: fetch from /api/game/stats // const response = await fetch('/api/admin/game/stats') // const data = await response.json() // setStats(data) // For now, use mock data await new Promise(resolve => setTimeout(resolve, 500)) setStats(mockStats) } catch (error) { console.error('Failed to fetch stats:', error) } finally { setLoading(false) } }, []) useEffect(() => { fetchStats() }, [fetchStats]) // Tab buttons const tabs: { id: TabType; label: string; icon: React.ReactNode }[] = [ { id: 'overview', label: 'Uebersicht', icon: ( ), }, { id: 'play', label: 'Spielen', icon: ( ), }, { id: 'stats', label: 'Statistiken', icon: ( ), }, ] return ( {/* Tab Navigation */}
{tabs.map((tab) => ( ))} {/* Wizard Link */} Lern-Wizard {/* Multiplayer Wizard Link */} Multiplayer {/* Build Pipeline Wizard Link */} Builds {/* Refresh Button */}
{/* Overview Tab */} {activeTab === 'overview' && ( <> {/* Stats Grid */}
} trend={{ value: 12, positive: true }} /> } /> } /> } trend={{ value: 3, positive: true }} /> } />
{/* Leaderboard & Info */}
{/* Quick Actions */}

Schnellzugriff

Im neuen Tab oeffnen
)} {/* Play Tab - Embedded Game */} {activeTab === 'play' && (
{!gameLoaded && (

Spiel wird geladen...

Unity WebGL wird initialisiert

)}