diff --git a/packages/frontend/src/components/DuplicatesViewer.tsx b/packages/frontend/src/components/DuplicatesViewer.tsx index ab64b85..d7cc5c1 100644 --- a/packages/frontend/src/components/DuplicatesViewer.tsx +++ b/packages/frontend/src/components/DuplicatesViewer.tsx @@ -1,5 +1,5 @@ -import React, { useEffect, useState } from 'react'; -import { Box, VStack, Heading, Text, HStack, Badge, Select, Spinner, Table, Thead, Tr, Th, Tbody, Td, IconButton, Tooltip } from '@chakra-ui/react'; +import React, { useEffect, useMemo, useState } from 'react'; +import { Box, VStack, Heading, Text, HStack, Badge, Select, Spinner, Table, Thead, Tr, Th, Tbody, Td, IconButton, Tooltip, Switch } from '@chakra-ui/react'; import { FiCheck, FiTrash2 } from 'react-icons/fi'; import { api } from '../services/api'; @@ -27,6 +27,7 @@ export const DuplicatesViewer: React.FC = () => { const [loading, setLoading] = useState(false); const [minGroupSize, setMinGroupSize] = useState(2); const [processingGroupKey, setProcessingGroupKey] = useState(null); + const [onlyWithPlaylists, setOnlyWithPlaylists] = useState(false); const loadDuplicates = async (minSize: number) => { setLoading(true); @@ -45,6 +46,11 @@ export const DuplicatesViewer: React.FC = () => { // eslint-disable-next-line react-hooks/exhaustive-deps }, [minGroupSize]); + const filteredGroups = useMemo(() => { + if (!onlyWithPlaylists) return groups; + return groups.filter(g => g.items.some(it => (it.playlists || []).length > 0)); + }, [groups, onlyWithPlaylists]); + return ( @@ -64,16 +70,25 @@ export const DuplicatesViewer: React.FC = () => { + + Only with playlists + setOnlyWithPlaylists(e.target.checked)} + colorScheme="blue" + /> + {loading ? ( Scanning duplicates… - ) : groups.length === 0 ? ( + ) : filteredGroups.length === 0 ? ( No duplicate groups found. ) : ( - {groups.map((group) => ( + {filteredGroups.map((group) => (