Files
sbd2-frontend/src/components/playlists/PlaylistRow.tsx
JSC dc1124dff6
Some checks failed
Frontend CI / lint (push) Failing after 18s
Frontend CI / build (push) Has been skipped
feat: add delete functionality for playlists with confirmation and error handling
2025-09-21 18:32:33 +02:00

140 lines
5.0 KiB
TypeScript

import { Badge } from '@/components/ui/badge'
import { Button } from '@/components/ui/button'
import { TableCell, TableRow } from '@/components/ui/table'
import type { Playlist } from '@/lib/api/services/playlists'
import { formatDateDistanceToNow } from '@/utils/format-date'
import { formatDuration } from '@/utils/format-duration'
import { cn } from '@/lib/utils'
import { Calendar, Clock, Edit, Heart, Music, Play, Trash2, User } from 'lucide-react'
interface PlaylistRowProps {
playlist: Playlist
onEdit: (playlist: Playlist) => void
onSetCurrent: (playlist: Playlist) => void
onFavoriteToggle?: (playlistId: number, isFavorited: boolean) => void
onDelete?: (playlist: Playlist) => void
}
export function PlaylistRow({ playlist, onEdit, onSetCurrent, onFavoriteToggle, onDelete }: PlaylistRowProps) {
const handleFavoriteToggle = () => {
if (onFavoriteToggle) {
onFavoriteToggle(playlist.id, !playlist.is_favorited)
}
}
return (
<TableRow className="hover:bg-muted/50">
<TableCell>
<div className="flex items-center gap-2">
<Music className="h-4 w-4 text-muted-foreground flex-shrink-0" />
<div className="min-w-0">
<div className="font-medium truncate">{playlist.name}</div>
{playlist.description && (
<div className="text-sm text-muted-foreground truncate">
{playlist.description}
</div>
)}
</div>
</div>
</TableCell>
<TableCell className="text-center">
<div className="flex items-center justify-center gap-1">
{playlist.genre ? (
<Badge variant="secondary">{playlist.genre}</Badge>
) : (
<span className="text-muted-foreground">-</span>
)}
</div>
</TableCell>
<TableCell>
{playlist.user_name ? (
<div className="flex items-center gap-2">
<User className="h-4 w-4 text-muted-foreground" />
<span>{playlist.user_name}</span>
</div>
) : (
<span className="text-muted-foreground">System</span>
)}
</TableCell>
<TableCell>
<div className="flex items-center gap-1">
<Music className="h-3 w-3 text-muted-foreground" />
{playlist.sound_count}
</div>
</TableCell>
<TableCell>
<div className="flex items-center gap-1">
<Clock className="h-3 w-3 text-muted-foreground" />
{formatDuration(playlist.total_duration || 0)}
</div>
</TableCell>
<TableCell>
<div className="flex items-center gap-1">
<Calendar className="h-3 w-3 text-muted-foreground" />
{formatDateDistanceToNow(playlist.created_at)}
</div>
</TableCell>
<TableCell className="text-center">
<div className="flex items-center justify-center gap-1">
{playlist.is_current && <Badge variant="default">Current</Badge>}
{playlist.is_main && <Badge variant="outline">Main</Badge>}
{!playlist.is_current && !playlist.is_main && (
<span className="text-muted-foreground">-</span>
)}
</div>
</TableCell>
<TableCell className="text-center">
<div className="flex items-center justify-center gap-1">
{onFavoriteToggle && (
<Button
size="sm"
variant="ghost"
onClick={handleFavoriteToggle}
className="h-8 w-8 p-0"
title={playlist.is_favorited ? "Remove from favorites" : "Add to favorites"}
>
<Heart
className={cn(
'h-4 w-4 transition-all duration-200',
playlist.is_favorited
? 'fill-current text-red-500 hover:text-red-600'
: 'text-muted-foreground hover:text-foreground'
)}
/>
</Button>
)}
<Button
size="sm"
variant="ghost"
onClick={() => onEdit(playlist)}
className="h-8 w-8 p-0"
title={`Edit "${playlist.name}"`}
>
<Edit className="h-4 w-4" />
</Button>
{!playlist.is_current && (
<Button
size="sm"
variant="ghost"
onClick={() => onSetCurrent(playlist)}
className="h-8 w-8 p-0"
title={`Set "${playlist.name}" as current playlist`}
>
<Play className="h-4 w-4" />
</Button>
)}
{onDelete && !playlist.is_main && playlist.is_deletable && (
<Button
size="sm"
variant="ghost"
onClick={() => onDelete(playlist)}
className="h-8 w-8 p-0 text-destructive hover:text-destructive"
title={`Delete "${playlist.name}"`}
>
<Trash2 className="h-4 w-4" />
</Button>
)}
</div>
</TableCell>
</TableRow>
)
}