Fix showing sorting values, add tooltips and translations to SeriesIndexPoster

This commit is contained in:
Bogdan 2023-05-25 00:36:07 +03:00 committed by Mark McDowall
parent 12374f7f00
commit f90bef6934
3 changed files with 107 additions and 23 deletions

View File

@ -14,7 +14,9 @@ import { Statistics } from 'Series/Series';
import SeriesPoster from 'Series/SeriesPoster'; import SeriesPoster from 'Series/SeriesPoster';
import { executeCommand } from 'Store/Actions/commandActions'; import { executeCommand } from 'Store/Actions/commandActions';
import createUISettingsSelector from 'Store/Selectors/createUISettingsSelector'; import createUISettingsSelector from 'Store/Selectors/createUISettingsSelector';
import formatDateTime from 'Utilities/Date/formatDateTime';
import getRelativeDate from 'Utilities/Date/getRelativeDate'; import getRelativeDate from 'Utilities/Date/getRelativeDate';
import translate from 'Utilities/String/translate';
import createSeriesIndexItemSelector from '../createSeriesIndexItemSelector'; import createSeriesIndexItemSelector from '../createSeriesIndexItemSelector';
import selectPosterOptions from './selectPosterOptions'; import selectPosterOptions from './selectPosterOptions';
import SeriesIndexPosterInfo from './SeriesIndexPosterInfo'; import SeriesIndexPosterInfo from './SeriesIndexPosterInfo';
@ -42,9 +44,8 @@ function SeriesIndexPoster(props: SeriesIndexPosterProps) {
showSearchAction, showSearchAction,
} = useSelector(selectPosterOptions); } = useSelector(selectPosterOptions);
const { showRelativeDates, shortDateFormat, timeFormat } = useSelector( const { showRelativeDates, shortDateFormat, longDateFormat, timeFormat } =
createUISettingsSelector() useSelector(createUISettingsSelector());
);
const { const {
title, title,
@ -52,7 +53,11 @@ function SeriesIndexPoster(props: SeriesIndexPosterProps) {
status, status,
path, path,
titleSlug, titleSlug,
originalLanguage,
network,
nextAiring, nextAiring,
previousAiring,
added,
statistics = {} as Statistics, statistics = {} as Statistics,
images, images,
} = series; } = series;
@ -122,14 +127,14 @@ function SeriesIndexPoster(props: SeriesIndexPosterProps) {
return ( return (
<div className={styles.content}> <div className={styles.content}>
<div className={styles.posterContainer}> <div className={styles.posterContainer} title={title}>
{isSelectMode ? <SeriesIndexPosterSelect seriesId={seriesId} /> : null} {isSelectMode ? <SeriesIndexPosterSelect seriesId={seriesId} /> : null}
<Label className={styles.controls}> <Label className={styles.controls}>
<SpinnerIconButton <SpinnerIconButton
className={styles.action} className={styles.action}
name={icons.REFRESH} name={icons.REFRESH}
title="Refresh series" title={translate('RefreshSeries')}
isSpinning={isRefreshingSeries} isSpinning={isRefreshingSeries}
onPress={onRefreshPress} onPress={onRefreshPress}
/> />
@ -138,7 +143,7 @@ function SeriesIndexPoster(props: SeriesIndexPosterProps) {
<SpinnerIconButton <SpinnerIconButton
className={styles.action} className={styles.action}
name={icons.SEARCH} name={icons.SEARCH}
title="Search for monitored episodes" title={translate('SearchForMonitoredEpisodes')}
isSpinning={isSearchingSeries} isSpinning={isSearchingSeries}
onPress={onSearchPress} onPress={onSearchPress}
/> />
@ -147,13 +152,13 @@ function SeriesIndexPoster(props: SeriesIndexPosterProps) {
<IconButton <IconButton
className={styles.action} className={styles.action}
name={icons.EDIT} name={icons.EDIT}
title="Edit Series" title={translate('EditSeries')}
onPress={onEditSeriesPress} onPress={onEditSeriesPress}
/> />
</Label> </Label>
{status === 'ended' ? ( {status === 'ended' ? (
<div className={styles.ended} title="Ended" /> <div className={styles.ended} title={translate('Ended')} />
) : null} ) : null}
<Link className={styles.link} style={elementStyle} to={link}> <Link className={styles.link} style={elementStyle} to={link}>
@ -185,20 +190,33 @@ function SeriesIndexPoster(props: SeriesIndexPosterProps) {
isStandalone={false} isStandalone={false}
/> />
{showTitle ? <div className={styles.title}>{title}</div> : null} {showTitle ? (
<div className={styles.title} title={title}>
{title}
</div>
) : null}
{showMonitored ? ( {showMonitored ? (
<div className={styles.title}> <div className={styles.title}>
{monitored ? 'Monitored' : 'Unmonitored'} {monitored ? translate('Monitored') : translate('Unmonitored')}
</div> </div>
) : null} ) : null}
{showQualityProfile ? ( {showQualityProfile ? (
<div className={styles.title}>{qualityProfile.name}</div> <div className={styles.title} title={translate('QualityProfile')}>
{qualityProfile.name}
</div>
) : null} ) : null}
{nextAiring ? ( {nextAiring ? (
<div className={styles.nextAiring}> <div
className={styles.nextAiring}
title={`${translate('NextAiring')}: ${formatDateTime(
nextAiring,
longDateFormat,
timeFormat
)}`}
>
{getRelativeDate(nextAiring, shortDateFormat, showRelativeDates, { {getRelativeDate(nextAiring, shortDateFormat, showRelativeDates, {
timeFormat, timeFormat,
timeForToday: true, timeForToday: true,
@ -207,6 +225,10 @@ function SeriesIndexPoster(props: SeriesIndexPosterProps) {
) : null} ) : null}
<SeriesIndexPosterInfo <SeriesIndexPosterInfo
originalLanguage={originalLanguage}
network={network}
previousAiring={previousAiring}
added={added}
seasonCount={seasonCount} seasonCount={seasonCount}
sizeOnDisk={sizeOnDisk} sizeOnDisk={sizeOnDisk}
path={path} path={path}
@ -215,6 +237,7 @@ function SeriesIndexPoster(props: SeriesIndexPosterProps) {
showRelativeDates={showRelativeDates} showRelativeDates={showRelativeDates}
sortKey={sortKey} sortKey={sortKey}
shortDateFormat={shortDateFormat} shortDateFormat={shortDateFormat}
longDateFormat={longDateFormat}
timeFormat={timeFormat} timeFormat={timeFormat}
/> />

View File

@ -1,10 +1,14 @@
import React from 'react'; import React from 'react';
import Language from 'Language/Language';
import QualityProfile from 'typings/QualityProfile'; import QualityProfile from 'typings/QualityProfile';
import formatDateTime from 'Utilities/Date/formatDateTime';
import getRelativeDate from 'Utilities/Date/getRelativeDate'; import getRelativeDate from 'Utilities/Date/getRelativeDate';
import formatBytes from 'Utilities/Number/formatBytes'; import formatBytes from 'Utilities/Number/formatBytes';
import translate from 'Utilities/String/translate';
import styles from './SeriesIndexPosterInfo.css'; import styles from './SeriesIndexPosterInfo.css';
interface SeriesIndexPosterInfoProps { interface SeriesIndexPosterInfoProps {
originalLanguage?: Language;
network?: string; network?: string;
showQualityProfile: boolean; showQualityProfile: boolean;
qualityProfile: QualityProfile; qualityProfile: QualityProfile;
@ -16,11 +20,13 @@ interface SeriesIndexPosterInfoProps {
sortKey: string; sortKey: string;
showRelativeDates: boolean; showRelativeDates: boolean;
shortDateFormat: string; shortDateFormat: string;
longDateFormat: string;
timeFormat: string; timeFormat: string;
} }
function SeriesIndexPosterInfo(props: SeriesIndexPosterInfoProps) { function SeriesIndexPosterInfo(props: SeriesIndexPosterInfoProps) {
const { const {
originalLanguage,
network, network,
qualityProfile, qualityProfile,
showQualityProfile, showQualityProfile,
@ -32,20 +38,44 @@ function SeriesIndexPosterInfo(props: SeriesIndexPosterInfoProps) {
sortKey, sortKey,
showRelativeDates, showRelativeDates,
shortDateFormat, shortDateFormat,
longDateFormat,
timeFormat, timeFormat,
} = props; } = props;
if (sortKey === 'network' && network) { if (sortKey === 'network' && network) {
return <div className={styles.info}>{network}</div>; return (
<div className={styles.info} title={translate('Network')}>
{network}
</div>
);
}
if (sortKey === 'originalLanguage' && !!originalLanguage?.name) {
return (
<div className={styles.info} title={translate('Original Language')}>
{originalLanguage.name}
</div>
);
} }
if (sortKey === 'qualityProfileId' && !showQualityProfile) { if (sortKey === 'qualityProfileId' && !showQualityProfile) {
return <div className={styles.info}>{qualityProfile.name}</div>; return (
<div className={styles.info} title={translate('QualityProfile')}>
{qualityProfile.name}
</div>
);
} }
if (sortKey === 'previousAiring' && previousAiring) { if (sortKey === 'previousAiring' && previousAiring) {
return ( return (
<div className={styles.info}> <div
className={styles.info}
title={`${translate('PreviousAiring')}: ${formatDateTime(
previousAiring,
longDateFormat,
timeFormat
)}`}
>
{getRelativeDate(previousAiring, shortDateFormat, showRelativeDates, { {getRelativeDate(previousAiring, shortDateFormat, showRelativeDates, {
timeFormat, timeFormat,
timeForToday: true, timeForToday: true,
@ -65,27 +95,42 @@ function SeriesIndexPosterInfo(props: SeriesIndexPosterInfoProps) {
} }
); );
return <div className={styles.info}>{`Added ${addedDate}`}</div>; return (
<div
className={styles.info}
title={formatDateTime(added, longDateFormat, timeFormat)}
>
{translate('Added')}: {addedDate}
</div>
);
} }
if (sortKey === 'seasonCount') { if (sortKey === 'seasonCount') {
let seasons = '1 season'; let seasons = translate('OneSeason');
if (seasonCount === 0) { if (seasonCount === 0) {
seasons = 'No seasons'; seasons = translate('NoSeasons');
} else if (seasonCount > 1) { } else if (seasonCount > 1) {
seasons = `${seasonCount} seasons`; seasons = translate('CountSeasons', { count: seasonCount });
} }
return <div className={styles.info}>{seasons}</div>; return <div className={styles.info}>{seasons}</div>;
} }
if (sortKey === 'path') { if (sortKey === 'path') {
return <div className={styles.info}>{path}</div>; return (
<div className={styles.info} title={translate('Path')}>
{path}
</div>
);
} }
if (sortKey === 'sizeOnDisk') { if (sortKey === 'sizeOnDisk') {
return <div className={styles.info}>{formatBytes(sizeOnDisk)}</div>; return (
<div className={styles.info} title={translate('SizeOnDisk')}>
{formatBytes(sizeOnDisk)}
</div>
);
} }
return null; return null;

View File

@ -1,24 +1,40 @@
{ {
"Added": "Added",
"ApplyChanges": "Apply Changes", "ApplyChanges": "Apply Changes",
"AutomaticAdd": "Automatic Add", "AutomaticAdd": "Automatic Add",
"Browser Reload Required": "Browser Reload Required", "Browser Reload Required": "Browser Reload Required",
"CountSeasons": "{count} seasons",
"EditSelectedDownloadClients": "Edit Selected Download Clients", "EditSelectedDownloadClients": "Edit Selected Download Clients",
"EditSelectedImportLists": "Edit Selected Import Lists", "EditSelectedImportLists": "Edit Selected Import Lists",
"EditSelectedIndexers": "Edit Selected Indexers", "EditSelectedIndexers": "Edit Selected Indexers",
"EditSeries": "Edit Series",
"EnableAutomaticSearch": "Enable Automatic Search", "EnableAutomaticSearch": "Enable Automatic Search",
"Enabled": "Enabled",
"EnableInteractiveSearch": "Enable Interactive Search", "EnableInteractiveSearch": "Enable Interactive Search",
"EnableRss": "Enable Rss", "EnableRss": "Enable Rss",
"Enabled": "Enabled",
"Ended": "Ended",
"HiddenClickToShow": "Hidden, click to show", "HiddenClickToShow": "Hidden, click to show",
"HideAdvanced": "Hide Advanced", "HideAdvanced": "Hide Advanced",
"Language": "Language", "Language": "Language",
"Language that Sonarr will use for UI": "Language that Sonarr will use for UI", "Language that Sonarr will use for UI": "Language that Sonarr will use for UI",
"Monitored": "Monitored",
"Network": "Network",
"NextAiring": "Next Airing",
"NoSeasons": "No seasons",
"OneSeason": "1 season",
"OriginalLanguage": "Original Language",
"Path": "Path",
"PreviousAiring": "Previous Airing",
"Priority": "Priority", "Priority": "Priority",
"QualityProfile": "Quality Profile", "QualityProfile": "Quality Profile",
"RefreshSeries": "Refresh Series",
"RemoveCompletedDownloads": "Remove Completed Downloads", "RemoveCompletedDownloads": "Remove Completed Downloads",
"RemoveFailedDownloads": "Remove Failed Downloads", "RemoveFailedDownloads": "Remove Failed Downloads",
"RootFolder": "Root Folder", "RootFolder": "Root Folder",
"SearchForMonitoredEpisodes": "Search for monitored episodes",
"ShowAdvanced": "Show Advanced", "ShowAdvanced": "Show Advanced",
"ShownClickToHide": "Shown, click to hide", "ShownClickToHide": "Shown, click to hide",
"UI Language": "UI Language" "SizeOnDisk": "Size on disk",
"UI Language": "UI Language",
"Unmonitored": "Unmonitored"
} }