// admin.jsx — Tutor admin shell + supporting screens (dashboard, attendance, rooms, students, login) const TutorShell = ({ active, onNav, children }) => { const navItems = [ { id: "dashboard", label: "Dashboard" }, { id: "live", label: "Live · Sitzplan" }, { id: "attendance", label: "Anwesenheit" }, { id: "rooms", label: "Räume" }, { id: "students", label: "Studierende" }, ]; return (
{/* Sidebar */}
{children}
); }; // Dashboard ───────────────────────────────────────────────────────────── const Dashboard = () => { const slots = [ { id: 1, week: 4, day: "Do, 30. April", time: "14:00 – 15:00", room: "BC2 1.103", status: "open", code: "K7QJMX2P", checkedIn: 14, total: 19 }, { id: 2, week: 4, day: "Do, 30. April", time: "17:00 – 18:00", room: "BC2 1.207", status: "closed", code: null, checkedIn: 0, total: 19 }, { id: 3, week: 3, day: "Do, 23. April", time: "14:00 – 15:00", room: "BC2 1.103", status: "locked", code: "RX48ZF2K", checkedIn: 17, total: 19 }, { id: 4, week: 3, day: "Do, 23. April", time: "17:00 – 18:00", room: "BC2 1.207", status: "locked", code: "QM9WJ3VC", checkedIn: 12, total: 19 }, { id: 5, week: 2, day: "Do, 16. April", time: "14:00 – 15:00", room: "BC2 1.103", status: "locked", code: "B2HFNX9P", checkedIn: 18, total: 19 }, { id: 6, week: 2, day: "Do, 16. April", time: "17:00 – 18:00", room: "BC2 1.207", status: "locked", code: "VJ5KQM7R", checkedIn: 15, total: 19 }, { id: 7, week: 1, day: "Do, 09. April", time: "14:00 – 15:00", room: "— (Papier)", status: "locked", code: null, checkedIn: 16, total: 19 }, ]; return (
Dashboard
Diese Woche, Woche 04
2 Slots geplant · 1 läuft gerade · 14 von 19 sind eingecheckt.
{/* Stat row */}
{/* Slots table */}
Slots
Sortiert: neueste zuerst
{slots.map((s, i) => ( ))}
Woche Datum Zeit Raum Status Code Eingecheckt Aktionen
W{String(s.week).padStart(2, "0")} {s.day} {s.time} {s.room} {s.code ? {s.code} : }
{s.checkedIn} / {s.total}
{s.status === "open" && } {s.status === "closed" && } {s.status === "locked" && }
); }; const Th = ({ children, style }) => {children}; const Td = ({ children, style, className }) => {children}; const StatCard = ({ label, value, suffix, hint, accent }) => (
{label}
{value} {suffix && {suffix}}
{hint &&
{hint}
}
); // Attendance matrix ───────────────────────────────────────────────────────────── const AttendanceMatrix = () => { const weeks = [1, 2, 3, 4]; // deterministic random-ish presence const presence = STUDENTS.map((s) => ({ student: s, weeks: weeks.map((w) => { const hash = (s.id * 31 + w * 7) % 11; return hash > 2; // ~80% }), })); return (
Anwesenheit
Kursmatrix · SS 2026
Bonus = Anwesenheiten × 3 Punkte
Pro Studierende:r
Pro Woche
Notizen
{weeks.map((w) => ( ))} {presence.map((row, i) => { const count = row.weeks.filter(Boolean).length; return ( {row.weeks.map((p, wi) => ( ))} ); })}
# Studierende:rW{String(w).padStart(2, "0")}Anwesend Bonus
{String(i + 1).padStart(2, "0")}
{row.student.initials} {row.student.name}
{p ? ( ) : ( )} {count} / {weeks.length} {count > 0 ? ( ) : ( )}
); }; // Rooms / layout editor ───────────────────────────────────────────────────────────── const RoomsScreen = () => { return (
Räume
Layout-Editor · {ROOM.name}
Räume sind kursunabhängig — einmal anlegen, mehrere Semester nutzen.
{/* Tool palette */}
Werkzeuge
Eigenschaften
Räume
{/* Editor canvas with seat being dragged */}
Bearbeiten
760 × 460 · 1× Zoom
ziehen um Sitz zu verschieben →
); }; const ToolBtn = ({ label, active }) => ( ); const Field = ({ label, value, mono }) => ( ); const RoomItem = ({ label, sub, active }) => ( ); // Students CRUD ───────────────────────────────────────────────────────────── const StudentsScreen = () => { return (
Studierende
{STUDENTS.length} Studierende · {COURSE.name}
{STUDENTS.map((s, i) => { const count = (s.id * 7) % 5; const noteCount = (s.id * 3) % 4; return ( ); })}
# Name Anwesend Bonus Notizen Letzte Sitzung
{String(i + 1).padStart(2, "0")}
{s.initials} {s.name}
{count} / 4 {count > 0 ? ( ) : ( )} {noteCount > 0 ? ( {noteCount} Notizen ) : ( )} Do, 23. April · T{(s.id % 4) + 1}-{(s.id % 5) + 1}
); }; // Login ───────────────────────────────────────────────────────────── const LoginScreen = () => { return (
Tutor·manager
Anwesenheit & Notizen für Tutorien.
Anmeldung
Willkommen zurück
Nur für Tutor:innen. Studierende nutzen den vom Beamer projizierten Code.
~ Donnerstags ab 14 Uhr ~
); }; Object.assign(window, { TutorShell, Dashboard, AttendanceMatrix, RoomsScreen, StudentsScreen, LoginScreen });