From 1d95368c8c5af160410652b2d8a7611e9300adea Mon Sep 17 00:00:00 2001 From: assistant Date: Tue, 31 Mar 2026 02:52:30 +0000 Subject: [PATCH] feat(tracks): track upload with validation + linking --- src/components/stages/StageTrackUploader.tsx | 2 +- src/components/stages/StageTracksSection.tsx | 34 ++++++++++++++++++-- 2 files changed, 33 insertions(+), 3 deletions(-) diff --git a/src/components/stages/StageTrackUploader.tsx b/src/components/stages/StageTrackUploader.tsx index afc192b..a19cb3b 100644 --- a/src/components/stages/StageTrackUploader.tsx +++ b/src/components/stages/StageTrackUploader.tsx @@ -91,7 +91,7 @@ export function StageTrackUploader({ stageId }: StageTrackUploaderProps) { - + {pendingTrack && (
diff --git a/src/components/stages/StageTracksSection.tsx b/src/components/stages/StageTracksSection.tsx index e2b03f1..33f2273 100644 --- a/src/components/stages/StageTracksSection.tsx +++ b/src/components/stages/StageTracksSection.tsx @@ -5,6 +5,7 @@ import { Button } from "@/components/ui/button"; import { StageTrackUploader } from "@/components/stages/StageTrackUploader"; import { Music, Plus, Radio, ArrowLeft } from "lucide-react"; import Link from "next/link"; +import { toast } from "sonner"; interface TrackSummary { id: string; @@ -12,6 +13,7 @@ interface TrackSummary { artist: string; duration: number | null; bpm: number | null; + fileUrl: string | null; } interface StageData { @@ -21,13 +23,20 @@ interface StageData { latitude: number; longitude: number; radius: number; - stageTrackLinks: { id: string; track: TrackSummary }[]; + stageTrackLinks: { id: string; track: TrackSummary; loopMode?: string }[]; } interface StageTracksSectionProps { stage: StageData; } +function formatDuration(seconds: number | null): string { + if (seconds == null || isNaN(seconds)) return "--:--"; + const m = Math.floor(seconds / 60); + const s = Math.floor(seconds % 60); + return `${m}:${s.toString().padStart(2, "0")}`; +} + export function StageTracksSection({ stage }: StageTracksSectionProps) { return (
@@ -45,7 +54,25 @@ export function StageTracksSection({ stage }: StageTracksSectionProps) {
{stage.stageTrackLinks.map((link) => (
- + {/* Play button or no-URL placeholder */} + {link.track.fileUrl ? ( + + ) : ( +
+ +
+ )}

{link.track.title}

{link.track.artist}

@@ -53,6 +80,9 @@ export function StageTracksSection({ stage }: StageTracksSectionProps) { {link.track.bpm && ( {Math.round(link.track.bpm)} BPM )} + + {formatDuration(link.track.duration)} +
))}