From 272e270339e028407298f5c317544d6c3210c47c Mon Sep 17 00:00:00 2001 From: Leo dev Date: Sat, 7 Feb 2026 14:29:31 +0100 Subject: [PATCH 01/10] Mobile friendly UI --- src/app/run/page.tsx | 27 +++++++++++++++++++-------- src/components/app/ProfileCard.tsx | 10 ++++------ 2 files changed, 23 insertions(+), 14 deletions(-) diff --git a/src/app/run/page.tsx b/src/app/run/page.tsx index 3962589..594ee56 100644 --- a/src/app/run/page.tsx +++ b/src/app/run/page.tsx @@ -21,9 +21,20 @@ export default function Run() { ]; return ( -
+
+ {/* Main column */}
-
+ {/* Top cards */} +
@@ -44,10 +55,10 @@ export default function Run() {
{/* Editor */} - + - {/* File tree */} -
+ {/* File tree – hide on small screens */} +
{/* Code */} -
+
myfile.js
-
+
@@ -78,7 +89,7 @@ export default function Run() {
{/* Timer & Chat */} -
+
diff --git a/src/components/app/ProfileCard.tsx b/src/components/app/ProfileCard.tsx index b6e878a..4550535 100644 --- a/src/components/app/ProfileCard.tsx +++ b/src/components/app/ProfileCard.tsx @@ -10,25 +10,23 @@ export default function ProfileCard({
- + {/* Avatar */} -
+
Img -
+
#{user.rank}
{/* User Info */}
-

- {user.username} -

+

{user.username}

World Record Holder
From 6afe9770660e69666d2626fb43b9b2ab9a7a39fb Mon Sep 17 00:00:00 2001 From: Leo dev Date: Sat, 7 Feb 2026 14:30:51 +0100 Subject: [PATCH 02/10] Scrolling fix --- src/app/globals.css | 1 + src/app/run/page.tsx | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/src/app/globals.css b/src/app/globals.css index efe06b6..afc34f5 100644 --- a/src/app/globals.css +++ b/src/app/globals.css @@ -314,5 +314,6 @@ } .cm-editor { + width: 100%; height: 100%; } diff --git a/src/app/run/page.tsx b/src/app/run/page.tsx index 594ee56..e2c1107 100644 --- a/src/app/run/page.tsx +++ b/src/app/run/page.tsx @@ -76,11 +76,11 @@ export default function Run() {
{/* Code */} -
+
myfile.js
-
+
From f930f0bca17ec701cdea587f79bd4b3f41ebf683 Mon Sep 17 00:00:00 2001 From: Leo dev Date: Sat, 7 Feb 2026 14:43:45 +0100 Subject: [PATCH 03/10] remaned now to row --- src/app/runs/components/{LiveRunNow.tsx => LiveRunRow.tsx} | 0 src/app/runs/page.tsx | 2 +- 2 files changed, 1 insertion(+), 1 deletion(-) rename src/app/runs/components/{LiveRunNow.tsx => LiveRunRow.tsx} (100%) diff --git a/src/app/runs/components/LiveRunNow.tsx b/src/app/runs/components/LiveRunRow.tsx similarity index 100% rename from src/app/runs/components/LiveRunNow.tsx rename to src/app/runs/components/LiveRunRow.tsx diff --git a/src/app/runs/page.tsx b/src/app/runs/page.tsx index 9ceebb6..6af1023 100644 --- a/src/app/runs/page.tsx +++ b/src/app/runs/page.tsx @@ -14,7 +14,7 @@ import { TableCell, } from "@/components/ui/table"; import { cn } from "@/lib/utils"; -import LiveRunRow from "./components/LiveRunNow"; +import LiveRunRow from "./components/LiveRunRow"; import StatCard from "@/components/app/StatCard"; import useAction from "@/hook/use-action"; import { getLiveRuns } from "@/modules/live-run/actions"; From 969500f5a4462abdf36d9be17c33c1e7a86275a7 Mon Sep 17 00:00:00 2001 From: Leo dev Date: Sat, 7 Feb 2026 15:44:38 +0100 Subject: [PATCH 04/10] Working leaderboard --- .../components/LeaderboardRow.tsx | 72 ++++--- src/app/leaderboards/page.tsx | 65 +++--- src/modules/leaderboard/actions.ts | 197 +----------------- src/modules/leaderboard/core.ts | 18 ++ src/modules/leaderboard/types.ts | 13 +- 5 files changed, 99 insertions(+), 266 deletions(-) diff --git a/src/app/leaderboards/components/LeaderboardRow.tsx b/src/app/leaderboards/components/LeaderboardRow.tsx index 884bc1b..fde8889 100644 --- a/src/app/leaderboards/components/LeaderboardRow.tsx +++ b/src/app/leaderboards/components/LeaderboardRow.tsx @@ -1,25 +1,33 @@ -import { LeaderboardRank } from "@/modules/leaderboard/types"; import { LinkIcon, Trophy } from "lucide-react"; import Link from "next/link"; +interface GlobalLeaderboardUser { + rank: number; + user_id: string; + username: string; + wins: number; + podiums: number; + problems_completed: number; +} + const LeaderboardRow = ({ index = 0, run, }: { index?: number; - run: LeaderboardRank; + run: GlobalLeaderboardUser; }) => { const getRankStyle = (rank: number) => { - if (run.rank === 1) return "rank-gold"; - if (run.rank === 2) return "rank-silver"; - if (run.rank === 3) return "rank-bronze"; + if (rank === 1) return "rank-gold"; + if (rank === 2) return "rank-silver"; + if (rank === 3) return "rank-bronze"; return "bg-secondary text-muted-foreground"; }; const getRankGlow = (rank: number) => { - if (run.rank === 1) return "glow-gold"; - if (run.rank === 2) return "glow-silver"; - if (run.rank === 3) return "glow-bronze"; + if (rank === 1) return "glow-gold"; + if (rank === 2) return "glow-silver"; + if (rank === 3) return "glow-bronze"; return ""; }; @@ -27,7 +35,9 @@ const LeaderboardRow = ({ return (
{isTopThree ? : run.rank}
@@ -46,41 +58,37 @@ const LeaderboardRow = ({
{run.username}
- {/* Time */} - - - {run.pb} - + {/* Wins */} + + {run.wins} - {/* Category */} - - - {run.category} - + {/* Podiums */} + + {run.podiums} - {/* Assisted */} - - - {run.assisted ? "Assisted" : "Unassisted"} - + {/* Problems Completed */} + + {run.problems_completed} - {/* Runs */} - {run.runsCount} - - {/* Problem */} + {/* Profile Link */} - - {run.problem} + + View Profile diff --git a/src/app/leaderboards/page.tsx b/src/app/leaderboards/page.tsx index 8487913..51e704a 100644 --- a/src/app/leaderboards/page.tsx +++ b/src/app/leaderboards/page.tsx @@ -3,8 +3,7 @@ import { Trophy, Calendar, Globe, TrendingUp } from "lucide-react"; import { useState } from "react"; -import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card"; -import { Button } from "@/components/ui/button"; +import { Card } from "@/components/ui/card"; import { Tabs, TabsList, TabsTrigger } from "@/components/ui/tabs"; import { Table, @@ -13,7 +12,6 @@ import { TableHeader, TableRow, } from "@/components/ui/table"; -import { Badge } from "@/components/ui/badge"; import { Pagination, PaginationContent, @@ -30,11 +28,10 @@ import { getGlobalLeaderboard, getWeeklyLeaderboard, } from "@/modules/leaderboard/actions"; -import { ToggleGroup, ToggleGroupItem } from "@/components/ui/toggle-group"; export default function Leaderboards() { - const [global, globalLoaded, globalError] = useAction(getGlobalLeaderboard); - const [weekly, weeklyLoaded, weeklyError] = useAction(getWeeklyLeaderboard); + const [global] = useAction(getGlobalLeaderboard); + const [weekly] = useAction(getWeeklyLeaderboard); const [activeTab, setActiveTab] = useState<"global" | "weekly">("global"); const data = (activeTab === "global" ? global : weekly) || []; @@ -95,26 +92,6 @@ export default function Leaderboards() { - -
- - - any% - - - 100% - - - - - - Assisted - - - Unassisted - - -
{/* Table */} @@ -122,28 +99,38 @@ export default function Leaderboards() { - -

Rank

+ {/* Rank */} + + Rank - -

Runner

+ + {/* Runner / Username */} + Runner + + {/* Wins */} + + Wins - -

Time

+ + {/* Podiums */} + + Podiums - -

Category

+ + {/* Problems Completed */} + + Problems Completed - -

Assisted

+ + {/* User ID (optional) */} + + User ID - Runs - Problem
{data.map((entry, i) => ( - + ))}
diff --git a/src/modules/leaderboard/actions.ts b/src/modules/leaderboard/actions.ts index c62bab4..4e395f6 100644 --- a/src/modules/leaderboard/actions.ts +++ b/src/modules/leaderboard/actions.ts @@ -1,194 +1,17 @@ "use server"; +import { createClient } from "@/lib/supabase/server"; import * as Core from "./core"; -import { LeaderboardRank } from "./types"; // updated interface +import { LeaderboardUser } from "./types"; // updated interface -export async function getGlobalLeaderboard(): Promise { - return [ - { - rank: 1, - username: "speedmaster_x", - pb: "2:34.21", - runsCount: 2341, - problem: "Fix broken login flow", - category: "any%", - assisted: false, - }, - { - rank: 2, - username: "algo_ninja", - pb: "2:38.54", - runsCount: 1876, - problem: "Refactor legacy API endpoints", - category: "any%", - assisted: false, - }, - { - rank: 3, - username: "clockwork", - pb: "2:41.02", - runsCount: 3102, - problem: "Optimize image upload pipeline", - category: "any%", - assisted: false, - }, - { - rank: 4, - username: "fastfingers99", - pb: "2:45.33", - runsCount: 987, - problem: "Build a mini chat server", - category: "any%", - assisted: false, - }, - { - rank: 5, - username: "recursion_queen", - pb: "2:47.89", - runsCount: 1543, - problem: "Fix CSS layout bug in dashboard", - category: "any%", - assisted: false, - }, - { - rank: 6, - username: "bitshifter", - pb: "2:52.11", - runsCount: 2109, - problem: "Implement JWT authentication", - category: "any%", - assisted: false, - }, - { - rank: 7, - username: "nullpointer", - pb: "2:54.67", - runsCount: 876, - problem: "Create REST endpoint for user data", - category: "any%", - assisted: false, - }, - { - rank: 8, - username: "stackattack", - pb: "2:58.23", - runsCount: 1234, - problem: "Fix off-by-one bug in sorting function", - category: "any%", - assisted: false, - }, - { - rank: 9, - username: "looplegend", - pb: "3:01.45", - runsCount: 654, - problem: "Optimize SQL query for reports", - category: "any%", - assisted: false, - }, - { - rank: 10, - username: "coderunner", - pb: "3:05.78", - runsCount: 1098, - problem: "Add file upload validation", - category: "any%", - assisted: false, - }, - ]; +export async function getGlobalLeaderboard(): Promise { + const supabase = await createClient(); + + return await Core.getGlobalLeaderboard(supabase); } -export async function getWeeklyLeaderboard(): Promise { - return [ - { - rank: 1, - username: "weekly_warrior", - pb: "2:51.33", - runsCount: 156, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - { - rank: 2, - username: "speedmaster_x", - pb: "2:53.12", - runsCount: 89, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - { - rank: 3, - username: "newbie_grinder", - pb: "2:58.67", - runsCount: 234, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - { - rank: 4, - username: "algo_ninja", - pb: "3:02.45", - runsCount: 67, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - { - rank: 5, - username: "fresh_runner", - pb: "3:05.89", - runsCount: 45, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - { - rank: 6, - username: "practice_makes", - pb: "3:08.12", - runsCount: 112, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - { - rank: 7, - username: "splitmaster", - pb: "3:12.34", - runsCount: 78, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - { - rank: 8, - username: "grindtime", - pb: "3:15.56", - runsCount: 92, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - { - rank: 9, - username: "pb_hunter", - pb: "3:18.90", - runsCount: 56, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - { - rank: 10, - username: "reset_king", - pb: "3:22.11", - runsCount: 187, - problem: "Build notifications API", - category: "any%", - assisted: false, - }, - ]; +export async function getWeeklyLeaderboard(): Promise { + const supabase = await createClient(); + + return await Core.getWeeklyLeaderboard(supabase); } diff --git a/src/modules/leaderboard/core.ts b/src/modules/leaderboard/core.ts index a59f71d..d981b6c 100644 --- a/src/modules/leaderboard/core.ts +++ b/src/modules/leaderboard/core.ts @@ -1,3 +1,21 @@ "use server"; +import { SupabaseClient } from "@supabase/supabase-js"; import "server-only"; +import { LeaderboardUser } from "./types"; + +export async function getGlobalLeaderboard( + supabase: SupabaseClient, +): Promise { + const { data, error } = await supabase.rpc("get_global_leaderboard"); + if (error) throw error; + return data; +} + +export async function getWeeklyLeaderboard( + supabase: SupabaseClient, +): Promise { + const { data, error } = await supabase.rpc("get_weekly_leaderboard"); + if (error) throw error; + return data; +} diff --git a/src/modules/leaderboard/types.ts b/src/modules/leaderboard/types.ts index 0f1cc51..c5edd3e 100644 --- a/src/modules/leaderboard/types.ts +++ b/src/modules/leaderboard/types.ts @@ -1,11 +1,8 @@ -export type Leaderboard = LeaderboardRank[]; - -export interface LeaderboardRank { +export interface LeaderboardUser { rank: number; + user_id: string; username: string; - pb: string; - runsCount: number; - problem: string; - category: "any%" | "100%"; - assisted: boolean; + wins: number; + podiums: number; + problems_completed: number; } From 4e92010bfe54d070d9ecd596dd579c7b339ebe09 Mon Sep 17 00:00:00 2001 From: Leo dev Date: Sat, 7 Feb 2026 16:08:22 +0100 Subject: [PATCH 05/10] working Problems --- src/app/problems/components/ProblemCard.tsx | 56 ++++++------- src/app/problems/page.tsx | 4 +- src/app/run/page.tsx | 12 ++- src/modules/problems/actions.ts | 87 +-------------------- src/modules/problems/core.ts | 43 ++++++++++ src/modules/problems/types.ts | 25 +++++- 6 files changed, 102 insertions(+), 125 deletions(-) diff --git a/src/app/problems/components/ProblemCard.tsx b/src/app/problems/components/ProblemCard.tsx index 1e7f9b6..e9239fe 100644 --- a/src/app/problems/components/ProblemCard.tsx +++ b/src/app/problems/components/ProblemCard.tsx @@ -1,23 +1,18 @@ import { Button } from "@/components/ui/button"; -import { Clock, Zap, Users } from "lucide-react"; - -interface ProblemCardProps { - name: string; - difficulty: "easy" | "medium" | "hard"; - tags: string[]; - bestTime?: string; - attempts: number; - index?: number; -} +import { Problem } from "@/modules/problems/types"; +import { Clock, Zap, Users, Code } from "lucide-react"; const ProblemCard = ({ - name, - difficulty, - tags, - bestTime, - attempts, + problem, index = 0, -}: ProblemCardProps) => { + bestTime, + attempts = 0, +}: { + problem: Problem; + index?: number; + bestTime?: string; + attempts?: number; +}) => { const difficultyStyles = { easy: "diff-easy", medium: "diff-medium", @@ -46,29 +41,30 @@ const ProblemCard = ({ {/* Header */}

- {name} + {problem.title}

- {difficultyLabels[difficulty]} + {difficultyLabels[problem.difficulty]}
- {/* Tags */} -
- {tags.map((tag) => ( - - {tag} + {/* Tags / Meta */} +
+ {problem.language && ( + + {problem.language} - ))} + )}
- {/* Spacer */} -
+ {/* Description */} +

+ {problem.description} +

{/* Stats + Action */}
diff --git a/src/app/problems/page.tsx b/src/app/problems/page.tsx index 02cb1ce..4eacb13 100644 --- a/src/app/problems/page.tsx +++ b/src/app/problems/page.tsx @@ -14,6 +14,8 @@ import { getProblems } from "@/modules/problems/actions"; export default function Problems() { const [problems, problemsLoaded, problemsError] = useAction(getProblems); + console.log(problems); + const [viewMode, setViewMode] = useState<"grid" | "list">("grid"); const difficulties = ["All", "Easy", "Medium", "Hard"]; @@ -84,7 +86,7 @@ export default function Problems() { > {problems && problems.map((problem, i) => ( - + ))}
diff --git a/src/app/run/page.tsx b/src/app/run/page.tsx index e2c1107..a43d804 100644 --- a/src/app/run/page.tsx +++ b/src/app/run/page.tsx @@ -45,11 +45,15 @@ export default function Run() {
diff --git a/src/modules/problems/actions.ts b/src/modules/problems/actions.ts index 0d587ef..a549c80 100644 --- a/src/modules/problems/actions.ts +++ b/src/modules/problems/actions.ts @@ -4,90 +4,5 @@ import * as Core from "./core"; import { Problem } from "./types"; export async function getProblems(): Promise { - return [ - { - name: "Two Sum Dash", - difficulty: "easy" as const, - tags: ["arrays", "hash-map"], - bestTime: "0:42", - attempts: 12453, - }, - { - name: "Binary Sprint", - difficulty: "easy" as const, - tags: ["binary-search"], - bestTime: "0:38", - attempts: 8921, - }, - { - name: "Linked List Rush", - difficulty: "medium" as const, - tags: ["linked-list", "pointers"], - bestTime: "1:24", - attempts: 6234, - }, - { - name: "Tree Traverse Blitz", - difficulty: "medium" as const, - tags: ["trees", "recursion"], - bestTime: "2:01", - attempts: 5102, - }, - { - name: "DP Gauntlet", - difficulty: "hard" as const, - tags: ["dynamic-programming"], - bestTime: "4:32", - attempts: 2341, - }, - { - name: "Graph Navigator", - difficulty: "hard" as const, - tags: ["graphs", "bfs", "dfs"], - bestTime: "3:45", - attempts: 3456, - }, - { - name: "String Scramble", - difficulty: "easy" as const, - tags: ["strings", "manipulation"], - bestTime: "0:55", - attempts: 9876, - }, - { - name: "Stack Overflow", - difficulty: "medium" as const, - tags: ["stacks", "queues"], - bestTime: "1:42", - attempts: 4567, - }, - { - name: "Heap Hero", - difficulty: "hard" as const, - tags: ["heaps", "priority-queue"], - bestTime: "3:21", - attempts: 1890, - }, - { - name: "Sliding Window Slam", - difficulty: "medium" as const, - tags: ["sliding-window", "arrays"], - bestTime: "1:56", - attempts: 5678, - }, - { - name: "Trie Triumph", - difficulty: "hard" as const, - tags: ["trie", "strings"], - bestTime: "4:12", - attempts: 1234, - }, - { - name: "Backtrack Blaster", - difficulty: "hard" as const, - tags: ["backtracking", "recursion"], - bestTime: "5:01", - attempts: 987, - }, - ]; + return await Core.getProblems(); } diff --git a/src/modules/problems/core.ts b/src/modules/problems/core.ts index a59f71d..0189644 100644 --- a/src/modules/problems/core.ts +++ b/src/modules/problems/core.ts @@ -1,3 +1,46 @@ "use server"; import "server-only"; +import { ProblemDefinition } from "./types"; + +const problems: ProblemDefinition[] = [ + { + id: "fix-auth-callback", + title: "Fix the Broken Auth Callback", + description: + "Users can log in with OAuth, but sessions aren't persisted. Fix it.", + language: "typescript", + difficulty: "easy", + validate100: () => true, + validateAny: () => true, + }, + { + id: "fix-prod-build", + title: "Patch a Failing Production Build", + description: + "Production build fails while development works. Fix the build.", + language: "javascript", + difficulty: "easy", + validate100: () => true, + validateAny: () => true, + }, + { + id: "add-user-profile-endpoint", + title: "Implement Missing API Endpoint", + description: "The frontend expects `/api/me`. Implement it correctly.", + language: "go", + difficulty: "easy", + validate100: () => true, + validateAny: () => true, + }, +]; + +export async function getProblems() { + return problems.map((def) => ({ + id: def.id, + title: def.title, + description: def.description, + difficulty: def.difficulty, + language: def.language, + })); +} diff --git a/src/modules/problems/types.ts b/src/modules/problems/types.ts index 6610746..50478c1 100644 --- a/src/modules/problems/types.ts +++ b/src/modules/problems/types.ts @@ -1,7 +1,24 @@ +export type ProblemValidator = (submission: any) => boolean; + export interface Problem { - name: string; + id: string; + title: string; + description: string; difficulty: "easy" | "medium" | "hard"; - tags: string[]; - bestTime?: string; - attempts: number; + language: + | "rust" + | "go" + | "java" + | "javascript" + | "typescript" + | "python" + | null; +} + +export interface ProblemDefinition extends Problem { + /* Any% validator */ + validateAny: ProblemValidator; + /* 100% validator */ + validate100: ProblemValidator; + metadata?: Record; // optional extra info like time limits, refs } From a508d44ecf801d71851794e0cd666a4abde3b820 Mon Sep 17 00:00:00 2001 From: Leo dev Date: Sat, 7 Feb 2026 18:59:24 +0100 Subject: [PATCH 06/10] Compact problems --- src/app/problems/components/ProblemCard.tsx | 39 ++++++++++----------- src/app/run/page.tsx | 2 +- 2 files changed, 19 insertions(+), 22 deletions(-) diff --git a/src/app/problems/components/ProblemCard.tsx b/src/app/problems/components/ProblemCard.tsx index e9239fe..2a9f5b8 100644 --- a/src/app/problems/components/ProblemCard.tsx +++ b/src/app/problems/components/ProblemCard.tsx @@ -1,4 +1,5 @@ import { Button } from "@/components/ui/button"; +import { cn } from "@/lib/utils"; import { Problem } from "@/modules/problems/types"; import { Clock, Zap, Users, Code } from "lucide-react"; @@ -53,21 +54,7 @@ const ProblemCard = ({
{/* Tags / Meta */} -
- {problem.language && ( - - {problem.language} - - )} -
- - {/* Description */} -

- {problem.description} -

- - {/* Stats + Action */} -
+
{bestTime && (
@@ -81,12 +68,22 @@ const ProblemCard = ({
- {/* Quick run button */} -
- -
+ {problem.language && ( + + {problem.language} + + )} +
+ + {/* Description */} +

+ {problem.description} +

+ +
+
diff --git a/src/app/run/page.tsx b/src/app/run/page.tsx index a43d804..aa5b2ca 100644 --- a/src/app/run/page.tsx +++ b/src/app/run/page.tsx @@ -43,7 +43,7 @@ export default function Run() { {runInfo && }
-
+
Date: Sat, 7 Feb 2026 19:17:42 +0100 Subject: [PATCH 07/10] Improved UI --- .../components/LeaderboardRow.tsx | 23 ++---------- src/app/profile/page.tsx | 5 +-- src/app/run/page.tsx | 8 ++--- src/components/app/ProfileCard.tsx | 35 ------------------- 4 files changed, 9 insertions(+), 62 deletions(-) delete mode 100644 src/components/app/ProfileCard.tsx diff --git a/src/app/leaderboards/components/LeaderboardRow.tsx b/src/app/leaderboards/components/LeaderboardRow.tsx index fde8889..8458976 100644 --- a/src/app/leaderboards/components/LeaderboardRow.tsx +++ b/src/app/leaderboards/components/LeaderboardRow.tsx @@ -1,3 +1,4 @@ +import Rank from "@/components/app/Rank"; import { LinkIcon, Trophy } from "lucide-react"; import Link from "next/link"; @@ -17,20 +18,6 @@ const LeaderboardRow = ({ index?: number; run: GlobalLeaderboardUser; }) => { - const getRankStyle = (rank: number) => { - if (rank === 1) return "rank-gold"; - if (rank === 2) return "rank-silver"; - if (rank === 3) return "rank-bronze"; - return "bg-secondary text-muted-foreground"; - }; - - const getRankGlow = (rank: number) => { - if (rank === 1) return "glow-gold"; - if (rank === 2) return "glow-silver"; - if (rank === 3) return "glow-bronze"; - return ""; - }; - const isTopThree = run.rank <= 3; return ( @@ -45,13 +32,7 @@ const LeaderboardRow = ({ > {/* Rank */} -
- {isTopThree ? : run.rank} -
+ {/* Username */} diff --git a/src/app/profile/page.tsx b/src/app/profile/page.tsx index 1b4411f..562878f 100644 --- a/src/app/profile/page.tsx +++ b/src/app/profile/page.tsx @@ -8,6 +8,7 @@ import { Button } from "@/components/ui/button"; import { Separator } from "@/components/ui/separator"; import ProfileStatCard from "@/app/profile/components/ProfileStatCard"; +import Rank from "@/components/app/Rank"; export default function Profile() { const user = { @@ -34,8 +35,8 @@ export default function Profile() {
{user.username[0].toUpperCase()}
-
- #{user.rank} +
+
diff --git a/src/app/run/page.tsx b/src/app/run/page.tsx index aa5b2ca..4753b42 100644 --- a/src/app/run/page.tsx +++ b/src/app/run/page.tsx @@ -9,7 +9,7 @@ import Editor from "./components/Editor"; import useAction from "@/hook/use-action"; import { getLiveRun } from "@/modules/live-run/actions"; import ProblemCard from "../problems/components/ProblemCard"; -import ProfileCard from "@/components/app/ProfileCard"; +import ProfileCard from "./components/ProfileCard"; export default function Run() { const [runInfo] = useAction(getLiveRun); @@ -28,13 +28,13 @@ export default function Run() { pt-20 sm:pt-24 pb-6 sm:pb-12 flex flex-col lg:flex-row - gap-6 lg:gap-8 + gap-5 " > {/* Main column */}
{/* Top cards */} -
+
@@ -80,7 +80,7 @@ export default function Run() {
{/* Code */} -
+
myfile.js
diff --git a/src/components/app/ProfileCard.tsx b/src/components/app/ProfileCard.tsx deleted file mode 100644 index 4550535..0000000 --- a/src/components/app/ProfileCard.tsx +++ /dev/null @@ -1,35 +0,0 @@ -import { Badge } from "../ui/badge"; -import { Card, CardContent } from "../ui/card"; - -export default function ProfileCard({ - user, -}: { - user: { username: string; rank: number }; -}) { - return ( - -
- - - {/* Avatar */} -
- Img - -
- #{user.rank} -
-
- - {/* User Info */} -
-

{user.username}

- World Record Holder -
-
- - ); -} From 9d9f0f2f324868aaf4a36cf4beb0465ad3ce6437 Mon Sep 17 00:00:00 2001 From: Leo dev Date: Sat, 7 Feb 2026 19:17:55 +0100 Subject: [PATCH 08/10] Rank --- src/app/run/components/ProfileCard.tsx | 36 ++++++++++++++++++++++++++ src/components/app/Rank.tsx | 29 +++++++++++++++++++++ 2 files changed, 65 insertions(+) create mode 100644 src/app/run/components/ProfileCard.tsx create mode 100644 src/components/app/Rank.tsx diff --git a/src/app/run/components/ProfileCard.tsx b/src/app/run/components/ProfileCard.tsx new file mode 100644 index 0000000..d8a6f42 --- /dev/null +++ b/src/app/run/components/ProfileCard.tsx @@ -0,0 +1,36 @@ +import Rank from "@/components/app/Rank"; +import { Badge } from "@/components/ui/badge"; +import { Card, CardContent } from "@/components/ui/card"; + +export default function ProfileCard({ + user, +}: { + user: { username: string; rank: number }; +}) { + return ( + +
+ + + {/* Avatar */} +
+ Img + +
+ +
+
+ + {/* User Info */} +
+

{user.username}

+ WR Holder +
+
+ + ); +} diff --git a/src/components/app/Rank.tsx b/src/components/app/Rank.tsx new file mode 100644 index 0000000..0727cad --- /dev/null +++ b/src/components/app/Rank.tsx @@ -0,0 +1,29 @@ +import { Trophy } from "lucide-react"; + +export default function Rank({ rank }: { rank: number }) { + const getRankStyle = (rank: number) => { + if (rank === 1) return "rank-gold"; + if (rank === 2) return "rank-silver"; + if (rank === 3) return "rank-bronze"; + return "bg-secondary text-muted-foreground"; + }; + + const getRankGlow = (rank: number) => { + if (rank === 1) return "glow-gold"; + if (rank === 2) return "glow-silver"; + if (rank === 3) return "glow-bronze"; + return ""; + }; + + const isTopThree = rank <= 3; + + return ( +
+ {isTopThree ? : rank} +
+ ); +} From 7ecb296a151511bdc050e55d7108fe0e3ff2df19 Mon Sep 17 00:00:00 2001 From: Leo dev Date: Sat, 7 Feb 2026 19:30:51 +0100 Subject: [PATCH 09/10] Timer display --- src/app/run/components/RunTimer.tsx | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/app/run/components/RunTimer.tsx b/src/app/run/components/RunTimer.tsx index 693256f..4f0748d 100644 --- a/src/app/run/components/RunTimer.tsx +++ b/src/app/run/components/RunTimer.tsx @@ -20,8 +20,9 @@ export default function RunTimer({ runInfo }: { runInfo: LiveRun }) { return (
- -

{time}

+ +

{time}

+

{runInfo.category}

); From c0e2dbe27e4808aaf7aa23faa1cdd47d48b71a7a Mon Sep 17 00:00:00 2001 From: Leo dev Date: Sat, 7 Feb 2026 19:36:40 +0100 Subject: [PATCH 10/10] Small fix in editor view --- src/app/run/page.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/app/run/page.tsx b/src/app/run/page.tsx index 4753b42..32312af 100644 --- a/src/app/run/page.tsx +++ b/src/app/run/page.tsx @@ -80,7 +80,7 @@ export default function Run() {
{/* Code */} -
+
myfile.js