diff --git a/frontend/styles/main.css b/frontend/styles/main.css index da05b7db..88a88242 100644 --- a/frontend/styles/main.css +++ b/frontend/styles/main.css @@ -2869,7 +2869,8 @@ body::-webkit-scrollbar-thumb { .rank-change[data-tooltip]::before { content: attr(data-tooltip); position: absolute; - bottom: 140%; + bottom: 140%; /* Default position */ + top: auto; left: 50%; transform: translateX(-50%); background: var(--bg-raised); @@ -2887,6 +2888,11 @@ body::-webkit-scrollbar-thumb { transition: opacity 0.15s ease-in-out; box-shadow: 0 0 15px rgba(0, 255, 65, 0.2); } +/* Prevent tooltip from overlapping the sticky header */ +.leaderboard-row:nth-child(-n + 3) .rank-change[data-tooltip]::before { + top: 140%; + bottom: auto; +} .rank-change[data-tooltip]:hover { z-index: 100; diff --git a/scripts/fetch-user-info.js b/scripts/fetch-user-info.js index eb130496..7506befc 100644 --- a/scripts/fetch-user-info.js +++ b/scripts/fetch-user-info.js @@ -18,6 +18,7 @@ async function fetchWithTimeout(url, timeoutMs = 15000) { } async function fetchUserInfo(username) { + let liveSolved = null; const usernameRegex = /^[a-zA-Z0-9_-]+$/; if (!username || !usernameRegex.test(username)) { throw new Error("Invalid username format"); @@ -79,13 +80,33 @@ async function fetchUserInfo(username) { } }); - // Wait for the live API task to complete - await livePromise; + ranking = apiData.ranking || 0; + contest = apiData.contest || null; // Ensure history is sorted chronologically // Guard against a corrupted history file (e.g. non-array `history` field) history = Array.isArray(history) ? history : []; history.sort((a, b) => new Date(a.date) - new Date(b.date)); + const today = new Date().toISOString().split("T")[0]; + let latestEntry = null; + + for (let i = history.length - 1; i >= 0; i--) { + const entry = history[i]; + + if ( + typeof entry.date === "string" && + entry.date.startsWith(today) + ) { + latestEntry = entry; + break; + } + } + + if (latestEntry && liveSolved) { + latestEntry.easy = liveSolved.easy; + latestEntry.medium = liveSolved.medium; + latestEntry.hard = liveSolved.hard; + } return { username,