feat(skywars): add full mode stats rows and best mode detection
This commit is contained in:
142
src/app/(stats)/player/[ign]/_stats/skywars/table.tsx
Normal file
142
src/app/(stats)/player/[ign]/_stats/skywars/table.tsx
Normal file
@@ -0,0 +1,142 @@
|
||||
import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from "@/components/ui/table"
|
||||
import { formatNumber } from "@/lib/formatters"
|
||||
import { _SkywarsStats, getBestMode, getSkywarsModeStats } from "@/lib/hypixel/skywars"
|
||||
import { NonNullStats } from "@/lib/schema/player"
|
||||
import { cn } from "@/lib/utils"
|
||||
|
||||
export default function SkywarsStatTable({ stats }: { stats: NonNullStats["SkyWars"] }) {
|
||||
return (
|
||||
<Table>
|
||||
<SkywarsTableHeader />
|
||||
<TableBody>
|
||||
<Normal stats={stats} />
|
||||
<Insane stats={stats} />
|
||||
<TeamsNormal stats={stats} />
|
||||
<TeamsInsane stats={stats} />
|
||||
<Mega stats={stats} />
|
||||
<MegaDoubles stats={stats} />
|
||||
<Ranked stats={stats} />
|
||||
</TableBody>
|
||||
</Table>
|
||||
)
|
||||
}
|
||||
|
||||
function SkywarsTableHeader() {
|
||||
const headerElements = [
|
||||
"Mode",
|
||||
"Kills",
|
||||
"Deaths",
|
||||
"KD",
|
||||
"Wins",
|
||||
"Losses",
|
||||
"WL"
|
||||
]
|
||||
|
||||
return (
|
||||
<TableHeader>
|
||||
<TableRow>
|
||||
{headerElements.map((v, i) => {
|
||||
return <TableHead key={i} className="font-bold">{v}</TableHead>
|
||||
})}
|
||||
</TableRow>
|
||||
</TableHeader>
|
||||
)
|
||||
}
|
||||
|
||||
function Normal({ stats }: { stats: NonNullStats["SkyWars"] }) {
|
||||
const modeStats = getSkywarsModeStats("normal", stats as _SkywarsStats)
|
||||
const isBest = getBestMode(stats as _SkywarsStats) === "normal"
|
||||
|
||||
return (
|
||||
<TableRow className={cn(isBest ? "font-bold text-mc-light-purple" : undefined)}>
|
||||
<TableCell>Solo Normal</TableCell>
|
||||
{modeStats.map((v, i) => {
|
||||
return <TableCell key={i}>{typeof v === "number" ? formatNumber(v) : v}</TableCell>
|
||||
})}
|
||||
</TableRow>
|
||||
)
|
||||
}
|
||||
|
||||
function Insane({ stats }: { stats: NonNullStats["SkyWars"] }) {
|
||||
const modeStats = getSkywarsModeStats("insane", stats as _SkywarsStats)
|
||||
const isBest = getBestMode(stats as _SkywarsStats) === "insane"
|
||||
|
||||
return (
|
||||
<TableRow className={cn(isBest ? "font-bold text-mc-light-purple" : undefined)}>
|
||||
<TableCell>Solo Insane</TableCell>
|
||||
{modeStats.map((v, i) => {
|
||||
return <TableCell key={i}>{typeof v === "number" ? formatNumber(v) : v}</TableCell>
|
||||
})}
|
||||
</TableRow>
|
||||
)
|
||||
}
|
||||
|
||||
function TeamsNormal({ stats }: { stats: NonNullStats["SkyWars"] }) {
|
||||
const modeStats = getSkywarsModeStats("teams_normal", stats as _SkywarsStats)
|
||||
const isBest = getBestMode(stats as _SkywarsStats) === "teams_normal"
|
||||
|
||||
return (
|
||||
<TableRow className={cn(isBest ? "font-bold text-mc-light-purple" : undefined)}>
|
||||
<TableCell>Teams Normal</TableCell>
|
||||
{modeStats.map((v, i) => {
|
||||
return <TableCell key={i}>{typeof v === "number" ? formatNumber(v) : v}</TableCell>
|
||||
})}
|
||||
</TableRow>
|
||||
)
|
||||
}
|
||||
|
||||
function TeamsInsane({ stats }: { stats: NonNullStats["SkyWars"] }) {
|
||||
const modeStats = getSkywarsModeStats("teams_insane", stats as _SkywarsStats)
|
||||
const isBest = getBestMode(stats as _SkywarsStats) === "teams_insane"
|
||||
|
||||
return (
|
||||
<TableRow className={cn(isBest ? "font-bold text-mc-light-purple" : undefined)}>
|
||||
<TableCell>Teams Insane</TableCell>
|
||||
{modeStats.map((v, i) => {
|
||||
return <TableCell key={i}>{typeof v === "number" ? formatNumber(v) : v}</TableCell>
|
||||
})}
|
||||
</TableRow>
|
||||
)
|
||||
}
|
||||
|
||||
function Mega({ stats }: { stats: NonNullStats["SkyWars"] }) {
|
||||
const modeStats = getSkywarsModeStats("mega", stats as _SkywarsStats)
|
||||
const isBest = getBestMode(stats as _SkywarsStats) === "mega"
|
||||
|
||||
return (
|
||||
<TableRow className={cn(isBest ? "font-bold text-mc-light-purple" : undefined)}>
|
||||
<TableCell>Mega</TableCell>
|
||||
{modeStats.map((v, i) => {
|
||||
return <TableCell key={i}>{typeof v === "number" ? formatNumber(v) : v}</TableCell>
|
||||
})}
|
||||
</TableRow>
|
||||
)
|
||||
}
|
||||
|
||||
function MegaDoubles({ stats }: { stats: NonNullStats["SkyWars"] }) {
|
||||
const modeStats = getSkywarsModeStats("mega_doubles", stats as _SkywarsStats)
|
||||
const isBest = getBestMode(stats as _SkywarsStats) === "mega_doubles"
|
||||
|
||||
return (
|
||||
<TableRow className={cn(isBest ? "font-bold text-mc-light-purple" : undefined)}>
|
||||
<TableCell>Mega Doubles</TableCell>
|
||||
{modeStats.map((v, i) => {
|
||||
return <TableCell key={i}>{typeof v === "number" ? formatNumber(v) : v}</TableCell>
|
||||
})}
|
||||
</TableRow>
|
||||
)
|
||||
}
|
||||
|
||||
function Ranked({ stats }: { stats: NonNullStats["SkyWars"] }) {
|
||||
const modeStats = getSkywarsModeStats("ranked", stats as _SkywarsStats)
|
||||
const isBest = getBestMode(stats as _SkywarsStats) === "ranked"
|
||||
|
||||
return (
|
||||
<TableRow className={cn(isBest ? "font-bold text-mc-light-purple" : undefined)}>
|
||||
<TableCell>Ranked</TableCell>
|
||||
{modeStats.map((v, i) => {
|
||||
return <TableCell key={i}>{typeof v === "number" ? formatNumber(v) : v}</TableCell>
|
||||
})}
|
||||
</TableRow>
|
||||
)
|
||||
}
|
||||
@@ -1,5 +1,6 @@
|
||||
import { ICONS, PRESTIGES } from "@/data/hypixel/skywars"
|
||||
import { floorLevel } from "./formatters"
|
||||
import { devide } from "./general"
|
||||
|
||||
export function getTextColor(level: number) {
|
||||
const floored = floorLevel(level, 5)
|
||||
@@ -36,3 +37,94 @@ export function getPrestigeName(level: number) {
|
||||
|
||||
return PRESTIGES.find(p => p.level === floored)!.name
|
||||
}
|
||||
|
||||
export type _SkywarsStats = Record<string, number>
|
||||
type Mode =
|
||||
| "normal"
|
||||
| "insane"
|
||||
| "teams_normal"
|
||||
| "teams_insane"
|
||||
| "mega"
|
||||
| "mega_doubles"
|
||||
| "ranked"
|
||||
|
||||
export type SkywarsModeStats = {
|
||||
kills: number
|
||||
deaths: number
|
||||
wins: number
|
||||
losses: number
|
||||
}
|
||||
|
||||
export function getBestMode(stats: _SkywarsStats): Mode | null {
|
||||
const { wins: normal } = getSkywarsModeStats("normal", stats, true)
|
||||
const { wins: insane } = getSkywarsModeStats("insane", stats, true)
|
||||
const { wins: teams_normal } = getSkywarsModeStats("teams_normal", stats, true)
|
||||
const { wins: teams_insane } = getSkywarsModeStats("teams_insane", stats, true)
|
||||
const { wins: mega } = getSkywarsModeStats("mega", stats, true)
|
||||
const { wins: mega_doubles } = getSkywarsModeStats("mega_doubles", stats, true)
|
||||
const { wins: ranked } = getSkywarsModeStats("ranked", stats, true)
|
||||
|
||||
const max = Math.max(normal, insane, teams_normal, teams_insane, mega, mega_doubles, ranked)
|
||||
|
||||
switch (max) {
|
||||
case normal:
|
||||
return "normal"
|
||||
case insane:
|
||||
return "insane"
|
||||
case teams_normal:
|
||||
return "teams_normal"
|
||||
case teams_insane:
|
||||
return "teams_insane"
|
||||
case mega:
|
||||
return "mega"
|
||||
case mega_doubles:
|
||||
return "mega_doubles"
|
||||
case ranked:
|
||||
return "ranked"
|
||||
default:
|
||||
return null
|
||||
}
|
||||
}
|
||||
|
||||
export function getSkywarsModeStats(mode: Mode, stats: _SkywarsStats, raw: true): SkywarsModeStats
|
||||
export function getSkywarsModeStats(mode: Mode, stats: _SkywarsStats, raw?: false): (string | number)[]
|
||||
export function getSkywarsModeStats(mode: Mode, stats: _SkywarsStats, raw = false) {
|
||||
switch (mode) {
|
||||
case "normal":
|
||||
return skywarsModeStats("solo_normal", stats, raw)
|
||||
case "insane":
|
||||
return skywarsModeStats("solo_insane", stats, raw)
|
||||
case "teams_normal":
|
||||
return skywarsModeStats("team_normal", stats, raw)
|
||||
case "teams_insane":
|
||||
return skywarsModeStats("team_insane", stats, raw)
|
||||
case "mega":
|
||||
return skywarsModeStats("mega_mega", stats, raw)
|
||||
case "mega_doubles":
|
||||
return skywarsModeStats("mega_doubles", stats, raw)
|
||||
case "ranked":
|
||||
return skywarsModeStats("ranked_normal", stats, raw)
|
||||
default:
|
||||
throw new Error(`${mode satisfies never} does not exist`)
|
||||
}
|
||||
}
|
||||
|
||||
function skywarsModeStats(suffix: string, stats: _SkywarsStats, raw = false) {
|
||||
if (raw) {
|
||||
return {
|
||||
kills: stats[`kills_${suffix}`],
|
||||
deaths: stats[`deaths_${suffix}`],
|
||||
wins: stats[`wins_${suffix}`],
|
||||
losses: stats[`losses_${suffix}`]
|
||||
}
|
||||
}
|
||||
|
||||
return [
|
||||
stats[`kills_${suffix}`],
|
||||
stats[`deaths_${suffix}`],
|
||||
devide(stats[`kills_${suffix}`], stats[`deaths_${suffix}`]).toFixed(2),
|
||||
stats[`wins_${suffix}`],
|
||||
stats[`losses_${suffix}`],
|
||||
devide(stats[`wins_${suffix}`], stats[`losses_${suffix}`]).toFixed(2)
|
||||
]
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user