import classNames from 'classnames'; import React, { useCallback, useState } from 'react'; import { useDispatch, useSelector } from 'react-redux'; import AlbumTitleLink from 'Album/AlbumTitleLink'; import { Statistics } from 'Artist/Artist'; import ArtistBanner from 'Artist/ArtistBanner'; import ArtistNameLink from 'Artist/ArtistNameLink'; import DeleteArtistModal from 'Artist/Delete/DeleteArtistModal'; import EditArtistModalConnector from 'Artist/Edit/EditArtistModalConnector'; import createArtistIndexItemSelector from 'Artist/Index/createArtistIndexItemSelector'; import ArtistStatusCell from 'Artist/Index/Table/ArtistStatusCell'; import { ARTIST_SEARCH, REFRESH_ARTIST } from 'Commands/commandNames'; import HeartRating from 'Components/HeartRating'; import IconButton from 'Components/Link/IconButton'; import Link from 'Components/Link/Link'; import SpinnerIconButton from 'Components/Link/SpinnerIconButton'; import ProgressBar from 'Components/ProgressBar'; import RelativeDateCellConnector from 'Components/Table/Cells/RelativeDateCellConnector'; import VirtualTableRowCell from 'Components/Table/Cells/VirtualTableRowCell'; import Column from 'Components/Table/Column'; import TagListConnector from 'Components/TagListConnector'; import { icons } from 'Helpers/Props'; import { executeCommand } from 'Store/Actions/commandActions'; import getProgressBarKind from 'Utilities/Artist/getProgressBarKind'; import formatBytes from 'Utilities/Number/formatBytes'; import translate from 'Utilities/String/translate'; import hasGrowableColumns from './hasGrowableColumns'; import selectTableOptions from './selectTableOptions'; import styles from './ArtistIndexRow.css'; interface ArtistIndexRowProps { artistId: number; sortKey: string; columns: Column[]; } function ArtistIndexRow(props: ArtistIndexRowProps) { const { artistId, columns } = props; const { artist, qualityProfile, metadataProfile, isRefreshingArtist, isSearchingArtist, } = useSelector(createArtistIndexItemSelector(props.artistId)); const { showBanners, showSearchAction } = useSelector(selectTableOptions); const { artistName, foreignArtistId, monitored, status, path, nextAlbum, lastAlbum, added, statistics = {} as Statistics, images, artistType, genres = [], ratings, tags = [], isSaving = false, } = artist; const { albumCount = 0, trackCount = 0, trackFileCount = 0, totalTrackCount = 0, sizeOnDisk = 0, } = statistics; const dispatch = useDispatch(); const [hasBannerError, setHasBannerError] = useState(false); const [isEditArtistModalOpen, setIsEditArtistModalOpen] = useState(false); const [isDeleteArtistModalOpen, setIsDeleteArtistModalOpen] = useState(false); const onRefreshPress = useCallback(() => { dispatch( executeCommand({ name: REFRESH_ARTIST, artistId, }) ); }, [artistId, dispatch]); const onSearchPress = useCallback(() => { dispatch( executeCommand({ name: ARTIST_SEARCH, artistId, }) ); }, [artistId, dispatch]); const onBannerLoadError = useCallback(() => { setHasBannerError(true); }, [setHasBannerError]); const onBannerLoad = useCallback(() => { setHasBannerError(false); }, [setHasBannerError]); const onEditArtistPress = useCallback(() => { setIsEditArtistModalOpen(true); }, [setIsEditArtistModalOpen]); const onEditArtistModalClose = useCallback(() => { setIsEditArtistModalOpen(false); }, [setIsEditArtistModalOpen]); const onDeleteArtistPress = useCallback(() => { setIsEditArtistModalOpen(false); setIsDeleteArtistModalOpen(true); }, [setIsDeleteArtistModalOpen]); const onDeleteArtistModalClose = useCallback(() => { setIsDeleteArtistModalOpen(false); }, [setIsDeleteArtistModalOpen]); return ( <> {columns.map((column) => { const { name, isVisible } = column; if (!isVisible) { return null; } if (name === 'status') { return ( ); } if (name === 'sortName') { return ( {showBanners ? ( {hasBannerError && (
{artistName}
)} ) : ( )}
); } if (name === 'artistType') { return ( {artistType} ); } if (name === 'qualityProfileId') { return ( {qualityProfile.name} ); } if (name === 'qualityProfileId') { return ( {qualityProfile.name} ); } if (name === 'metadataProfileId') { return ( {metadataProfile.name} ); } if (name === 'nextAlbum') { if (nextAlbum) { return ( ); } return ( None ); } if (name === 'lastAlbum') { if (lastAlbum) { return ( ); } return ( None ); } if (name === 'added') { return ( ); } if (name === 'albumCount') { return ( {albumCount} ); } if (name === 'trackProgress') { const progress = trackCount ? (trackFileCount / trackCount) * 100 : 100; return ( ); } if (name === 'trackCount') { return ( {totalTrackCount} ); } if (name === 'path') { return ( {path} ); } if (name === 'sizeOnDisk') { return ( {formatBytes(sizeOnDisk)} ); } if (name === 'genres') { const joinedGenres = genres.join(', '); return ( {joinedGenres} ); } if (name === 'ratings') { return ( ); } if (name === 'tags') { return ( ); } if (name === 'actions') { return ( {showSearchAction ? ( ) : null} ); } return null; })} ); } export default ArtistIndexRow;