Add Local leaderboard, CSS optimiztion

This commit is contained in:
Carsten Graf
2025-09-23 20:07:35 +02:00
parent 8fac847a75
commit 5ca67d8804
8 changed files with 849 additions and 45 deletions

View File

@@ -353,7 +353,7 @@ void setupBackendRoutes(AsyncWebServer &server) {
// Andere Logik wie in getBestLocs
});
// Lokales Leaderboard API
// Lokales Leaderboard API (für Hauptseite - 6 Einträge)
server.on("/api/leaderboard", HTTP_GET, [](AsyncWebServerRequest *request) {
// Sortiere nach Zeit (beste zuerst)
std::sort(localTimes.begin(), localTimes.end(),
@@ -364,10 +364,10 @@ void setupBackendRoutes(AsyncWebServer &server) {
DynamicJsonDocument doc(2048);
JsonArray leaderboard = doc.createNestedArray("leaderboard");
// Nimm die besten 5
// Nimm die besten 6
int count = 0;
for (const auto &time : localTimes) {
if (count >= 5)
if (count >= 6)
break;
JsonObject entry = leaderboard.createNestedObject();
@@ -403,6 +403,58 @@ void setupBackendRoutes(AsyncWebServer &server) {
request->send(200, "application/json", result);
});
// Erweiterte Leaderboard API (für Leaderboard-Seite - 10 Einträge)
server.on(
"/api/leaderboard-full", HTTP_GET, [](AsyncWebServerRequest *request) {
// Sortiere nach Zeit (beste zuerst)
std::sort(localTimes.begin(), localTimes.end(),
[](const LocalTime &a, const LocalTime &b) {
return a.timeMs < b.timeMs;
});
DynamicJsonDocument doc(2048);
JsonArray leaderboard = doc.createNestedArray("leaderboard");
// Nimm die besten 10
int count = 0;
for (const auto &time : localTimes) {
if (count >= 10)
break;
JsonObject entry = leaderboard.createNestedObject();
entry["rank"] = count + 1;
entry["name"] = time.name;
entry["uid"] = time.uid;
entry["time"] = time.timeMs / 1000.0;
// Format time inline
float seconds = time.timeMs / 1000.0;
int totalSeconds = (int)seconds;
int minutes = totalSeconds / 60;
int remainingSeconds = totalSeconds % 60;
int milliseconds = (int)((seconds - totalSeconds) * 100);
String timeFormatted;
if (minutes > 0) {
timeFormatted =
String(minutes) + ":" + (remainingSeconds < 10 ? "0" : "") +
String(remainingSeconds) + "." +
(milliseconds < 10 ? "0" : "") + String(milliseconds);
} else {
timeFormatted = String(remainingSeconds) + "." +
(milliseconds < 10 ? "0" : "") +
String(milliseconds);
}
entry["timeFormatted"] = timeFormatted;
count++;
}
String result;
serializeJson(doc, result);
request->send(200, "application/json", result);
});
// Add more routes as needed
}

View File

@@ -72,7 +72,8 @@ void IndividualMode(const char *action, int press, int lane,
sendTimeToOnlineAPI(1, getStart1UID(), currentTime / 1000.0);
} else {
// Kein User gefunden - speichere Zeit ohne UID und Namen
addLocalTime("", "Anonym", currentTime);
addLocalTime("", "Spieler " + String((localTimes.size() + 1)),
currentTime);
}
}
}
@@ -118,7 +119,8 @@ void IndividualMode(const char *action, int press, int lane,
sendTimeToOnlineAPI(2, getStart2UID(), currentTime / 1000.0);
} else {
// Kein User gefunden - speichere Zeit ohne UID und Namen
addLocalTime("", "Anonym", currentTime);
addLocalTime("", "Spieler " + String((localTimes.size() + 1)),
currentTime);
}
}
}

View File

@@ -76,8 +76,6 @@ void loop() {
loopRFID();
}
// loopBattery(); // Batterie-Loop aufrufen
// Kurze Pause um anderen Tasks Zeit zu geben
delay(1);
}

View File

@@ -33,6 +33,10 @@ void setupRoutes() {
request->send(SPIFFS, "/settings.html", "text/html");
});
server.on("/leaderboard", HTTP_GET, [](AsyncWebServerRequest *request) {
request->send(SPIFFS, "/leaderboard.html", "text/html");
});
server.on("/firmware.bin", HTTP_GET, [](AsyncWebServerRequest *request) {
if (SPIFFS.exists("/firmware.bin")) {
request->send(SPIFFS, "/firmware.bin", "application/octet-stream");