New: Add Missing Translations

pull/5399/head
bakerboy448 4 years ago committed by Qstick
parent 86118b4537
commit 699d2be938

@ -208,9 +208,9 @@ class Blacklist extends Component {
<ConfirmModal
isOpen={isConfirmRemoveModalOpen}
kind={kinds.DANGER}
title="Remove Selected"
message={'Are you sure you want to remove the selected items from the blacklist?'}
confirmLabel="Remove Selected"
title={translate('RemoveSelected')}
message={translate('AreYouSureYouWantToRemoveTheSelectedItemsFromBlacklist')}
confirmLabel={translate('RemoveSelected')}
onConfirm={this.onRemoveSelectedConfirmed}
onCancel={this.onConfirmRemoveModalClose}
/>

@ -173,13 +173,13 @@ function HistoryDetails(props) {
switch (reason) {
case 'Manual':
reasonMessage = 'File was deleted by via UI';
reasonMessage = translate('FileWasDeletedByViaUI');
break;
case 'MissingFromDisk':
reasonMessage = 'Radarr was unable to find the file on disk so it was removed';
reasonMessage = translate('MissingFromDisk');
break;
case 'Upgrade':
reasonMessage = 'File was deleted to import an upgrade';
reasonMessage = translate('FileWasDeletedByUpgrade');
break;
default:
reasonMessage = '';

@ -94,7 +94,7 @@ class History extends Component {
isPopulated && !hasError && !items.length &&
<div>
No history found
{translate('NoHistory')}
</div>
}

@ -203,14 +203,14 @@ class Queue extends Component {
{
!isRefreshing && hasError &&
<div>
Failed to load Queue
{translate('FailedToLoadQueue')}
</div>
}
{
isPopulated && !hasError && !items.length &&
<div>
Queue is empty
{translate('QueueIsEmpty')}
</div>
}

@ -45,7 +45,7 @@ function QueueDetails(props) {
<Icon
name={icons.DOWNLOAD}
kind={kinds.WARNING}
title={'Downloaded - Unable to Import: check logs for details'}
title={translate('UnableToImportCheckLogs')}
/>
);
}

@ -81,12 +81,12 @@ class RemoveQueueItemModal extends Component {
onModalClose={this.onModalClose}
>
<ModalHeader>
Remove - {sourceTitle}
{translate('Remove')} - {sourceTitle}
</ModalHeader>
<ModalBody>
<div>
Are you sure you want to remove '{sourceTitle}' from the queue?
{translate('RemoveFromQueueText', [sourceTitle])}
</div>
<FormGroup>

@ -87,7 +87,7 @@ class RemoveQueueItemsModal extends Component {
<ModalBody>
<div className={styles.message}>
Are you sure you want to remove {selectedCount} item{selectedCount > 1 ? 's' : ''} from the queue?
{translate('AreYouSureYouWantToRemoveSelectedItemsFromQueue', [selectedCount, selectedCount > 1 ? 's' : ''])}
</div>
<FormGroup>

@ -116,7 +116,7 @@ class ImportMovie extends Component {
rootFoldersPopulated &&
!unmappedFolders.length ?
<div>
All movies in {path} have been imported
{translate('AllMoviesInPathHaveBeenImported', [path])}
</div> :
null
}

@ -26,27 +26,27 @@ function AppUpdatedModalContent(props) {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Radarr Updated
{translate('RadarrUpdated')}
</ModalHeader>
<ModalBody>
<div>
Version <span className={styles.version}>{version}</span> of Radarr has been installed, in order to get the latest changes you'll need to reload Radarr.
</div>
<div dangerouslySetInnerHTML={{ __html: translate('VersionUpdateText', [`<span className=${styles.version}>${version}</span>`]) }} />
{
isPopulated && !error && !!update &&
<div>
{
!update.changes &&
<div className={styles.maintenance}>Maintenance release</div>
<div className={styles.maintenance}>
{translate('MaintenanceRelease')}
</div>
}
{
!!update.changes &&
<div>
<div className={styles.changes}>
What's new?
{translate('WhatsNew')}
</div>
<UpdateChanges
@ -73,14 +73,14 @@ function AppUpdatedModalContent(props) {
<Button
onPress={onSeeChangesPress}
>
Recent Changes
translate('RecentChanges')
</Button>
<Button
kind={kinds.PRIMARY}
onPress={onModalClose}
>
Reload
translate('Reload')
</Button>
</ModalFooter>
</ModalContent>

@ -168,7 +168,7 @@ class CalendarHeader extends Component {
selectedView={view}
onPress={this.onViewChange}
>
Month
{translate('Month')}
</ViewMenuItem>
}
@ -177,7 +177,7 @@ class CalendarHeader extends Component {
selectedView={view}
onPress={this.onViewChange}
>
Week
{translate('Week')}
</ViewMenuItem>
<ViewMenuItem
@ -185,7 +185,7 @@ class CalendarHeader extends Component {
selectedView={view}
onPress={this.onViewChange}
>
Forecast
{translate('Forecast')}
</ViewMenuItem>
<ViewMenuItem

@ -1,6 +1,7 @@
import PropTypes from 'prop-types';
import React from 'react';
import { icons, kinds } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
import LegendIconItem from './LegendIconItem';
import LegendItem from './LegendItem';
import styles from './Legend.css';
@ -16,10 +17,10 @@ function Legend(props) {
if (showCutoffUnmetIcon) {
iconsToShow.push(
<LegendIconItem
name="Cutoff Not Met"
name={translate('CutoffUnmet')}
icon={icons.MOVIE_FILE}
kind={kinds.WARNING}
tooltip="Quality or language cutoff has not been met"
tooltip={translate('QualityOrLangCutoffHasNotBeenMet')}
/>
);
}
@ -28,28 +29,28 @@ function Legend(props) {
<div className={styles.legend}>
<div>
<LegendItem
status="unreleased"
tooltip="Movie hasn't released yet"
status={translate('Unreleased')}
tooltip={translate('MovieHasntReleasedYet')}
colorImpairedMode={colorImpairedMode}
/>
<LegendItem
status="unmonitored"
tooltip="Movie is unmonitored"
status={translate('Unmonitored')}
tooltip={translate('MovieIsUnmonitored')}
colorImpairedMode={colorImpairedMode}
/>
</div>
<div>
<LegendItem
status="downloading"
tooltip="Movie is currently downloading"
status={translate('Downloading')}
tooltip={translate('MovieIsDownloading')}
colorImpairedMode={colorImpairedMode}
/>
<LegendItem
status="downloaded"
tooltip="Movie was downloaded and sorted"
status={translate('Downloaded')}
tooltip={translate('MovieWasDownloadedAndSorted')}
colorImpairedMode={colorImpairedMode}
/>
</div>

@ -107,7 +107,7 @@ class CalendarOptionsModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Calendar Options
{translate('CalendarOptions')}
</ModalHeader>
<ModalBody>

@ -109,7 +109,7 @@ class CalendarLinkModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Radarr Calendar Feed
{translate('RadarrCalendarFeed')}
</ModalHeader>
<ModalBody>

@ -5,16 +5,17 @@ import SelectInput from 'Components/Form/SelectInput';
import TextInput from 'Components/Form/TextInput';
import { IN_LAST, IN_NEXT, NOT_IN_LAST, NOT_IN_NEXT } from 'Helpers/Props/filterTypes';
import isString from 'Utilities/String/isString';
import translate from 'Utilities/String/translate';
import { NAME } from './FilterBuilderRowValue';
import styles from './DateFilterBuilderRowValue.css';
const timeOptions = [
{ key: 'seconds', value: 'seconds' },
{ key: 'minutes', value: 'minutes' },
{ key: 'hours', value: 'hours' },
{ key: 'days', value: 'days' },
{ key: 'weeks', value: 'weeks' },
{ key: 'months', value: 'months' }
{ key: 'seconds', value: translate('Seconds') },
{ key: 'minutes', value: translate('Minutes') },
{ key: 'hours', value: translate('Hours') },
{ key: 'days', value: translate('Days') },
{ key: 'weeks', value: translate('Weeks') },
{ key: 'months', value: translate('Months') }
];
function isInFilter(filterType) {

@ -1,12 +1,13 @@
import PropTypes from 'prop-types';
import React from 'react';
import translate from 'Utilities/String/translate';
import SelectInput from './SelectInput';
const availabilityOptions = [
{ key: 'announced', value: 'Announced' },
{ key: 'inCinemas', value: 'In Cinemas' },
{ key: 'released', value: 'Released' },
{ key: 'preDB', value: 'PreDB' }
{ key: 'announced', value: translate('Announced') },
{ key: 'inCinemas', value: translate('InCinemas') },
{ key: 'released', value: translate('Released') },
{ key: 'preDB', value: translate('PreDB') }
];
function AvailabilitySelectInput(props) {

@ -279,7 +279,7 @@ class DiscoverMovie extends Component {
<PageToolbar>
<PageToolbarSection>
<PageToolbarButton
label='Refresh Lists'
label={translate('RefreshLists')}
iconName={icons.REFRESH}
isSpinning={isSyncingLists}
isDisabled={hasNoMovie}

@ -138,8 +138,8 @@ class DiscoverMovieFooter extends Component {
} = this.state;
const monitoredOptions = [
{ key: true, value: 'Monitored' },
{ key: false, value: 'Unmonitored' }
{ key: true, value: translate('Monitored') },
{ key: false, value: translate('Unmonitored') }
];
return (

@ -38,7 +38,7 @@ class ExcludeMovieModalContent extends Component {
<ModalBody>
<div className={styles.pathContainer}>
Exclude {title}? This will prevent Radarr from adding automatically via list sync.
{translate('ExcludeTitle', [title])}
</div>
</ModalBody>

@ -4,6 +4,7 @@ import MenuContent from 'Components/Menu/MenuContent';
import SortMenu from 'Components/Menu/SortMenu';
import SortMenuItem from 'Components/Menu/SortMenuItem';
import { align, sortDirections } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
function DiscoverMovieSortMenu(props) {
const {
@ -25,7 +26,7 @@ function DiscoverMovieSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
Status
{translate('Status')}
</SortMenuItem>
<SortMenuItem
@ -34,7 +35,7 @@ function DiscoverMovieSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
Title
{translate('Title')}
</SortMenuItem>
<SortMenuItem
@ -43,7 +44,7 @@ function DiscoverMovieSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
Studio
{translate('Studio')}
</SortMenuItem>
<SortMenuItem
@ -52,7 +53,7 @@ function DiscoverMovieSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
In Cinemas
{translate('InCinemas')}
</SortMenuItem>
<SortMenuItem
@ -61,7 +62,7 @@ function DiscoverMovieSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
Physical Release
{translate('PhysicalRelease')}
</SortMenuItem>
<SortMenuItem
@ -70,7 +71,7 @@ function DiscoverMovieSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
Digital Release
{translate('DigitalRelease')}
</SortMenuItem>
<SortMenuItem
@ -79,7 +80,7 @@ function DiscoverMovieSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
Runtime
{translate('Runtime')}
</SortMenuItem>
<SortMenuItem
@ -88,7 +89,7 @@ function DiscoverMovieSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
Rating
{translate('Rating')}
</SortMenuItem>
<SortMenuItem
@ -97,7 +98,7 @@ function DiscoverMovieSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
Certification
{translate('Certification')}
</SortMenuItem>
</MenuContent>
</SortMenu>

@ -4,6 +4,7 @@ import MenuContent from 'Components/Menu/MenuContent';
import ViewMenu from 'Components/Menu/ViewMenu';
import ViewMenuItem from 'Components/Menu/ViewMenuItem';
import { align } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
function DiscoverMovieViewMenu(props) {
const {
@ -23,7 +24,7 @@ function DiscoverMovieViewMenu(props) {
selectedView={view}
onPress={onViewSelect}
>
Table
{translate('Table')}
</ViewMenuItem>
<ViewMenuItem
@ -31,7 +32,7 @@ function DiscoverMovieViewMenu(props) {
selectedView={view}
onPress={onViewSelect}
>
Posters
{translate('Posters')}
</ViewMenuItem>
<ViewMenuItem
@ -39,7 +40,7 @@ function DiscoverMovieViewMenu(props) {
selectedView={view}
onPress={onViewSelect}
>
Overview
{translate('Overview')}
</ViewMenuItem>
</MenuContent>
</ViewMenu>

@ -21,7 +21,7 @@ function NoDiscoverMovie(props) {
return (
<div>
<div className={styles.message}>
No list items or recommendations found, to get started you'll want to add a new movie, import some existing ones, or add a list.
{translate('NoListRecommendations')}
</div>
<div className={styles.buttonContainer}>

@ -2,6 +2,7 @@ import PropTypes from 'prop-types';
import React from 'react';
import { icons } from 'Helpers/Props';
import dimensions from 'Styles/Variables/dimensions';
import translate from 'Utilities/String/translate';
import DiscoverMovieOverviewInfoRow from './DiscoverMovieOverviewInfoRow';
import styles from './DiscoverMovieOverviewInfo.css';
@ -54,7 +55,7 @@ function getInfoRowProps(row, props) {
if (name === 'year') {
return {
title: 'Year',
title: translate('Year'),
iconName: icons.CALENDAR,
label: props.year
};
@ -62,7 +63,7 @@ function getInfoRowProps(row, props) {
if (name === 'genres') {
return {
title: 'Genres',
title: translate('Genres'),
iconName: icons.GENRE,
label: props.genres.slice(0, 2).join(', ')
};
@ -70,7 +71,7 @@ function getInfoRowProps(row, props) {
if (name === 'ratings') {
return {
title: 'Ratings',
title: translate('Ratings'),
iconName: icons.HEART,
label: `${props.ratings.value * 10}%`
};
@ -78,7 +79,7 @@ function getInfoRowProps(row, props) {
if (name === 'certification') {
return {
title: 'Certification',
title: translate('Certification'),
iconName: icons.FILM,
label: props.certification
};
@ -86,7 +87,7 @@ function getInfoRowProps(row, props) {
if (name === 'studio') {
return {
title: 'Studio',
title: translate('Studio'),
iconName: icons.STUDIO,
label: props.studio
};

@ -14,9 +14,9 @@ import { inputTypes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
const posterSizeOptions = [
{ key: 'small', value: 'Small' },
{ key: 'medium', value: 'Medium' },
{ key: 'large', value: 'Large' }
{ key: 'small', value: translate('Small') },
{ key: 'medium', value: translate('Medium') },
{ key: 'large', value: translate('Large') }
];
class DiscoverMovieOverviewOptionsModalContent extends Component {

@ -14,9 +14,9 @@ import { inputTypes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
const posterSizeOptions = [
{ key: 'small', value: 'Small' },
{ key: 'medium', value: 'Medium' },
{ key: 'large', value: 'Large' }
{ key: 'small', value: translate('Small') },
{ key: 'medium', value: translate('Medium') },
{ key: 'large', value: translate('Large') }
];
class DiscoverMoviePosterOptionsModalContent extends Component {

@ -17,11 +17,11 @@ import styles from './InteractiveImportSelectFolderModalContent.css';
const recentFoldersColumns = [
{
name: 'folder',
label: 'Folder'
label: translate('Folder')
},
{
name: 'lastUsed',
label: 'Last Used'
label: translate('LastUsed')
},
{
name: 'actions',

@ -69,8 +69,8 @@ const columns = [
];
const filterExistingFilesOptions = {
ALL: 'all',
NEW: 'new'
ALL: translate('All'),
NEW: translate('New')
};
const importModeOptions = [
@ -198,25 +198,25 @@ class InteractiveImportModalContent extends Component {
} = this.state;
const selectedIds = this.getSelectedIds();
const errorMessage = getErrorMessage(error, 'Unable to load manual import items');
const errorMessage = getErrorMessage(error, translate('UnableToLoadManualImportItems'));
const bulkSelectOptions = [
{ key: SELECT, value: 'Select...', disabled: true },
{ key: LANGUAGE, value: 'Select Language' },
{ key: QUALITY, value: 'Select Quality' }
];
{
key: SELECT, value: translate('SelectDotDot'), disabled: true },
{ key: LANGUAGE, value: translate('SelectLanguage') },
{ key: QUALITY, value: translate('SelectQuality') }];
if (allowMovieChange) {
bulkSelectOptions.splice(1, 0, {
key: MOVIE,
value: 'Select Movie'
value: translate('SelectMovie')
});
}
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Manual Import - {title || folder}
{translate('ManualImport')} - {title || folder}
</ModalHeader>
<ModalBody scrollDirection={scrollDirections.BOTH}>
@ -232,7 +232,7 @@ class InteractiveImportModalContent extends Component {
<div className={styles.filterText}>
{
filterExistingFiles ? 'Unmapped Files Only' : 'All Files'
filterExistingFiles ? translate('UnmappedFilesOnly') : translate('AllFiles')
}
</div>
</MenuButton>
@ -243,7 +243,7 @@ class InteractiveImportModalContent extends Component {
isSelected={!filterExistingFiles}
onPress={this.onFilterExistingFilesChange}
>
All Files
{translate('AllFiles')}
</SelectedMenuItem>
<SelectedMenuItem
@ -251,7 +251,7 @@ class InteractiveImportModalContent extends Component {
isSelected={filterExistingFiles}
onPress={this.onFilterExistingFilesChange}
>
Unmapped Files Only
{translate('UnmappedFilesOnly')}
</SelectedMenuItem>
</MenuContent>
</Menu>
@ -302,7 +302,7 @@ class InteractiveImportModalContent extends Component {
{
isPopulated && !items.length && !isFetching &&
'No video files were found in the selected folder'
translate('NoVideoFilesFoundSelectedFolder')
}
</ModalBody>
@ -345,7 +345,7 @@ class InteractiveImportModalContent extends Component {
isDisabled={!selectedIds.length || !!invalidRowsSelected.length}
onPress={this.onImportSelectedPress}
>
Import
{translate('Import')}
</Button>
</div>
</ModalFooter>

@ -7,6 +7,7 @@ import * as commandNames from 'Commands/commandNames';
import { executeCommand } from 'Store/Actions/commandActions';
import { clearInteractiveImport, fetchInteractiveImportItems, setInteractiveImportMode, setInteractiveImportSort } from 'Store/Actions/interactiveImportActions';
import createClientSideCollectionSelector from 'Store/Selectors/createClientSideCollectionSelector';
import translate from 'Utilities/String/translate';
import InteractiveImportModalContent from './InteractiveImportModalContent';
function createMapStateToProps() {
@ -113,17 +114,17 @@ class InteractiveImportModalContentConnector extends Component {
} = item;
if (!movie) {
this.setState({ interactiveImportErrorMessage: 'Movie must be chosen for each selected file' });
this.setState({ interactiveImportErrorMessage: translate('InteractiveImportErrMovie') });
return false;
}
if (!quality) {
this.setState({ interactiveImportErrorMessage: 'Quality must be chosen for each selected file' });
this.setState({ interactiveImportErrorMessage: translate('InteractiveImportErrQuality') });
return false;
}
if (!languages) {
this.setState({ interactiveImportErrorMessage: 'Language must be chosen for each selected file' });
this.setState({ interactiveImportErrorMessage: translate('InteractiveImportErrLanguage') });
return false;
}

@ -77,7 +77,7 @@ class SelectLanguageModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Manual Import - Select Language
{translate('ManualImportSelectLanguage')}
</ModalHeader>
<ModalBody>
@ -128,7 +128,7 @@ class SelectLanguageModalContent extends Component {
kind={kinds.SUCCESS}
onPress={this.onLanguageSelect}
>
Select Languges
{translate('SelectLanguges')}
</Button>
</ModalFooter>
</ModalContent>

@ -173,7 +173,7 @@ class SelectMovieModalContent extends Component {
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
<div className={styles.header}>
Manual Import - Select Movie
{translate('ManualImportSelectMovie')}
</div>
</ModalHeader>

@ -81,7 +81,7 @@ class SelectQualityModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Manual Import - Select Quality
{translate('ManualImportSelectQuality')}
</ModalHeader>
<ModalBody>
@ -146,7 +146,7 @@ class SelectQualityModalContent extends Component {
kind={kinds.SUCCESS}
onPress={this.onQualitySelect}
>
Select Quality
{translate('SelectQuality')}
</Button>
</ModalFooter>
</ModalContent>

@ -128,21 +128,21 @@ function InteractiveSearchContent(props) {
{
!isFetching && !!error &&
<div>
Unable to load results for this movie search. Try again later
{translate('UnableToLoadResultsIntSearch')}
</div>
}
{
!isFetching && isPopulated && !totalReleasesCount &&
<div>
No results found
{translate('NoResultsFound')}
</div>
}
{
!!totalReleasesCount && isPopulated && !items.length &&
<div>
All results are hidden by the applied filter
{translate('AllResultsHiddenFilter')}
</div>
}
@ -176,7 +176,7 @@ function InteractiveSearchContent(props) {
{
totalReleasesCount !== items.length && !!items.length &&
<div className={styles.filteredMessage}>
Some results are hidden by the applied filter
{translate('SomeResultsHiddenFilter')}
</div>
}
</div>

@ -35,12 +35,12 @@ function getDownloadTooltip(isGrabbing, isGrabbed, grabError) {
if (isGrabbing) {
return '';
} else if (isGrabbed) {
return 'Added to downloaded queue';
return translate('AddedToDownloadQueue');
} else if (grabError) {
return grabError;
}
return 'Add to downloaded queue';
return translate('AddToDownloadQueue');
}
class InteractiveSearchRow extends Component {

@ -66,12 +66,12 @@ class DeleteMovieModalContent extends Component {
const deleteFiles = this.state.deleteFiles;
const addImportExclusion = this.state.addImportExclusion;
let deleteFilesLabel = `Delete ${movieFileCount} Movie Files`;
let deleteFilesHelpText = 'Delete the movie files and movie folder';
let deleteFilesLabel = translate('DeleteFilesLabel', [movieFileCount]);
let deleteFilesHelpText = translate('DeleteFilesHelpText');
if (movieFileCount === 0) {
deleteFilesLabel = 'Delete Movie Folder';
deleteFilesHelpText = 'Delete the movie folder and it\'s contents';
deleteFilesLabel = translate('DeleteMovieFolderLabel');
deleteFilesHelpText = translate('DeleteMovieFolderHelpText');
}
return (
@ -79,7 +79,7 @@ class DeleteMovieModalContent extends Component {
onModalClose={onModalClose}
>
<ModalHeader>
Delete - {title}
{translate('DeleteHeader', [title])}
</ModalHeader>
<ModalBody>
@ -108,23 +108,29 @@ class DeleteMovieModalContent extends Component {
{
deleteFiles &&
<div className={styles.deleteFilesMessage}>
<div>The movie folder <strong>{path}</strong> and all it's content will be deleted.</div>
<div>
{translate('DeleteTheMovieFolder', [path])}
</div>
{
!!movieFileCount &&
<div>{movieFileCount} movie files totaling {formatBytes(sizeOnDisk)}</div>
<div>
{movieFileCount} {translate('MovieFilesTotaling')} {formatBytes(sizeOnDisk)}
</div>
}
</div>
}
<FormGroup>
<FormLabel>Add List Exclusion</FormLabel>
<FormLabel>
{translate('AddListExclusion')}
</FormLabel>
<FormInputGroup
type={inputTypes.CHECK}
name="addImportExclusion"
value={addImportExclusion}
helpText="Prevent movie from being added to Radarr by lists"
helpText={translate('AddImportExclusionHelpText')}
kind={kinds.DANGER}
onChange={this.onAddImportExclusionChange}
/>

@ -3,6 +3,7 @@ import React from 'react';
import Label from 'Components/Label';
import Link from 'Components/Link/Link';
import { kinds, sizes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
import styles from './MovieDetailsLinks.css';
function MovieDetailsLinks(props) {
@ -23,7 +24,7 @@ function MovieDetailsLinks(props) {
kind={kinds.INFO}
size={sizes.LARGE}
>
TMDb
{translate('TMDb')}
</Label>
</Link>
@ -36,7 +37,7 @@ function MovieDetailsLinks(props) {
kind={kinds.INFO}
size={sizes.LARGE}
>
Trakt
{translate('Trakt')}
</Label>
</Link>
@ -51,7 +52,7 @@ function MovieDetailsLinks(props) {
kind={kinds.INFO}
size={sizes.LARGE}
>
IMDb
{translate('IMDb')}
</Label>
</Link>
}
@ -67,7 +68,7 @@ function MovieDetailsLinks(props) {
kind={kinds.INFO}
size={sizes.LARGE}
>
Movie Chat
{translate('MovieChat')}
</Label>
</Link>
}
@ -83,7 +84,7 @@ function MovieDetailsLinks(props) {
kind={kinds.DANGER}
size={sizes.LARGE}
>
Trailer
{translate('Trailer')}
</Label>
</Link>
}

@ -85,7 +85,7 @@ class MovieDetailsPageConnector extends Component {
if (!isFetching && !!error) {
return (
<div className={styles.errorMessage}>
{getErrorMessage(error, 'Failed to load movie from API')}
{getErrorMessage(error, translate('FailedToLoadMovieFromAPI'))}
</div>
);
}

@ -48,12 +48,16 @@ class MovieTitlesTableContent extends Component {
{
!isFetching && !!error &&
<div className={styles.blankpad}>Unable to load alternative titles.</div>
<div className={styles.blankpad}>
{translate('UnableToLoadAltTitle')}
</div>
}
{
isPopulated && !hasItems && !error &&
<div className={styles.blankpad}>No alternative titles.</div>
<div className={styles.blankpad}>
{translate('NoAltTitle')}
</div>
}
{

@ -60,7 +60,7 @@ class DeleteMovieModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Delete Selected Movie(s)
{translate('DeleteSelectedMovie')}
</ModalHeader>
<ModalBody>

@ -154,9 +154,9 @@ class MovieEditorFooter extends Component {
} = this.state;
const monitoredOptions = [
{ key: NO_CHANGE, value: 'No Change', disabled: true },
{ key: 'monitored', value: 'Monitored' },
{ key: 'unmonitored', value: 'Unmonitored' }
{ key: NO_CHANGE, value: translate('NoChange'), disabled: true },
{ key: 'monitored', value: translate('Monitored') },
{ key: 'unmonitored', value: translate('Unmonitored') }
];
return (

@ -21,12 +21,12 @@ function OrganizeMovieModalContent(props) {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Organize Selected Movies
{translate('OrganizeSelectedMovies')}
</ModalHeader>
<ModalBody>
<Alert>
Tip: To preview a rename... select "Cancel" then click any movie title and use the
{translate('PreviewRenameHelpText')}
<Icon
className={styles.renameIcon}
name={icons.ORGANIZE}
@ -34,7 +34,7 @@ function OrganizeMovieModalContent(props) {
</Alert>
<div className={styles.message}>
Are you sure you want to organize all files in the {movieTitles.length} selected movie(s)?
{translate('OrganizeConfirm', [movieTitles.length])}
</div>
<ul>
@ -59,7 +59,7 @@ function OrganizeMovieModalContent(props) {
kind={kinds.DANGER}
onPress={onOrganizeMoviePress}
>
Organize
{translate('Organize')}
</Button>
</ModalFooter>
</ModalContent>

@ -61,9 +61,9 @@ class TagsModalContent extends Component {
} = this.state;
const applyTagsOptions = [
{ key: 'add', value: 'Add' },
{ key: 'remove', value: 'Remove' },
{ key: 'replace', value: 'Replace' }
{ key: 'add', value: translate('Add') },
{ key: 'remove', value: translate('Remove') },
{ key: 'replace', value: translate('Replace') }
];
return (

@ -72,12 +72,16 @@ class MovieHistoryTableContent extends Component {
{
!isFetching && !!error &&
<div className={styles.blankpad}>Unable to load history</div>
<div className={styles.blankpad}>
{translate('UnableToLoadHistory')}
</div>
}
{
isPopulated && !hasItems && !error &&
<div className={styles.blankpad}>No history</div>
<div className={styles.blankpad}>
{translate('NoHistory')}
</div>
}
{

@ -5,6 +5,7 @@ import MenuContent from 'Components/Menu/MenuContent';
import SearchMenuItem from 'Components/Menu/SearchMenuItem';
import ToolbarMenuButton from 'Components/Menu/ToolbarMenuButton';
import { align, icons } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
class MovieIndexSearchMenu extends Component {
@ -29,14 +30,14 @@ class MovieIndexSearchMenu extends Component {
name="missingMoviesSearch"
onPress={onSearchPress}
>
Search Missing
{translate('SearchMissing')}
</SearchMenuItem>
<SearchMenuItem
name="cutoffUnmetMoviesSearch"
onPress={onSearchPress}
>
Search Cutoff Unmet
{translate('SearchCutoffUnmet')}
</SearchMenuItem>
</MenuContent>
</Menu>

@ -26,7 +26,7 @@ function MovieIndexSortMenu(props) {
sortDirection={sortDirection}
onPress={onSortSelect}
>
Monitored/Status
{translate('MonitoredStatus')}
</SortMenuItem>
<SortMenuItem

@ -519,7 +519,7 @@ class MovieIndex extends Component {
{
!isFetching && !!error &&
<div className={styles.errorMessage}>
{getErrorMessage(error, 'Failed to load movie from API')}
{getErrorMessage(error, translate('FailedToLoadMovieFromAPI'))}
</div>
}
@ -610,7 +610,7 @@ class MovieIndex extends Component {
Are you sure you want to perform mass movie search for {isMovieEditorActive && selectedMovieIds.length > 0 ? selectedMovieIds.length : this.props.items.length} movies?
</div>
<div>
This cannot be cancelled once started without restarting Radarr.
{translate('ThisCannotBeCancelled')}
</div>
</div>
}

@ -14,9 +14,9 @@ import { inputTypes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
const posterSizeOptions = [
{ key: 'small', value: 'Small' },
{ key: 'medium', value: 'Medium' },
{ key: 'large', value: 'Large' }
{ key: 'small', value: translate('Small') },
{ key: 'medium', value: translate('Medium') },
{ key: 'large', value: translate('Large') }
];
class MovieIndexOverviewOptionsModalContent extends Component {

@ -242,7 +242,7 @@ class MovieIndexPoster extends Component {
{
showMonitored &&
<div className={styles.title}>
{monitored ? 'Monitored' : 'Unmonitored'}
{monitored ? translate('Monitored') : translate('Unmonitored')}
</div>
}

@ -14,9 +14,9 @@ import { inputTypes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
const posterSizeOptions = [
{ key: 'small', value: 'Small' },
{ key: 'medium', value: 'Medium' },
{ key: 'large', value: 'Large' }
{ key: 'small', value: translate('Small') },
{ key: 'medium', value: translate('Medium') },
{ key: 'large', value: translate('Large') }
];
class MovieIndexPosterOptionsModalContent extends Component {

@ -7,6 +7,7 @@ import ModalContent from 'Components/Modal/ModalContent';
import ModalFooter from 'Components/Modal/ModalFooter';
import ModalHeader from 'Components/Modal/ModalHeader';
import { kinds, sizes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
import styles from './MoveMovieModal.css';
function MoveMovieModal(props) {
@ -40,19 +41,19 @@ function MoveMovieModal(props) {
onModalClose={onSavePress}
>
<ModalHeader>
Move Files
{translate('MoveFiles')}
</ModalHeader>
<ModalBody>
{
destinationRootFolder ?
`Would you like to move the movie folders to '${destinationRootFolder}'?` :
`Would you like to move the movie files from '${originalPath}' to '${destinationPath}'?`
translate('MovieFolders1', [destinationRootFolder]) :
translate('MovieFolders2', [originalPath, destinationPath])
}
{
destinationRootFolder ?
<div>
This will also rename the movie folder per the movie folder format in settings.
{translate('FolderMoveRenameWarning')}
</div> :
null
}
@ -63,14 +64,14 @@ function MoveMovieModal(props) {
className={styles.doNotMoveButton}
onPress={onSavePress}
>
No, I'll Move the Files Myself
{translate('NoMoveFilesSelf')}
</Button>
<Button
kind={kinds.DANGER}
onPress={onMoveMoviePress}
>
Yes, Move the Files
{translate('YesMoveFiles')}
</Button>
</ModalFooter>
</ModalContent>

@ -35,7 +35,7 @@ function MovieLanguage(props) {
className={className}
kind={isCutoffNotMet ? kinds.INVERSE : kinds.DEFAULT}
>
Multi-Language
{translate('MultiLanguage')}
</Label>
}
title={translate('Languages')}

@ -1,30 +1,31 @@
import { icons } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
export function getMovieStatusDetails(status) {
let statusDetails = {
icon: icons.ANNOUNCED,
title: 'Announced',
message: 'Movie is announced'
title: translate('Announced'),
message: translate('AnnoucedMsg')
};
if (status === 'deleted') {
statusDetails = {
icon: icons.MOVIE_DELETED,
title: 'Deleted',
message: 'Movie was deleted from TMDb'
title: translate('Deleted'),
message: translate('DeletedMsg')
};
} else if (status === 'inCinemas') {
statusDetails = {
icon: icons.IN_CINEMAS,
title: 'In Cinemas',
message: 'Movie is in Cinemas'
title: translate('InCinemas'),
message: translate('InCinemasMsg')
};
} else if (status === 'released') {
statusDetails = {
icon: icons.MOVIE_FILE,
title: 'Released',
message: 'Movie is released'
title: translate('Released'),
message: translate('ReleasedMsg')
};
}

@ -21,7 +21,7 @@ function NoMovie(props) {
return (
<div>
<div className={styles.message}>
No movies found, to get started you'll want to add a new movie or import some existing ones.
{translate('NoMoviesExist')}
</div>
<div className={styles.buttonContainer}>

@ -11,7 +11,7 @@ import styles from './MovieFileEditorTableContent.css';
const columns = [
{
name: 'title',
label: 'Relative Path',
label: translate('RelativePath'),
isVisible: true
},
{

@ -81,7 +81,7 @@ class SelectQualityModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Manual Import - Select Quality
{translate('ManualImportSelectQuality')}
</ModalHeader>
<ModalBody>
@ -146,7 +146,7 @@ class SelectQualityModalContent extends Component {
kind={kinds.SUCCESS}
onPress={this.onQualitySelect}
>
Select Quality
{translate('SelectQuality')}
</Button>
</ModalFooter>
</ModalContent>

@ -154,7 +154,7 @@ class CustomFormat extends Component {
message={
<div>
<div>
Are you sure you want to delete custom format '{name}'?
{translate('AreYouSureYouWantToDeleteFormat', [name])}
</div>
</div>
}

@ -100,7 +100,7 @@ class EditCustomFormatModalContent extends Component {
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
{id ? 'Edit Custom Format' : 'Add Custom Format'}
{id ? translate('EditCustomFormat') : translate('AddCustomFormat')}
</ModalHeader>
<ModalBody>
@ -125,7 +125,7 @@ class EditCustomFormatModalContent extends Component {
>
<FormGroup>
<FormLabel>
Name
{translate('Name')}
</FormLabel>
<FormInputGroup

@ -58,7 +58,7 @@ class AddSpecificationItem extends Component {
size={sizes.SMALL}
onPress={this.onSpecificationSelect}
>
Custom
{translate('Custom')}
</Button>
<Menu className={styles.presetsMenu}>
@ -66,7 +66,7 @@ class AddSpecificationItem extends Component {
className={styles.presetsMenuButton}
size={sizes.SMALL}
>
Presets
{translate('Presets')}
</Button>
<MenuContent>

@ -64,7 +64,7 @@ function EditSpecificationModalContent(props) {
<FormGroup>
<FormLabel>
Name
{translate('Name')}
</FormLabel>
<FormInputGroup
@ -92,7 +92,7 @@ function EditSpecificationModalContent(props) {
<FormGroup>
<FormLabel>
Negate
{translate('Negate')}
</FormLabel>
<FormInputGroup
@ -106,7 +106,7 @@ function EditSpecificationModalContent(props) {
<FormGroup>
<FormLabel>
Required
{translate('Required')}
</FormLabel>
<FormInputGroup

@ -92,14 +92,14 @@ class Specification extends Component {
{
negate &&
<Label kind={kinds.DANGER}>
{'Negated'}
{translate('Negated')}
</Label>
}
{
required &&
<Label kind={kinds.SUCCESS}>
{'Required'}
{translate('Required')}
</Label>
}
</div>
@ -118,7 +118,7 @@ class Specification extends Component {
message={
<div>
<div>
Are you sure you want to delete format tag '{name}'?
{translate('AreYouSureYouWantToDeleteFormat', [name])}
</div>
</div>
}

@ -58,7 +58,7 @@ class AddDownloadClientItem extends Component {
size={sizes.SMALL}
onPress={this.onDownloadClientSelect}
>
Custom
{translate('Custom')}
</Button>
<Menu className={styles.presetsMenu}>
@ -66,7 +66,7 @@ class AddDownloadClientItem extends Component {
className={styles.presetsMenuButton}
size={sizes.SMALL}
>
Presets
{translate('Presets')}
</Button>
<MenuContent>

@ -32,7 +32,7 @@ class AddDownloadClientModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Add DownloadClient
{translate('AddDownloadClient')}
</ModalHeader>
<ModalBody>

@ -73,13 +73,13 @@ class DownloadClient extends Component {
{
enable ?
<Label kind={kinds.SUCCESS}>
Enabled
{translate('Enabled')}
</Label> :
<Label
kind={kinds.DISABLED}
outline={true}
>
Disabled
{translate('Disabled')}
</Label>
}
@ -89,7 +89,7 @@ class DownloadClient extends Component {
kind={kinds.DISABLED}
outline={true}
>
Priority: {priority}
{translate('PrioritySettings', [priority])}
</Label>
}
</div>

@ -53,7 +53,7 @@ class EditDownloadClientModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
{`${id ? 'Edit' : 'Add'} Download Client - ${implementationName}`}
{`${id ? translate('Edit') : translate('Add')} ${translate('DownloadClient')} - ${implementationName}`}
</ModalHeader>
<ModalBody>

@ -8,9 +8,9 @@ import { inputTypes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
const logLevelOptions = [
{ key: 'info', value: 'Info' },
{ key: 'debug', value: 'Debug' },
{ key: 'trace', value: 'Trace' }
{ key: 'info', value: translate('Info') },
{ key: 'debug', value: translate('Debug') },
{ key: 'trace', value: translate('Trace') }
];
function LoggingSettings(props) {

@ -25,9 +25,9 @@ function ProxySettings(props) {
} = settings;
const proxyTypeOptions = [
{ key: 'http', value: 'HTTP(S)' },
{ key: 'socks4', value: 'Socks4' },
{ key: 'socks5', value: 'Socks5 (Support TOR)' }
{ key: 'http', value: translate('HttpHttps') },
{ key: 'socks4', value: translate('Socks4') },
{ key: 'socks5', value: translate('Socks5') }
];
return (

@ -12,15 +12,15 @@ import { icons, inputTypes, kinds } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
const authenticationMethodOptions = [
{ key: 'none', value: 'None' },
{ key: 'basic', value: 'Basic (Browser Popup)' },
{ key: 'forms', value: 'Forms (Login Page)' }
{ key: 'none', value: translate('None') },
{ key: 'basic', value: translate('AuthBasic') },
{ key: 'forms', value: translate('AuthForm') }
];
const certificateValidationOptions = [
{ key: 'enabled', value: 'Enabled' },
{ key: 'disabledForLocalAddresses', value: 'Disabled for Local Addresses' },
{ key: 'disabled', value: 'Disabled' }
{ key: 'enabled', value: translate('Enabled') },
{ key: 'disabledForLocalAddresses', value: translate('CertValidationNoLocal') },
{ key: 'disabled', value: translate('Disabled') }
];
class SecuritySettings extends Component {

@ -38,10 +38,10 @@ function UpdateSettings(props) {
value: titleCase(packageUpdateMechanism)
});
} else {
updateOptions.push({ key: 'builtIn', value: 'Built-In' });
updateOptions.push({ key: 'builtIn', value: translate('BuiltIn') });
}
updateOptions.push({ key: 'script', value: 'Script' });
updateOptions.push({ key: 'script', value: translate('Script') });
return (
<FieldSet legend={translate('Updates')}>

@ -39,7 +39,7 @@ function EditImportExclusionModalContent(props) {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
{id ? 'Edit List Exclusion' : 'Add List Exclusion'}
{id ? translate('EditListExclusion') : translate('AddListExclusion')}
</ModalHeader>
<ModalBody className={styles.body}>

@ -58,7 +58,7 @@ class AddImportListItem extends Component {
size={sizes.SMALL}
onPress={this.onImportListSelect}
>
Custom
{translate('Custom')}
</Button>
<Menu className={styles.presetsMenu}>
@ -66,7 +66,7 @@ class AddImportListItem extends Component {
className={styles.presetsMenuButton}
size={sizes.SMALL}
>
Presets
{translate('Presets')}
</Button>
<MenuContent>

@ -52,7 +52,7 @@ function EditImportListModalContent(props) {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
{`${id ? 'Edit' : 'Add'} List - ${implementationName}`}
{`${id ? translate('Edit') : translate('Add')} ${translate('List')} - ${implementationName}`}
</ModalHeader>
<ModalBody>

@ -74,14 +74,14 @@ class ImportList extends Component {
{
enabled &&
<Label kind={kinds.SUCCESS}>
Enabled
{translate('Enabled')}
</Label>
}
{
enableAuto &&
<Label kind={kinds.SUCCESS}>
Auto
{translate('Auto')}
</Label>
}
@ -91,7 +91,7 @@ class ImportList extends Component {
kind={kinds.DISABLED}
outline={true}
>
Disabled
{translate('Disabled')}
</Label>
}
</div>

@ -19,11 +19,11 @@ function ImportListOptions(props) {
} = props;
const cleanLibraryLevelOptions = [
{ key: 'disabled', value: 'Disabled' },
{ key: 'logOnly', value: 'Log Only' },
{ key: 'keepAndUnmonitor', value: 'Keep and Unmonitor Movie' },
{ key: 'removeAndKeep', value: 'Remove Movie and Keep Files' },
{ key: 'removeAndDelete', value: 'Remove Movie and Delete Files' }
{ key: 'disabled', value: translate('Disabled') },
{ key: 'logOnly', value: translate('LogOnly') },
{ key: 'keepAndUnmonitor', value: translate('KeepAndUnmonitorMovie') },
{ key: 'removeAndKeep', value: translate('RemoveMovieAndKeepFiles') },
{ key: 'removeAndDelete', value: translate('RemoveMovieAndDeleteFiles') }
];
return (

@ -58,7 +58,7 @@ class AddIndexerItem extends Component {
size={sizes.SMALL}
onPress={this.onIndexerSelect}
>
Custom
{translate('Custom')}
</Button>
<Menu className={styles.presetsMenu}>
@ -66,7 +66,7 @@ class AddIndexerItem extends Component {
className={styles.presetsMenuButton}
size={sizes.SMALL}
>
Presets
{translate('Presets')}
</Button>
<MenuContent>

@ -32,7 +32,7 @@ class AddIndexerModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Add Indexer
{translate('AddIndexer')}
</ModalHeader>
<ModalBody>

@ -98,7 +98,7 @@ class Indexer extends Component {
{
supportsRss && enableRss &&
<Label kind={kinds.SUCCESS}>
RSS
{translate('RSS')}
</Label>
}

@ -16,21 +16,21 @@ import NamingConnector from './Naming/NamingConnector';
import AddRootFolderConnector from './RootFolder/AddRootFolderConnector';
const rescanAfterRefreshOptions = [
{ key: 'always', value: 'Always' },
{ key: 'afterManual', value: 'After Manual Refresh' },
{ key: 'never', value: 'Never' }
{ key: 'always', value: translate('Always') },
{ key: 'afterManual', value: translate('AfterManualRefresh') },
{ key: 'never', value: translate('Never') }
];
const downloadPropersAndRepacksOptions = [
{ key: 'preferAndUpgrade', value: 'Prefer and Upgrade' },
{ key: 'doNotUpgrade', value: 'Do not Upgrade Automatically' },
{ key: 'doNotPrefer', value: 'Do not Prefer' }
{ key: 'preferAndUpgrade', value: translate('PreferAndUpgrade') },
{ key: 'doNotUpgrade', value: translate('DoNotUpgradeAutomatically') },
{ key: 'doNotPrefer', value: translate('DoNotPrefer') }
];
const fileDateOptions = [
{ key: 'none', value: 'None' },
{ key: 'cinemas', value: 'In Cinemas Date' },
{ key: 'release', value: 'Physical Release Date' }
{ key: 'none', value: translate('None') },
{ key: 'cinemas', value: translate('InCinemasDate') },
{ key: 'release', value: translate('PhysicalReleaseDate') }
];
class MediaManagement extends Component {

@ -13,10 +13,10 @@ import NamingModal from './NamingModal';
import styles from './Naming.css';
const colonReplacementOptions = [
{ key: 'delete', value: 'Delete' },
{ key: 'dash', value: 'Replace with Dash' },
{ key: 'spaceDash', value: 'Replace with Space Dash' },
{ key: 'spaceDashSpace', value: 'Replace with Space Dash Space' }
{ key: 'delete', value: translate('Delete') },
{ key: 'dash', value: translate('ReplaceWithDash') },
{ key: 'spaceDash', value: translate('ReplaceWithSpaceDash') },
{ key: 'spaceDashSpace', value: translate('ReplaceWithSpaceDashSpace') }
];
class Naming extends Component {
@ -91,13 +91,13 @@ class Naming extends Component {
if (examples.movieExample) {
standardMovieFormatHelpTexts.push(`Movie: ${examples.movieExample}`);
} else {
standardMovieFormatErrors.push({ message: 'Movie: Invalid Format' });
standardMovieFormatErrors.push({ message: translate('MovieInvalidFormat') });
}
if (examples.movieFolderExample) {
movieFolderFormatHelpTexts.push(`Example: ${examples.movieFolderExample}`);
} else {
movieFolderFormatErrors.push({ message: 'Invalid Format' });
movieFolderFormatErrors.push({ message: translate('InvalidFormat') });
}
}

@ -102,9 +102,9 @@ class NamingModal extends Component {
];
const caseOptions = [
{ key: 'title', value: 'Default Case' },
{ key: 'lower', value: 'Lower Case' },
{ key: 'upper', value: 'Upper Case' }
{ key: 'title', value: translate('DefaultCase') },
{ key: 'lower', value: translate('LowerCase') },
{ key: 'upper', value: translate('UpperCase') }
];
const fileNameTokens = [
@ -174,7 +174,7 @@ class NamingModal extends Component {
>
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
File Name Tokens
{translate('FileNameTokens')}
</ModalHeader>
<ModalBody>

@ -4,6 +4,7 @@ import FileBrowserModal from 'Components/FileBrowser/FileBrowserModal';
import Icon from 'Components/Icon';
import Button from 'Components/Link/Button';
import { icons, kinds, sizes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
import styles from './AddRootFolder.css';
class AddRootFolder extends Component {
@ -49,7 +50,7 @@ class AddRootFolder extends Component {
className={styles.importButtonIcon}
name={icons.DRIVE}
/>
Add Root Folder
{translate('AddRootFolder')}
</Button>
<FileBrowserModal

@ -3,6 +3,7 @@ import React, { Component } from 'react';
import Card from 'Components/Card';
import Label from 'Components/Label';
import { kinds } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
import EditMetadataModalConnector from './EditMetadataModalConnector';
import styles from './Metadata.css';
@ -66,13 +67,13 @@ class Metadata extends Component {
{
enable ?
<Label kind={kinds.SUCCESS}>
Enabled
{translate('Enabled')}
</Label> :
<Label
kind={kinds.DISABLED}
outline={true}
>
Disabled
{translate('Disabled')}
</Label>
}
</div>
@ -81,7 +82,7 @@ class Metadata extends Component {
enable && !!metadataFields.length &&
<div>
<div className={styles.section}>
Metadata
{translate('Metadata')}
</div>
{
@ -107,7 +108,7 @@ class Metadata extends Component {
enable && !!imageFields.length &&
<div>
<div className={styles.section}>
Images
{translate('Images')}
</div>
{

@ -9,6 +9,8 @@ import LoadingIndicator from 'Components/Loading/LoadingIndicator';
import { inputTypes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
// Note: Do Not Translate Certification Countries
export const certificationCountryOptions = [
{ key: 'au', value: 'Australia' },
{ key: 'br', value: 'Brazil' },

@ -58,7 +58,7 @@ class AddNotificationItem extends Component {
size={sizes.SMALL}
onPress={this.onNotificationSelect}
>
Custom
{translate('Custom')}
</Button>
<Menu className={styles.presetsMenu}>
@ -66,7 +66,7 @@ class AddNotificationItem extends Component {
className={styles.presetsMenuButton}
size={sizes.SMALL}
>
Presets
{translate('Presets')}
</Button>
<MenuContent>

@ -28,7 +28,7 @@ class AddNotificationModalContent extends Component {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Add Notification
{translate('AddNotification')}
</ModalHeader>
<ModalBody>

@ -48,7 +48,7 @@ function EditNotificationModalContent(props) {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
{`${id ? 'Edit' : 'Add'} Connection - ${implementationName}`}
{`${id ? translate('Edit') : translate('Add')} ${translate('Connection')} - ${implementationName}`}
</ModalHeader>
<ModalBody>

@ -82,42 +82,42 @@ class Notification extends Component {
{
supportsOnGrab && onGrab &&
<Label kind={kinds.SUCCESS}>
On Grab
{translate('OnGrab')}
</Label>
}
{
supportsOnDelete && onDelete &&
<Label kind={kinds.SUCCESS}>
On Delete
{translate('OnDelete')}
</Label>
}
{
supportsOnDownload && onDownload &&
<Label kind={kinds.SUCCESS}>
On Import
{translate('OnImport')}
</Label>
}
{
supportsOnUpgrade && onDownload && onUpgrade &&
<Label kind={kinds.SUCCESS}>
On Upgrade
{translate('OnUpgrade')}
</Label>
}
{
supportsOnRename && onRename &&
<Label kind={kinds.SUCCESS}>
On Rename
{translate('OnRename')}
</Label>
}
{
supportsOnHealthIssue && onHealthIssue &&
<Label kind={kinds.SUCCESS}>
On Health Issue
{translate('OnHealthIssue')}
</Label>
}
@ -127,7 +127,7 @@ class Notification extends Component {
kind={kinds.DISABLED}
outline={true}
>
Disabled
{translate('Disabled')}
</Label>
}

@ -88,9 +88,9 @@ class DelayProfile extends Component {
let preferred = titleCase(preferredProtocol);
if (!enableUsenet) {
preferred = 'Only Torrent';
preferred = translate('OnlyTorrent');
} else if (!enableTorrent) {
preferred = 'Only Usenet';
preferred = translate('OnlyUsenet');
}
return (

@ -46,7 +46,7 @@ function EditDelayProfileModalContent(props) {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
{id ? 'Edit Delay Profile' : 'Add Delay Profile'}
{id ? translate('EditDelayProfile') : translate('AddDelayProfile')}
</ModalHeader>
<ModalBody>
@ -113,7 +113,7 @@ function EditDelayProfileModalContent(props) {
{
id === 1 ?
<Alert>
This is the default profile. It applies to all movies that don't have an explicit profile.
{translate('DefaultDelayProfile')}
</Alert> :
<FormGroup>

@ -5,6 +5,7 @@ import { connect } from 'react-redux';
import { createSelector } from 'reselect';
import { saveDelayProfile, setDelayProfileValue } from 'Store/Actions/settingsActions';
import selectSettings from 'Store/Selectors/selectSettings';
import translate from 'Utilities/String/translate';
import EditDelayProfileModalContent from './EditDelayProfileModalContent';
const newDelayProfile = {
@ -17,10 +18,10 @@ const newDelayProfile = {
};
const protocolOptions = [
{ key: 'preferUsenet', value: 'Prefer Usenet' },
{ key: 'preferTorrent', value: 'Prefer Torrent' },
{ key: 'onlyUsenet', value: 'Only Usenet' },
{ key: 'onlyTorrent', value: 'Only Torrent' }
{ key: 'preferUsenet', value: translate('PreferUsenet') },
{ key: 'preferTorrent', value: translate('PreferTorrent') },
{ key: 'onlyUsenet', value: translate('OnlyUsenet') },
{ key: 'onlyTorrent', value: translate('OnlyTorrent') }
];
function createDelayProfileSelector() {

@ -29,9 +29,9 @@ class Profiles extends Component {
<QualityProfilesConnector />
<DelayProfilesConnector />
<div className={styles.addCustomFormatMessage}>
Looking for Release Profiles? Try
<Link to='/settings/customformats'> Custom Formats </Link>
instead.
{translate('LookingForReleaseProfiles1')}
<Link to='/settings/customformats'> {translate('CustomFormats')} </Link>
{translate('LookingForReleaseProfiles2')}
</div>
</DndProvider>
</PageContentBody>

@ -140,7 +140,7 @@ class EditQualityProfileModalContent extends Component {
onMeasure={this.onHeaderMeasure}
>
<ModalHeader>
{id ? 'Edit Quality Profile' : 'Add Quality Profile'}
{id ? translate('EditQualityProfile') : translate('AddQualityProfile')}
</ModalHeader>
</Measure>
@ -171,7 +171,7 @@ class EditQualityProfileModalContent extends Component {
<div className={styles.formGroupWrapper}>
<FormGroup size={sizes.EXTRA_SMALL}>
<FormLabel size={sizes.SMALL}>
Name
{translate('Name')}
</FormLabel>
<FormInputGroup
@ -184,7 +184,7 @@ class EditQualityProfileModalContent extends Component {
<FormGroup size={sizes.EXTRA_SMALL}>
<FormLabel size={sizes.SMALL}>
Upgrades Allowed
{translate('UpgradesAllowed')}
</FormLabel>
<FormInputGroup
@ -200,7 +200,7 @@ class EditQualityProfileModalContent extends Component {
upgradeAllowed.value &&
<FormGroup size={sizes.EXTRA_SMALL}>
<FormLabel size={sizes.SMALL}>
Upgrade Until Quality
{translate('UpgradeUntilQuality')}
</FormLabel>
<FormInputGroup
@ -218,7 +218,7 @@ class EditQualityProfileModalContent extends Component {
formatItems.value.length > 0 &&
<FormGroup size={sizes.EXTRA_SMALL}>
<FormLabel size={sizes.SMALL}>
Minimum Custom Format Score
{translate('MinimumCustomFormatScore')}
</FormLabel>
<FormInputGroup
@ -235,7 +235,7 @@ class EditQualityProfileModalContent extends Component {
upgradeAllowed.value && formatItems.value.length > 0 &&
<FormGroup size={sizes.EXTRA_SMALL}>
<FormLabel size={sizes.SMALL}>
Upgrade Until Custom Format Score
{translate('UpgradeUntilCustomFormatScore')}
</FormLabel>
<FormInputGroup
@ -250,7 +250,7 @@ class EditQualityProfileModalContent extends Component {
<FormGroup size={sizes.EXTRA_SMALL}>
<FormLabel size={sizes.SMALL}>
Language
{translate('Language')}
</FormLabel>
<FormInputGroup
@ -301,7 +301,7 @@ class EditQualityProfileModalContent extends Component {
className={styles.deleteButtonContainer}
title={
isInUse ?
'Can\'t delete a quality profile that is attached to a movie' :
translate('QualityProfileInUse') :
undefined
}
>

@ -68,8 +68,8 @@ class QualityProfileFormatItems extends Component {
if (profileFormatItems.length < 1) {
return (
<div className={styles.addCustomFormatMessage}>
Want more control over which downloads are preferred? Add a
<Link to='/settings/customformats'> Custom Format </Link>
{translate('MoreControlCFText')}
<Link to='/settings/customformats'> {translate('CustomFormat')} </Link>
</div>
);
}
@ -82,7 +82,7 @@ class QualityProfileFormatItems extends Component {
<div>
<FormInputHelpText
text='Radarr scores each release using the sum of scores for matching custom formats. If a new release would improve the score, at the same or better quality, then Radarr will grab it.'
text={translate('CustomFormatHelpText')}
/>
{
@ -114,10 +114,10 @@ class QualityProfileFormatItems extends Component {
<div className={styles.formats}>
<div className={styles.headerContainer}>
<div className={styles.headerTitle}>
Custom Format
{translate('CustomFormat')}
</div>
<div className={styles.headerScore}>
Score
{translate('Score')}
</div>
</div>
{

@ -7,6 +7,7 @@ import Icon from 'Components/Icon';
import Button from 'Components/Link/Button';
import Measure from 'Components/Measure';
import { icons, kinds, sizes } from 'Helpers/Props';
import translate from 'Utilities/String/translate';
import QualityProfileItemDragPreview from './QualityProfileItemDragPreview';
import QualityProfileItemDragSource from './QualityProfileItemDragSource';
import styles from './QualityProfileItems.css';
@ -69,12 +70,12 @@ class QualityProfileItems extends Component {
return (
<FormGroup size={sizes.EXTRA_SMALL}>
<FormLabel size={sizes.SMALL}>
Qualities
{translate('Qualities')}
</FormLabel>
<div>
<FormInputHelpText
text="Qualities higher in the list are more preferred. Qualities within the same group are equal. Only checked qualities are wanted"
text={translate('QualitiesHelpText')}
/>
{
@ -115,7 +116,7 @@ class QualityProfileItems extends Component {
/>
{
editGroups ? 'Done Editing Groups' : 'Edit Groups'
editGroups ? translate('DoneEditingGroups') : translate('EditGroups')
}
</div>
</Button>

@ -152,10 +152,10 @@ class QualityDefinition extends Component {
const minSixty = `${formatBytes(minBytes * 60)}/h`;
const preferredBytes = preferredSize * 1024 * 1024;
const preferredSixty = preferredBytes ? `${formatBytes(preferredBytes * 60)}/h` : 'Unlimited';
const preferredSixty = preferredBytes ? `${formatBytes(preferredBytes * 60)}/h` : translate('Unlimited');
const maxBytes = maxSize && maxSize * 1024 * 1024;
const maxSixty = maxBytes ? `${formatBytes(maxBytes * 60)}/h` : 'Unlimited';
const maxSixty = maxBytes ? `${formatBytes(maxBytes * 60)}/h` : translate('Unlimited');
return (
<div className={styles.qualityDefinition}>
@ -243,7 +243,7 @@ class QualityDefinition extends Component {
advancedSettings &&
<div className={styles.megabytesPerMinute}>
<div>
Min
{translate('Min')}
<NumberInput
className={styles.sizeInput}
@ -258,7 +258,7 @@ class QualityDefinition extends Component {
</div>
<div>
Preferred
{translate('Preferred')}
<NumberInput
className={styles.sizeInput}
@ -273,7 +273,7 @@ class QualityDefinition extends Component {
</div>
<div>
Max
{translate('Max')}
<NumberInput
className={styles.sizeInput}

@ -32,7 +32,7 @@ class QualityDefinitions extends Component {
{
advancedSettings ?
<div className={styles.megabytesPerMinute}>
Megabytes Per Minute
{translate('MegabytesPerMinute')}
</div> :
null
}
@ -54,7 +54,7 @@ class QualityDefinitions extends Component {
<div className={styles.sizeLimitHelpTextContainer}>
<div className={styles.sizeLimitHelpText}>
Limits are automatically adjusted for the movie runtime.
{translate('QualityLimitsHelpText')}
</div>
</div>
</PageSectionContent>

@ -1,6 +1,7 @@
import PropTypes from 'prop-types';
import React from 'react';
import titleCase from 'Utilities/String/titleCase';
import translate from '../../../Utilities/String/translate';
function TagDetailsDelayProfile(props) {
const {
@ -20,16 +21,16 @@ function TagDetailsDelayProfile(props) {
<div>
{
enableUsenet ?
`Usenet Delay: ${usenetDelay}` :
'Usenet disabled'
translate('UsenetDelayTime', [usenetDelay]) :
translate('UsenetDisabled')
}
</div>
<div>
{
enableTorrent ?
`Torrent Delay: ${torrentDelay}` :
'Torrents disabled'
translate('TorrentDelayTime', [torrentDelay]) :
translate('TorrentsDisabled')
}
</div>
</div>

@ -29,7 +29,7 @@ function TagDetailsModalContent(props) {
return (
<ModalContent onModalClose={onModalClose}>
<ModalHeader>
Tag Details - {label}
{translate('TagDetails', [label])}
</ModalHeader>
<ModalBody>

@ -126,7 +126,7 @@ class Tag extends Component {
{
!isTagUsed &&
<div>
No links
{translate('NoLinks')}
</div>
}

@ -13,8 +13,8 @@ import SettingsToolbarConnector from 'Settings/SettingsToolbarConnector';
import translate from 'Utilities/String/translate';
export const firstDayOfWeekOptions = [
{ key: 0, value: 'Sunday' },
{ key: 1, value: 'Monday' }
{ key: 0, value: translate('Sunday') },
{ key: 1, value: translate('Monday') }
];
export const weekColumnOptions = [

@ -14,7 +14,7 @@ import styles from './RestoreBackupModalContent.css';
function getErrorMessage(error) {
if (!error || !error.responseJSON || !error.responseJSON.message) {
return 'Error restoring backup';
return translate('ErrorRestoringBackup');
}
return error.responseJSON.message;
@ -146,7 +146,7 @@ class RestoreBackupModalContent extends Component {
<ModalBody>
{
!!id && `Would you like to restore the backup '${name}'?`
!!id && translate('WouldYouLikeToRestoreBackup', [name])
}
{
@ -203,7 +203,7 @@ class RestoreBackupModalContent extends Component {
<ModalFooter>
<div className={styles.additionalInfo}>
Note: Radarr will automatically restart and reload the UI during the restore process.
{translate('RestartReloadNote')}
</div>
<Button onPress={onModalClose}>
@ -216,7 +216,7 @@ class RestoreBackupModalContent extends Component {
isSpinning={isRestoring}
onPress={this.onRestorePress}
>
Restore
{translate('Restore')}
</SpinnerButton>
</ModalFooter>
</ModalContent>

@ -83,7 +83,7 @@ function LogsTable(props) {
{
isPopulated && !error && !items.length &&
<div>
No events found
{translate('NoEventsFound')}
</div>
}

@ -28,7 +28,7 @@ function LogsTableDetailsModal(props) {
onModalClose={onModalClose}
>
<ModalHeader>
Details
{translate('Details')}
</ModalHeader>
<ModalBody>

Some files were not shown because too many files have changed in this diff Show More

Loading…
Cancel
Save