Finished first sw stats

This commit is contained in:
2025-08-22 13:51:18 +02:00
parent 4dd571c367
commit 054ec7841b
6 changed files with 153 additions and 3 deletions

View File

@@ -1,5 +1,6 @@
import { getSkyWarsIcon, getTextColor } from "@/lib/hypixel/skywars"
import { getPrestigeName, getSkyWarsIcon, getTextColor } from "@/lib/hypixel/skywars"
import { getSkywarsLevel } from "@/lib/hypixel/skyWarsLevel"
import { cn } from "@/lib/utils"
export function SkywarsLevel({ xp, icon }: { xp: number, icon: string | undefined }) {
const level = getSkywarsLevel(xp)
@@ -49,3 +50,77 @@ export function SkywarsLevel({ xp, icon }: { xp: number, icon: string | undefine
</p>
)
}
export function SkywarsProgress({ level, percent }: { level: number, percent: number }) {
return (
<div className="flex items-center mb-10">
<LevelNumber level={level} className="mr-2" />
<Progress level={level} percent={percent} />
<div className="flex-1 h-5 rounded-r-md bg-background"></div>
<LevelNumber level={level + 1} className="ml-2" />
</div>
)
}
function LevelNumber({ level, className }: { level: number, className?: string }) {
if (level > 150 || level === 50) {
return (
<div
className={cn(level > 150 ? "font-bold" : undefined, className)}
style={{
backgroundImage: "linear-gradient(to left,#a0a,#f5f,#5ff,#5f5,#ff5,#fa0,#f55)",
WebkitBackgroundClip: "text",
color: "transparent"
}}
>
{level}
</div>
)
}
return <div className={cn(`text-mc-${getTextColor(level).text}`, className)}>{level}</div>
}
function Progress({ level, percent }: { level: number, percent: number }) {
if (level > 150 || level === 50) {
return (
<div
className="h-5 rounded-l-md"
style={{
width: `${percent}%`,
background: "repeating-linear-gradient(to right,#f55,#fa0,#ff5,#5f5,#5ff,#f5f,#a0a,#f55 16rem)"
}}
>
</div>
)
}
return <div className={`h-5 bg-mc-${getTextColor(level).text} rounded-l-md`} style={{ width: `${percent}%` }}></div>
}
export function SkywarsPrestige({ level, icon }: { level: number, icon?: string }) {
const swIcon = getSkyWarsIcon(icon)
const pres = getPrestigeName(level)
const val = `${pres} ${swIcon}`
if (level > 150 || level === 50) {
return (
<span
style={{
backgroundImage: "linear-gradient(to left,#a0a,#f5f,#5ff,#5f5,#ff5,#fa0,#f55)",
WebkitBackgroundClip: "text",
color: "transparent"
}}
className={level > 150 ? "font-bold" : undefined}
>
{val}
</span>
)
}
return (
<span className={`text-mc-${getTextColor(level).text}`}>
{val}
</span>
)
}

View File

@@ -4,11 +4,14 @@ import { Card, CardContent } from "@/components/ui/card"
import { Collapsible, CollapsibleContent, CollapsibleTrigger } from "@/components/ui/collapsible"
import { Separator } from "@/components/ui/separator"
import { formatNumber } from "@/lib/formatters"
import { getProgress } from "@/lib/hypixel/general"
import { getSkywarsLevel, getSkywarsXpForLevel } from "@/lib/hypixel/skyWarsLevel"
import { Player } from "@/lib/schema/player"
import { ChevronDown, ChevronUp } from "lucide-react"
import { useEffect, useRef, useState } from "react"
import CollapsedStats from "../../_components/CollapsedStats"
import { SkywarsLevel } from "./skywars-components"
import { SkywarsLevel, SkywarsProgress } from "./skywars-components"
import SkyWarsGeneralStats from "./stats"
export default function SkyWarsStats({ stats }: { stats: Player["player"]["stats"]["SkyWars"] }) {
const ref = useRef<HTMLDivElement>(null)
@@ -36,9 +39,16 @@ export default function SkyWarsStats({ stats }: { stats: Player["player"]["stats
if (!stats) return null
const level = getSkywarsLevel(stats.skywars_experience)
const kd = (stats.kills / stats.deaths).toFixed(2)
const wl = (stats.wins / stats.losses).toFixed(2)
const percent = getProgress(
getSkywarsXpForLevel(Math.floor(level)),
stats.skywars_experience,
getSkywarsXpForLevel(Math.floor(level) + 1)
)
return (
<Card>
<CardContent>
@@ -73,6 +83,8 @@ export default function SkyWarsStats({ stats }: { stats: Player["player"]["stats
</div>
<CollapsibleContent>
<Separator className="my-4" />
<SkywarsProgress level={Math.floor(level)} percent={percent} />
<SkyWarsGeneralStats statsChecked={stats} level={level} />
</CollapsibleContent>
</Collapsible>
</CardContent>

View File

@@ -0,0 +1,29 @@
import { formatNumber } from "@/lib/formatters"
import { Player } from "@/lib/schema/player"
import { BasicStat, Stat } from "../../_components/Stats"
import { SkywarsPrestige } from "./skywars-components"
export default function SkyWarsGeneralStats({
statsChecked,
level
}: {
statsChecked: Player["player"]["stats"]["SkyWars"]
level: number
}) {
const stats = statsChecked!
return (
<div className="flex mb-10">
<div className="flex-1">
<BasicStat title="Level: " value={level.toFixed(2)} />
<Stat title="Prestige: ">
<SkywarsPrestige level={Math.floor(level)} icon={stats.selected_prestige_icon} />
</Stat>
<BasicStat title="Coins: " value={formatNumber(stats.coins)} className="text-mc-gold" />
<BasicStat title="Token: " value={formatNumber(stats.cosmetic_tokens)} className="text-mc-dark-green" />
</div>
<div className="flex-1"></div>
<div className="flex-1"></div>
</div>
)
}